From 5779d8d985d95104ad74332f5fa3cb6c67645509 Mon Sep 17 00:00:00 2001 From: wdenk Date: Sat, 6 Dec 2003 23:55:10 +0000 Subject: =?UTF-8?q?*=20Patch=20by=20Nicolas=20Lacressonni=E8re,=2012=20Nov?= =?UTF-8?q?=202003:=20=20=20update=20for=20for=20Atmel=20AT91RM9200DK=20de?= =?UTF-8?q?velopment=20kit:=20=20=20-=20support=20for=20environment=20vari?= =?UTF-8?q?ables=20in=20DataFlash=20=20=20-=20Atmel=20DataFlash=20AT45DB12?= =?UTF-8?q?82=20support?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Patch by Jeff Carr, 11 Nov 2003: add support for new version of 8270 processors * Patches by George G. Davis, 05 Nov 2003: - only pass the ARM linux initrd tag to the kernel when an initrd is actually present - update omap1510inn configuration file --- CHANGELOG | 13 ++ README | 14 ++ common/Makefile | 2 +- common/cmd_flash.c | 22 ++- common/cmd_mem.c | 19 +- common/cmd_nvedit.c | 8 +- common/env_dataflash.c | 104 +++++++++++ cpu/at91rm9200/at45.c | 145 ++++++++++++--- cpu/mpc8260/cpu.c | 1 + cpu/mpc8260/speed.c | 2 +- drivers/dataflash.c | 143 +++++++++++++-- include/asm-ppc/processor.h | 1 + include/configs/at91rm9200dk.h | 13 +- include/configs/omap1510inn.h | 10 +- include/dataflash.h | 22 ++- lib_arm/armlinux.c | 404 ++++++++++++++++++++--------------------- 16 files changed, 652 insertions(+), 271 deletions(-) create mode 100644 common/env_dataflash.c diff --git a/CHANGELOG b/CHANGELOG index f8129e4..5848e11 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -2,6 +2,19 @@ Changes since U-Boot 1.0.0: ====================================================================== +* Patch by Nicolas Lacressonnière, 12 Nov 2003: + update for for Atmel AT91RM9200DK development kit: + - support for environment variables in DataFlash + - Atmel DataFlash AT45DB1282 support + +* Patch by Jeff Carr, 11 Nov 2003: + add support for new version of 8270 processors + +* Patches by George G. Davis, 05 Nov 2003: + - only pass the ARM linux initrd tag to the kernel when an initrd + is actually present + - update omap1510inn configuration file + * Patches by Stephan Linz, 3 Nov 2003: - more endianess fixes for LAN91C111 driver - CFG_HZ configuration patch for NIOS Cyclone board diff --git a/README b/README index cdf3f55..681038e 100644 --- a/README +++ b/README @@ -1760,6 +1760,20 @@ to save the current settings. The size in bytes of the EEPROM device. +- CFG_ENV_IS_IN_DATAFLASH: + + Define this if you have a DataFlash memory device which you + want to use for the environment. + + - CFG_ENV_OFFSET: + - CFG_ENV_ADDR: + - CFG_ENV_SIZE: + + These three #defines specify the offset and size of the + environment area within the total memory of your DataFlash placed + at the specified address. + + - CFG_SPI_INIT_OFFSET Defines offset to the initial SPI buffer area in DPRAM. The diff --git a/common/Makefile b/common/Makefile index dae5942..5595c23 100644 --- a/common/Makefile +++ b/common/Makefile @@ -42,7 +42,7 @@ COBJS = main.o ACEX1K.o altera.o bedbug.o \ cmd_reginfo.o cmd_scsi.o cmd_spi.o cmd_usb.o cmd_vfd.o \ command.o console.o devices.o dlmalloc.o docecc.o \ environment.o env_common.o \ - env_flash.o env_eeprom.o env_nvram.o env_nowhere.o exports.o \ + env_dataflash.o env_flash.o env_eeprom.o env_nvram.o env_nowhere.o exports.o \ flash.o fpga.o \ hush.o kgdb.o lists.o lynxkdi.o miiphybb.o miiphyutil.o \ s_record.o soft_i2c.o soft_spi.o spartan2.o \ diff --git a/common/cmd_flash.c b/common/cmd_flash.c index 430a33e..a51b5e9 100644 --- a/common/cmd_flash.c +++ b/common/cmd_flash.c @@ -307,7 +307,9 @@ int do_protect (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) ulong bank, addr_first, addr_last; int i, p, n, sect_first, sect_last; int rcode = 0; - +#ifdef CONFIG_HAS_DATAFLASH + int status; +#endif if (argc < 3) { printf ("Usage:\n%s\n", cmdtp->usage); return 1; @@ -322,6 +324,24 @@ int do_protect (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) return 1; } +#ifdef CONFIG_HAS_DATAFLASH + if ((strcmp(argv[2], "all") != 0) && (strcmp(argv[2], "bank") != 0)) { + addr_first = simple_strtoul(argv[2], NULL, 16); + addr_last = simple_strtoul(argv[3], NULL, 16); + + if (addr_dataflash(addr_first) && addr_dataflash(addr_last)) { + status = dataflash_real_protect(p,addr_first,addr_last); + if (status < 0){ + printf("Bad DataFlash sector specification\n"); + return 1; + } + printf("%sProtect %d DataFlash Sectors\n", + p ? "" : "Un-", status); + return 0; + } + } +#endif + if (strcmp(argv[2], "all") == 0) { for (bank=1; bank<=CFG_MAX_FLASH_BANKS; ++bank) { info = &flash_info[bank-1]; diff --git a/common/cmd_mem.c b/common/cmd_mem.c index 3918678..35b3901 100644 --- a/common/cmd_mem.c +++ b/common/cmd_mem.c @@ -136,13 +136,19 @@ int do_mem_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) uint *uip = (uint *)linebuf; ushort *usp = (ushort *)linebuf; u_char *ucp = (u_char *)linebuf; - +#ifdef CONFIG_HAS_DATAFLASH + int rc; +#endif printf("%08lx:", addr); linebytes = (nbytes>DISP_LINE_LEN)?DISP_LINE_LEN:nbytes; #ifdef CONFIG_HAS_DATAFLASH - if (read_dataflash(addr, (linebytes/size)*size, linebuf) != -1){ - + if ((rc = read_dataflash(addr, (linebytes/size)*size, linebuf)) == DATAFLASH_OK){ + /* if outside dataflash */ + /*if (rc != 1) { + dataflash_perror (rc); + return (1); + }*/ for (i=0; i #endif -#if !defined(CFG_ENV_IS_IN_NVRAM) && !defined(CFG_ENV_IS_IN_EEPROM) && !defined(CFG_ENV_IS_IN_FLASH) && !defined(CFG_ENV_IS_NOWHERE) -# error Define one of CFG_ENV_IS_IN_NVRAM, CFG_ENV_IS_IN_EEPROM, CFG_ENV_IS_IN_FLASH, CFG_ENV_IS_NOWHERE +#if !defined(CFG_ENV_IS_IN_NVRAM) && \ + !defined(CFG_ENV_IS_IN_EEPROM) && \ + !defined(CFG_ENV_IS_IN_FLASH) && \ + !defined(CFG_ENV_IS_IN_DATAFLASH) && \ + !defined(CFG_ENV_IS_NOWHERE) +# error Define one of CFG_ENV_IS_IN_{NVRAM|EEPROM|FLASH|DATAFLASH|NOWHERE} #endif #define XMK_STR(x) #x diff --git a/common/env_dataflash.c b/common/env_dataflash.c new file mode 100644 index 0000000..8bfbbc9 --- /dev/null +++ b/common/env_dataflash.c @@ -0,0 +1,104 @@ +/* LowLevel function for DataFlash environment support + * Author : Gilles Gastaldi (Atmel) + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + * + */ +#include + +#if defined(CFG_ENV_IS_IN_DATAFLASH) /* Environment is in DataFlash */ + +#include +#include +#include +#include +#include + +env_t *env_ptr = NULL; + +char * env_name_spec = "dataflash"; + +extern int read_dataflash (unsigned long addr, unsigned long size, char +*result); +extern int write_dataflash (unsigned long addr_dest, unsigned long addr_src, + unsigned long size); +extern int AT91F_DataflashInit (void); +extern uchar default_environment[]; +/* extern int default_environment_size; */ + + +uchar env_get_char_spec (int index) +{ + uchar c; + read_dataflash (CFG_ENV_ADDR+index+offsetof(env_t,data),1,&c); + return (c); +} + +void env_relocate_spec (void) +{ + read_dataflash (CFG_ENV_ADDR,CFG_ENV_SIZE,(uchar *)env_ptr); +} + +int saveenv(void) +{ +/* env must be copied to do not alter env structure in memory*/ +unsigned char temp[CFG_ENV_SIZE]; +int i; + memcpy(temp, env_ptr, CFG_ENV_SIZE); + return write_dataflash (CFG_ENV_ADDR, (unsigned long)temp, CFG_ENV_SIZE); +} + +/************************************************************************ + * Initialize Environment use + * + * We are still running from ROM, so data use is limited + * Use a (moderately small) buffer on the stack + */ +int env_init(void) +{ + DECLARE_GLOBAL_DATA_PTR; + + ulong crc, len, new; + unsigned off; + uchar buf[64]; + if (gd->env_valid == 0){ + AT91F_DataflashInit(); /* prepare for DATAFLASH read/write */ + + /* read old CRC */ + read_dataflash (CFG_ENV_ADDR+offsetof(env_t,crc),sizeof(ulong),&crc); + new = 0; + len = ENV_SIZE; + off = offsetof(env_t,data); + while (len > 0) { + int n = (len > sizeof(buf)) ? sizeof(buf) : len; + read_dataflash (CFG_ENV_ADDR+off,n , buf); + new = crc32 (new, buf, n); + len -= n; + off += n; + } + if (crc == new) { + gd->env_addr = offsetof(env_t,data); + gd->env_valid = 1; + } else { + gd->env_addr = (ulong)&default_environment[0]; + gd->env_valid = 0; + } + } + + return (0); +} + +#endif /* CFG_ENV_IS_IN_DATAFLASH */ diff --git a/cpu/at91rm9200/at45.c b/cpu/at91rm9200/at45.c index cf456fb..9dfe560 100644 --- a/cpu/at91rm9200/at45.c +++ b/cpu/at91rm9200/at45.c @@ -26,6 +26,7 @@ #include #define SPI_CLK 5000000 +#define AT91C_TIMEOUT_WRDY 200000 #define AT91C_SPI_PCS0_SERIAL_DATAFLASH 0xE /* Chip Select 0 : NPCS0 %1110 */ #define AT91C_SPI_PCS3_DATAFLASH_CARD 0x7 /* Chip Select 3 : NPCS3 %0111 */ @@ -145,10 +146,17 @@ AT91S_DataFlashStatus AT91F_DataFlashSendCommand( /* fill the command buffer */ pDataFlash->pDataFlashDesc->command[0] = OpCode; - pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x00FF0000) >> 16); - pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x0000FF00) >> 8); - pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(adr & 0x000000FF) ; - pDataFlash->pDataFlashDesc->command[4] = 0; + if (pDataFlash->pDevice->pages_number >= 16384) { + pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x0F000000) >> 24); + pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x00FF0000) >> 16); + pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((adr & 0x0000FF00) >> 8); + pDataFlash->pDataFlashDesc->command[4] = (unsigned char)(adr & 0x000000FF); + } else { + pDataFlash->pDataFlashDesc->command[1] = (unsigned char)((adr & 0x00FF0000) >> 16); + pDataFlash->pDataFlashDesc->command[2] = (unsigned char)((adr & 0x0000FF00) >> 8); + pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(adr & 0x000000FF) ; + pDataFlash->pDataFlashDesc->command[4] = 0; + } pDataFlash->pDataFlashDesc->command[5] = 0; pDataFlash->pDataFlashDesc->command[6] = 0; pDataFlash->pDataFlashDesc->command[7] = 0; @@ -205,8 +213,7 @@ AT91S_DataFlashStatus AT91F_DataFlashWaitReady(AT91PS_DataflashDesc pDataFlashDe do { AT91F_DataFlashGetStatus(pDataFlashDesc); timeout--; - } - while( ((pDataFlashDesc->DataFlash_state & 0x80) != 0x80) && (timeout > 0) ); + } while( ((pDataFlashDesc->DataFlash_state & 0x80) != 0x80) && (timeout > 0) ); if((pDataFlashDesc->DataFlash_state & 0x80) != 0x80) return DATAFLASH_ERROR; @@ -230,6 +237,7 @@ AT91S_DataFlashStatus AT91F_DataFlashContinuousRead ( unsigned char *dataBuffer, int sizeToRead ) { + AT91S_DataFlashStatus status; /* Test the size to read in the device */ if ( (src + sizeToRead) > (pDataFlash->pDevice->pages_size * (pDataFlash->pDevice->pages_number))) return DATAFLASH_MEMORY_OVERFLOW; @@ -239,8 +247,9 @@ AT91S_DataFlashStatus AT91F_DataFlashContinuousRead ( pDataFlash->pDataFlashDesc->tx_data_pt = dataBuffer; pDataFlash->pDataFlashDesc->tx_data_size = sizeToRead; + status = AT91F_DataFlashSendCommand (pDataFlash, DB_CONTINUOUS_ARRAY_READ, 8, src); /* Send the command to the dataflash */ - return(AT91F_DataFlashSendCommand (pDataFlash, DB_CONTINUOUS_ARRAY_READ, 8, src)); + return(status); } @@ -259,13 +268,17 @@ AT91S_DataFlashStatus AT91F_DataFlashPagePgmBuf( unsigned int dest, unsigned int SizeToWrite) { + int cmdsize; pDataFlash->pDataFlashDesc->tx_data_pt = src ; pDataFlash->pDataFlashDesc->tx_data_size = SizeToWrite ; pDataFlash->pDataFlashDesc->rx_data_pt = src; pDataFlash->pDataFlashDesc->rx_data_size = SizeToWrite; + cmdsize = 4; /* Send the command to the dataflash */ - return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_PGM_BUF1, 4, dest)); + if (pDataFlash->pDevice->pages_number >= 16384) + cmdsize = 5; + return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_PGM_BUF1, cmdsize, dest)); } @@ -282,14 +295,17 @@ AT91S_DataFlashStatus AT91F_MainMemoryToBufferTransfert( unsigned char BufferCommand, unsigned int page) { + int cmdsize; /* Test if the buffer command is legal */ if ((BufferCommand != DB_PAGE_2_BUF1_TRF) && (BufferCommand != DB_PAGE_2_BUF2_TRF)) return DATAFLASH_BAD_COMMAND; /* no data to transmit or receive */ pDataFlash->pDataFlashDesc->tx_data_size = 0; - - return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, 4, page*pDataFlash->pDevice->pages_size)); + cmdsize = 4; + if (pDataFlash->pDevice->pages_number >= 16384) + cmdsize = 5; + return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, cmdsize, page*pDataFlash->pDevice->pages_size)); } @@ -310,6 +326,7 @@ AT91S_DataFlashStatus AT91F_DataFlashWriteBuffer ( unsigned int bufferAddress, int SizeToWrite ) { + int cmdsize; /* Test if the buffer command is legal */ if ((BufferCommand != DB_BUF1_WRITE) && (BufferCommand != DB_BUF2_WRITE)) return DATAFLASH_BAD_COMMAND; @@ -324,14 +341,22 @@ AT91S_DataFlashStatus AT91F_DataFlashWriteBuffer ( /* Send first Write Command */ pDataFlash->pDataFlashDesc->command[0] = BufferCommand; pDataFlash->pDataFlashDesc->command[1] = 0; - pDataFlash->pDataFlashDesc->command[2] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ; - pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ; - + if (pDataFlash->pDevice->pages_number >= 16384) { + pDataFlash->pDataFlashDesc->command[2] = 0; + pDataFlash->pDataFlashDesc->command[3] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ; + pDataFlash->pDataFlashDesc->command[4] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ; + cmdsize = 5; + } else { + pDataFlash->pDataFlashDesc->command[2] = (unsigned char)(((unsigned int)(bufferAddress & pDataFlash->pDevice->byte_mask)) >> 8) ; + pDataFlash->pDataFlashDesc->command[3] = (unsigned char)((unsigned int)bufferAddress & 0x00FF) ; + pDataFlash->pDataFlashDesc->command[4] = 0; + cmdsize = 4; + } pDataFlash->pDataFlashDesc->tx_cmd_pt = pDataFlash->pDataFlashDesc->command ; - pDataFlash->pDataFlashDesc->tx_cmd_size = 4 ; + pDataFlash->pDataFlashDesc->tx_cmd_size = cmdsize ; pDataFlash->pDataFlashDesc->rx_cmd_pt = pDataFlash->pDataFlashDesc->command ; - pDataFlash->pDataFlashDesc->rx_cmd_size = 4 ; + pDataFlash->pDataFlashDesc->rx_cmd_size = cmdsize ; pDataFlash->pDataFlashDesc->rx_data_pt = dataBuffer ; pDataFlash->pDataFlashDesc->tx_data_pt = dataBuffer ; @@ -341,6 +366,51 @@ AT91S_DataFlashStatus AT91F_DataFlashWriteBuffer ( return AT91F_SpiWrite(pDataFlash->pDataFlashDesc); } +/*------------------------------------------------------------------------------*/ +/* Function Name : AT91F_PageErase */ +/* Object : Erase a page */ +/* Input Parameters : DataFlash Service */ +/* : Page concerned */ +/* : */ +/* Return value : State of the dataflash */ +/*------------------------------------------------------------------------------*/ +AT91S_DataFlashStatus AT91F_PageErase( + AT91PS_DataFlash pDataFlash, + unsigned int page) +{ + int cmdsize; + /* Test if the buffer command is legal */ + /* no data to transmit or receive */ + pDataFlash->pDataFlashDesc->tx_data_size = 0; + + cmdsize = 4; + if (pDataFlash->pDevice->pages_number >= 16384) + cmdsize = 5; + return(AT91F_DataFlashSendCommand (pDataFlash, DB_PAGE_ERASE, cmdsize, page*pDataFlash->pDevice->pages_size)); +} + + +/*------------------------------------------------------------------------------*/ +/* Function Name : AT91F_BlockErase */ +/* Object : Erase a Block */ +/* Input Parameters : DataFlash Service */ +/* : Page concerned */ +/* : */ +/* Return value : State of the dataflash */ +/*------------------------------------------------------------------------------*/ +AT91S_DataFlashStatus AT91F_BlockErase( + AT91PS_DataFlash pDataFlash, + unsigned int block) +{ + int cmdsize; + /* Test if the buffer command is legal */ + /* no data to transmit or receive */ + pDataFlash->pDataFlashDesc->tx_data_size = 0; + cmdsize = 4; + if (pDataFlash->pDevice->pages_number >= 16384) + cmdsize = 5; + return(AT91F_DataFlashSendCommand (pDataFlash, DB_BLOCK_ERASE,cmdsize, block*8*pDataFlash->pDevice->pages_size)); +} /*------------------------------------------------------------------------------*/ /* Function Name : AT91F_WriteBufferToMain */ @@ -355,6 +425,7 @@ AT91S_DataFlashStatus AT91F_WriteBufferToMain ( unsigned char BufferCommand, unsigned int dest ) { + int cmdsize; /* Test if the buffer command is correct */ if ((BufferCommand != DB_BUF1_PAGE_PGM) && (BufferCommand != DB_BUF1_PAGE_ERASE_PGM) && @@ -365,8 +436,11 @@ AT91S_DataFlashStatus AT91F_WriteBufferToMain ( /* no data to transmit or receive */ pDataFlash->pDataFlashDesc->tx_data_size = 0; + cmdsize = 4; + if (pDataFlash->pDevice->pages_number >= 16384) + cmdsize = 5; /* Send the command to the dataflash */ - return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, 4, dest)); + return(AT91F_DataFlashSendCommand (pDataFlash, BufferCommand, cmdsize, dest)); } @@ -391,10 +465,18 @@ AT91S_DataFlashStatus AT91F_PartialPageWrite ( /* Read the contents of the page in the Sram Buffer */ AT91F_MainMemoryToBufferTransfert(pDataFlash, DB_PAGE_2_BUF1_TRF, page); - AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); /*Update the SRAM buffer */ AT91F_DataFlashWriteBuffer(pDataFlash, DB_BUF1_WRITE, src, AdrInPage, size); - AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000); + + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); + + /* Erase page if a 128 Mbits device */ + if (pDataFlash->pDevice->pages_number >= 16384) { + AT91F_PageErase(pDataFlash, page); + /* Rewrite the modified Sram Buffer in the main memory */ + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); + } /* Rewrite the modified Sram Buffer in the main memory */ return(AT91F_WriteBufferToMain(pDataFlash, DB_BUF1_PAGE_ERASE_PGM, (page*pDataFlash->pDevice->pages_size))); @@ -402,7 +484,7 @@ AT91S_DataFlashStatus AT91F_PartialPageWrite ( /*------------------------------------------------------------------------------*/ -/* Function Name : AT91F_DataFlashWrite_Overloaded */ +/* Function Name : AT91F_DataFlashWrite */ /* Object : */ /* Input Parameters : <*src> = Source buffer */ /* : = dataflash adress */ @@ -415,6 +497,8 @@ AT91S_DataFlashStatus AT91F_DataFlashWrite( int size ) { unsigned int length; + unsigned int page; + unsigned int status; AT91F_SpiEnable(pDataFlash->pDevice->cs); @@ -431,7 +515,7 @@ AT91S_DataFlashStatus AT91F_DataFlashWrite( if(!AT91F_PartialPageWrite(pDataFlash,src, dest, length)) return DATAFLASH_ERROR; - AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); /* Update size, source and destination pointers */ size -= length; @@ -441,10 +525,21 @@ AT91S_DataFlashStatus AT91F_DataFlashWrite( while (( size - pDataFlash->pDevice->pages_size ) >= 0 ) { /* program dataflash page */ - if(!AT91F_DataFlashPagePgmBuf(pDataFlash, src, dest, pDataFlash->pDevice->pages_size )) + page = (unsigned int)dest / (pDataFlash->pDevice->pages_size); + + status = AT91F_DataFlashWriteBuffer(pDataFlash, DB_BUF1_WRITE, src, 0, pDataFlash->pDevice->pages_size); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); + + status = AT91F_PageErase(pDataFlash, page); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); + if (!status) + return DATAFLASH_ERROR; + + status = AT91F_WriteBufferToMain (pDataFlash, DB_BUF1_PAGE_PGM, dest); + if(!status) return DATAFLASH_ERROR; - AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); /* Update size, source and destination pointers */ size -= pDataFlash->pDevice->pages_size ; @@ -458,7 +553,7 @@ AT91S_DataFlashStatus AT91F_DataFlashWrite( if(!AT91F_PartialPageWrite(pDataFlash, src, dest, size) ) return DATAFLASH_ERROR; - AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000); + AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY); } return DATAFLASH_OK; } @@ -480,13 +575,13 @@ int AT91F_DataFlashRead( AT91F_SpiEnable(pDataFlash->pDevice->cs); - if(AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000) != DATAFLASH_OK) + if(AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY) != DATAFLASH_OK) return -1; while (size) { SizeToRead = (size < 0x8000)? size:0x8000; - if (AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, 1000) != DATAFLASH_OK) + if (AT91F_DataFlashWaitReady(pDataFlash->pDataFlashDesc, AT91C_TIMEOUT_WRDY) != DATAFLASH_OK) return -1; if (AT91F_DataFlashContinuousRead (pDataFlash, addr, buffer, SizeToRead) != DATAFLASH_OK) diff --git a/cpu/mpc8260/cpu.c b/cpu/mpc8260/cpu.c index f4f5279..db8b89e 100644 --- a/cpu/mpc8260/cpu.c +++ b/cpu/mpc8260/cpu.c @@ -67,6 +67,7 @@ int checkcpu (void) case PVR_8260_HIP4: k = 4; break; + case PVR_8260_HIP7R1: case PVR_8260_HIP7: k = 7; break; diff --git a/cpu/mpc8260/speed.c b/cpu/mpc8260/speed.c index 6a3176a..a20f612 100644 --- a/cpu/mpc8260/speed.c +++ b/cpu/mpc8260/speed.c @@ -125,7 +125,7 @@ int get_clocks (void) busdf = (scmr & SCMR_BUSDF_MSK) >> SCMR_BUSDF_SHIFT; cpmdf = (scmr & SCMR_CPMDF_MSK) >> SCMR_CPMDF_SHIFT; - if (get_pvr () == PVR_8260_HIP7) { /* HiP7 */ + if ((get_pvr () == PVR_8260_HIP7) || (get_pvr () == PVR_8260_HIP7R1)) { /* HiP7 */ pllmf = (scmr & SCMR_PLLMF_MSKH7) >> SCMR_PLLMF_SHIFT; gd->vco_out = clkin * (pllmf + 1); } else { /* HiP3, HiP4 */ diff --git a/drivers/dataflash.c b/drivers/dataflash.c index 26a6f84..13f0068 100644 --- a/drivers/dataflash.c +++ b/drivers/dataflash.c @@ -31,12 +31,23 @@ int cs[][CFG_MAX_DATAFLASH_BANKS] = { {CFG_DATAFLASH_LOGIC_ADDR_CS3, 3} }; +/*define the area offsets*/ +dataflash_protect_t area_list[NB_DATAFLASH_AREA] = { + {0, 0x7fff, FLAG_PROTECT_SET}, /* ROM code */ + {0x8000, 0x1ffff, FLAG_PROTECT_SET}, /* u-boot code */ + {0x20000, 0x27fff, FLAG_PROTECT_CLEAR}, /* u-boot environment */ + {0x28000, 0x1fffff, FLAG_PROTECT_CLEAR}, /* data area size to tune */ +}; + extern void AT91F_SpiInit (void); extern int AT91F_DataflashProbe (int i, AT91PS_DataflashDesc pDesc); extern int AT91F_DataFlashRead (AT91PS_DataFlash pDataFlash, unsigned long addr, unsigned long size, char *buffer); - +extern int AT91F_DataFlashWrite( AT91PS_DataFlash pDataFlash, + unsigned char *src, + int dest, + int size ); int AT91F_DataflashInit (void) { @@ -46,7 +57,7 @@ int AT91F_DataflashInit (void) AT91F_SpiInit (); for (i = 0; i < CFG_MAX_DATAFLASH_BANKS; i++) { - + dataflash_info[i].Desc.state = IDLE; dataflash_info[i].id = 0; dataflash_info[i].Device.pages_number = 0; dfcode = AT91F_DataflashProbe (cs[i][1], &dataflash_info[i].Desc); @@ -84,14 +95,31 @@ int AT91F_DataflashInit (void) dataflash_info[i].logical_address = cs[i][0]; dataflash_info[i].id = dfcode; break; + case AT45DB128: + dataflash_info[i].Device.pages_number = 16384; + dataflash_info[i].Device.pages_size = 1056; + dataflash_info[i].Device.page_offset = 11; + dataflash_info[i].Device.byte_mask = 0x700; + dataflash_info[i].Device.cs = cs[i][1]; + dataflash_info[i].Desc.DataFlash_state = IDLE; + dataflash_info[i].logical_address = cs[i][0]; + dataflash_info[i].id = dfcode; + break; default: break; } - - for (j = 0; j < dataflash_info[i].Device.pages_number; j++) - dataflash_info[i].protect[j] = FLAG_PROTECT_SET; - + /* set the last area end to the dataflash size*/ + area_list[NB_DATAFLASH_AREA -1].end = + (dataflash_info[i].Device.pages_number * + dataflash_info[i].Device.pages_size)-1; + + /* set the area addresses */ + for(j = 0; j (pdataFlash->pDevice->pages_size * + pdataFlash->pDevice->pages_number)) return 0; + /* is too large for the dataflash */ + if (size > ((pdataFlash->pDevice->pages_size * + pdataFlash->pDevice->pages_number) - ((int)addr & 0x0FFFFFFF))) return 0; + + return 1; +} +/*-----------------------------------------------------------------------------*/ +/* Function Name : prot_dataflash */ +/* Object : Test if destination area is protected */ +/*-----------------------------------------------------------------------------*/ +int prot_dataflash (AT91PS_DataFlash pdataFlash, unsigned long addr) +{ +int area; + /* find area */ + for (area=0; area < NB_DATAFLASH_AREA; area++) { + if ((addr >= pdataFlash->pDevice->area_list[area].start) && + (addr < pdataFlash->pDevice->area_list[area].end)) + break; + } + if (area == NB_DATAFLASH_AREA) return -1; + /*test protection value*/ + if (pdataFlash->pDevice->area_list[area].protected == FLAG_PROTECT_SET) return 0; + + return 1; +} +/*-----------------------------------------------------------------------------*/ +/* Function Name : dataflash_real_protect */ +/* Object : protect/unprotect area */ +/*-----------------------------------------------------------------------------*/ +int dataflash_real_protect (int flag, unsigned long start_addr, unsigned long end_addr) +{ +int i,j, area1, area2, addr_valid = 0; + /* find dataflash */ + for (i = 0; i < CFG_MAX_DATAFLASH_BANKS; i++) { + if ((((int) start_addr) & 0xF0000000) == + dataflash_info[i].logical_address) { + addr_valid = 1; + break; + } + } + if (!addr_valid) { + return -1; + } + /* find start area */ + for (area1=0; area1 < NB_DATAFLASH_AREA; area1++) { + if (start_addr == dataflash_info[i].Device.area_list[area1].start) break; + } + if (area1 == NB_DATAFLASH_AREA) return -1; + /* find end area */ + for (area2=0; area2 < NB_DATAFLASH_AREA; area2++) { + if (end_addr == dataflash_info[i].Device.area_list[area2].end) break; + } + if (area2 == NB_DATAFLASH_AREA) return -1; + + /*set protection value*/ + for(j = area1; j < area2+1 ; j++) + if (flag == 0) dataflash_info[i].Device.area_list[j].protected = FLAG_PROTECT_CLEAR; + else dataflash_info[i].Device.area_list[j].protected = FLAG_PROTECT_SET; + + return (area2-area1+1); +} /*------------------------------------------------------------------------------*/ /* Function Name : read_dataflash */ @@ -187,8 +295,12 @@ int read_dataflash (unsigned long addr, unsigned long size, char *result) AT91PS_DataFlash pFlash = &DataFlashInst; pFlash = AT91F_DataflashSelect (pFlash, &AddrToRead); + if (pFlash == 0) - return -1; + return ERR_UNKNOWN_FLASH_TYPE; + + if (size_dataflash(pFlash,addr,size) == 0) + return ERR_INVAL; return (AT91F_DataFlashRead (pFlash, AddrToRead, size, result)); } @@ -201,17 +313,24 @@ int read_dataflash (unsigned long addr, unsigned long size, char *result) int write_dataflash (unsigned long addr_dest, unsigned long addr_src, unsigned long size) { - extern AT91S_DataFlashStatus AT91F_DataFlashWrite( - AT91PS_DataFlash, uchar *, int, int); int AddrToWrite = addr_dest; AT91PS_DataFlash pFlash = &DataFlashInst; pFlash = AT91F_DataflashSelect (pFlash, &AddrToWrite); + + if (pFlash == 0) + return ERR_UNKNOWN_FLASH_TYPE; + + if (size_dataflash(pFlash,addr_dest,size) == 0) + return ERR_INVAL; + + if (prot_dataflash(pFlash,addr_dest) == 0) + return ERR_PROTECTED; + if (AddrToWrite == -1) return -1; - return AT91F_DataFlashWrite (pFlash, (char *) addr_src, AddrToWrite, - size); + return AT91F_DataFlashWrite (pFlash, (char *) addr_src, AddrToWrite, size); } diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h index 4d9c62b..9ca11d9 100644 --- a/include/asm-ppc/processor.h +++ b/include/asm-ppc/processor.h @@ -732,6 +732,7 @@ #define PVR_8260_HIP3 0x00810101 #define PVR_8260_HIP4 0x80811014 #define PVR_8260_HIP7 0x80822011 +#define PVR_8260_HIP7R1 0x80822013 /* I am just adding a single entry for 8260 boards. I think we may be * able to combine mbx, fads, rpxlite, bseip, and classic into a single diff --git a/include/configs/at91rm9200dk.h b/include/configs/at91rm9200dk.h index b092ec7..d971826 100644 --- a/include/configs/at91rm9200dk.h +++ b/include/configs/at91rm9200dk.h @@ -114,7 +114,7 @@ #define CONFIG_NET_RETRY_COUNT 20 #define CONFIG_HAS_DATAFLASH 1 -#define CFG_SPI_WRITE_TOUT CFG_HZ +#define CFG_SPI_WRITE_TOUT (5*CFG_HZ) #define CFG_MAX_DATAFLASH_BANKS 2 #define CFG_MAX_DATAFLASH_PAGES 16384 #define CFG_DATAFLASH_LOGIC_ADDR_CS0 0xC0000000 /* Logical adress for CS0 */ @@ -127,9 +127,20 @@ #define CFG_MAX_FLASH_SECT 40 #define CFG_FLASH_ERASE_TOUT (2*CFG_HZ) /* Timeout for Flash Erase */ #define CFG_FLASH_WRITE_TOUT (2*CFG_HZ) /* Timeout for Flash Write */ + +#undef CFG_ENV_IS_IN_DATAFLASH + +#ifdef CFG_ENV_IS_IN_DATAFLASH +#define CFG_ENV_OFFSET 0x20000 +#define CFG_ENV_ADDR (CFG_DATAFLASH_LOGIC_ADDR_CS0 + CFG_ENV_OFFSET) +#define CFG_ENV_SIZE 0x2000 /* 0x8000 */ +#else #define CFG_ENV_IS_IN_FLASH 1 #define CFG_ENV_ADDR (PHYS_FLASH_1 + 0xe000) /* 0x10000 */ #define CFG_ENV_SIZE 0x2000 /* 0x8000 */ +#endif + + #define CFG_LOAD_ADDR 0x21000000 /* default load address */ #define CFG_BOOT_SIZE 0x6000 /* 24 KBytes */ diff --git a/include/configs/omap1510inn.h b/include/configs/omap1510inn.h index 845e4d2..97466c1 100644 --- a/include/configs/omap1510inn.h +++ b/include/configs/omap1510inn.h @@ -50,6 +50,7 @@ #define CONFIG_CMDLINE_TAG 1 /* enable passing of ATAGs */ #define CONFIG_SETUP_MEMORY_TAGS 1 +#define CONFIG_INITRD_TAG 1 /* * Size of malloc() pool @@ -99,12 +100,9 @@ #include #define CONFIG_BOOTDELAY 3 -#define CONFIG_BOOTARGS "mem=32M console=ttyS0,115200n8 noinitrd root=/dev/nfs rw nfsroot=157.87.82.48:/home/a0875451/mwd/myfs/target ip=dhcp" -/*#define CONFIG_ETHADDR 00:0B:36:00:05:25 */ -#define CONFIG_NETMASK 255.255.254.0 /* talk on MY local net */ -#define CONFIG_IPADDR 156.117.97.156 /* static IP I currently own */ -#define CONFIG_SERVERIP 156.117.97.139 /* current IP of my dev pc */ -#define CONFIG_BOOTFILE "/tftpboot/uImage" /* file to load */ +#define CONFIG_BOOTARGS "console=ttyS0,115200n8 noinitrd root=/dev/nfs ip=bootp" +#define CONFIG_BOOTCOMMAND "bootp;tftp;bootm" +#define CFG_AUTOLOAD "n" /* No autoload */ #if (CONFIG_COMMANDS & CFG_CMD_KGDB) #define CONFIG_KGDB_BAUDRATE 115200 /* speed to run kgdb serial port */ diff --git a/include/dataflash.h b/include/dataflash.h index 5e11863..c404016 100644 --- a/include/dataflash.h +++ b/include/dataflash.h @@ -37,16 +37,15 @@ #include #include "config.h" +/*number of protected area*/ +#define NB_DATAFLASH_AREA 4 +/*define the area structure*/ typedef struct { - unsigned long base; /* logical base address for a bank */ - unsigned long size; /* total bank size */ - unsigned long page_count; - unsigned long page_size; - unsigned long id; /* device id */ - unsigned char protect[CFG_MAX_DATAFLASH_PAGES]; /* page protection status */ -} dataflash_info_t; - + unsigned long start; + unsigned long end; + unsigned char protected; +} dataflash_protect_t; typedef unsigned int AT91S_DataFlashStatus; @@ -80,6 +79,7 @@ typedef struct _AT91S_Dataflash { int page_offset; /* page offset in command */ int byte_mask; /* byte mask in command */ int cs; + dataflash_protect_t area_list[NB_DATAFLASH_AREA]; /* area protection status */ } AT91S_DataflashFeatures, *AT91PS_DataflashFeatures; /*---------------------------------------------*/ @@ -91,13 +91,13 @@ typedef struct _AT91S_DataFlash { } AT91S_DataFlash, *AT91PS_DataFlash; + typedef struct _AT91S_DATAFLASH_INFO { AT91S_DataflashDesc Desc; AT91S_DataflashFeatures Device; /* Pointer on a dataflash features array */ unsigned long logical_address; unsigned int id; /* device id */ - unsigned char protect[CFG_MAX_DATAFLASH_PAGES]; /* page protection status */ } AT91S_DATAFLASH_INFO, *AT91PS_DATAFLASH_INFO; @@ -106,6 +106,7 @@ typedef struct _AT91S_DATAFLASH_INFO { #define AT45DB161 0x2c #define AT45DB321 0x34 #define AT45DB642 0x3c +#define AT45DB128 0x10 #define AT91C_DATAFLASH_TIMEOUT 10000 /* For AT91F_DataFlashWaitReady */ @@ -166,6 +167,9 @@ typedef struct _AT91S_DATAFLASH_INFO { /*-------------------------------------------------------------------------------------------------*/ +extern int size_dataflash (AT91PS_DataFlash pdataFlash, unsigned long addr, unsigned long size); +extern int prot_dataflash (AT91PS_DataFlash pdataFlash, unsigned long addr); +extern int dataflash_real_protect (int flag, unsigned long start_addr, unsigned long end_addr); extern int addr_dataflash (unsigned long addr); extern int read_dataflash (unsigned long addr, unsigned long size, char *result); extern int write_dataflash (unsigned long addr, unsigned long dest, unsigned long size); diff --git a/lib_arm/armlinux.c b/lib_arm/armlinux.c index 68e12d3..0b3d01e 100644 --- a/lib_arm/armlinux.c +++ b/lib_arm/armlinux.c @@ -41,20 +41,24 @@ extern int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]); defined (CONFIG_CMDLINE_TAG) || \ defined (CONFIG_INITRD_TAG) || \ defined (CONFIG_VFD) -static void setup_start_tag(bd_t *bd); +static void setup_start_tag (bd_t *bd); + # ifdef CONFIG_SETUP_MEMORY_TAGS -static void setup_memory_tags(bd_t *bd); +static void setup_memory_tags (bd_t *bd); # endif -static void setup_commandline_tag(bd_t *bd, char *commandline); +static void setup_commandline_tag (bd_t *bd, char *commandline); + #if 0 -static void setup_ramdisk_tag(bd_t *bd); +static void setup_ramdisk_tag (bd_t *bd); #endif # ifdef CONFIG_INITRD_TAG -static void setup_initrd_tag(bd_t *bd, ulong initrd_start, ulong initrd_end); +static void setup_initrd_tag (bd_t *bd, ulong initrd_start, + ulong initrd_end); # endif -static void setup_end_tag(bd_t *bd); +static void setup_end_tag (bd_t *bd); + # if defined (CONFIG_VFD) -static void setup_videolfb_tag(gd_t *gd); +static void setup_videolfb_tag (gd_t *gd); # endif @@ -68,180 +72,179 @@ static struct tag *params; # define SHOW_BOOT_PROGRESS(arg) #endif -extern image_header_t header; /* from cmd_bootm.c */ +extern image_header_t header; /* from cmd_bootm.c */ -void do_bootm_linux(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[], - ulong addr, ulong *len_ptr, int verify) +void do_bootm_linux (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[], + ulong addr, ulong *len_ptr, int verify) { DECLARE_GLOBAL_DATA_PTR; - ulong len = 0, checksum; - ulong initrd_start, initrd_end; - ulong data; - void (*theKernel)(int zero, int arch); - image_header_t *hdr = &header; - bd_t *bd = gd->bd; + ulong len = 0, checksum; + ulong initrd_start, initrd_end; + ulong data; + void (*theKernel) (int zero, int arch); + image_header_t *hdr = &header; + bd_t *bd = gd->bd; + #ifdef CONFIG_CMDLINE_TAG - char *commandline = getenv("bootargs"); + char *commandline = getenv ("bootargs"); #endif - theKernel = (void (*)(int, int))ntohl(hdr->ih_ep); + theKernel = (void (*)(int, int)) ntohl (hdr->ih_ep); - /* - * Check if there is an initrd image - */ - if (argc >= 3) { - SHOW_BOOT_PROGRESS (9); + /* + * Check if there is an initrd image + */ + if (argc >= 3) { + SHOW_BOOT_PROGRESS (9); - addr = simple_strtoul(argv[2], NULL, 16); + addr = simple_strtoul (argv[2], NULL, 16); - printf ("## Loading Ramdisk Image at %08lx ...\n", addr); + printf ("## Loading Ramdisk Image at %08lx ...\n", addr); - /* Copy header so we can blank CRC field for re-calculation */ + /* Copy header so we can blank CRC field for re-calculation */ #ifdef CONFIG_HAS_DATAFLASH - if (addr_dataflash(addr)){ - read_dataflash(addr, sizeof(image_header_t), (char *)&header); - } else + if (addr_dataflash (addr)) { + read_dataflash (addr, sizeof (image_header_t), + (char *) &header); + } else #endif - memcpy (&header, (char *)addr, sizeof(image_header_t)); + memcpy (&header, (char *) addr, + sizeof (image_header_t)); - if (ntohl(hdr->ih_magic) != IH_MAGIC) { - printf ("Bad Magic Number\n"); - SHOW_BOOT_PROGRESS (-10); - do_reset (cmdtp, flag, argc, argv); - } + if (ntohl (hdr->ih_magic) != IH_MAGIC) { + printf ("Bad Magic Number\n"); + SHOW_BOOT_PROGRESS (-10); + do_reset (cmdtp, flag, argc, argv); + } - data = (ulong)&header; - len = sizeof(image_header_t); + data = (ulong) & header; + len = sizeof (image_header_t); - checksum = ntohl(hdr->ih_hcrc); - hdr->ih_hcrc = 0; + checksum = ntohl (hdr->ih_hcrc); + hdr->ih_hcrc = 0; - if (crc32 (0, (char *)data, len) != checksum) { - printf ("Bad Header Checksum\n"); - SHOW_BOOT_PROGRESS (-11); - do_reset (cmdtp, flag, argc, argv); - } + if (crc32 (0, (char *) data, len) != checksum) { + printf ("Bad Header Checksum\n"); + SHOW_BOOT_PROGRESS (-11); + do_reset (cmdtp, flag, argc, argv); + } - SHOW_BOOT_PROGRESS (10); + SHOW_BOOT_PROGRESS (10); - print_image_hdr (hdr); + print_image_hdr (hdr); - data = addr + sizeof(image_header_t); - len = ntohl(hdr->ih_size); + data = addr + sizeof (image_header_t); + len = ntohl (hdr->ih_size); #ifdef CONFIG_HAS_DATAFLASH - if (addr_dataflash(addr)){ - read_dataflash(data, len, (char *)CFG_LOAD_ADDR); - data = CFG_LOAD_ADDR; - } + if (addr_dataflash (addr)) { + read_dataflash (data, len, (char *) CFG_LOAD_ADDR); + data = CFG_LOAD_ADDR; + } #endif - if (verify) { - ulong csum = 0; - - printf (" Verifying Checksum ... "); - csum = crc32 (0, (char *)data, len); - if (csum != ntohl(hdr->ih_dcrc)) { - printf ("Bad Data CRC\n"); - SHOW_BOOT_PROGRESS (-12); - do_reset (cmdtp, flag, argc, argv); - } - printf ("OK\n"); - } - - SHOW_BOOT_PROGRESS (11); - - if ((hdr->ih_os != IH_OS_LINUX) || - (hdr->ih_arch != IH_CPU_ARM) || - (hdr->ih_type != IH_TYPE_RAMDISK) ) { - printf ("No Linux ARM Ramdisk Image\n"); - SHOW_BOOT_PROGRESS (-13); - do_reset (cmdtp, flag, argc, argv); - } - - /* - * Now check if we have a multifile image - */ - } else if ((hdr->ih_type==IH_TYPE_MULTI) && (len_ptr[1])) { - ulong tail = ntohl(len_ptr[0]) % 4; - int i; - - SHOW_BOOT_PROGRESS (13); - - /* skip kernel length and terminator */ - data = (ulong)(&len_ptr[2]); - /* skip any additional image length fields */ - for (i=1; len_ptr[i]; ++i) - data += 4; - /* add kernel length, and align */ - data += ntohl(len_ptr[0]); - if (tail) { - data += 4 - tail; + if (verify) { + ulong csum = 0; + + printf (" Verifying Checksum ... "); + csum = crc32 (0, (char *) data, len); + if (csum != ntohl (hdr->ih_dcrc)) { + printf ("Bad Data CRC\n"); + SHOW_BOOT_PROGRESS (-12); + do_reset (cmdtp, flag, argc, argv); + } + printf ("OK\n"); + } + + SHOW_BOOT_PROGRESS (11); + + if ((hdr->ih_os != IH_OS_LINUX) || + (hdr->ih_arch != IH_CPU_ARM) || + (hdr->ih_type != IH_TYPE_RAMDISK)) { + printf ("No Linux ARM Ramdisk Image\n"); + SHOW_BOOT_PROGRESS (-13); + do_reset (cmdtp, flag, argc, argv); + } + + /* + * Now check if we have a multifile image + */ + } else if ((hdr->ih_type == IH_TYPE_MULTI) && (len_ptr[1])) { + ulong tail = ntohl (len_ptr[0]) % 4; + int i; + + SHOW_BOOT_PROGRESS (13); + + /* skip kernel length and terminator */ + data = (ulong) (&len_ptr[2]); + /* skip any additional image length fields */ + for (i = 1; len_ptr[i]; ++i) + data += 4; + /* add kernel length, and align */ + data += ntohl (len_ptr[0]); + if (tail) { + data += 4 - tail; + } + + len = ntohl (len_ptr[1]); + + } else { + /* + * no initrd image + */ + SHOW_BOOT_PROGRESS (14); + + len = data = 0; } - len = ntohl(len_ptr[1]); - - } else { - /* - * no initrd image - */ - SHOW_BOOT_PROGRESS (14); - - data = 0; - } - #ifdef DEBUG - if (!data) { - printf ("No initrd\n"); - } + if (!data) { + printf ("No initrd\n"); + } #endif - if (data) { - initrd_start = data; - initrd_end = initrd_start + len; - } else { - initrd_start = 0; - initrd_end = 0; - } + if (data) { + initrd_start = data; + initrd_end = initrd_start + len; + } else { + initrd_start = 0; + initrd_end = 0; + } - SHOW_BOOT_PROGRESS (15); + SHOW_BOOT_PROGRESS (15); -#ifdef DEBUG - printf ("## Transferring control to Linux (at address %08lx) ...\n", - (ulong)theKernel); -#endif + debug ("## Transferring control to Linux (at address %08lx) ...\n", + (ulong) theKernel); #if defined (CONFIG_SETUP_MEMORY_TAGS) || \ defined (CONFIG_CMDLINE_TAG) || \ defined (CONFIG_INITRD_TAG) || \ defined (CONFIG_VFD) - setup_start_tag(bd); + setup_start_tag (bd); #ifdef CONFIG_SETUP_MEMORY_TAGS - setup_memory_tags(bd); + setup_memory_tags (bd); #endif #ifdef CONFIG_CMDLINE_TAG - setup_commandline_tag(bd, commandline); + setup_commandline_tag (bd, commandline); #endif #ifdef CONFIG_INITRD_TAG - setup_initrd_tag(bd, initrd_start, initrd_end); -#endif -#if 0 - setup_ramdisk_tag(bd); + if (initrd_start && initrd_end) + setup_initrd_tag (bd, initrd_start, initrd_end); #endif #if defined (CONFIG_VFD) - setup_videolfb_tag((gd_t *)gd); + setup_videolfb_tag ((gd_t *) gd); #endif - setup_end_tag(bd); + setup_end_tag (bd); #endif - /* we assume that the kernel is in place */ - printf("\nStarting kernel ...\n\n"); + /* we assume that the kernel is in place */ + printf ("\nStarting kernel ...\n\n"); - cleanup_before_linux(); + cleanup_before_linux (); - theKernel(0, bd->bi_arch_number); + theKernel (0, bd->bi_arch_number); } @@ -249,59 +252,59 @@ void do_bootm_linux(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[], defined (CONFIG_CMDLINE_TAG) || \ defined (CONFIG_INITRD_TAG) || \ defined (CONFIG_VFD) -static void setup_start_tag(bd_t *bd) +static void setup_start_tag (bd_t *bd) { - params = (struct tag *)bd->bi_boot_params; + params = (struct tag *) bd->bi_boot_params; - params->hdr.tag = ATAG_CORE; - params->hdr.size = tag_size(tag_core); + params->hdr.tag = ATAG_CORE; + params->hdr.size = tag_size (tag_core); - params->u.core.flags = 0; - params->u.core.pagesize = 0; - params->u.core.rootdev = 0; + params->u.core.flags = 0; + params->u.core.pagesize = 0; + params->u.core.rootdev = 0; - params = tag_next(params); + params = tag_next (params); } #ifdef CONFIG_SETUP_MEMORY_TAGS -static void setup_memory_tags(bd_t *bd) +static void setup_memory_tags (bd_t *bd) { - int i; + int i; - for(i = 0; i < CONFIG_NR_DRAM_BANKS; i++) { - params->hdr.tag = ATAG_MEM; - params->hdr.size = tag_size(tag_mem32); + for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) { + params->hdr.tag = ATAG_MEM; + params->hdr.size = tag_size (tag_mem32); - params->u.mem.start = bd->bi_dram[i].start; - params->u.mem.size = bd->bi_dram[i].size; + params->u.mem.start = bd->bi_dram[i].start; + params->u.mem.size = bd->bi_dram[i].size; - params = tag_next(params); - } + params = tag_next (params); + } } -#endif /* CONFIG_SETUP_MEMORY_TAGS */ +#endif /* CONFIG_SETUP_MEMORY_TAGS */ -static void setup_commandline_tag(bd_t *bd, char *commandline) +static void setup_commandline_tag (bd_t *bd, char *commandline) { - char *p; + char *p; - /* eat leading white space */ - for(p = commandline; *p == ' '; p++) - ; + /* eat leading white space */ + for (p = commandline; *p == ' '; p++); - /* skip non-existent command lines so the kernel will still - * use its default command line. - */ - if(*p == '\0') - return; + /* skip non-existent command lines so the kernel will still + * use its default command line. + */ + if (*p == '\0') + return; - params->hdr.tag = ATAG_CMDLINE; - params->hdr.size = (sizeof(struct tag_header) + strlen(p) + 1 + 4) >> 2; + params->hdr.tag = ATAG_CMDLINE; + params->hdr.size = + (sizeof (struct tag_header) + strlen (p) + 1 + 4) >> 2; - strcpy(params->u.cmdline.cmdline, p); + strcpy (params->u.cmdline.cmdline, p); - params = tag_next(params); + params = tag_next (params); } @@ -310,64 +313,47 @@ static void setup_commandline_tag(bd_t *bd, char *commandline) #endif #ifdef CONFIG_INITRD_TAG -static void setup_initrd_tag(bd_t *bd, ulong initrd_start, ulong initrd_end) +static void setup_initrd_tag (bd_t *bd, ulong initrd_start, ulong initrd_end) { - /* an ATAG_INITRD node tells the kernel where the compressed - * ramdisk can be found. ATAG_RDIMG is a better name, actually. - */ - params->hdr.tag = ATAG_INITRD2; - params->hdr.size = tag_size(tag_initrd); + /* an ATAG_INITRD node tells the kernel where the compressed + * ramdisk can be found. ATAG_RDIMG is a better name, actually. + */ + params->hdr.tag = ATAG_INITRD2; + params->hdr.size = tag_size (tag_initrd); - params->u.initrd.start = initrd_start; - params->u.initrd.size = initrd_end - initrd_start; + params->u.initrd.start = initrd_start; + params->u.initrd.size = initrd_end - initrd_start; - params = tag_next(params); + params = tag_next (params); } -#endif /* CONFIG_INITRD_TAG */ +#endif /* CONFIG_INITRD_TAG */ -#if 0 -static void setup_ramdisk_tag(bd_t *bd) +#if defined (CONFIG_VFD) +static void setup_videolfb_tag (gd_t *gd) { - /* an ATAG_RAMDISK node tells the kernel how large the - * decompressed ramdisk will become. - */ - params->hdr.tag = ATAG_RAMDISK; - params->hdr.size = tag_size(tag_ramdisk); - - params->u.ramdisk.start = 0; - /*params->u.ramdisk.size = RAMDISK_SIZE; */ - params->u.ramdisk.flags = 1; /* automatically load ramdisk */ + /* An ATAG_VIDEOLFB node tells the kernel where and how large + * the framebuffer for video was allocated (among other things). + * Note that a _physical_ address is passed ! + * + * We only use it to pass the address and size, the other entries + * in the tag_videolfb are not of interest. + */ + params->hdr.tag = ATAG_VIDEOLFB; + params->hdr.size = tag_size (tag_videolfb); - params = tag_next(params); -} -#endif /* 0 */ + params->u.videolfb.lfb_base = (u32) gd->fb_base; + /* 7168 = 256*4*56/8 - actually 2 pages (8192 bytes) are allocated */ + params->u.videolfb.lfb_size = 7168; -#if defined (CONFIG_VFD) -static void setup_videolfb_tag(gd_t *gd) -{ - /* An ATAG_VIDEOLFB node tells the kernel where and how large - * the framebuffer for video was allocated (among other things). - * Note that a _physical_ address is passed ! - * - * We only use it to pass the address and size, the other entries - * in the tag_videolfb are not of interest. - */ - params->hdr.tag = ATAG_VIDEOLFB; - params->hdr.size = tag_size(tag_videolfb); - - params->u.videolfb.lfb_base = (u32)gd->fb_base; - /* 7168 = 256*4*56/8 - actually 2 pages (8192 bytes) are allocated */ - params->u.videolfb.lfb_size = 7168; - - params = tag_next(params); + params = tag_next (params); } #endif -static void setup_end_tag(bd_t *bd) +static void setup_end_tag (bd_t *bd) { - params->hdr.tag = ATAG_NONE; - params->hdr.size = 0; + params->hdr.tag = ATAG_NONE; + params->hdr.size = 0; } #endif /* CONFIG_SETUP_MEMORY_TAGS || CONFIG_CMDLINE_TAG || CONFIG_INITRD_TAG */ -- cgit v1.1