From 6aff3115b90780933d390d2b471479179927468d Mon Sep 17 00:00:00 2001 From: wdenk Date: Tue, 17 Dec 2002 01:51:00 +0000 Subject: * Use 1-byte-read instead of -write for iprobe() function Add i2c commands to PM826 config * extend I2C POST code: check for list on known addresses diff --git a/CHANGELOG b/CHANGELOG index 32957fe..eb21b03 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -2,6 +2,11 @@ Changes since for U-Boot 0.1.0: ====================================================================== +* Use 1-byte-read instead of -write for iprobe() function + Add i2c commands to PM826 config + +* extend I2C POST code: check for list on known addresses + * Improve log buffer code; use "loglevel" to decide which messages to log on the console, too (like in Linux); get rid of "logstart" diff --git a/README b/README index 2287f14..05f8b1f 100644 --- a/README +++ b/README @@ -2633,7 +2633,7 @@ U-Boot Porting Guide: ---------------------- [Based on messages by Jerry Van Baren in the U-Boot-Users mailing -list, Octover 2002] +list, October 2002] int main (int argc, char *argv[]) @@ -2650,6 +2650,8 @@ int main (int argc, char *argv[]) Download latest U-Boot source; + Subscribe to u-boot-users mailing list; + if (clueless) { email ("Hi, I am new to U-Boot, how do I get started?"); } @@ -2668,6 +2670,8 @@ int main (int argc, char *argv[]) Create your own board support subdirectory; + Create your own board config file; + while (!running) { do { Add / modify source code; diff --git a/common/cmd_bootm.c b/common/cmd_bootm.c index 2cf625d..e138d78b 100644 --- a/common/cmd_bootm.c +++ b/common/cmd_bootm.c @@ -366,6 +366,7 @@ do_bootm_linux (cmd_tbl_t *cmdtp, int flag, } #ifdef CONFIG_LOGBUFFER + kbd=gd->bd; /* Prevent initrd from overwriting logbuffer */ if (initrd_high < (kbd->bi_memsize-LOGBUFF_LEN-LOGBUFF_OVERHEAD)) initrd_high = kbd->bi_memsize-LOGBUFF_LEN-LOGBUFF_OVERHEAD; diff --git a/common/soft_i2c.c b/common/soft_i2c.c index 7777480..6357404 100644 --- a/common/soft_i2c.c +++ b/common/soft_i2c.c @@ -287,8 +287,9 @@ int i2c_probe(uchar addr) { int rc; + /* perform 1 byte read transaction */ send_start(); - rc = write_byte ((addr << 1) | 1); + rc = write_byte ((addr << 1) | 0); send_stop(); return (rc ? 1 : 0); diff --git a/include/configs/CCM.h b/include/configs/CCM.h index 0e0248d..0fb24db 100644 --- a/include/configs/CCM.h +++ b/include/configs/CCM.h @@ -212,6 +212,10 @@ #define CFG_ENV_IS_IN_FLASH 1 #define CFG_ENV_OFFSET 0x8000 /* Offset of Environment Sector */ #define CFG_ENV_SIZE 0x4000 /* Total Size of Environment Sector */ + +/* Address and size of Redundant Environment Sector */ +#define CFG_ENV_OFFSET_REDUND (CFG_ENV_OFFSET+CFG_ENV_SIZE) +#define CFG_ENV_SIZE_REDUND (CFG_ENV_SIZE) #else /* Final version: environment in EEPROM */ #define CFG_ENV_IS_IN_EEPROM 1 @@ -242,7 +246,8 @@ #define CFG_SYPCR (SYPCR_SWTC | SYPCR_BMT | SYPCR_BME | SYPCR_SWF | \ SYPCR_SWE | SYPCR_SWRI| SYPCR_SWP) #else -#define CFG_SYPCR (SYPCR_SWTC | SYPCR_BMT | SYPCR_BME | SYPCR_SWF | SYPCR_SWP) +#define CFG_SYPCR (SYPCR_SWTC | SYPCR_BMT | SYPCR_BME | SYPCR_SWF | \ + SYPCR_SWP) #endif /*----------------------------------------------------------------------- diff --git a/include/configs/PM826.h b/include/configs/PM826.h index dc06f95..13d7632 100644 --- a/include/configs/PM826.h +++ b/include/configs/PM826.h @@ -140,6 +140,7 @@ CFG_CMD_BEDBUG | \ CFG_CMD_DATE | \ CFG_CMD_EEPROM | \ + CFG_CMD_I2C | \ CFG_CMD_DOC) /* this must be included AFTER the definition of CONFIG_COMMANDS (if any) */ diff --git a/include/configs/TQM823L.h b/include/configs/TQM823L.h index 4eec70c..bff0cec 100644 --- a/include/configs/TQM823L.h +++ b/include/configs/TQM823L.h @@ -57,11 +57,25 @@ #define CONFIG_PREBOOT "echo;echo Type \"run flash_nfs\" to mount root filesystem over NFS;echo" #undef CONFIG_BOOTARGS -#define CONFIG_BOOTCOMMAND \ - "bootp; " \ - "setenv bootargs root=/dev/nfs rw nfsroot=$(serverip):$(rootpath) " \ - "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask):$(hostname)::off; " \ - "bootm" + +#define CONFIG_EXTRA_ENV_SETTINGS \ + "nfsargs=setenv bootargs root=/dev/nfs rw " \ + "nfsroot=$(serverip):$(rootpath)\0" \ + "ramargs=setenv bootargs root=/dev/ram rw\0" \ + "addip=setenv bootargs $(bootargs) " \ + "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask)" \ + ":$(hostname):$(netdev):off panic=1\0" \ + "flash_nfs=run nfsargs addip;" \ + "bootm $(kernel_addr)\0" \ + "flash_self=run ramargs addip;" \ + "bootm $(kernel_addr) $(ramdisk_addr)\0" \ + "net_nfs=tftp 200000 $(bootfile);run nfsargs addip;bootm\0" \ + "rootpath=/opt/eldk/ppc_8xx\0" \ + "bootfile=/tftpboot/TQM860L/pImage\0" \ + "kernel_addr=40040000\0" \ + "ramdisk_addr=40100000\0" \ + "" +#define CONFIG_BOOTCOMMAND "run flash_self" #define CONFIG_LOADS_ECHO 1 /* echo on for serial download */ #undef CFG_LOADS_BAUD_CHANGE /* don't allow baudrate change */ @@ -84,6 +98,7 @@ #define CONFIG_RTC_MPC8xx /* use internal RTC of MPC8xx */ #define CONFIG_COMMANDS ( CONFIG_CMD_DFL | \ + CFG_CMD_ASKENV | \ CFG_CMD_DHCP | \ CFG_CMD_IDE | \ CFG_CMD_DATE ) @@ -95,14 +110,22 @@ * Miscellaneous configurable options */ #define CFG_LONGHELP /* undef to save memory */ -#define CFG_PROMPT "=> " /* Monitor Command Prompt */ +#define CFG_PROMPT "=> " /* Monitor Command Prompt */ + +#if 0 +#define CFG_HUSH_PARSER 1 /* use "hush" command parser */ +#endif +#ifdef CFG_HUSH_PARSER +#define CFG_PROMPT_HUSH_PS2 "> " +#endif + #if (CONFIG_COMMANDS & CFG_CMD_KGDB) -#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ #else -#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ #endif #define CFG_PBSIZE (CFG_CBSIZE+sizeof(CFG_PROMPT)+16) /* Print Buffer Size */ -#define CFG_MAXARGS 16 /* max number of command args */ +#define CFG_MAXARGS 16 /* max number of command args */ #define CFG_BARGSIZE CFG_CBSIZE /* Boot Argument Buffer Size */ #define CFG_MEMTEST_START 0x0400000 /* memtest works on */ @@ -110,7 +133,7 @@ #define CFG_LOAD_ADDR 0x100000 /* default load address */ -#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ +#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ #define CFG_BAUDRATE_TABLE { 9600, 19200, 38400, 57600, 115200 } diff --git a/include/configs/TQM850L.h b/include/configs/TQM850L.h index 71ea2a8..a326375 100644 --- a/include/configs/TQM850L.h +++ b/include/configs/TQM850L.h @@ -53,11 +53,25 @@ #define CONFIG_PREBOOT "echo;echo Type \"run flash_nfs\" to mount root filesystem over NFS;echo" #undef CONFIG_BOOTARGS -#define CONFIG_BOOTCOMMAND \ - "bootp; " \ - "setenv bootargs root=/dev/nfs rw nfsroot=$(serverip):$(rootpath) " \ - "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask):$(hostname)::off; " \ - "bootm" + +#define CONFIG_EXTRA_ENV_SETTINGS \ + "nfsargs=setenv bootargs root=/dev/nfs rw " \ + "nfsroot=$(serverip):$(rootpath)\0" \ + "ramargs=setenv bootargs root=/dev/ram rw\0" \ + "addip=setenv bootargs $(bootargs) " \ + "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask)" \ + ":$(hostname):$(netdev):off panic=1\0" \ + "flash_nfs=run nfsargs addip;" \ + "bootm $(kernel_addr)\0" \ + "flash_self=run ramargs addip;" \ + "bootm $(kernel_addr) $(ramdisk_addr)\0" \ + "net_nfs=tftp 200000 $(bootfile);run nfsargs addip;bootm\0" \ + "rootpath=/opt/eldk/ppc_8xx\0" \ + "bootfile=/tftpboot/TQM860L/pImage\0" \ + "kernel_addr=40040000\0" \ + "ramdisk_addr=40100000\0" \ + "" +#define CONFIG_BOOTCOMMAND "run flash_self" #define CONFIG_LOADS_ECHO 1 /* echo on for serial download */ #undef CFG_LOADS_BAUD_CHANGE /* don't allow baudrate change */ @@ -76,6 +90,7 @@ #define CONFIG_RTC_MPC8xx /* use internal RTC of MPC8xx */ #define CONFIG_COMMANDS ( CONFIG_CMD_DFL | \ + CFG_CMD_ASKENV | \ CFG_CMD_DHCP | \ CFG_CMD_IDE | \ CFG_CMD_DATE ) @@ -87,14 +102,22 @@ * Miscellaneous configurable options */ #define CFG_LONGHELP /* undef to save memory */ -#define CFG_PROMPT "=> " /* Monitor Command Prompt */ +#define CFG_PROMPT "=> " /* Monitor Command Prompt */ + +#if 0 +#define CFG_HUSH_PARSER 1 /* use "hush" command parser */ +#endif +#ifdef CFG_HUSH_PARSER +#define CFG_PROMPT_HUSH_PS2 "> " +#endif + #if (CONFIG_COMMANDS & CFG_CMD_KGDB) -#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ #else -#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ #endif #define CFG_PBSIZE (CFG_CBSIZE+sizeof(CFG_PROMPT)+16) /* Print Buffer Size */ -#define CFG_MAXARGS 16 /* max number of command args */ +#define CFG_MAXARGS 16 /* max number of command args */ #define CFG_BARGSIZE CFG_CBSIZE /* Boot Argument Buffer Size */ #define CFG_MEMTEST_START 0x0400000 /* memtest works on */ @@ -102,7 +125,7 @@ #define CFG_LOAD_ADDR 0x100000 /* default load address */ -#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ +#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ #define CFG_BAUDRATE_TABLE { 9600, 19200, 38400, 57600, 115200 } @@ -294,7 +317,6 @@ /* Offset for alternate registers */ #define CFG_ATA_ALT_OFFSET 0x0100 - /*----------------------------------------------------------------------- * *----------------------------------------------------------------------- diff --git a/include/configs/TQM855L.h b/include/configs/TQM855L.h index 68151b4..f204e01 100644 --- a/include/configs/TQM855L.h +++ b/include/configs/TQM855L.h @@ -39,25 +39,39 @@ #define CONFIG_8xx_CONS_SMC1 1 /* Console is on SMC1 */ #undef CONFIG_8xx_CONS_SMC2 #undef CONFIG_8xx_CONS_NONE + #define CONFIG_BAUDRATE 115200 /* console baudrate = 115kbps */ -#if 0 -#define CONFIG_BOOTDELAY -1 /* autoboot disabled */ -#else + #define CONFIG_BOOTDELAY 5 /* autoboot after 5 seconds */ -#endif #define CONFIG_CLOCKS_IN_MHZ 1 /* clocks passsed to Linux in MHz */ #define CONFIG_BOARD_TYPES 1 /* support board types */ -#define CONFIG_PREBOOT "echo;echo Type \"run flash_nfs\" to mount root filesystem over NFS;echo" +#define CONFIG_PREBOOT "echo;" \ + "echo Type \"run flash_nfs\" to mount root filesystem over NFS;" \ + "echo" #undef CONFIG_BOOTARGS -#define CONFIG_BOOTCOMMAND \ - "bootp; " \ - "setenv bootargs root=/dev/nfs rw nfsroot=$(serverip):$(rootpath) " \ - "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask):$(hostname)::off; " \ - "bootm" + +#define CONFIG_EXTRA_ENV_SETTINGS \ + "nfsargs=setenv bootargs root=/dev/nfs rw " \ + "nfsroot=$(serverip):$(rootpath)\0" \ + "ramargs=setenv bootargs root=/dev/ram rw\0" \ + "addip=setenv bootargs $(bootargs) " \ + "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask)" \ + ":$(hostname):$(netdev):off panic=1\0" \ + "flash_nfs=run nfsargs addip;" \ + "bootm $(kernel_addr)\0" \ + "flash_self=run ramargs addip;" \ + "bootm $(kernel_addr) $(ramdisk_addr)\0" \ + "net_nfs=tftp 200000 $(bootfile);run nfsargs addip;bootm\0" \ + "rootpath=/opt/eldk/ppc_8xx\0" \ + "bootfile=/tftpboot/TQM860L/pImage\0" \ + "kernel_addr=40040000\0" \ + "ramdisk_addr=40100000\0" \ + "" +#define CONFIG_BOOTCOMMAND "run flash_self" #define CONFIG_LOADS_ECHO 1 /* echo on for serial download */ #undef CFG_LOADS_BAUD_CHANGE /* don't allow baudrate change */ @@ -76,6 +90,7 @@ #define CONFIG_RTC_MPC8xx /* use internal RTC of MPC8xx */ #define CONFIG_COMMANDS ( CONFIG_CMD_DFL | \ + CFG_CMD_ASKENV | \ CFG_CMD_DHCP | \ CFG_CMD_IDE | \ CFG_CMD_DATE ) @@ -87,14 +102,22 @@ * Miscellaneous configurable options */ #define CFG_LONGHELP /* undef to save memory */ -#define CFG_PROMPT "=> " /* Monitor Command Prompt */ +#define CFG_PROMPT "=> " /* Monitor Command Prompt */ + +#if 0 +#define CFG_HUSH_PARSER 1 /* use "hush" command parser */ +#endif +#ifdef CFG_HUSH_PARSER +#define CFG_PROMPT_HUSH_PS2 "> " +#endif + #if (CONFIG_COMMANDS & CFG_CMD_KGDB) -#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 1024 /* Console I/O Buffer Size */ #else -#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ +#define CFG_CBSIZE 256 /* Console I/O Buffer Size */ #endif #define CFG_PBSIZE (CFG_CBSIZE+sizeof(CFG_PROMPT)+16) /* Print Buffer Size */ -#define CFG_MAXARGS 16 /* max number of command args */ +#define CFG_MAXARGS 16 /* max number of command args */ #define CFG_BARGSIZE CFG_CBSIZE /* Boot Argument Buffer Size */ #define CFG_MEMTEST_START 0x0400000 /* memtest works on */ @@ -102,7 +125,7 @@ #define CFG_LOAD_ADDR 0x100000 /* default load address */ -#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ +#define CFG_HZ 1000 /* decrementer freq: 1 ms ticks */ #define CFG_BAUDRATE_TABLE { 9600, 19200, 38400, 57600, 115200 } @@ -294,7 +317,6 @@ /* Offset for alternate registers */ #define CFG_ATA_ALT_OFFSET 0x0100 - /*----------------------------------------------------------------------- * *----------------------------------------------------------------------- @@ -441,5 +463,7 @@ #define BOOTFLAG_WARM 0x02 /* Software reboot */ #define CONFIG_SCC1_ENET +#define CONFIG_FEC_ENET +#define CONFIG_ETHPRIME "SCC ETHERNET" #endif /* __CONFIG_H */ diff --git a/include/configs/TQM860L.h b/include/configs/TQM860L.h index a3d6b27..dc5eb3c 100644 --- a/include/configs/TQM860L.h +++ b/include/configs/TQM860L.h @@ -49,15 +49,29 @@ #define CONFIG_BOARD_TYPES 1 /* support board types */ #define CONFIG_PREBOOT "echo;" \ - "echo Type \"run flash_nfs\" to mount root filesystem over NFS;" \ - "echo" + "echo Type \"run flash_nfs\" to mount root filesystem over NFS;" \ + "echo" #undef CONFIG_BOOTARGS -#define CONFIG_BOOTCOMMAND \ - "bootp; " \ - "setenv bootargs root=/dev/nfs rw nfsroot=$(serverip):$(rootpath) " \ - "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask):$(hostname)::off; " \ - "bootm" + +#define CONFIG_EXTRA_ENV_SETTINGS \ + "nfsargs=setenv bootargs root=/dev/nfs rw " \ + "nfsroot=$(serverip):$(rootpath)\0" \ + "ramargs=setenv bootargs root=/dev/ram rw\0" \ + "addip=setenv bootargs $(bootargs) " \ + "ip=$(ipaddr):$(serverip):$(gatewayip):$(netmask)" \ + ":$(hostname):$(netdev):off panic=1\0" \ + "flash_nfs=run nfsargs addip;" \ + "bootm $(kernel_addr)\0" \ + "flash_self=run ramargs addip;" \ + "bootm $(kernel_addr) $(ramdisk_addr)\0" \ + "net_nfs=tftp 200000 $(bootfile);run nfsargs addip;bootm\0" \ + "rootpath=/opt/eldk/ppc_8xx\0" \ + "bootfile=/tftpboot/TQM860L/pImage\0" \ + "kernel_addr=40040000\0" \ + "ramdisk_addr=40100000\0" \ + "" +#define CONFIG_BOOTCOMMAND "run flash_self" #define CONFIG_LOADS_ECHO 1 /* echo on for serial download */ #undef CFG_LOADS_BAUD_CHANGE /* don't allow baudrate change */ diff --git a/include/configs/lwmon.h b/include/configs/lwmon.h index 587de2d..d227fff 100644 --- a/include/configs/lwmon.h +++ b/include/configs/lwmon.h @@ -288,6 +288,17 @@ #endif /* CONFIG_USE_FRAM */ #define CFG_EEPROM_PAGE_WRITE_BITS 4 +/* List of I2C addresses to be verified by POST */ +#define I2C_ADDR_LIST { /* CFG_I2C_AUDIO_ADDR, */ \ + CFG_I2C_SYSMON_ADDR, \ + CFG_I2C_RTC_ADDR, \ + CFG_I2C_POWER_A_ADDR, \ + CFG_I2C_POWER_B_ADDR, \ + CFG_I2C_KEYBD_ADDR, \ + CFG_I2C_PICIO_ADDR, \ + CFG_I2C_EEPROM_ADDR, \ + } + /*----------------------------------------------------------------------- * Cache Configuration */ diff --git a/post/i2c.c b/post/i2c.c index 2e38986..1b2e644 100644 --- a/post/i2c.c +++ b/post/i2c.c @@ -29,8 +29,13 @@ * I2C test * * For verifying the I2C bus, a full I2C bus scanning is performed. - * If any I2C device is found, the test is considered as passed, - * otherwise failed. + * + * #ifdef I2C_ADDR_LIST + * The test is considered as passed if all the devices and + * only the devices in the list are found. + * #else [ ! I2C_ADDR_LIST ] + * The test is considered as passed if any I2C device is found. + * #endif */ #include @@ -41,14 +46,48 @@ int i2c_post_test (int flags) { unsigned int i; - unsigned int chips = 0; + unsigned int good = 0; +#ifdef I2C_ADDR_LIST + unsigned int bad = 0; + int j; + unsigned char i2c_addr_list[] = I2C_ADDR_LIST; + unsigned char i2c_miss_list[] = I2C_ADDR_LIST; +#endif for (i = 0; i < 128; i++) { - if (i2c_probe (i) == 0) - chips++; + if (i2c_probe (i) == 0) { +#ifndef I2C_ADDR_LIST + good++; +#else /* I2C_ADDR_LIST */ + for (j=0; j 0 ? 0 : -1; +#ifndef I2C_ADDR_LIST + return good > 0 ? 0 : -1; +#else /* I2C_ADDR_LIST */ + if (good != sizeof(i2c_addr_list)) { + for (j=0; j $@ + +sinclude .depend + +######################################################################### + diff --git a/tools/env/README b/tools/env/README new file mode 100644 index 0000000..2b54adf --- /dev/null +++ b/tools/env/README @@ -0,0 +1,29 @@ + +This is a demo implementation of a Linux command line tool to access +the U-Boot's environment variables. + +Configuration is done via #defines in the fw_env.h file. The +following lines are relevant: + +#define HAVE_REDUND /* For systems with 2 env sectors */ +#define DEVICE1_NAME "/dev/mtd1" +#define DEVICE2_NAME "/dev/mtd2" +#define ENV1_SIZE 0x4000 +#define DEVICE1_ESIZE 0x4000 +#define ENV2_SIZE 0x4000 +#define DEVICE2_ESIZE 0x4000 + +Current configuration matches the environment layout of the TRAB +board. + +Un-define HAVE_REDUND, if you want to use the utlities on a system +that does not have support for redundant environment enabled. The +DEVICEx_NAME constants define which MTD character device(s) is (are) +to be used to access the environment. If HAVE_REDUND is undefined, +DEVICE2_NAME is ignored, as is ENV2_SIZE and DEVICE2_ESIZE. ENVx_SIZE +defines the size in bytes taken by the environment, which may be less +then flash sector size, if the environment takes less then 1 sector. +DEVICEx_ESIZE defines the size of the first sector in the flash +partition where the environment resides. It is assumed that the +environment is located in the first ENVx_SIZE bytes of the device +DEVICEx_NAME. diff --git a/tools/env/fw_env.c b/tools/env/fw_env.c new file mode 100644 index 0000000..5bf75ac --- /dev/null +++ b/tools/env/fw_env.c @@ -0,0 +1,662 @@ +/* + * (C) Copyright 2000 + * Wolfgang Denk, DENX Software Engineering, wd@denx.de. + * + * See file CREDITS for list of people who contributed to this + * project. + * + * 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 +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "fw_env.h" + +typedef unsigned char uchar; + +#define CMD_GETENV "fw_printenv" +#define CMD_SETENV "fw_setenv" + +typedef struct envdev_s { + uchar devname[16]; /* Device name */ + ulong env_size; /* environment size */ + ulong erase_size; /* device erase size */ +} envdev_t; + +static envdev_t envdevices[2]; +static int curdev; + +#define DEVNAME(i) envdevices[(i)].devname +#define ENVSIZE(i) envdevices[(i)].env_size +#define DEVESIZE(i) envdevices[(i)].erase_size + +#define CFG_ENV_SIZE ENVSIZE(curdev) + +#ifdef HAVE_REDUND +#define ENV_SIZE (CFG_ENV_SIZE - sizeof(long) - 1) +#else +#define ENV_SIZE (CFG_ENV_SIZE - sizeof(long)) +#endif + +typedef struct environment_s { + ulong crc; /* CRC32 over data bytes */ + uchar flags; /* active or obsolete */ + uchar *data; +} env_t; + +static env_t environment; +static int valid = 0; + +#ifdef HAVE_REDUND +static uchar active_flag = 1; +static uchar obsolete_flag = 0; +#endif + +#define XMK_STR(x) #x +#define MK_STR(x) XMK_STR(x) + +static uchar default_environment[] = { +#ifdef CONFIG_BOOTARGS + "bootargs=" CONFIG_BOOTARGS "\0" +#endif +#ifdef CONFIG_BOOTCOMMAND + "bootcmd=" CONFIG_BOOTCOMMAND "\0" +#endif +#if (CONFIG_BOOTDELAY >= 0) + "bootdelay=" MK_STR(CONFIG_BOOTDELAY) "\0" +#endif +#if (CONFIG_BAUDRATE >= 0) + "baudrate=" MK_STR(CONFIG_BAUDRATE) "\0" +#endif +#ifdef CONFIG_ETHADDR + "ethaddr=" MK_STR(CONFIG_ETHADDR) "\0" +#endif +#ifdef CONFIG_IPADDR + "ipaddr=" MK_STR(CONFIG_IPADDR) "\0" +#endif +#ifdef CONFIG_SERVERIP + "serverip=" MK_STR(CONFIG_SERVERIP) "\0" +#endif + "\0" +}; + +static int flash_io (int mode); +static uchar *envmatch(uchar *s1, uchar *s2); +static int env_init(void); +static int parse_config(void); + + +/* + * Search the environment for a variable. + * Return the value, if found, or NULL, if not found. + */ +unsigned char *fw_getenv (unsigned char *name) +{ + uchar *env, *nxt; + + if (env_init()) + return (NULL); + + for (env=environment.data; *env; env=nxt+1) { + uchar *val; + + for (nxt=env; *nxt; ++nxt) { + if (nxt >= &environment.data[ENV_SIZE]) { + fprintf (stderr, "## Error: " + "environment not terminated\n"); + return (NULL); + } + } + val=envmatch(name, env); + if (!val) + continue; + return (val); + } + return (NULL); +} + +/* + * Print the current definition of one, or more, or all + * environment variables + */ +void fw_printenv(int argc, char *argv[]) +{ + uchar *env, *nxt; + int i, n_flag; + + if (env_init()) + return; + + if (argc == 1) { /* Print all env variables */ + for (env=environment.data; *env; env=nxt+1) { + for (nxt=env; *nxt; ++nxt) { + if (nxt >= &environment.data[ENV_SIZE]) { + fprintf (stderr, "## Error: " + "environment not terminated\n"); + return; + } + } + + printf("%s\n", env); + } + return; + } + + if (strcmp(argv[1], "-n") == 0) { + n_flag = 1; + ++argv; + --argc; + if (argc != 2) { + fprintf (stderr, "## Error: " + "`-n' option requires exactly one argument\n"); + return; + } + } else { + n_flag = 0; + } + + for (i=1; i= &environment.data[ENV_SIZE]) { + fprintf (stderr, "## Error: " + "environment not terminated\n"); + return; + } + } + val=envmatch(name, env); + if (val) { + if (!n_flag) { + fputs (name, stdout); + putc ('=', stdout); + } + puts (val); + break; + } + } + if (!val) + fprintf (stderr, "## Error: \"%s\" not defined\n", + name); + } +} + +/* + * Deletes or sets environment variables. Returns errno style error codes: + * 0 - OK + * EINVAL - need at least 1 argument + * EROFS - certain variables ("ethaddr", "serial#") cannot be + * modified or deleted + * + */ +int fw_setenv (int argc, char *argv[]) +{ + int i, len; + uchar *env, *nxt; + uchar *oldval = NULL; + uchar *name; + + if (argc < 2) { + return (EINVAL); + } + + if (env_init()) + return (errno); + + name = argv[1]; + + /* + * search if variable with this name already exists + */ + for (env=environment.data; *env; env=nxt+1) { + for (nxt=env; *nxt; ++nxt) { + if (nxt >= &environment.data[ENV_SIZE]) { + fprintf (stderr, "## Error: " + "environment not terminated\n"); + return (EINVAL); + } + } + if ((oldval=envmatch(name, env)) != NULL) + break; + } + + /* + * Delete any existing definition + */ + if (oldval) { + /* + * Ethernet Address and serial# can be set only once + */ + if ((strcmp (name, "ethaddr") == 0) || + (strcmp (name, "serial#") == 0) ) { + fprintf (stderr, "Can't overwrite \"%s\"\n", name); + return (EROFS); + } + + if (*++nxt == '\0') { + *env = '\0'; + } else { + for (;;) { + *env = *nxt++; + if ((*env == '\0') && (*nxt == '\0')) + break; + ++env; + } + } + *++env = '\0'; + } + + /* Delete only ? */ + if (argc < 3) + goto WRITE_FLASH; + + /* + * Append new definition at the end + */ + for (env=environment.data; *env || *(env+1); ++env) + ; + if (env > environment.data) + ++env; + /* + * Overflow when: + * "name" + "=" + "val" +"\0\0" > CFG_ENV_SIZE - (env-environment) + */ + len = strlen(name) + 2; + /* add '=' for first arg, ' ' for all others */ + for (i=2; i (&environment.data[ENV_SIZE]-env)) { + fprintf (stderr, + "Error: environment overflow, \"%s\" deleted\n", + name); + return (-1); + } + while ((*env = *name++) != '\0') + env++; + for (i=2; i