Contiki 2.6

elfloader-msp430.c

00001 /*
00002  * Copyright (c) 2005, Swedish Institute of Computer Science
00003  * All rights reserved.
00004  *
00005  * Redistribution and use in source and binary forms, with or without
00006  * modification, are permitted provided that the following conditions
00007  * are met:
00008  * 1. Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  * 2. Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in the
00012  *    documentation and/or other materials provided with the distribution.
00013  * 3. Neither the name of the Institute nor the names of its contributors
00014  *    may be used to endorse or promote products derived from this software
00015  *    without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
00018  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
00021  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00022  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
00023  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00024  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00025  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
00026  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
00027  * SUCH DAMAGE.
00028  *
00029  * This file is part of the Contiki operating system.
00030  *
00031  * @(#)$Id: elfloader-msp430.c,v 1.5 2009/03/26 12:25:05 fros4943 Exp $
00032  */
00033 #include "elfloader-arch.h"
00034 
00035 #include "dev/flash.h"
00036 
00037 static uint16_t datamemory_aligned[ELFLOADER_DATAMEMORY_SIZE/2+1];
00038 static uint8_t* datamemory = (uint8_t *)datamemory_aligned;
00039 #if ELFLOADER_CONF_TEXT_IN_ROM
00040 static const char textmemory[ELFLOADER_TEXTMEMORY_SIZE] = {0};
00041 #else /* ELFLOADER_CONF_TEXT_IN_ROM */
00042 static char textmemory[ELFLOADER_TEXTMEMORY_SIZE];
00043 #endif /* ELFLOADER_CONF_TEXT_IN_ROM */
00044 /*---------------------------------------------------------------------------*/
00045 void *
00046 elfloader_arch_allocate_ram(int size)
00047 {
00048   return datamemory;
00049 }
00050 /*---------------------------------------------------------------------------*/
00051 void *
00052 elfloader_arch_allocate_rom(int size)
00053 {
00054 #if ELFLOADER_CONF_TEXT_IN_ROM
00055   /* Return an 512-byte aligned pointer. */
00056   return (char *)
00057     ((unsigned long)&textmemory[0] & 0xfffffe00) +
00058     (((unsigned long)&textmemory[0] & 0x1ff) == 0? 0: 0x200);
00059 #else /* ELFLOADER_CONF_TEXT_IN_ROM */
00060   return textmemory;
00061 #endif /* ELFLOADER_CONF_TEXT_IN_ROM */
00062 }
00063 /*---------------------------------------------------------------------------*/
00064 #define READSIZE 32
00065 void
00066 elfloader_arch_write_rom(int fd, unsigned short textoff, unsigned int size, char *mem)
00067 {
00068 #if ELFLOADER_CONF_TEXT_IN_ROM
00069   int i;
00070   unsigned int ptr;
00071   unsigned short *flashptr;
00072 
00073   flash_setup();
00074 
00075   flashptr = (unsigned short *)mem;
00076 
00077   cfs_seek(fd, textoff, CFS_SEEK_SET);
00078   for(ptr = 0; ptr < size; ptr += READSIZE) {
00079 
00080     /* Read data from file into RAM. */
00081     cfs_read(fd, (unsigned char *)datamemory, READSIZE);
00082 
00083     /* Clear flash page on 512 byte boundary. */
00084     if((((unsigned short)flashptr) & 0x01ff) == 0) {
00085       flash_clear(flashptr);
00086     }
00087 
00088     /* Burn data from RAM into flash ROM. Flash is burned one 16-bit
00089        word at a time, so we need to be careful when incrementing
00090        pointers. The flashptr is already a short pointer, so
00091        incrementing it by one will actually increment the address by
00092        two. */
00093     for(i = 0; i < READSIZE / 2; ++i) {
00094       flash_write(flashptr, ((unsigned short *)datamemory)[i]);
00095       ++flashptr;
00096     }
00097   }
00098 
00099   flash_done();
00100 #else /* ELFLOADER_CONF_TEXT_IN_ROM */
00101   cfs_seek(fd, textoff, CFS_SEEK_SET);
00102   cfs_read(fd, (unsigned char *)mem, size);
00103 #endif /* ELFLOADER_CONF_TEXT_IN_ROM */
00104 }
00105 /*---------------------------------------------------------------------------*/
00106 void
00107 elfloader_arch_relocate(int fd, unsigned int sectionoffset,
00108                         char *sectionaddr,
00109                         struct elf32_rela *rela, char *addr)
00110 {
00111   addr += rela->r_addend;
00112 
00113   cfs_seek(fd, sectionoffset + rela->r_offset, CFS_SEEK_SET);
00114   cfs_write(fd, (char *)&addr, 2);
00115 }
00116 /*---------------------------------------------------------------------------*/