===================================================================
--- u-boot-1.2.0/Makefile	(revision 2338)
+++ u-boot-1.2.0/Makefile	(revision 5555)
@@ -202,7 +202,7 @@
 LIBS += dtt/libdtt.a
 LIBS += drivers/libdrivers.a
 LIBS += drivers/nand/libnand.a
-LIBS += drivers/nand_legacy/libnand_legacy.a
+#LIBS += drivers/nand_legacy/libnand_legacy.a
 ifeq ($(CPU),mpc83xx)
 LIBS += drivers/qe/qe.a
 endif
@@ -219,10 +219,10 @@
 
 # The "tools" are needed early, so put this first
 # Don't include stuff already done in $(LIBS)
-SUBDIRS	= tools \
-	  examples \
-	  post \
-	  post/cpu
+SUBDIRS = tools
+#SUBDIRS += examples
+SUBDIRS += post
+SUBDIRS += post/cpu
 .PHONY : $(SUBDIRS)
 
 ifeq ($(CONFIG_NAND_U_BOOT),y)
@@ -230,26 +230,38 @@
 U_BOOT_NAND = $(obj)u-boot-nand.bin
 endif
 
+ifdef RESCUE
+UBOOT_BIN = u-boot.rescue.bin
+else
+UBOOT_BIN = u-boot.bin
+endif
+
 __OBJS := $(subst $(obj),,$(OBJS))
 __LIBS := $(subst $(obj),,$(LIBS))
 
 #########################################################################
 #########################################################################
 
-ALL = $(obj)u-boot.srec $(obj)u-boot.bin $(obj)System.map $(U_BOOT_NAND)
+ALL = $(obj)u-boot.srec $(obj)$(UBOOT_BIN) $(obj)System.map $(U_BOOT_NAND)
 
 all:		$(ALL)
 
 $(obj)u-boot.hex:	$(obj)u-boot
 		$(OBJCOPY) ${OBJCFLAGS} -O ihex $< $@
 
-$(obj)u-boot.srec:	$(obj)u-boot
-		$(OBJCOPY) ${OBJCFLAGS} -O srec $< $@
+$(obj)u-boot.srec:	$(obj)$(UBOOT_BIN)
+		$(OBJCOPY) -I binary -O srec $< $@
 
-$(obj)u-boot.bin:	$(obj)u-boot
+$(obj)$(UBOOT_BIN):	$(obj)u-boot
 		$(OBJCOPY) ${OBJCFLAGS} -O binary $< $@
+		@if [ -n "$(AIMAGE_SIGN)" ]; then \
+			[ "$${_TMTGTENDIAN}" = "el" ] && IMAGE_TYPE="uboot_mipsel" || IMAGE_TYPE="uboot_mipseb"; \
+			LA="$$($(OBJDUMP) -p $< | grep LOAD | head -n1 | sed 's/.*vaddr[ \t]\(0x[^ \t]\+\).*/\1/')"; \
+			if [ "$${LA}" != "$(TEXT_BASE)" ]; then echo -e "\n\nWarning: Unexpected Load Address... !?!\n"; fi; \
+			$(AIMAGE_SIGN) --type $${IMAGE_TYPE} --linkaddress $${LA} $@; \
+		fi
 
-$(obj)u-boot.img:	$(obj)u-boot.bin
+$(obj)u-boot.img:	$(obj)$(UBOOT_BIN)
 		./tools/mkimage -A $(ARCH) -T firmware -C none \
 		-a $(TEXT_BASE) -e 0 \
 		-n $(shell sed -n -e 's/.*U_BOOT_VERSION//p' $(VERSION_FILE) | \
@@ -260,7 +272,7 @@
 		$(OBJDUMP) -d $< > $@
 
 $(obj)u-boot:		depend version $(SUBDIRS) $(OBJS) $(LIBS) $(LDSCRIPT)
-		UNDEF_SYM=`$(OBJDUMP) -x $(LIBS) |sed  -n -e 's/.*\(__u_boot_cmd_.*\)/-u\1/p'|sort|uniq`;\
+		UNDEF_SYM=`$(OBJDUMP) -x $(LIBS) | sed -n -e 's/.*\(__u_boot_cmd_.*\)/-u\1/p' | sort | uniq`; \
 		cd $(LNDIR) && $(LD) $(LDFLAGS) $$UNDEF_SYM $(__OBJS) \
 			--start-group $(__LIBS) --end-group $(PLATFORM_LIBS) \
 			-Map u-boot.map -o u-boot
@@ -2127,6 +2139,9 @@
 tb0229_config: unconfig
 	@$(MKCONFIG) $(@:_config=) mips mips tb0229
 
+STB225v1_config:	unconfig
+	@$(MKCONFIG) $(@:_config=) mips pnx8330 stb22x
+
 #########################################################################
 ## MIPS32 AU1X00
 #########################################################################
@@ -2322,6 +2337,7 @@
 	rm -f $(obj)board/integratorap/u-boot.lds $(obj)board/integratorcp/u-boot.lds
 	rm -f $(obj)include/bmp_logo.h
 	rm -f $(obj)nand_spl/u-boot-spl $(obj)nand_spl/u-boot-spl.map
+	rm -f .buildinfo
 
 clobber:	clean
 	find $(OBJTREE) -type f \( -name .depend \

===================================================================
--- u-boot-1.2.0/common/Makefile	(revision 2338)
+++ u-boot-1.2.0/common/Makefile	(revision 2339)
@@ -43,7 +43,7 @@
 	  cmd_usb.o cmd_vfd.o \
 	  command.o console.o cyclon2.o devices.o dlmalloc.o docecc.o \
 	  environment.o env_common.o \
-	  env_nand.o env_dataflash.o env_flash.o env_eeprom.o \
+	  env_nand.o env_dataflash.o env_flash.o env_eeprom.o env_miuspi.o \
 	  env_nvram.o env_nowhere.o \
 	  exports.o \
 	  flash.o fpga.o ft_build.o \

===================================================================
--- u-boot-1.2.0/common/cmd_boot.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_boot.c	(revision 2339)
@@ -83,7 +83,13 @@
 extern int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
 
 U_BOOT_CMD(
-	reset, CFG_MAXARGS, 1,	do_reset,
+	reset, 1, 0,	do_reset,
 	"reset   - Perform RESET of the CPU\n",
 	NULL
 );
+
+U_BOOT_CMD(
+	reboot, 1, 0,	do_reset,
+	"reboot  - Perform RESET of the CPU\n",
+	NULL
+);

===================================================================
--- u-boot-1.2.0/common/cmd_bootm.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_bootm.c	(revision 5928)
@@ -33,7 +33,13 @@
 #include <bzlib.h>
 #include <environment.h>
 #include <asm/byteorder.h>
+#include <aimage.h>
+#include <bl_image_db.h>
 
+#if defined (CFG_BOOTN_ENABLE)
+#include <nand.h>
+#endif
+
 #ifdef CONFIG_OF_FLAT_TREE
 #include <ft_build.h>
 #endif
@@ -70,6 +76,30 @@
 #include <dataflash.h>
 #endif
 
+#if defined(__PPC__)
+#define IH_CPU_EXPECTED IH_CPU_PPC
+#elif defined(__ARM__)
+#define IH_CPU_EXPECTED IH_CPU_ARM
+#elif defined(__I386__)
+#define IH_CPU_EXPECTED IH_CPU_I386
+#elif defined(__mips__)
+#define IH_CPU_EXPECTED IH_CPU_MIPS
+#elif defined(__nios__)
+#define IH_CPU_EXPECTED IH_CPU_NIOS
+#elif defined(__M68K__)
+#define IH_CPU_EXPECTED IH_CPU_M68K
+#elif defined(__microblaze__)
+#define IH_CPU_EXPECTED IH_CPU_MICROBLAZE
+#elif defined(__nios2__)
+#define IH_CPU_EXPECTED IH_CPU_NIOS2
+#elif defined(__blackfin__)
+#define IH_CPU_EXPECTED IH_CPU_BLACKFIN
+#elif defined(__avr32__)
+#define IH_CPU_EXPECTED IH_CPU_AVR32
+#else
+#error Unknown CPU type
+#endif
+
 /*
  * Some systems (for example LWMON) have very short watchdog periods;
  * we must make sure to split long operations like memmove() or
@@ -146,6 +176,10 @@
 #define CFG_BOOTM_LEN	0x800000	/* use 8MByte as default max gunzip size */
 #endif
 
+#ifndef CFG_BOOTM_LEN_COMPRESSED
+#define CFG_BOOTM_LEN_COMPRESSED	CFG_BOOTM_LEN
+#endif
+
 image_header_t header;
 
 ulong load_addr = CFG_LOAD_ADDR;		/* Default Load Address */
@@ -171,6 +205,8 @@
 		addr = simple_strtoul(argv[1], NULL, 16);
 	}
 
+retry:
+
 	SHOW_BOOT_PROGRESS (1);
 	printf ("## Booting image at %08lx ...\n", addr);
 
@@ -195,6 +231,16 @@
 #endif	/* __I386__ */
 	    {
 		puts ("Bad Magic Number\n");
+
+		/*
+		   Couldn't find a valid uImage header... maybe we have an auImage instead ??
+		   If aimage header is found, skip it and retry.
+		*/
+		if (aimage_v1_sanity_check ((aimage_v1_header_t *) addr, 0, CFG_BOOTM_LEN_COMPRESSED) == 0) {
+			addr += sizeof(aimage_v1_header_t);
+			goto retry;
+		}
+
 		SHOW_BOOT_PROGRESS (-1);
 		return 1;
 	    }
@@ -242,29 +288,7 @@
 
 	len_ptr = (ulong *)data;
 
-#if defined(__PPC__)
-	if (hdr->ih_arch != IH_CPU_PPC)
-#elif defined(__ARM__)
-	if (hdr->ih_arch != IH_CPU_ARM)
-#elif defined(__I386__)
-	if (hdr->ih_arch != IH_CPU_I386)
-#elif defined(__mips__)
-	if (hdr->ih_arch != IH_CPU_MIPS)
-#elif defined(__nios__)
-	if (hdr->ih_arch != IH_CPU_NIOS)
-#elif defined(__M68K__)
-	if (hdr->ih_arch != IH_CPU_M68K)
-#elif defined(__microblaze__)
-	if (hdr->ih_arch != IH_CPU_MICROBLAZE)
-#elif defined(__nios2__)
-	if (hdr->ih_arch != IH_CPU_NIOS2)
-#elif defined(__blackfin__)
-	if (hdr->ih_arch != IH_CPU_BLACKFIN)
-#elif defined(__avr32__)
-	if (hdr->ih_arch != IH_CPU_AVR32)
-#else
-# error Unknown CPU type
-#endif
+	if (hdr->ih_arch != IH_CPU_EXPECTED)
 	{
 		printf ("Unsupported Architecture 0x%x\n", hdr->ih_arch);
 		SHOW_BOOT_PROGRESS (-4);
@@ -349,6 +373,7 @@
 			SHOW_BOOT_PROGRESS (-6);
 			do_reset (cmdtp, flag, argc, argv);
 		}
+		unc_len = len;
 		break;
 #ifdef CONFIG_BZIP2
 	case IH_COMP_BZIP2:
@@ -378,6 +403,10 @@
 	}
 	puts ("OK\n");
 	SHOW_BOOT_PROGRESS (7);
+	
+#ifdef CONFIG_SOC_PNX833X
+	flush_cache(ntohl(hdr->ih_load), unc_len);
+#endif
 
 	switch (hdr->ih_type) {
 	case IH_TYPE_STANDALONE:
@@ -476,7 +505,645 @@
 #endif
 );
 
+static void print_bootargs (char *args, char *desc, char *pad)
+{
+	char buf[256];
+
+	char *output = buf;
+	char *output_end = buf + sizeof(buf);
+	char *input = args;
+	char *next, *quote;
+	unsigned int len;
+	int printed = 0;
+
+	printf ("%s: ", desc);
+
+	while (1) {
+		if ((input == NULL) || (*input == 0))
+			break;
+		while (*input == ' ')
+			input++;
+		if ((*input == 0) || ((output_end - output) == 0))
+			break;
+
+		quote = strchr (input, '"');
+		next = strchr (input, ' ');
+		while ((next != NULL) && (quote != NULL) && (quote < next)) {
+			next = strchr (quote + 1, '"');
+			if (next != NULL) {
+				quote = strchr (next + 1, '"');
+				next = strchr (next + 1, ' ');
+			}
+		}
+
+		if (next == NULL)
+			next = input + strlen (input);
+
+		len = (next - input);
+		if (len >= ((output_end - output) - 1))
+			len = ((output_end - output) - 1);
+
+		memcpy (output, input, len);
+		output[len] = 0;
+
+		if (printed == 0) {
+			printf ("'%s'\n", output);
+			printed = 1;
+		}
+		else
+			printf ("%s  '%s'\n", pad, output);
+
+		input = next;
+	}
+
+	if (printed == 0)
+		printf ("<NONE>\n");
+}
+
+static void fixup_bootargs (char *root_device, char *mtdparts, char *rootfstype)
+{
+	char buf[2048];
+
+	static const char * args_blacklist[] =
+	{
+		"ro",
+		"rw",
+//		"ip=",
+		"root=",
+		"nfsroot=",
+		"mtdparts=",
+		"rootfstype="
+	};
+
+	int i;
+	char *output = buf;
+	char *output_end = buf + sizeof(buf);
+	char *input = getenv ("bootargs");
+	char *next, *quote;
+	unsigned int len;
+
+	print_bootargs (input, "\nbargs old", "         ");
+
+	output += sprintf (output, "mtdparts=%s root=%s ro rootfstype=%s", mtdparts, root_device, rootfstype);
+
+#if 0
+	/*
+	   Without an IP address on its command line, older versions of the NXP kernel
+	   hung for a while at startup. Below is a temp hack to avoid this startup delay.
+	*/
+	if ((input == NULL) || ((strstr (input, " ip=") == NULL) && (strstr (input, "ip=") != input)))
+		output += sprintf (output, " ip=192.168.0.2:192.168.0.1:192.168.0.1:255.255.255.0:stb:eth0");
+#endif
+
+	while (1) {
+		if ((input == NULL) || (*input == 0))
+			break;
+		while (*input == ' ')
+			input++;
+		if ((*input == 0) || ((output_end - output) == 0))
+			break;
+
+		quote = strchr (input, '"');
+		next = strchr (input, ' ');
+		while ((next != NULL) && (quote != NULL) && (quote < next)) {
+			next = strchr (quote + 1, '"');
+			if (next != NULL) {
+				quote = strchr (next + 1, '"');
+				next = strchr (next + 1, ' ');
+			}
+		}
+
+		if (next == NULL)
+			next = input + strlen (input);
+
+		len = (next - input);
+
+		for (i = 0; i < sizeof(args_blacklist)/sizeof(args_blacklist[0]); i++) {
+			char *arg = (char *) args_blacklist[i];
+			int arglen = strlen (arg);
+			if (arg[arglen - 1] == '=') {
+				if ((len >= arglen) && (memcmp (input, arg, arglen) == 0))
+					goto skip;
+			}
+			else {
+				if ((len == arglen) && (memcmp (input, arg, arglen) == 0))
+					goto skip;
+			}
+		}
+
+		*output++ = ' ';
+		*output = 0;
+
+		if (len >= (output_end - output))
+			break;
+
+		memcpy (output, input, len);
+		output += len;
+		*output = 0;
+skip:
+		input = next;
+	}
+
+	print_bootargs (buf, "\nbargs new", "         ");
+
+	setenv ("bootargs", buf);
+}
+
+/*
+   inline only to avoid "unused static function" compiler warnings...
+*/
+static inline unsigned int ticks_delta_to_kbps (unsigned int delta, unsigned int bytes)
+{
+	return (unsigned int) ((((unsigned long long) bytes) * get_tbclk()) /
+			       (((unsigned long long) delta) * 1024));
+}
+
+int do_boota (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+	int i;
+	int verify;
+	char *name;
+	char *rootfstype;
+	unsigned long *len_ptr;
+	unsigned long checksum_tmp;
+	unsigned long uimage_addr;		/* uimage header */
+	unsigned long uimage_data;		/* uimage data (follows header...) */
+	unsigned long uimage_data_len = 0;	/* compressed data length */
+	unsigned long uimage_load_address;
+	unsigned long aimage_load_address;
+	unsigned long entry_point;
+	unsigned long uncomp_kernel_length;	/* uncompressed size of kernel boot image */
+	unsigned long temp;
+	imagedb_entry_t *db_entry_k;		/* kernel */
+	imagedb_entry_t *db_entry_fs;		/* filesystem */
+	aimage_v1_header_t *aimage_header;	/* aimage header (kernel) */
+	image_header_t *uimage_header_copy;	/* pointer to temp copy of uimage header used while crc checking header data... */
+
+	image_db_init();
+
+#if (CONFIG_COMMANDS & CFG_CMD_NAND)
+	image_db_scan_flash_nand();
+#else
+	image_db_scan_flash_nor();
+#endif
+	image_db_show_selected();
+
+	if ((db_entry_k = image_db_find_bootable()) == NULL) {
+		printf ("%s: No valid bootable image found\n", __FUNCTION__);
+		return 1;
+	}
+
+	if ((db_entry_fs = image_db_find (IMG_TYPE_INITFS_CRAMFS)) != NULL) {
+		rootfstype = "cramfs";
+	}
+	else if ((db_entry_fs = image_db_find (IMG_TYPE_INITFS_SQUASHFS)) != NULL) {
+		rootfstype = "squashfs";
+	}
+	else {
+		printf ("%s: No valid filesystem image found\n", __FUNCTION__);
+		return 1;
+	}
+
+	if (db_entry_k->source_type == IMAGEDB_SOURCE_TYPE_MEM) {
+		aimage_header = db_entry_k->mem_image;
+		if ((aimage_header->flags & IMG_FLAG_ENCMODE_MASK) != IMG_FLAG_ENCMODE_NONE) {
+#if (CONFIG_COMMANDS & CFG_CMD_NAND)
+			unsigned int start, stop;
+
+			printf ("Decrypting kernel... ");
+			start = get_ticks();
+			if (aimage_v1_decrypt_inplace_dk (aimage_header) != 0) {
+				printf ("Error !!\n");
+				return 1;
+			}
+			stop = get_ticks();
+			printf (" done (%d kbps)\n", ticks_delta_to_kbps ((stop - start), aimage_header->data_length));
+#else
+			/*
+			   We can't decrypt in-place with memory mapped images located
+			   in NOR Flash... and decrypt with copy isn't implemented yet.
+			   ie encrypted kernels from NOR are not supported.
+			*/
+			printf ("%s: Decrypting kernel images from NOR Flash isn't supported yet...\n", __FUNCTION__);
+			return 1;
+#endif
+		}
+	}
+	else {
+		printf ("%s: Unexpected %s %d\n", __FUNCTION__, "image_db entry type", db_entry_k->source_type);
+		return 1;
+	}
+
+	if (aimage_header->type == IMG_TYPE_UIMAGE)
+	{
+		uimage_addr = (unsigned long) aimage_v1_start_of_image_data (aimage_header);
+
+		/*
+		   Copy uimage header to global header buffer (we need to blank the
+		   CRC field for CRC re-calculation...).
+
+		   Note that we also use the copy of the header for other sanity
+		   checking steps etc for performance reasons: we know that the copy
+		   is now in fast memory (ie SDRAM) while the original header may be
+		   in slower Flash.
+		*/
+
+		memcpy (&header, (char *) uimage_addr, sizeof(image_header_t));
+		uimage_header_copy = &header;
+
+		if (ntohl (uimage_header_copy->ih_magic) != IH_MAGIC) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "uImage magic", uimage_header_copy->ih_magic);
+			return 1;
+		}
+
+		checksum_tmp = ntohl (uimage_header_copy->ih_hcrc);
+
+		uimage_header_copy->ih_hcrc = 0;
+		if (crc32 (0, (unsigned char *) uimage_header_copy, sizeof(image_header_t)) != checksum_tmp) {
+			puts ("Bad Header Checksum\n");
+			return 1;
+		}
+
+		/*
+		   Use the original uimage header when calling print_image_hdr(), rather than the copy.
+		   (printing 'header' info for multi-file uimages requires access to the data part too).
+		*/
+		print_image_hdr ((image_header_t *) uimage_addr);
+
+		if (uimage_header_copy->ih_arch != IH_CPU_EXPECTED) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "architecture", uimage_header_copy->ih_arch);
+			return 1;
+		}
+
+		if (uimage_header_copy->ih_type != IH_TYPE_KERNEL) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "uImage type", uimage_header_copy->ih_type);
+			return 1;
+		}
+		name = "Kernel Image";
+
+		if (uimage_header_copy->ih_comp != IH_COMP_GZIP) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "compression type", uimage_header_copy->ih_comp);
+			return 1;
+		}
+
+		if (uimage_header_copy->ih_os != IH_OS_LINUX) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "OS type", uimage_header_copy->ih_os);
+			return 1;
+		}
+
+		uimage_data = uimage_addr + sizeof(image_header_t);
+
+		if (uimage_data & 0x03) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "uImage data alignment", uimage_data);
+			return 1;
+		}
+
+		uimage_data_len = ntohl (uimage_header_copy->ih_size);
+
+		if (uimage_data_len > aimage_header->data_length) {
+			printf ("%s: Unexpected %s %d\n", __FUNCTION__, "uImage data length", uimage_data_len);
+			return 1;
+		}
+
+		uimage_load_address = ntohl (uimage_header_copy->ih_load);
+		aimage_load_address = aimage_header->data_link_address;
+
+		if (uimage_load_address != aimage_load_address) {
+			printf ("%s: uImage load address (0x%08lx) != aimage load address (0x%08lx)\n",
+				__FUNCTION__, uimage_load_address, aimage_load_address);
+			return 1;
+		}
+
+		entry_point = ntohl (uimage_header_copy->ih_ep);
+	}
+	else if (aimage_header->type == IMG_TYPE_ZIMAGE) {
+		printf ("%s: Support for booting zImages is not complete yet... sorry\n", __FUNCTION__);
+		return 1;
+	}
+	else {
+		printf ("%s: Unexpected %s %d\n", __FUNCTION__, "aimage image type", aimage_header->type);
+		return 1;
+	}
+
+	fixup_bootargs (db_entry_fs->devname, db_entry_fs->mtdparts, rootfstype);
+
+	printf ("\nUncompressing uImage %s to 0x%08lx... ", name, aimage_load_address);
+
+	/*
+	   Apparently, on some platforms, uncompressing the boot image is a point of no return...
+	   Exception vectors get over-written, which makes recovery from failures tricky.
+	   ie rebooting is the easiest way to handle errors from this point on.
+	*/
+
+	disable_interrupts();
+
+	temp = uimage_data_len; 	/* input to gunzip() : amount of compressed data available */
+
+	if (gunzip ((void *) aimage_load_address, CFG_BOOTM_LEN, (unsigned char *) uimage_data, &temp) != 0) {
+		printf ("GUNZIP ERROR - rebooting\n");
+		goto failure;
+	}
+	printf ("OK\n");
+
+	uncomp_kernel_length = temp;	/* output from gunzip() : uncompressed size */
+
+	if ((entry_point < aimage_load_address) || (entry_point >= (aimage_load_address + uncomp_kernel_length))) {
+		printf ("%s: entry point (0x%08lx) outside expected range (0x%08lx..0x%08lx))\n",
+			__FUNCTION__, entry_point, aimage_load_address, (aimage_load_address + uncomp_kernel_length));
+		goto failure;
+	}
+
+#ifdef CONFIG_SOC_PNX833X
+	flush_cache (aimage_load_address, uncomp_kernel_length);
+#endif
+
 #ifdef CONFIG_SILENT_CONSOLE
+	fixup_silent_linux();
+#endif
+
+	argc = 0;
+	argv = NULL;
+	len_ptr = (ulong *) uimage_data;
+	verify = 0;
+
+	do_bootm_linux (cmdtp, flag, argc, argv, uimage_addr, len_ptr, verify);
+
+	printf ("%s: Huh !?!\n", __FUNCTION__);
+
+failure:
+	/*
+	   Fixme: stb225 reset function doesn't flush uart Tx fifo before rebooting...
+	   As a temporary hack, print extra debug here to so all previous messages are seen.
+	*/
+	for (i = 5; i; i--)
+		printf ("do_boota: failure... rebooting %d\n", i);
+
+	while (1)
+		do_reset (cmdtp, flag, argc, argv);
+}
+
+U_BOOT_CMD(
+	boota, CFG_MAXARGS, 0, do_boota,
+	"boota   - find, verify and boot signed kernel image\n",
+	"   - find, verify and boot signed kernel image\n"
+);
+
+#if defined (CFG_BOOTN_ENABLE)
+
+static aimage_v1_header_t* get_aimage_v1_header(unsigned offset)
+{
+	static aimage_v1_header_t hdr;
+	ulong total = sizeof(hdr);
+	int ret1, ret2;
+
+	memset(&hdr, 0, sizeof(hdr));
+	ret1 = nand_read(&nand_info[0], offset, &total, (u_char*)&hdr);
+	ret2 = aimage_v1_sanity_check (&hdr, 0, CFG_BOOTN_FS_SIZE);
+	if (ret1 !=0 || ret2 != 0 || total != sizeof(hdr)) {
+		printf ("%s: header not found (offset 0x%08x), %d (%d, %d)\n", 
+		          __FUNCTION__, offset ,ret2, total, ret1);
+		return 0;
+	}
+	return &hdr;
+}
+
+static int verify_aimage(unsigned offset, unsigned length, unsigned type)
+{
+	static u_char buf[64*1024];
+	aimage_stream_context_t ctx;
+
+	aimage_v1_verify_signature_stream_init_dk (&ctx, type, length, NULL);
+	while (length) {
+		ulong amt = sizeof(buf);
+		int ret;
+
+		if (length < amt) amt = length;
+		ret = nand_read(&nand_info[0], offset, &amt, buf);
+		if (ret != 0 || amt == 0) {
+			printf ("%s: read failed (offset 0x%08x), %d (%d)\n", 
+		          __FUNCTION__, offset ,ret, amt);
+			break;
+		}
+		offset += amt;
+		length -= amt;
+		printf(".");
+        	ret = aimage_v1_verify_signature_stream_update (&ctx, buf, amt);
+		if (ret == 0) return 1;
+		if (ret == -1) return 0;
+	}
+	printf("%s: Not enough data\n", __FUNCTION__);
+	return 0;
+}
+
+static u_char* verify_auimage(unsigned offset, unsigned length)
+{
+	u_char* buf = 0;
+	int ret;
+	ulong amt = length;
+
+	if (length > KERNEL_SIZE_MAX) {
+		printf("uimage too big: %d\n", length);
+		return 0;
+	}
+	buf = malloc(length);
+	ret = nand_read(&nand_info[0], offset, &amt, buf);
+	if (ret != 0 || amt != length) {
+		printf ("%s: read failed (offset 0x%08x), %d (%d)\n", 
+	          __FUNCTION__, offset ,ret, amt);
+		free(buf);
+		return 0;
+	}
+	ret = aimage_v1_verify_signature_dk ((aimage_v1_header_t *) buf, IMG_TYPE_UIMAGE, amt);
+	if (ret == 0) return buf;
+	free(buf);
+	return 0;
+}
+
+static void append_to_bootargs(const char* s)
+{
+	char* b = getenv("bootargs");
+	char* n = malloc(strlen(b) + strlen(s) + 1);
+
+	strcat(strcpy(n,b),s);
+	setenv("bootargs",n);
+	free(n);
+}
+
+extern unsigned nand_map_block(struct mtd_info* mtd, unsigned offset);
+
+static void append_mtdparts(int swap)
+{
+	char buf[128];
+	unsigned start[5];
+	unsigned size[5];
+	unsigned f,g;
+
+	start[0] = 0;
+	start[1] = nand_map_block(&nand_info[0],CFG_BOOTN_BOOT_SIZE-CFG_BOOTN_ID_SIZE)/1024;
+	start[2] = nand_map_block(&nand_info[0],CFG_BOOTN_BOOT_SIZE)/1024;
+	start[3] = nand_map_block(&nand_info[0],CFG_BOOTN_BOOT_SIZE+CFG_BOOTN_FS_SIZE)/1024;
+	start[4] = nand_map_block(&nand_info[0],CFG_BOOTN_BOOT_SIZE+2*CFG_BOOTN_FS_SIZE)/1024;
+	size[0] = start[1] - start[0];
+	size[1] = start[2] - start[1];
+	size[2] = start[3] - start[2];
+	size[3] = start[4] - start[3];
+	size[4] = nand_info[0].size/1024 - start[4];
+	f = swap ? 3 : 2;
+	g = swap ? 2 : 3;
+	sprintf(buf, " mtdparts=gen_nand:%dk(Boot),%dk@%dk(Active),%dk@%dk(Update)"
+                  ",%dk@%dk(RW),%dk@%dk(ID),%dk@0k(All)", size[0], size[f], 
+	          start[f], size[g], start[g], size[4], start[4], size[1], 
+	          start[1], nand_info[0].size/1024);
+	append_to_bootargs(buf);
+}
+
+static void read_macaddr(unsigned char a[3])
+{
+	int ret;
+	ulong amt = sizeof(a);
+	unsigned offset = CFG_BOOTN_MAC_OFFSET;
+	unsigned length = amt;
+
+	ret = nand_read(&nand_info[0], offset, &amt, a);
+	if (ret != 0 || amt != length) {
+		printf ("%s: read failed (offset 0x%08x), %d (%d)\n", 
+	          __FUNCTION__, offset ,ret, amt);
+		memset(a, 0xff, sizeof(a));
+	}
+}
+
+static void append_ethaddr(void)
+{
+	char buf[40];
+	unsigned char a[3];
+	unsigned val;
+	const char* oui;
+
+	read_macaddr(a);
+	val = (a[2] << 16) | (a[1] << 8) | a[0];
+	oui = (val < 800) ? "00:1D:F2" : "00:0D:4B";
+	sprintf(buf, " ip3902.mac_address=%s:%02X:%02X:%02X", oui, a[2], a[1],
+	        a[0] & ~1);
+	append_to_bootargs(buf);
+}
+
+static unsigned get_img_offset(unsigned part)
+{
+	return CFG_BOOTN_BOOT_SIZE + (part ? CFG_BOOTN_FS_SIZE : 0);
+}
+
+static void setversion(unsigned part, unsigned value)
+{
+	unsigned offset = get_img_offset(part);
+	ulong amt = nand_info[0].erasesize;
+	u_char* buf = malloc(amt);
+	int ret = nand_read(&nand_info[0], offset, &amt, buf);
+
+	if (ret != 0 || amt != nand_info[0].erasesize) {
+		printf ("%s: read failed (offset 0x%08x), %d (%d)\n", 
+	          __FUNCTION__, offset ,ret, amt);
+		free(buf);
+		return;
+	}
+	ret = nand_erase(&nand_info[0], offset, amt);
+	if (ret != 0) {
+		printf ("%s: write failed (offset 0x%08x), %d\n", 
+	          __FUNCTION__, offset ,ret);
+		free(buf);
+		return;
+	}
+	((aimage_v1_header_t *)buf)->usd = value;
+	ret = nand_write(&nand_info[0], offset, &amt, buf);
+	if (ret != 0 || amt != nand_info[0].erasesize)
+		printf ("%s: write failed (offset 0x%08x), %d (%d)\n", 
+	          __FUNCTION__, offset ,ret, amt);
+	free(buf);
+	printf("Partition %d: Set Version: %d\n", part, value);
+}
+
+static u_char* is_image_valid(unsigned part)
+{
+	unsigned part_start = get_img_offset(part);
+	aimage_v1_header_t* hdr = get_aimage_v1_header(part_start);
+	int good = 0;
+	unsigned offset = part_start;
+	u_char* buf;
+
+	if (!hdr) return 0;
+	if (hdr->type != IMG_TYPE_INITFS_CRAMFS && hdr->type != IMG_TYPE_UIMAGE)
+	{
+		printf("Partition %d: unknown aimage type: %d\n",part,
+		        hdr->type);
+		return 0;
+	}
+	if (hdr->type == IMG_TYPE_INITFS_CRAMFS) {
+		good = verify_aimage(offset, hdr->length, IMG_TYPE_INITFS_CRAMFS);
+		printf("Partition %d: Verify cramfs: %s\n",part,
+		         good ? "Success" : "Fail");
+		if (!good) return 0;
+		offset = part_start + (hdr->length & ~3);	/* fixme... rounding down hdr->length shouldn't be required... ?!? */
+		hdr = get_aimage_v1_header(offset);
+		if (!hdr) return 0;
+	}
+	if (hdr->type != IMG_TYPE_UIMAGE) {
+		printf("Partition %d: unexpected image type: %d\n", part,
+		        hdr->type);
+		return 0;
+	}
+	buf = verify_auimage(offset,hdr->length);
+	printf("Partition %d: Verify uimage: %s\n",part,buf?"Success":"Fail");
+	return buf;
+}
+
+static void boot_auimage(cmd_tbl_t *cmdtp, int flag, u_char* buf, unsigned part)
+{
+	ulong orig = load_addr;		
+
+	load_addr = (ulong) aimage_v1_start_of_image_data((aimage_v1_header_t*)buf);
+	append_mtdparts(part);
+	append_ethaddr();
+	do_bootm (cmdtp, flag, 0, 0);
+	load_addr = orig;
+	free(buf);
+}
+
+static int get_image_version(unsigned part, unsigned* ver)
+{ 
+	unsigned part_start = get_img_offset(part);
+	aimage_v1_header_t* hdr = get_aimage_v1_header(part_start);
+
+	if (!hdr) return 0;
+	*ver = hdr->usd;
+	printf("Image %d: Version %d\n", part, *ver);
+	return 1;
+}
+
+int do_bootn (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+	unsigned ver[2], i, j;
+	int has_hdr[2];
+	u_char* buf;
+
+	for (i=0;i<2;i++) has_hdr[i] = get_image_version(i,ver+i);
+	j = has_hdr[1] && (!has_hdr[0] || ver[1] < ver[0]);
+	for (i=0;i<2;i++,j=!j) {
+		buf = is_image_valid(j);
+		if ((ver[j] == 0 || !buf) && has_hdr[j]) 
+			setversion(j,has_hdr[!j] ? (ver[!j] + 1) : 1);
+		if (buf) boot_auimage(cmdtp,flag,buf,j);
+	}
+	return 0;
+}
+
+U_BOOT_CMD(
+	bootn, CFG_MAXARGS, 0, do_bootn,
+	"bootn   - find, verify and boot signed kernel image\n",
+	"   - find, verify and boot signed kernel image\n"
+);
+
+#endif
+
+#ifdef CONFIG_SILENT_CONSOLE
 static void
 fixup_silent_linux ()
 {
@@ -1334,39 +2001,39 @@
 
 	switch (hdr->ih_os) {
 	case IH_OS_INVALID:	os = "Invalid OS";		break;
-	case IH_OS_NETBSD:	os = "NetBSD";			break;
+//	case IH_OS_NETBSD:	os = "NetBSD";			break;
 	case IH_OS_LINUX:	os = "Linux";			break;
-	case IH_OS_VXWORKS:	os = "VxWorks";			break;
-	case IH_OS_QNX:		os = "QNX";			break;
+//	case IH_OS_VXWORKS:	os = "VxWorks";			break;
+//	case IH_OS_QNX:		os = "QNX";			break;
 	case IH_OS_U_BOOT:	os = "U-Boot";			break;
-	case IH_OS_RTEMS:	os = "RTEMS";			break;
+//	case IH_OS_RTEMS:	os = "RTEMS";			break;
 #ifdef CONFIG_ARTOS
-	case IH_OS_ARTOS:	os = "ARTOS";			break;
+//	case IH_OS_ARTOS:	os = "ARTOS";			break;
 #endif
 #ifdef CONFIG_LYNXKDI
-	case IH_OS_LYNXOS:	os = "LynxOS";			break;
+//	case IH_OS_LYNXOS:	os = "LynxOS";			break;
 #endif
 	default:		os = "Unknown OS";		break;
 	}
 
 	switch (hdr->ih_arch) {
 	case IH_CPU_INVALID:	arch = "Invalid CPU";		break;
-	case IH_CPU_ALPHA:	arch = "Alpha";			break;
+//	case IH_CPU_ALPHA:	arch = "Alpha";			break;
 	case IH_CPU_ARM:	arch = "ARM";			break;
-	case IH_CPU_AVR32:	arch = "AVR32";			break;
-	case IH_CPU_I386:	arch = "Intel x86";		break;
-	case IH_CPU_IA64:	arch = "IA64";			break;
+//	case IH_CPU_AVR32:	arch = "AVR32";			break;
+//	case IH_CPU_I386:	arch = "Intel x86";		break;
+//	case IH_CPU_IA64:	arch = "IA64";			break;
 	case IH_CPU_MIPS:	arch = "MIPS";			break;
 	case IH_CPU_MIPS64:	arch = "MIPS 64 Bit";		break;
-	case IH_CPU_PPC:	arch = "PowerPC";		break;
-	case IH_CPU_S390:	arch = "IBM S390";		break;
-	case IH_CPU_SH:		arch = "SuperH";		break;
-	case IH_CPU_SPARC:	arch = "SPARC";			break;
-	case IH_CPU_SPARC64:	arch = "SPARC 64 Bit";		break;
-	case IH_CPU_M68K:	arch = "M68K"; 			break;
-	case IH_CPU_MICROBLAZE:	arch = "Microblaze"; 		break;
-	case IH_CPU_NIOS:	arch = "Nios";			break;
-	case IH_CPU_NIOS2:	arch = "Nios-II";		break;
+//	case IH_CPU_PPC:	arch = "PowerPC";		break;
+//	case IH_CPU_S390:	arch = "IBM S390";		break;
+//	case IH_CPU_SH:		arch = "SuperH";		break;
+//	case IH_CPU_SPARC:	arch = "SPARC";			break;
+//	case IH_CPU_SPARC64:	arch = "SPARC 64 Bit";		break;
+//	case IH_CPU_M68K:	arch = "M68K"; 			break;
+//	case IH_CPU_MICROBLAZE:	arch = "Microblaze"; 		break;
+//	case IH_CPU_NIOS:	arch = "Nios";			break;
+//	case IH_CPU_NIOS2:	arch = "Nios-II";		break;
 	default:		arch = "Unknown Architecture";	break;
 	}
 

===================================================================
--- u-boot-1.2.0/common/cmd_flash.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_flash.c	(revision 2339)
@@ -433,7 +433,12 @@
 				rcode = flash_erase (info, s_first[bank], s_last[bank]);
 			}
 		}
-		printf ("Erased %d sectors\n", erased);
+		if ( rcode == ERR_OK ) {
+			printf ("Erased %d sectors\n", erased);
+		}
+		else {
+			flash_perror (rcode);
+		}
 	} else if (rcode == 0) {
 		puts ("Error: start and/or end address"
 			" not on sector boundary\n");

===================================================================
--- u-boot-1.2.0/common/cmd_ide.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_ide.c	(revision 2339)
@@ -41,6 +41,13 @@
 #include <mpc5xxx.h>
 #endif
 #include <ide.h>
+#ifdef CONFIG_SATA_NHP
+/* Define parameters of SATA_NHP before including ata.h */
+  #define CFG_ATA_STRIDE	4
+  #define CFG_ATA_DATA_OFFSET	0
+  #define CFG_ATA_REG_OFFSET	0
+  #define CFG_ATA_ALT_OFFSET	(0x20 - 6 * CFG_ATA_STRIDE)	/* to get ATA_IO_CTL at 0x20 offset */
+#endif
 #include <ata.h>
 #ifdef CONFIG_STATUS_LED
 # include <status_led.h>
@@ -697,7 +704,10 @@
 
 block_dev_desc_t * ide_get_dev(int dev)
 {
-	return ((block_dev_desc_t *)&ide_dev_desc[dev]);
+	if (dev < 0 || dev >= CFG_IDE_MAXDEVICE)
+		return NULL;
+	else
+		return ((block_dev_desc_t *)&ide_dev_desc[dev]);
 }
 
 
@@ -858,6 +868,10 @@
 #if defined(__LITTLE_ENDIAN) || ( defined(CONFIG_AU1X00) && !defined(CONFIG_GTH2) )
 #define input_swap_data(x,y,z) input_data(x,y,z)
 #else
+#ifdef CONFIG_SATA_NHP
+#error input_swap_data() for CONFIG_SATA_NHP is not checked yet in big endian mode
+#define input_swap_data(x,y,z) input_data(x,y,z)
+#else
 static void
 input_swap_data(int dev, ulong *sect_buf, int words)
 {
@@ -891,6 +905,7 @@
 	}
 #endif
 }
+#endif	/* CONFIG_SATA_NHP */
 #endif	/* __LITTLE_ENDIAN || CONFIG_AU1X00 */
 
 
@@ -931,11 +946,64 @@
 #endif
 }
 #else	/* ! __PPC__ */
+
+#ifdef CONFIG_SATA_NHP
+
+/* On SATA NHP we have to deal with handshare register */
+
+#define SATA_NHP_HANDSHAKE_REG	0x24
+#define SATA_NHP_READ_HANDSHAKE_REG(dev) \
+		inl(ATA_CURR_BASE(dev) + SATA_NHP_HANDSHAKE_REG)
+#define SATA_NHP_WILL_DO_IO(hsval)		((hsval & (1 << 3)) != 0)
+#define SATA_NHP_WRITE_READY(hsval)		((hsval & (1 << 2)) != 0)
+#define SATA_NHP_READ_READY(hsval)		((hsval & (1 << 1)) != 0)
+#define SATA_NHP_CONFIRM_READ(dev) \
+		outl(1, ATA_CURR_BASE(dev) + SATA_NHP_HANDSHAKE_REG)
+
+#define SATA_NHP_DATA_REG	0x0
+#define SATA_NHP_WRITE_WORD(dev, word) \
+		outl((ulong)(word), ATA_CURR_BASE(dev) + SATA_NHP_DATA_REG)
+#define SATA_NHP_READ_WORD(dev) \
+		inl(ATA_CURR_BASE(dev) + SATA_NHP_DATA_REG)
+
 static void
+output_data_shorts(int dev, ushort *sect_buf, int words)
+{
+	int w;
+
+	for (w = 0; w < words; w++) {
+		int timeleft = 5000000;	/* to avoid hangs if something went wrong */
+		while (--timeleft) {
+			unsigned long hs = SATA_NHP_READ_HANDSHAKE_REG(dev);
+			if (!SATA_NHP_WILL_DO_IO(hs)) {
+				printf("ERROR: SATA device refused to write word at sector offset %d\n", w << 1);
+				return;
+			}
+			if (SATA_NHP_WRITE_READY(hs)) {
+				SATA_NHP_WRITE_WORD(dev, sect_buf[w]);
+				break;
+			}
+		}
+		if (!timeleft) {
+			printf("ERROR: timed out while waiting for handshake when writing word at sector offset %d to ATA device\n", w << 1);
+			return;
+		}
+	}
+}
+
+static inline void
 output_data(int dev, ulong *sect_buf, int words)
 {
+	output_data_shorts(dev, (ushort *)sect_buf, words << 1);
+}
+	
+#else
+static void
+output_data(int dev, ulong *sect_buf, int words)
+{
 	outsw(ATA_CURR_BASE(dev)+ATA_DATA_REG, sect_buf, words<<1);
 }
+#endif	/* CONFIG_SATA_NHP */
 #endif	/* __PPC__ */
 
 #if defined(__PPC__) || defined(CONFIG_PXA_PCMCIA)
@@ -982,11 +1050,46 @@
 #endif
 }
 #else	/* ! __PPC__ */
+#ifdef CONFIG_SATA_NHP
+
 static void
+input_data_shorts(int dev, ushort *sect_buf, int words)
+{
+	int w;
+
+	for (w = 0; w < words; w++) {
+		int timeleft = 5000000;	/* to avoid hangs if something went wrong */
+		while (--timeleft) {
+			unsigned long hs = SATA_NHP_READ_HANDSHAKE_REG(dev);
+			if (!SATA_NHP_WILL_DO_IO(hs)) {
+				printf("ERROR: SATA device refused to read word at sector offset %d\n", w << 1);
+				return;
+			}
+			if (SATA_NHP_READ_READY(hs)) {
+				sect_buf[w] = SATA_NHP_READ_WORD(dev);
+				break;
+			}
+		}
+		if (!timeleft) {
+			printf("ERROR: timed out while waiting for handshake when writing word at sector offset %d to ATA device\n", w << 1);
+			return;
+		}
+	}
+}
+
+static inline void
 input_data(int dev, ulong *sect_buf, int words)
 {
+	input_data_shorts(dev, (ushort *)sect_buf, words << 1);
+}
+
+#else
+static void
+input_data(int dev, ulong *sect_buf, int words)
+{
 	insw(ATA_CURR_BASE(dev)+ATA_DATA_REG, sect_buf, words << 1);
 }
+#endif	/* CONFIG_SATA_NHP */
 
 #endif	/* __PPC__ */
 
@@ -1483,8 +1586,40 @@
 /* ------------------------------------------------------------------------- */
 
 #ifdef CONFIG_IDE_RESET
+
+#ifdef CONFIG_SATA_NHP
+
+#define SATA_NHP_RESET_REG	0xc00
+#define SATA_NHP_RESET_VALUE	1
+
+#define SATA_NHP_INT_ENABLE_REG	0xfe4
+#define SATA_NHP_INT_CLEAR_REG	0xfe8
+
+void ide_set_reset(int reset)
+{
+	/* When reset=1, we actually reset hardware, and also clean
+	 * interrupt masks.
+	 * When reset=0, we do nothing */
+
+	int dev;
+	
+	if (!reset)
+		return;
+
+	for (dev = 0; dev < CFG_IDE_MAXDEVICE; dev++) {
+		unsigned long base = ATA_CURR_BASE(dev);
+		outl(SATA_NHP_RESET_VALUE, base + SATA_NHP_RESET_REG);
+		outl(0, base + SATA_NHP_INT_ENABLE_REG);
+		outl(0xffffffff, base + SATA_NHP_INT_CLEAR_REG);
+		outl(0, base + SATA_NHP_INT_CLEAR_REG);
+	}
+}
+#else
+
 extern void ide_set_reset(int idereset);
 
+#endif	/* CONFIG_SATA_NHP */
+
 static void ide_reset (void)
 {
 #if defined(CFG_PB_12V_ENABLE) || defined(CFG_PB_IDE_MOTOR)
@@ -1659,6 +1794,8 @@
 }
 
 #else	/* ! __PPC__ */
+#ifndef CONFIG_SATA_NHP
+
 static void
 output_data_shorts(int dev, ushort *sect_buf, int shorts)
 {
@@ -1671,6 +1808,7 @@
 	insw(ATA_CURR_BASE(dev)+ATA_DATA_REG, sect_buf, shorts);
 }
 
+#endif	/* CONFIG_SATA_NHP */
 #endif	/* __PPC__ */
 
 /*

===================================================================
--- u-boot-1.2.0/common/cmd_jffs2.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_jffs2.c	(revision 2763)
@@ -105,6 +105,10 @@
 #include <linux/mtd/nand.h>
 #include <nand.h>
 #endif /* !CFG_NAND_LEGACY */
+#if defined (CFG_NAND_BB_REMAP)
+extern unsigned nand_map_block(struct mtd_info* mtd, unsigned offset);
+extern unsigned nand_map_getsize(struct mtd_info* mtd, unsigned offset, unsigned size);
+#endif
 #endif /* (CONFIG_COMMANDS & CFG_CMD_NAND) */
 /* enable/disable debugging messages */
 #define	DEBUG_JFFS
@@ -339,7 +343,7 @@
 		}
 	}
 	if (offset_aligned == 0) {
-		printf("%s%d: partition (%s) start offset alignment incorrect\n",
+		printf("%s%d: NOR partition (%s) start offset alignment incorrect\n",
 				MTD_DEV_TYPE(id->type), id->num, part->name);
 		return 1;
 	}
@@ -353,7 +357,7 @@
 	if (flash->size == end_offset)
 		return 0;
 
-	printf("%s%d: partition (%s) size alignment incorrect\n",
+	printf("%s%d: NOR partition (%s) size alignment incorrect\n",
 			MTD_DEV_TYPE(id->type), id->num, part->name);
 #endif
 	return 1;
@@ -377,13 +381,13 @@
 	nand = &nand_info[id->num];
 
 	if ((unsigned long)(part->offset) % nand->erasesize) {
-		printf("%s%d: partition (%s) start offset alignment incorrect\n",
+		printf("%s%d: NAND partition (%s) start offset alignment incorrect\n",
 				MTD_DEV_TYPE(id->type), id->num, part->name);
 		return 1;
 	}
 
 	if (part->size % nand->erasesize) {
-		printf("%s%d: partition (%s) size alignment incorrect\n",
+		printf("%s%d: NAND partition (%s) size alignment incorrect\n",
 				MTD_DEV_TYPE(id->type), id->num, part->name);
 		return 1;
 	}
@@ -1104,7 +1108,7 @@
  * @param buflen buffer size
  * @return 0 on success, 1 otherwise
  */
-static int generate_mtdparts(char *buf, u32 buflen)
+static int generate_mtdparts(char *buf, u32 buflen, int real)
 {
 	struct list_head *pentry, *dentry;
 	struct mtd_device *dev;
@@ -1141,8 +1145,17 @@
 		part_cnt = 0;
 		list_for_each(pentry, &dev->parts) {
 			part = list_entry(pentry, struct part_info, link);
-			size = part->size;
-			offset = part->offset;
+#if defined (CFG_NAND_BB_REMAP)
+			if (real) {
+				offset = nand_map_block (&nand_info[0], part->offset);
+				size = nand_map_getsize (&nand_info[0], part->offset, part->size);
+			}
+			else
+#endif
+			{
+				offset = part->offset;
+				size = part->size;
+			}
 			part_cnt++;
 
 			/* partition size */
@@ -1231,16 +1244,16 @@
  * @param buflen buffer size
  * @return 0 on success, 1 otherwise
  */
-static int generate_mtdparts_save(char *buf, u32 buflen)
+static int generate_mtdparts_save(char *buf, u32 buflen, int real)
 {
 	int ret;
 
-	ret = generate_mtdparts(buf, buflen);
+	ret = generate_mtdparts(buf, buflen, real);
 
 	if ((buf[0] != '\0') && (ret == 0))
-		setenv("mtdparts", buf);
+		setenv(real ? "mtdpartsr" : "mtdparts", buf);
 	else
-		setenv("mtdparts", NULL);
+		setenv(real ? "mtdpartsr" : "mtdparts", NULL);
 
 	return ret;
 }
@@ -1381,7 +1394,7 @@
 		if (part_del(dev, part) != 0)
 			return 1;
 
-		if (generate_mtdparts_save(last_parts, MTDPARTS_MAXLEN) != 0) {
+		if (generate_mtdparts_save(last_parts, MTDPARTS_MAXLEN, 0) != 0) {
 			printf("generated mtdparts too long, reseting to null\n");
 			return 1;
 		}
@@ -1836,6 +1849,8 @@
 /* U-boot commands				   */
 /***************************************************/
 
+#ifndef CFG_NO_FS_ACCESS
+
 /**
  * Routine implementing fsload u-boot command. This routine tries to load
  * a requested file from jffs2/cramfs filesystem on a current partition.
@@ -1976,6 +1991,8 @@
 	return 1;
 }
 
+#endif
+
 /* command line only */
 #ifdef CONFIG_JFFS2_CMDLINE
 /**
@@ -2052,7 +2069,14 @@
 		return 1;
 
 	if (argc == 1) {
+#if defined (CFG_NAND_BB_REMAP)
+		char mparts[MTDPARTS_MAXLEN];
 		list_partitions();
+		generate_mtdparts_save(mparts,sizeof(mparts),1);
+		printf("mtdparts: %s\n",mparts);
+#else
+		list_partitions();
+#endif
 		return 0;
 	}
 
@@ -2105,7 +2129,7 @@
 			}
 		}
 
-		if (generate_mtdparts_save(last_parts, MTDPARTS_MAXLEN) != 0) {
+		if (generate_mtdparts_save(last_parts, MTDPARTS_MAXLEN, 0) != 0) {
 			printf("generated mtdparts too long, reseting to null\n");
 			return 1;
 		}
@@ -2126,6 +2150,9 @@
 #endif /* #ifdef CONFIG_JFFS2_CMDLINE */
 
 /***************************************************/
+
+#ifndef CFG_NO_FS_ACCESS
+
 U_BOOT_CMD(
 	fsload,	3,	0,	do_jffs2_fsload,
 	"fsload\t- load binary file from a filesystem image\n",
@@ -2146,6 +2173,8 @@
 	"    - print information about filesystems\n"
 );
 
+#endif
+
 #ifdef CONFIG_JFFS2_CMDLINE
 U_BOOT_CMD(
 	chpart,	2,	0,	do_jffs2_chpart,

===================================================================
--- u-boot-1.2.0/common/cmd_mem.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_mem.c	(revision 2339)
@@ -29,6 +29,7 @@
 
 #include <common.h>
 #include <command.h>
+#include <sha.h>
 #if (CONFIG_COMMANDS & CFG_CMD_MMC)
 #include <mmc.h>
 #endif
@@ -1185,6 +1186,57 @@
 }
 #endif	/* CONFIG_CRC32_VERIFY */
 
+static void sha1sum_buffer (unsigned char *hash, unsigned char *buf, unsigned int length)
+{
+	SHA_CTX context;
+
+	SHA1_Init (&context);
+	SHA1_Update (&context, buf, length);
+	SHA1_Final (hash, &context);
+}
+
+void sha1sum_display (unsigned char *buf, unsigned int length)
+{
+	int i;
+	unsigned char hash[SHA_DIGEST_LENGTH];
+	unsigned long start, stop, delta;
+	unsigned int kbps;
+
+	start = get_ticks();
+	sha1sum_buffer (hash, buf, length);
+	stop = get_ticks();
+
+	delta = stop - start;
+	kbps = (unsigned int) ((((unsigned long long) length) * get_tbclk()) /
+			       (((unsigned long long) delta ) * 1024));
+
+	printf ("sha1sum 0x%08lx..0x%08lx: " , (unsigned long) buf, (unsigned long) buf + length - 1);
+	for (i = 0; i < SHA_DIGEST_LENGTH; i++)
+		printf ("%02x", hash[i]);
+	printf (" (%7d bytes, %4d kbps)\n", length, kbps);
+}
+
+int do_mem_sha1 (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+	ulong addr;
+	unsigned int length;
+
+	if (argc < 3) {
+		printf ("Usage:\n%s\n", cmdtp->usage);
+		return 1;
+	}
+
+	addr = simple_strtoul (argv[1], NULL, 16);
+	addr += base_address;
+
+	length = simple_strtoul (argv[2], NULL, 16);
+
+	sha1sum_display ((unsigned char *) addr, length);
+
+	return 0;
+}
+
+
 /**************************************************/
 #if (CONFIG_COMMANDS & CFG_CMD_MEMORY)
 U_BOOT_CMD(
@@ -1245,6 +1297,12 @@
 #endif	/* CONFIG_CRC32_VERIFY */
 
 U_BOOT_CMD(
+	sha1,    3,    1,     do_mem_sha1,
+	"sha1    - sha1 hash calculation\n",
+	"address count\n    - compute SHA1 checksum\n"
+);
+
+U_BOOT_CMD(
 	base,    2,    1,     do_mem_base,
 	"base    - print or set address offset\n",
 	"\n    - print address offset for memory commands\n"

===================================================================
--- u-boot-1.2.0/common/cmd_misc.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_misc.c	(revision 2339)
@@ -31,21 +31,32 @@
 
 int do_sleep (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
 {
-	ulong start = get_timer(0);
-	ulong delay;
+	ulong start;
+	ulong seconds;
+	ulong ticks_per_second;
 
 	if (argc != 2) {
 		printf ("Usage:\n%s\n", cmdtp->usage);
 		return 1;
 	}
+	if ((seconds = simple_strtoul (argv[1], NULL, 10)) == 0)
+		return 0;
 
-	delay = simple_strtoul(argv[1], NULL, 10) * CFG_HZ;
+	ticks_per_second = get_tbclk();
 
-	while (get_timer(start) < delay) {
-		if (ctrlc ()) {
-			return (-1);
+	while (1) {
+		start = get_timer (0);
+		printf ("%c", (seconds < 10) ? ('0' + seconds) : '.');
+		if (seconds == 0) {
+			printf ("\n");
+			break;
 		}
-		udelay (100);
+		seconds--;
+		while (get_timer (start) < ticks_per_second) {
+			if (ctrlc())
+				return -1;
+			udelay (100);
+		}
 	}
 
 	return 0;

===================================================================
--- u-boot-1.2.0/common/cmd_nand.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_nand.c	(revision 5928)
@@ -21,6 +21,7 @@
 
 #if (CONFIG_COMMANDS & CFG_CMD_NAND)
 
+#include <aimage.h>
 #include <command.h>
 #include <watchdog.h>
 #include <malloc.h>
@@ -45,8 +46,14 @@
 		u8 *part_num, struct part_info **part);
 #endif
 
-extern nand_info_t nand_info[];       /* info for NAND chips */
+#ifndef CFG_BOOTM_LEN
+#define CFG_BOOTM_LEN	0x800000	/* use 8MByte as default max gunzip size */
+#endif
 
+#ifndef CFG_BOOTM_LEN_COMPRESSED
+#define CFG_BOOTM_LEN_COMPRESSED	CFG_BOOTM_LEN
+#endif
+
 static int nand_dump_oob(nand_info_t *nand, ulong off)
 {
 	return 0;
@@ -181,6 +188,19 @@
 
 	cmd = argv[1];
 
+#if defined (CONFIG_NAND_DBG_CONTROL)
+	if (strcmp(cmd, "dbgon") == 0) {
+		printf ("debug on\n");
+		nand_debug_enable = 1;
+		return 0;
+	}
+	if (strcmp(cmd, "dbgoff") == 0) {
+		printf ("debug off\n");
+		nand_debug_enable = 0;
+		return 0;
+	}
+#endif
+
 	if (strcmp(cmd, "info") == 0) {
 
 		putc('\n');
@@ -315,6 +335,8 @@
 	/* read write */
 	if (strncmp(cmd, "read", 4) == 0 || strncmp(cmd, "write", 5) == 0) {
 		int read;
+		unsigned long ticks_start, ticks_stop, ticks_delta;
+		unsigned int kbps;
 
 		if (argc < 4)
 			goto usage;
@@ -326,9 +348,11 @@
 		if (arg_off_size(argc - 3, argv + 3, nand, &off, &size) != 0)
 			return 1;
 
+		ticks_start = get_ticks();
+
 		s = strchr(cmd, '.');
 		if (s != NULL &&
-		    (!strcmp(s, ".jffs2") || !strcmp(s, ".e") || !strcmp(s, ".i"))) {
+		    (!strcmp(s, ".jffs2") || !strcmp(s, ".jffs") || !strcmp(s, ".e") || !strcmp(s, ".i"))) {
 			if (read) {
 				/* read */
 				nand_read_options_t opts;
@@ -352,15 +376,22 @@
 				ret = nand_write_opts(nand, &opts);
 			}
 		} else {
+			printf ("nand_%s(), no opts (probably not what you really want...)\n", read ? "read" : "write");
 			if (read)
 				ret = nand_read(nand, off, &size, (u_char *)addr);
 			else
 				ret = nand_write(nand, off, &size, (u_char *)addr);
 		}
 
-		printf(" %d bytes %s: %s\n", size,
-		       read ? "read" : "written", ret ? "ERROR" : "OK");
+		ticks_stop = get_ticks();
 
+		ticks_delta = ticks_stop - ticks_start;
+		kbps = (unsigned int) ((((unsigned long long) size) * get_tbclk()) /
+				       (((unsigned long long) ticks_delta) * 1024));
+
+		printf(" %d bytes %s: %s (%4d kbps)\n", size,
+		       read ? "read" : "written", ret ? "ERROR" : "OK", kbps);
+
 		return ret == 0 ? 0 : 1;
 	}
 
@@ -455,7 +486,7 @@
 	return 1;
 }
 
-U_BOOT_CMD(nand, 5, 1, do_nand,
+U_BOOT_CMD(nand, 5, 0, do_nand,
 	"nand    - NAND sub-system\n",
 	"info                  - show available NAND devices\n"
 	"nand device [dev]     - show or set current device\n"
@@ -476,21 +507,42 @@
 			   ulong offset, ulong addr, char *cmd)
 {
 	int r;
-	char *ep;
+	char *ep, *s;
 	ulong cnt;
+	ulong addr_end;
 	image_header_t *hdr;
+	int jffs2 = 0;
 
+	s = strchr(cmd, '.');
+	if (s != NULL &&
+	    (!strcmp(s, ".jffs2") || !strcmp(s, ".jffs") || !strcmp(s, ".e") || !strcmp(s, ".i")))
+		jffs2 = 1;
+
 	printf("\nLoading from %s, offset 0x%lx\n", nand->name, offset);
 
 	cnt = nand->oobblock;
-	r = nand_read(nand, offset, &cnt, (u_char *) addr);
+	if (jffs2) {
+		nand_read_options_t opts;
+		memset(&opts, 0, sizeof(opts));
+		opts.buffer	= (u_char*) addr;
+		opts.length	= cnt;
+		opts.offset	= offset;
+		opts.quiet      = 1;
+		r = nand_read_opts(nand, &opts);
+	} else {
+	    r = nand_read(nand, offset, &cnt, (u_char *) addr);
+	}
+
 	if (r) {
 		puts("** Read error\n");
 		SHOW_BOOT_PROGRESS(-1);
 		return 1;
 	}
 
-	hdr = (image_header_t *) addr;
+	if (aimage_v1_sanity_check ((aimage_v1_header_t *) addr, 0, CFG_BOOTM_LEN_COMPRESSED) == 0)
+		hdr = (image_header_t *) (addr + sizeof(aimage_v1_header_t));
+	else
+		hdr = (image_header_t *) addr;
 
 	if (ntohl(hdr->ih_magic) != IH_MAGIC) {
 		printf("\n** Bad Magic Number 0x%x **\n", hdr->ih_magic);
@@ -498,11 +550,23 @@
 		return 1;
 	}
 
-	print_image_hdr(hdr);
+//	print_image_hdr(hdr);
 
-	cnt = (ntohl(hdr->ih_size) + sizeof (image_header_t));
+	addr_end = ((ulong) hdr) + sizeof(image_header_t) + ntohl(hdr->ih_size);
+	cnt = addr_end - addr;
 
-	r = nand_read(nand, offset, &cnt, (u_char *) addr);
+	if (jffs2) {
+		nand_read_options_t opts;
+		memset(&opts, 0, sizeof(opts));
+		opts.buffer	= (u_char*) addr;
+		opts.length	= cnt;
+		opts.offset	= offset;
+		opts.quiet      = 1;
+		r = nand_read_opts(nand, &opts);
+	} else {
+	    r = nand_read(nand, offset, &cnt, (u_char *) addr);
+	}
+
 	if (r) {
 		puts("** Read error\n");
 		SHOW_BOOT_PROGRESS(-1);
@@ -511,7 +575,7 @@
 
 	/* Loading ok, update default load address */
 
-	load_addr = addr;
+	load_addr = (ulong) hdr;
 
 	/* Check if we should attempt an auto-start */
 	if (((ep = getenv("autostart")) != NULL) && (strcmp(ep, "yes") == 0)) {
@@ -550,7 +614,7 @@
 			if (argc > 3)
 				goto usage;
 			if (argc == 3)
-				addr = simple_strtoul(argv[2], NULL, 16);
+				addr = simple_strtoul(argv[1], NULL, 16);
 			else
 				addr = CFG_LOAD_ADDR;
 			return nand_load_image(cmdtp, &nand_info[dev->id->num],
@@ -605,386 +669,10 @@
 
 U_BOOT_CMD(nboot, 4, 1, do_nandboot,
 	"nboot   - boot from NAND device\n",
-	"[partition] | [[[loadAddr] dev] offset]\n");
+	"[.jffs2] [partition] | [[[loadAddr] dev] offset]\n");
 
 #endif				/* (CONFIG_COMMANDS & CFG_CMD_NAND) */
 
-#else /* CFG_NAND_LEGACY */
-/*
- *
- * Legacy NAND support - to be phased out
- *
- */
-#include <command.h>
-#include <malloc.h>
-#include <asm/io.h>
-#include <watchdog.h>
-
-#ifdef CONFIG_SHOW_BOOT_PROGRESS
-# include <status_led.h>
-# define SHOW_BOOT_PROGRESS(arg)	show_boot_progress(arg)
 #else
-# define SHOW_BOOT_PROGRESS(arg)
+#error "CFG_NAND_LEGACY not supported"
 #endif
-
-#if (CONFIG_COMMANDS & CFG_CMD_NAND)
-#include <linux/mtd/nand_legacy.h>
-#if 0
-#include <linux/mtd/nand_ids.h>
-#include <jffs2/jffs2.h>
-#endif
-
-#ifdef CONFIG_OMAP1510
-void archflashwp(void *archdata, int wp);
-#endif
-
-#define ROUND_DOWN(value,boundary)      ((value) & (~((boundary)-1)))
-
-#undef	NAND_DEBUG
-#undef	PSYCHO_DEBUG
-
-/* ****************** WARNING *********************
- * When ALLOW_ERASE_BAD_DEBUG is non-zero the erase command will
- * erase (or at least attempt to erase) blocks that are marked
- * bad. This can be very handy if you are _sure_ that the block
- * is OK, say because you marked a good block bad to test bad
- * block handling and you are done testing, or if you have
- * accidentally marked blocks bad.
- *
- * Erasing factory marked bad blocks is a _bad_ idea. If the
- * erase succeeds there is no reliable way to find them again,
- * and attempting to program or erase bad blocks can affect
- * the data in _other_ (good) blocks.
- */
-#define	 ALLOW_ERASE_BAD_DEBUG 0
-
-#define CONFIG_MTD_NAND_ECC  /* enable ECC */
-#define CONFIG_MTD_NAND_ECC_JFFS2
-
-/* bits for nand_legacy_rw() `cmd'; or together as needed */
-#define NANDRW_READ	0x01
-#define NANDRW_WRITE	0x00
-#define NANDRW_JFFS2	0x02
-#define NANDRW_JFFS2_SKIP	0x04
-
-/*
- * Imports from nand_legacy.c
- */
-extern struct nand_chip nand_dev_desc[CFG_MAX_NAND_DEVICE];
-extern int curr_device;
-extern int nand_legacy_erase(struct nand_chip *nand, size_t ofs,
-			    size_t len, int clean);
-extern int nand_legacy_rw(struct nand_chip *nand, int cmd, size_t start,
-			 size_t len, size_t *retlen, u_char *buf);
-extern void nand_print(struct nand_chip *nand);
-extern void nand_print_bad(struct nand_chip *nand);
-extern int nand_read_oob(struct nand_chip *nand, size_t ofs,
-			       size_t len, size_t *retlen, u_char *buf);
-extern int nand_write_oob(struct nand_chip *nand, size_t ofs,
-				size_t len, size_t *retlen, const u_char *buf);
-
-
-int do_nand (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
-{
-	int rcode = 0;
-
-	switch (argc) {
-	case 0:
-	case 1:
-		printf ("Usage:\n%s\n", cmdtp->usage);
-		return 1;
-	case 2:
-		if (strcmp (argv[1], "info") == 0) {
-			int i;
-
-			putc ('\n');
-
-			for (i = 0; i < CFG_MAX_NAND_DEVICE; ++i) {
-				if (nand_dev_desc[i].ChipID ==
-				    NAND_ChipID_UNKNOWN)
-					continue;	/* list only known devices */
-				printf ("Device %d: ", i);
-				nand_print (&nand_dev_desc[i]);
-			}
-			return 0;
-
-		} else if (strcmp (argv[1], "device") == 0) {
-			if ((curr_device < 0)
-			    || (curr_device >= CFG_MAX_NAND_DEVICE)) {
-				puts ("\nno devices available\n");
-				return 1;
-			}
-			printf ("\nDevice %d: ", curr_device);
-			nand_print (&nand_dev_desc[curr_device]);
-			return 0;
-
-		} else if (strcmp (argv[1], "bad") == 0) {
-			if ((curr_device < 0)
-			    || (curr_device >= CFG_MAX_NAND_DEVICE)) {
-				puts ("\nno devices available\n");
-				return 1;
-			}
-			printf ("\nDevice %d bad blocks:\n", curr_device);
-			nand_print_bad (&nand_dev_desc[curr_device]);
-			return 0;
-
-		}
-		printf ("Usage:\n%s\n", cmdtp->usage);
-		return 1;
-	case 3:
-		if (strcmp (argv[1], "device") == 0) {
-			int dev = (int) simple_strtoul (argv[2], NULL, 10);
-
-			printf ("\nDevice %d: ", dev);
-			if (dev >= CFG_MAX_NAND_DEVICE) {
-				puts ("unknown device\n");
-				return 1;
-			}
-			nand_print (&nand_dev_desc[dev]);
-			/*nand_print (dev); */
-
-			if (nand_dev_desc[dev].ChipID == NAND_ChipID_UNKNOWN) {
-				return 1;
-			}
-
-			curr_device = dev;
-
-			puts ("... is now current device\n");
-
-			return 0;
-		} else if (strcmp (argv[1], "erase") == 0
-			   && strcmp (argv[2], "clean") == 0) {
-			struct nand_chip *nand = &nand_dev_desc[curr_device];
-			ulong off = 0;
-			ulong size = nand->totlen;
-			int ret;
-
-			printf ("\nNAND erase: device %d offset %ld, size %ld ... ", curr_device, off, size);
-
-			ret = nand_legacy_erase (nand, off, size, 1);
-
-			printf ("%s\n", ret ? "ERROR" : "OK");
-
-			return ret;
-		}
-
-		printf ("Usage:\n%s\n", cmdtp->usage);
-		return 1;
-	default:
-		/* at least 4 args */
-
-		if (strncmp (argv[1], "read", 4) == 0 ||
-		    strncmp (argv[1], "write", 5) == 0) {
-			ulong addr = simple_strtoul (argv[2], NULL, 16);
-			ulong off = simple_strtoul (argv[3], NULL, 16);
-			ulong size = simple_strtoul (argv[4], NULL, 16);
-			int cmd = (strncmp (argv[1], "read", 4) == 0) ?
-				NANDRW_READ : NANDRW_WRITE;
-			int ret, total;
-			char *cmdtail = strchr (argv[1], '.');
-
-			if (cmdtail && !strncmp (cmdtail, ".oob", 2)) {
-				/* read out-of-band data */
-				if (cmd & NANDRW_READ) {
-					ret = nand_read_oob (nand_dev_desc + curr_device,
-							     off, size, (size_t *) & total,
-							     (u_char *) addr);
-				} else {
-					ret = nand_write_oob (nand_dev_desc + curr_device,
-							      off, size, (size_t *) & total,
-							      (u_char *) addr);
-				}
-				return ret;
-			} else if (cmdtail && !strncmp (cmdtail, ".jffs2", 2))
-				cmd |= NANDRW_JFFS2;	/* skip bad blocks */
-			else if (cmdtail && !strncmp (cmdtail, ".jffs2s", 2)) {
-				cmd |= NANDRW_JFFS2;	/* skip bad blocks (on read too) */
-				if (cmd & NANDRW_READ)
-					cmd |= NANDRW_JFFS2_SKIP;	/* skip bad blocks (on read too) */
-			}
-#ifdef SXNI855T
-			/* need ".e" same as ".j" for compatibility with older units */
-			else if (cmdtail && !strcmp (cmdtail, ".e"))
-				cmd |= NANDRW_JFFS2;	/* skip bad blocks */
-#endif
-#ifdef CFG_NAND_SKIP_BAD_DOT_I
-			/* need ".i" same as ".jffs2s" for compatibility with older units (esd) */
-			/* ".i" for image -> read skips bad block (no 0xff) */
-			else if (cmdtail && !strcmp (cmdtail, ".i")) {
-				cmd |= NANDRW_JFFS2;	/* skip bad blocks (on read too) */
-				if (cmd & NANDRW_READ)
-					cmd |= NANDRW_JFFS2_SKIP;	/* skip bad blocks (on read too) */
-			}
-#endif /* CFG_NAND_SKIP_BAD_DOT_I */
-			else if (cmdtail) {
-				printf ("Usage:\n%s\n", cmdtp->usage);
-				return 1;
-			}
-
-			printf ("\nNAND %s: device %d offset %ld, size %ld ...\n",
-				(cmd & NANDRW_READ) ? "read" : "write",
-				curr_device, off, size);
-
-			ret = nand_legacy_rw (nand_dev_desc + curr_device,
-					      cmd, off, size,
-					      (size_t *) & total,
-					      (u_char *) addr);
-
-			printf (" %d bytes %s: %s\n", total,
-				(cmd & NANDRW_READ) ? "read" : "written",
-				ret ? "ERROR" : "OK");
-
-			return ret;
-		} else if (strcmp (argv[1], "erase") == 0 &&
-			   (argc == 4 || strcmp ("clean", argv[2]) == 0)) {
-			int clean = argc == 5;
-			ulong off =
-				simple_strtoul (argv[2 + clean], NULL, 16);
-			ulong size =
-				simple_strtoul (argv[3 + clean], NULL, 16);
-			int ret;
-
-			printf ("\nNAND erase: device %d offset %ld, size %ld ...\n",
-				curr_device, off, size);
-
-			ret = nand_legacy_erase (nand_dev_desc + curr_device,
-						 off, size, clean);
-
-			printf ("%s\n", ret ? "ERROR" : "OK");
-
-			return ret;
-		} else {
-			printf ("Usage:\n%s\n", cmdtp->usage);
-			rcode = 1;
-		}
-
-		return rcode;
-	}
-}
-
-U_BOOT_CMD(
-	nand,	5,	1,	do_nand,
-	"nand    - legacy NAND sub-system\n",
-	"info  - show available NAND devices\n"
-	"nand device [dev] - show or set current device\n"
-	"nand read[.jffs2[s]]  addr off size\n"
-	"nand write[.jffs2] addr off size - read/write `size' bytes starting\n"
-	"    at offset `off' to/from memory address `addr'\n"
-	"nand erase [clean] [off size] - erase `size' bytes from\n"
-	"    offset `off' (entire device if not specified)\n"
-	"nand bad - show bad blocks\n"
-	"nand read.oob addr off size - read out-of-band data\n"
-	"nand write.oob addr off size - read out-of-band data\n"
-);
-
-int do_nandboot (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
-{
-	char *boot_device = NULL;
-	char *ep;
-	int dev;
-	ulong cnt;
-	ulong addr;
-	ulong offset = 0;
-	image_header_t *hdr;
-	int rcode = 0;
-	switch (argc) {
-	case 1:
-		addr = CFG_LOAD_ADDR;
-		boot_device = getenv ("bootdevice");
-		break;
-	case 2:
-		addr = simple_strtoul(argv[1], NULL, 16);
-		boot_device = getenv ("bootdevice");
-		break;
-	case 3:
-		addr = simple_strtoul(argv[1], NULL, 16);
-		boot_device = argv[2];
-		break;
-	case 4:
-		addr = simple_strtoul(argv[1], NULL, 16);
-		boot_device = argv[2];
-		offset = simple_strtoul(argv[3], NULL, 16);
-		break;
-	default:
-		printf ("Usage:\n%s\n", cmdtp->usage);
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	if (!boot_device) {
-		puts ("\n** No boot device **\n");
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	dev = simple_strtoul(boot_device, &ep, 16);
-
-	if ((dev >= CFG_MAX_NAND_DEVICE) ||
-	    (nand_dev_desc[dev].ChipID == NAND_ChipID_UNKNOWN)) {
-		printf ("\n** Device %d not available\n", dev);
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	printf ("\nLoading from device %d: %s at 0x%lx (offset 0x%lx)\n",
-		dev, nand_dev_desc[dev].name, nand_dev_desc[dev].IO_ADDR,
-		offset);
-
-	if (nand_legacy_rw (nand_dev_desc + dev, NANDRW_READ, offset,
-			SECTORSIZE, NULL, (u_char *)addr)) {
-		printf ("** Read error on %d\n", dev);
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	hdr = (image_header_t *)addr;
-
-	if (ntohl(hdr->ih_magic) == IH_MAGIC) {
-
-		print_image_hdr (hdr);
-
-		cnt = (ntohl(hdr->ih_size) + sizeof(image_header_t));
-		cnt -= SECTORSIZE;
-	} else {
-		printf ("\n** Bad Magic Number 0x%x **\n", ntohl(hdr->ih_magic));
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	if (nand_legacy_rw (nand_dev_desc + dev, NANDRW_READ,
-			offset + SECTORSIZE, cnt, NULL,
-			(u_char *)(addr+SECTORSIZE))) {
-		printf ("** Read error on %d\n", dev);
-		SHOW_BOOT_PROGRESS (-1);
-		return 1;
-	}
-
-	/* Loading ok, update default load address */
-
-	load_addr = addr;
-
-	/* Check if we should attempt an auto-start */
-	if (((ep = getenv("autostart")) != NULL) && (strcmp(ep,"yes") == 0)) {
-		char *local_args[2];
-		extern int do_bootm (cmd_tbl_t *, int, int, char *[]);
-
-		local_args[0] = argv[0];
-		local_args[1] = NULL;
-
-		printf ("Automatic boot of image at addr 0x%08lx ...\n", addr);
-
-		do_bootm (cmdtp, 0, 1, local_args);
-		rcode = 1;
-	}
-	return rcode;
-}
-
-U_BOOT_CMD(
-	nboot,	4,	1,	do_nandboot,
-	"nboot   - boot from NAND device\n",
-	"loadAddr dev\n"
-);
-
-#endif /* (CONFIG_COMMANDS & CFG_CMD_NAND) */
-
-#endif /* CFG_NAND_LEGACY */

===================================================================
--- u-boot-1.2.0/common/cmd_nvedit.c	(revision 2338)
+++ u-boot-1.2.0/common/cmd_nvedit.c	(revision 4586)
@@ -57,8 +57,9 @@
     !defined(CFG_ENV_IS_IN_FLASH)	&& \
     !defined(CFG_ENV_IS_IN_DATAFLASH)	&& \
     !defined(CFG_ENV_IS_IN_NAND)	&& \
+    !defined(CFG_ENV_IS_IN_MIU_SPI_FLASH)	&& \
     !defined(CFG_ENV_IS_NOWHERE)
-# error Define one of CFG_ENV_IS_IN_{NVRAM|EEPROM|FLASH|DATAFLASH|NOWHERE}
+# error Define one of CFG_ENV_IS_IN_{NVRAM|EEPROM|FLASH|DATAFLASH|MIU_SPI|NOWHERE}
 #endif
 
 #define XMK_STR(x)	#x
@@ -498,7 +499,7 @@
 		int val;
 
 		for (nxt=i; env_get_char(nxt) != '\0'; ++nxt) {
-			if (nxt >= CFG_ENV_SIZE) {
+			if (nxt >= sizeof (env_t)) {
 				return (NULL);
 			}
 		}
@@ -518,7 +519,7 @@
 		int val, n;
 
 		for (nxt=i; env_get_char(nxt) != '\0'; ++nxt) {
-			if (nxt >= CFG_ENV_SIZE) {
+			if (nxt >= sizeof (env_t)) {
 				return (-1);
 			}
 		}
@@ -549,7 +550,14 @@
 	return (saveenv() ? 1 : 0);
 }
 
+int do_clearenv (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+	extern char * env_name_spec;
 
+	printf ("Clearing Environment in %s...\n", env_name_spec);
+
+	return (clearenv() ? 1 : 0);
+}
 #endif
 
 
@@ -599,6 +607,11 @@
     ((CONFIG_COMMANDS & (CFG_CMD_ENV|CFG_CMD_NAND)) == \
       (CFG_CMD_ENV|CFG_CMD_NAND))
 U_BOOT_CMD(
+	clearenv, 1, 0,	do_clearenv,
+	"clearenv- erase environment variables persistent storage\n",
+	NULL
+);
+U_BOOT_CMD(
 	saveenv, 1, 0,	do_saveenv,
 	"saveenv - save environment variables to persistent storage\n",
 	NULL

===================================================================
--- u-boot-1.2.0/common/console.c	(revision 2338)
+++ u-boot-1.2.0/common/console.c	(revision 4493)
@@ -214,12 +214,21 @@
 	}
 }
 
+#if 0
+
 void printf (const char *fmt, ...)
 {
 	va_list args;
 	uint i;
 	char printbuffer[CFG_PBSIZE];
 
+	static int timing = 1;
+	
+	if (timing) {
+		timing = 0;
+		printf ("[%4d] ", (unsigned int) (get_ticks() / (get_tbclk() / 1000)));
+	}
+
 	va_start (args, fmt);
 
 	/* For this to work, printbuffer must be larger than
@@ -230,8 +239,33 @@
 
 	/* Print the string */
 	puts (printbuffer);
+
+	if (printbuffer[strlen (printbuffer) - 1] == '\n')
+		timing = 1;
 }
 
+#else
+
+void printf (const char *fmt, ...)
+{
+	va_list args;
+	uint i;
+	char printbuffer[CFG_PBSIZE];
+
+	va_start (args, fmt);
+
+	/* For this to work, printbuffer must be larger than
+	 * anything we ever want to print.
+	 */
+	i = vsprintf (printbuffer, fmt, args);
+	va_end (args);
+
+	/* Print the string */
+	puts (printbuffer);
+}
+
+#endif
+
 void vprintf (const char *fmt, va_list args)
 {
 	uint i;
@@ -364,6 +398,7 @@
 	gd->have_console = 1;
 
 #ifdef CONFIG_SILENT_CONSOLE
+#error "Don't access environment before relocation..."
 	if (getenv("silent") != NULL)
 		gd->flags |= GD_FLG_SILENT;
 #endif

===================================================================
--- u-boot-1.2.0/common/env_common.c	(revision 2338)
+++ u-boot-1.2.0/common/env_common.c	(revision 4586)
@@ -141,8 +141,18 @@
 	"\0"
 };
 
+uchar secure_environment[] = {
+#ifdef	CONFIG_BOOTARGS_SECURE
+	"bootargs="	CONFIG_BOOTARGS_SECURE		"\0"
+#endif
+#ifdef	CONFIG_BOOTCOMMAND_SECURE
+	"bootcmd="	CONFIG_BOOTCOMMAND_SECURE	"\0"
+#endif
+};
+
 #if defined(CFG_ENV_IS_IN_NAND)		/* Environment is in Nand Flash */
 int default_environment_size = sizeof(default_environment);
+int secure_environment_size = sizeof(secure_environment);
 #endif
 
 void env_crc_update (void)
@@ -218,7 +228,7 @@
 	/*
 	 * We must allocate a buffer for the environment
 	 */
-	env_ptr = (env_t *)malloc (CFG_ENV_SIZE);
+	env_ptr = (env_t *)malloc (sizeof (env_t));
 	DEBUGF ("%s[%d] malloced ENV at %p\n", __FUNCTION__,__LINE__,env_ptr);
 #endif
 
@@ -231,7 +241,8 @@
 #if defined(CONFIG_GTH)	|| defined(CFG_ENV_IS_NOWHERE)	/* Environment not changable */
 		puts ("Using default environment\n\n");
 #else
-		puts ("*** Warning - bad CRC, using default environment\n\n");
+		puts ("Using default environment\n\n");
+//		puts ("*** Warning - bad CRC, using default environment\n\n");
 		SHOW_BOOT_PROGRESS (-1);
 #endif
 
@@ -241,14 +252,14 @@
 			return;
 		}
 
-		memset (env_ptr, 0, sizeof(env_t));
-		memcpy (env_ptr->data,
-			default_environment,
-			sizeof(default_environment));
+		memset (env_ptr, 0, sizeof(env_t) - ENV_SIZE);
+		memcpy (env_ptr->data, default_environment, sizeof(default_environment));
+		memset (env_ptr->data + sizeof(default_environment), 0, ENV_SIZE - sizeof(default_environment));
+
 #ifdef CFG_REDUNDAND_ENVIRONMENT
 		env_ptr->flags = 0xFF;
 #endif
-		env_crc_update ();
+		env_ptr->crc = crc32(0, env_ptr->data, ENV_SIZE);
 		gd->env_valid = 1;
 	}
 	else {

===================================================================
--- u-boot-1.2.0/common/env_eeprom.c	(revision 2338)
+++ u-boot-1.2.0/common/env_eeprom.c	(revision 4586)
@@ -58,7 +58,7 @@
 	eeprom_read (CFG_DEF_EEPROM_ADDR,
 		     CFG_ENV_OFFSET,
 		     (uchar*)env_ptr,
-		     CFG_ENV_SIZE);
+		     sizeof (env_t));
 }
 
 int saveenv(void)
@@ -66,7 +66,7 @@
 	return eeprom_write (CFG_DEF_EEPROM_ADDR,
 			     CFG_ENV_OFFSET,
 			     (uchar *)env_ptr,
-			     CFG_ENV_SIZE);
+			     sizeof (env_t));
 }
 
 /************************************************************************

===================================================================
--- u-boot-1.2.0/common/env_flash.c	(revision 2338)
+++ u-boot-1.2.0/common/env_flash.c	(revision 3701)
@@ -253,6 +253,15 @@
 
 	return rc;
 }
+
+int clearenv(void)
+{
+#error "FIXME: clearenv not yet supported with CFG_ENV_ADDR_REDUND"
+
+	printf ("\nError: clearenv not yet supported with CFG_ENV_ADDR_REDUND\n\n");
+	return 1;
+}
+
 #endif /* CMD_SAVEENV */
 
 #else /* ! CFG_ENV_ADDR_REDUND */
@@ -348,6 +357,36 @@
 	return rcode;
 }
 
+int clearenv(void)
+{
+	ulong end_addr;
+	ulong flash_sect_addr = (ulong) flash_addr;
+	int len = CFG_ENV_SIZE;
+
+#if defined (CONFIG_INFERNO)
+	/* this is the last sector, and the size is hardcoded here */
+	/* otherwise we will get stack problems on loading 128 KB environment */
+	end_addr = flash_sect_addr + 0x20000 - 1;
+#else
+	end_addr = flash_sect_addr + len - 1;
+#endif
+
+	debug ("Protect off %08lX ... %08lX\n",
+		(ulong)flash_sect_addr, end_addr);
+
+	if (flash_sect_protect (0, flash_sect_addr, end_addr))
+		return 1;
+
+	puts ("Erasing Flash...");
+	if (flash_sect_erase (flash_sect_addr, end_addr))
+		return 1;
+
+	/* try to re-protect */
+	(void) flash_sect_protect (1, flash_sect_addr, end_addr);
+
+	return 0;
+}
+
 #endif /* CMD_SAVEENV */
 
 #endif /* CFG_ENV_ADDR_REDUND */

===================================================================
--- u-boot-1.2.0/common/env_nand.c	(revision 2338)
+++ u-boot-1.2.0/common/env_nand.c	(revision 4586)
@@ -39,6 +39,10 @@
 #include <malloc.h>
 #include <nand.h>
 
+#if defined (CONFIG_STB225)
+extern int stb225_secure_boot (void);
+#endif
+
 #if ((CONFIG_COMMANDS&(CFG_CMD_ENV|CFG_CMD_NAND)) == (CFG_CMD_ENV|CFG_CMD_NAND))
 #define CMD_SAVEENV
 #elif defined(CFG_ENV_OFFSET_REDUND)
@@ -64,6 +68,9 @@
 extern uchar default_environment[];
 extern int default_environment_size;
 
+extern uchar secure_environment[];
+extern int secure_environment_size;
+
 char * env_name_spec = "NAND";
 
 
@@ -77,7 +84,8 @@
 
 /* local functions */
 #if !defined(ENV_IS_EMBEDDED)
-static void use_default(void);
+static void use_secure (void);
+static void use_default (void);
 #endif
 
 DECLARE_GLOBAL_DATA_PTR;
@@ -185,25 +193,79 @@
 	gd->env_valid = (gd->env_valid == 2 ? 1 : 2);
 	return ret;
 }
+
+int clearenv(void)
+{
+#error "FIXME: clearenv command not yet supported with CFG_ENV_ADDR_REDUND"
+
+	printf ("\nError: clearenv command not yet supported with CFG_ENV_ADDR_REDUND\n\n");
+	return 1;
+}
+
 #else /* ! CFG_ENV_OFFSET_REDUND */
+
 int saveenv(void)
 {
-	ulong total;
-	int ret = 0;
+	nand_erase_options_t e_opts;
+	nand_write_options_t w_opts;
 
-	puts ("Erasing Nand...");
-	if (nand_erase(&nand_info[0], CFG_ENV_OFFSET, CFG_ENV_SIZE))
+#if defined (CONFIG_STB225)
+	if (stb225_secure_boot())
+		return 0;
+#endif
+
+	memset(&e_opts, 0, sizeof(e_opts));
+	e_opts.offset = CFG_ENV_OFFSET;
+	e_opts.length = CFG_ENV_SIZE;		/* CFG_ENV_SIZE : size of entire Env partition */
+	e_opts.jffs2 = 1;
+	e_opts.quiet = 1;
+
+	printf ("Erasing Nand (%d bytes)...\n", e_opts.length);
+
+	if (nand_erase_opts(&nand_info[0], &e_opts))
 		return 1;
 
-	puts ("Writing to Nand... ");
-	total = CFG_ENV_SIZE;
-	ret = nand_write(&nand_info[0], CFG_ENV_OFFSET, &total, (u_char*)env_ptr);
-	if (ret || total != CFG_ENV_SIZE)
+	memset(&w_opts, 0, sizeof(w_opts));
+	w_opts.buffer = (u_char*) env_ptr;
+	w_opts.length = sizeof (env_t); 	/* size of environment structure... maybe much smaller than Env partition */
+	w_opts.offset = CFG_ENV_OFFSET;
+	w_opts.pad = 1;
+	w_opts.blockalign = 1;
+	w_opts.quiet = 0;
+
+	printf ("Writing to Nand (%d bytes)...", w_opts.length);
+
+	if (nand_write_opts(&nand_info[0], &w_opts))
 		return 1;
 
 	puts ("done\n");
-	return ret;
+	return 0;
 }
+
+int clearenv(void)
+{
+	nand_erase_options_t e_opts;
+
+#if defined (CONFIG_STB225)
+	if (stb225_secure_boot())
+		return 0;
+#endif
+
+	memset(&e_opts, 0, sizeof(e_opts));
+	e_opts.offset = CFG_ENV_OFFSET;
+	e_opts.length = CFG_ENV_SIZE;		/* CFG_ENV_SIZE : size of entire Env partition */
+	e_opts.jffs2 = 1;
+	e_opts.quiet = 1;
+
+	printf ("Erasing Nand (%d bytes)...", e_opts.length);
+
+	if (nand_erase_opts(&nand_info[0], &e_opts))
+		return 1;
+
+	puts (" done\n");
+	return 0;
+}
+
 #endif /* CFG_ENV_OFFSET_REDUND */
 #endif /* CMD_SAVEENV */
 
@@ -215,15 +277,18 @@
 	int crc1_ok = 0, crc2_ok = 0;
 	env_t *tmp_env1, *tmp_env2;
 
+#if defined (CONFIG_STB225)
+	if (stb225_secure_boot())
+		return use_secure();
+#endif
+
 	total = CFG_ENV_SIZE;
 
-	tmp_env1 = (env_t *) malloc(CFG_ENV_SIZE);
-	tmp_env2 = (env_t *) malloc(CFG_ENV_SIZE);
+	tmp_env1 = (env_t *) malloc(sizeof (env_t));
+	tmp_env2 = (env_t *) malloc(sizeof (env_t));
 
-	nand_read(&nand_info[0], CFG_ENV_OFFSET, &total,
-		  (u_char*) tmp_env1);
-	nand_read(&nand_info[0], CFG_ENV_OFFSET_REDUND, &total,
-		  (u_char*) tmp_env2);
+	nand_read(&nand_info[0], CFG_ENV_OFFSET, &total, (u_char*) tmp_env1);
+	nand_read(&nand_info[0], CFG_ENV_OFFSET_REDUND, &total, (u_char*) tmp_env2);
 
 	crc1_ok = (crc32(0, tmp_env1->data, ENV_SIZE) == tmp_env1->crc);
 	crc2_ok = (crc32(0, tmp_env2->data, ENV_SIZE) == tmp_env2->crc);
@@ -246,10 +311,14 @@
 			gd->env_valid = 2;
 		else /* flags are equal - almost impossible */
 			gd->env_valid = 1;
-
 	}
 
+	/*
+	   If ! ENV_IS_EMBEDDED, env_ptr was malloced in env_relocate().
+	   Free it here and then change env_ptr to point to one of the locally malloced buffers.
+	*/
 	free(env_ptr);
+
 	if(gd->env_valid == 1) {
 		env_ptr = tmp_env1;
 		free(tmp_env2);
@@ -260,7 +329,9 @@
 
 #endif /* ! ENV_IS_EMBEDDED */
 }
+
 #else /* ! CFG_ENV_OFFSET_REDUND */
+
 /*
  * The legacy NAND code saved the environment in the first NAND device i.e.,
  * nand_dev_desc + 0. This is also the behaviour using the new NAND code.
@@ -268,38 +339,157 @@
 void env_relocate_spec (void)
 {
 #if !defined(ENV_IS_EMBEDDED)
-	ulong total;
+	int i;
 	int ret;
+	int erased;
+	int erased_check_size;
+	nand_read_options_t r_opts;
+	unsigned long crc;
 
-	total = CFG_ENV_SIZE;
-	ret = nand_read(&nand_info[0], CFG_ENV_OFFSET, &total, (u_char*)env_ptr);
-  	if (ret || total != CFG_ENV_SIZE)
-		return use_default();
+#if defined (CONFIG_STB225)
+	if (stb225_secure_boot()) {
+		use_secure();
+		return;
+	}
+#endif
 
-	if (crc32(0, env_ptr->data, ENV_SIZE) != env_ptr->crc)
-		return use_default();
+	memset(&r_opts, 0, sizeof(r_opts));
+	r_opts.buffer = (u_char*)env_ptr;
+	r_opts.length = sizeof (env_t); 	/* size of environment structure... maybe much smaller than Env partition */
+	r_opts.offset = CFG_ENV_OFFSET;
+	r_opts.quiet = 1;
+
+	ret = nand_read_opts(&nand_info[0], &r_opts);
+	if (ret || r_opts.length != sizeof (env_t)) {
+		/*
+		   Unable to read from NAND... use default environment
+		*/
+		printf ("\nEnv: Warning: %s\n\n", "Error reading from NAND");
+		use_default();
+		return;
+	}
+
+	erased = 1;
+	erased_check_size = 128;
+	if (erased_check_size > sizeof (env_t))
+		erased_check_size = sizeof (env_t);
+
+	for (i = 0; i < erased_check_size; i++) {
+		if (((unsigned char *)env_ptr)[i] == 0xFF)
+			continue;
+		erased = 0;
+		break;
+	}
+
+	if (erased) {
+		/*
+		   Env partition is empty... use default environment
+		*/
+		use_default();
+		return;
+	}
+
+	crc = crc32 (0, env_ptr->data, ENV_SIZE);
+
+	if (crc == env_ptr->crc) {
+		/*
+		   CRC check for env_ptr->data passed... env loaded from NAND is OK.
+		*/
+		return;
+	}
+
+	/*
+	   CRC check for env_ptr->data failed...
+
+	   If CFG_ENV_ACTIVE_SIZE is defined and less than CFG_ENV_SIZE, it's
+	   possible that the Env partition in NAND was written with by an older
+	   version of u-boot (without CFG_ENV_ACTIVE_SIZE support). To catch this,
+	   check the CRC against one re-calculated based on CFG_ENV_SIZE.
+	*/
+
+#if defined (CFG_ENV_ACTIVE_SIZE) && (CFG_ENV_ACTIVE_SIZE < CFG_ENV_SIZE)
+
+	i = CFG_ENV_SIZE - CFG_ENV_ACTIVE_SIZE;
+
+	while (i) {
+		static const unsigned char zeros[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
+		unsigned int chunksize = (i >= sizeof(zeros)) ? sizeof(zeros) : 1;
+		crc = crc32 (crc, zeros, chunksize);
+		i -= chunksize;
+	}
+
+	if (crc == env_ptr->crc) {
+		/*
+		   CRC check for env_ptr->data passed... env loaded from NAND is OK, but crc needs to be updated.
+		*/
+		printf ("\nEnv: Warning: %s\n\n", "Legacy CRC of entire partition... use 'saveenv' to fix");
+		crc = crc32 (0, env_ptr->data, ENV_SIZE);
+		env_ptr->crc = crc;
+		return;
+	}
+
+#endif
+
+	/*
+	   NAND is readable, not empty, but CRC check fails... use default environment
+	*/
+	printf ("\nEnv: Warning: %s\n\n", "Env CRC check failed...");
+	use_default();
+
 #endif /* ! ENV_IS_EMBEDDED */
 }
 #endif /* CFG_ENV_OFFSET_REDUND */
 
 #if !defined(ENV_IS_EMBEDDED)
+
+#if defined (CONFIG_STB225)
+static void use_secure (void)
+{
+#if defined (CONFIG_DEFAULT_ENV_IS_SECURE)
+	unsigned char *sec_env_ptr = default_environment;
+	unsigned int sec_env_size = default_environment_size;
+	char *sec_env_type = "default";
+#else
+	unsigned char *sec_env_ptr = secure_environment;
+	unsigned int sec_env_size = secure_environment_size;
+	char *sec_env_type = "secure";
+#endif
+
+	if (sec_env_size > ENV_SIZE){
+		/* Fixme: this should be fatal... env not initialised on return */
+		printf ("*** Error - %s environment is too large\n\n", sec_env_type);
+		return;
+	}
+
+	printf ("Env: %s\n", sec_env_type);
+
+	memset (env_ptr, 0, sizeof(env_t) - ENV_SIZE);
+	memcpy (env_ptr->data, sec_env_ptr, sec_env_size);
+	memset (env_ptr->data + sec_env_size, 0, ENV_SIZE - sec_env_size);
+
+	env_ptr->crc = crc32(0, env_ptr->data, ENV_SIZE);
+	gd->env_valid = 1;
+}
+#endif
+
 static void use_default()
 {
-	puts ("*** Warning - bad CRC or NAND, using default environment\n\n");
+	puts ("Using default environment\n\n");
 
-	if (default_environment_size > CFG_ENV_SIZE){
+	if (default_environment_size > ENV_SIZE){
+		/* Fixme: this should be fatal... env not initialised on return */
 		puts ("*** Error - default environment is too large\n\n");
 		return;
 	}
 
-	memset (env_ptr, 0, sizeof(env_t));
-	memcpy (env_ptr->data,
-			default_environment,
-			default_environment_size);
+	memset (env_ptr, 0, sizeof(env_t) - ENV_SIZE);
+	memcpy (env_ptr->data, default_environment, default_environment_size);
+	memset (env_ptr->data + default_environment_size, 0, ENV_SIZE - default_environment_size);
+
 	env_ptr->crc = crc32(0, env_ptr->data, ENV_SIZE);
 	gd->env_valid = 1;
-
 }
 #endif
 
 #endif /* CFG_ENV_IS_IN_NAND */
+

===================================================================
--- u-boot-1.2.0/common/env_nvram.c	(revision 2338)
+++ u-boot-1.2.0/common/env_nvram.c	(revision 4586)
@@ -101,9 +101,9 @@
 void env_relocate_spec (void)
 {
 #if defined(CFG_NVRAM_ACCESS_ROUTINE)
-	nvram_read(env_ptr, CFG_ENV_ADDR, CFG_ENV_SIZE);
+	nvram_read(env_ptr, CFG_ENV_ADDR, sizeof (env_t));
 #else
-	memcpy (env_ptr, (void*)CFG_ENV_ADDR, CFG_ENV_SIZE);
+	memcpy (env_ptr, (void*)CFG_ENV_ADDR, sizeof (env_t));
 #endif
 }
 
@@ -114,9 +114,9 @@
 	enable_nvram();
 #endif
 #ifdef CFG_NVRAM_ACCESS_ROUTINE
-	nvram_write(CFG_ENV_ADDR, env_ptr, CFG_ENV_SIZE);
+	nvram_write(CFG_ENV_ADDR, env_ptr, sizeof (env_t));
 #else
-	if (memcpy ((char *)CFG_ENV_ADDR, env_ptr, CFG_ENV_SIZE) == NULL)
+	if (memcpy ((char *)CFG_ENV_ADDR, env_ptr, sizeof (env_t)) == NULL)
 		    rcode = 1 ;
 #endif
 #ifdef CONFIG_AMIGAONEG3SE

===================================================================
--- u-boot-1.2.0/common/environment.c	(revision 2338)
+++ u-boot-1.2.0/common/environment.c	(revision 4503)
@@ -45,6 +45,9 @@
  * inside U-Boot image, if needed.
  */
 #if defined(ENV_IS_EMBEDDED)
+
+#error "Doesn't work for STB225... multiple issues"
+
 /*
  * Only put the environment in it's own section when we are building
  * U-Boot proper.  The host based program "tools/envcrc" does not need
@@ -204,7 +207,14 @@
  * .data/.sdata section.
  *
  */
+
+#ifdef CONFIG_SOC_PNX833X
+/* For strange reason this gets to the object file before environment ...
+   See no reason to put it into .text anyway */
+unsigned long env_size = sizeof(env_t);
+#else
 unsigned long env_size __PPCTEXT__ = sizeof(env_t);
+#endif
 
 /*
  * Add in absolutes.

===================================================================
--- u-boot-1.2.0/common/main.c	(revision 2338)
+++ u-boot-1.2.0/common/main.c	(revision 2339)
@@ -44,6 +44,10 @@
 DECLARE_GLOBAL_DATA_PTR;
 #endif
 
+#if defined (CONFIG_STB225)
+extern int stb225_secure_boot (void);
+#endif
+
 #if defined(CONFIG_BOOT_RETRY_TIME) && defined(CONFIG_RESET_TO_RETRY)
 extern int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);		/* for do_reset() prototype */
 #endif
@@ -233,7 +237,8 @@
 #ifdef CONFIG_MENUPROMPT
 	printf(CONFIG_MENUPROMPT, bootdelay);
 #else
-	printf("Hit any key to stop autoboot: %2d ", bootdelay);
+	if (bootdelay > 0)
+		printf ("Hit any key to stop autoboot: %2d ", bootdelay);
 #endif
 
 #if defined CONFIG_ZERO_BOOTDELAY_CHECK
@@ -386,6 +391,11 @@
 	s = getenv ("bootdelay");
 	bootdelay = s ? (int)simple_strtol(s, NULL, 10) : CONFIG_BOOTDELAY;
 
+#if defined (CONFIG_STB225)
+	if (stb225_secure_boot())
+		bootdelay = 0;
+#endif
+
 	debug ("### main_loop entered: bootdelay=%d\n\n", bootdelay);
 
 # ifdef CONFIG_BOOT_RETRY_TIME

===================================================================
--- u-boot-1.2.0/config.mk	(revision 2338)
+++ u-boot-1.2.0/config.mk	(revision 3694)
@@ -159,10 +159,10 @@
 	-isystem $(gccincdir) -pipe $(PLATFORM_CPPFLAGS)
 
 ifdef BUILD_TAG
-CFLAGS := $(CPPFLAGS) -Wall -Wstrict-prototypes \
+CFLAGS := $(CPPFLAGS) -Wall -Werror -Wstrict-prototypes \
 	-DBUILD_TAG='"$(BUILD_TAG)"'
 else
-CFLAGS := $(CPPFLAGS) -Wall -Wstrict-prototypes
+CFLAGS := $(CPPFLAGS) -Wall -Werror -Wstrict-prototypes
 endif
 
 # avoid trigraph warnings while parsing pci.h (produced by NIOS gcc-2.9)
@@ -224,23 +224,33 @@
 
 #########################################################################
 
+ifneq "$(V)" "1"
+  Q=@
+endif
+
 ifndef REMOTE_BUILD
 
 %.s:	%.S
-	$(CPP) $(AFLAGS) -o $@ $<
+	@echo CPP $<
+	$(Q)$(CPP) $(AFLAGS) -o $@ $<
 %.o:	%.S
-	$(CC) $(AFLAGS) -c -o $@ $<
+	@echo ASM $<
+	$(Q)$(CC) $(AFLAGS) -c -o $@ $<
 %.o:	%.c
-	$(CC) $(CFLAGS) -c -o $@ $<
+	@echo CC $<
+	$(Q)$(CC) $(CFLAGS) -c -o $@ $<
 
 else
 
 $(obj)%.s:	%.S
-	$(CPP) $(AFLAGS) -o $@ $<
+	@echo CPP $<
+	$(Q)$(CPP) $(AFLAGS) -o $@ $<
 $(obj)%.o:	%.S
-	$(CC) $(AFLAGS) -c -o $@ $<
+	@echo ASM $<
+	$(Q)$(CC) $(AFLAGS) -c -o $@ $<
 $(obj)%.o:	%.c
-	$(CC) $(CFLAGS) -c -o $@ $<
+	@echo CC $<
+	$(Q)$(CC) $(CFLAGS) -c -o $@ $<
 endif
 
 #########################################################################

===================================================================
--- u-boot-1.2.0/cpu/mips/cpu.c	(revision 2338)
+++ u-boot-1.2.0/cpu/mips/cpu.c	(revision 2339)
@@ -52,3 +52,11 @@
 	write_32bit_cp0_register(CP0_INDEX, index);
 	tlb_write_indexed();
 }
+
+unsigned int k1_get (void)
+{
+	unsigned int k1;
+	asm volatile ("move %0, $27" : "=r" (k1) :);
+	return k1;
+}
+

===================================================================
--- u-boot-1.2.0/drivers/Makefile	(revision 2338)
+++ u-boot-1.2.0/drivers/Makefile	(revision 2339)
@@ -32,7 +32,7 @@
 	  cs8900.o ct69000.o dataflash.o dc2114x.o dm9000x.o \
 	  e1000.o eepro100.o \
 	  i8042.o inca-ip_sw.o keyboard.o \
-	  lan91c96.o \
+	  lan91c96.o 911x.o ip3902.o \
 	  natsemi.o ne2000.o netarm_eth.o netconsole.o \
 	  ns16550.o ns8382x.o ns87308.o ns7520_eth.o omap1510_i2c.o \
 	  omap24xx_i2c.o pci.o pci_auto.o pci_indirect.o \

===================================================================
--- u-boot-1.2.0/drivers/cfb_console.c	(revision 2338)
+++ u-boot-1.2.0/drivers/cfb_console.c	(revision 4586)
@@ -726,10 +726,20 @@
 	fb += 2;					\
 }
 
+#if defined (CONSOLE_X888RGB_INIT_ALPHA_FF)
+/*
+   Alpha byte typically initialised to 0, but sometimes setting 0xFF is prefered...
+*/
 #define FILL_32BIT_X888RGB(r,g,b) {			\
+	*(unsigned long *)fb = SWAP32((unsigned long)(((0xFF<<24) | (r<<16) | (g<<8) | b))); \
+	fb += 4;					\
+}
+#else
+#define FILL_32BIT_X888RGB(r,g,b) {			\
 	*(unsigned long *)fb = SWAP32((unsigned long)(((r<<16) | (g<<8) | b))); \
 	fb += 4;					\
 }
+#endif
 
 #ifdef VIDEO_FB_LITTLE_ENDIAN
 #define FILL_24BIT_888RGB(r,g,b) {			\
@@ -776,8 +786,16 @@
 #ifdef CONFIG_VIDEO_BMP_GZIP
 		/*
 		 * Could be a gzipped bmp image, try to decrompress...
+		 *
+		 * Fixme: Setting "len = CFG_VIDEO_LOGO_MAX_SIZE" below is a bug.
+		 *        The value of len should be set to the amount of gzipped data
+		 *        available... NOT the size of the output buffer. It's probably
+		 *        safe in most cases though (and not easy to fix without
+		 *        changing the video_display_bitmap() API).
 		 */
+
 		len = CFG_VIDEO_LOGO_MAX_SIZE;
+
 		dst = malloc(CFG_VIDEO_LOGO_MAX_SIZE);
 		if (dst == NULL) {
 			printf("Error: malloc in gunzip failed!\n");
@@ -814,8 +832,12 @@
 	colors = le32_to_cpu (bmp->header.colors_used);
 	compression = le32_to_cpu (bmp->header.compression);
 
+#if defined (CONFIG_STB225) && (CONFIG_STB225 == 1)
+	printf ("Splash BMP: %dx%d, %d bpp\n", width, height, bpp);
+#else
 	debug ("Display-bmp: %d x %d  with %d colors\n",
 	       width, height, colors);
+#endif
 
 	if (compression != BMP_BI_RGB) {
 		printf ("Error: compression type %ld not supported\n",
@@ -899,6 +921,26 @@
 			while (ycount--) {
 				WATCHDOG_RESET ();
 				xcount = width;
+				while (xcount >= 8) {
+					cte = bmp->color_table[bmap[0]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[1]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[2]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[3]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[4]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[5]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[6]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					cte = bmp->color_table[bmap[7]];
+					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
+					bmap += 8;
+					xcount -= 8;
+				}
 				while (xcount--) {
 					cte = bmp->color_table[*bmap++];
 					FILL_32BIT_X888RGB (cte.red, cte.green, cte.blue);
@@ -965,6 +1007,18 @@
 			while (ycount--) {
 				WATCHDOG_RESET ();
 				xcount = width;
+				while (xcount >= 8) {
+					FILL_32BIT_X888RGB (bmap[ 2], bmap[ 1], bmap[ 0]);
+					FILL_32BIT_X888RGB (bmap[ 5], bmap[ 4], bmap[ 3]);
+					FILL_32BIT_X888RGB (bmap[ 8], bmap[ 7], bmap[ 6]);
+					FILL_32BIT_X888RGB (bmap[11], bmap[10], bmap[ 9]);
+					FILL_32BIT_X888RGB (bmap[14], bmap[13], bmap[12]);
+					FILL_32BIT_X888RGB (bmap[17], bmap[16], bmap[15]);
+					FILL_32BIT_X888RGB (bmap[20], bmap[19], bmap[18]);
+					FILL_32BIT_X888RGB (bmap[23], bmap[22], bmap[21]);
+					bmap += (8 * 3);
+					xcount -= 8;
+				}
 				while (xcount--) {
 					FILL_32BIT_X888RGB (bmap[2], bmap[1], bmap[0]);
 					bmap += 3;
@@ -1232,6 +1286,16 @@
 	if (video_init () == -1)
 		skip_dev_init = 1;
 
+	/*
+	   For stb225, we don't actually want to register a framebuffer
+	   console (we use drv_video_init() only to setup the framebuffer
+	   and video output).
+	   To avoid registering a console, STB225v1.h does not define
+	   CONFIG_VGA_AS_SINGLE_DEVICE and sets VIDEO_KBD_INIT_FCT to -1
+	   therefore code below will behave as if the keyboard init function
+	   has failed... ugly, but functional...
+	*/
+
 #ifdef CONFIG_VGA_AS_SINGLE_DEVICE
 	/* Devices VGA and Keyboard will be assigned seperately */
 	/* Init vga device */

===================================================================
--- u-boot-1.2.0/drivers/cfi_flash.c	(revision 2338)
+++ u-boot-1.2.0/drivers/cfi_flash.c	(revision 2763)
@@ -256,13 +256,26 @@
 	uchar *cp;
 
 	cp = flash_make_addr (info, 0, offset);
-#if defined(__LITTLE_ENDIAN)
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
 	return (cp[0]);
 #else
 	return (cp[info->portwidth - 1]);
 #endif
 }
 
+/* Extended mode for 8/16 flash */
+inline uchar flash_read_ucharx (flash_info_t * info, uint offset, int s)
+{
+	uchar *cp;
+
+	cp = flash_make_addr (info, 0, offset * s);
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
+	return (cp[0]);
+#else
+	return (cp[info->portwidth - 1]);
+#endif
+}
+
 /*-----------------------------------------------------------------------
  * read a short word by swapping for ppc format.
  */
@@ -283,7 +296,7 @@
 		debug ("addr[%x] = 0x%x\n", x, addr[x]);
 	}
 #endif
-#if defined(__LITTLE_ENDIAN)
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
 	retval = ((addr[(info->portwidth)] << 8) | addr[0]);
 #else
 	retval = ((addr[(2 * info->portwidth) - 1] << 8) |
@@ -294,6 +307,34 @@
 	return retval;
 }
 
+ushort flash_read_ushortx (flash_info_t * info, flash_sect_t sect, uint offset, int s)
+{
+	uchar *addr;
+	ushort retval;
+
+#ifdef DEBUG
+	int x;
+#endif
+	addr = flash_make_addr (info, sect, offset * s);
+
+#ifdef DEBUG
+	debug ("ushort addr is at %p info->portwidth = %d\n", addr,
+	       info->portwidth);
+	for (x = 0; x < 2 * info->portwidth; x += s) {
+		debug ("addr[%x] = 0x%x\n", x, addr[x]);
+	}
+#endif
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
+	retval = ((addr[(info->portwidth) * s ] << 8) | addr[0]);
+#else
+	retval = ((addr[( (2 * info->portwidth) - 1) * s ] << 8) |
+		  addr[( info->portwidth - 1) * s ]);
+#endif
+
+	debug ("retval = 0x%x\n", retval);
+	return retval;
+}
+
 /*-----------------------------------------------------------------------
  * read a long word by picking the least significant byte of each maximum
  * port size word. Swap for ppc format.
@@ -315,7 +356,7 @@
 		debug ("addr[%x] = 0x%x\n", x, addr[x]);
 	}
 #endif
-#if defined(__LITTLE_ENDIAN)
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
 	retval = (addr[0] << 16) | (addr[(info->portwidth)] << 24) |
 		(addr[(2 * info->portwidth)]) | (addr[(3 * info->portwidth)] << 8);
 #else
@@ -419,6 +460,35 @@
 	return (size);
 }
 
+ulong flash_read_longx (flash_info_t * info, flash_sect_t sect, uint offset, int s)
+{
+	uchar *addr;
+	ulong retval;
+
+#ifdef DEBUG
+	int x;
+#endif
+	addr = flash_make_addr (info, sect, offset * s);
+
+#ifdef DEBUG
+	debug ("long addr is at %p info->portwidth = %d\n", addr,
+	       info->portwidth);
+	for (x = 0; x < 4 * info->portwidth; x += s) {
+		debug ("addr[%x] = 0x%x\n", x, addr[x]);
+	}
+#endif
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
+	retval = (addr[0] << 16) | (addr[(s * info->portwidth)] << 24) |
+		(addr[s * (2 * info->portwidth)]) | (addr[s * (3 * info->portwidth)] << 8);
+#else
+	retval = (addr[((2 * info->portwidth) - 1) * s] << 24) |
+		(addr[((info->portwidth) - 1) * s] << 16) |
+		(addr[((4 * info->portwidth) - 1) * s] << 8) |
+		addr[((3 * info->portwidth) - 1) * s];
+#endif
+	return retval;
+}
+
 /*-----------------------------------------------------------------------
  */
 #if defined(CFG_ENV_IS_IN_FLASH) || defined(CFG_ENV_ADDR_REDUND) || (CFG_MONITOR_BASE >= CFG_FLASH_BASE)
@@ -792,7 +862,9 @@
 {
 	ulong start;
 
-#if CFG_HZ != 1000
+#if defined(CFG_MS_HZ)
+	tout *= CFG_MS_HZ;
+#elif CFG_HZ != 1000
 	tout *= CFG_HZ/1000;
 #endif
 
@@ -905,12 +977,17 @@
 	int i;
 	uchar *cp = (uchar *) cmdbuf;
 
-#if defined(__LITTLE_ENDIAN)
+	debug ( "FMC=> Port=%d Chip=%d", info->portwidth, info->chipwidth ) ;
+#if defined(__LITTLE_ENDIAN) || defined(CONFIG_STB225)
 	for (i = info->portwidth; i > 0; i--)
 #else
 	for (i = 1; i <= info->portwidth; i++)
 #endif
+	  {
 		*cp++ = (i & (info->chipwidth - 1)) ? '\0' : cmd;
+		debug ( " %02X", * ( cp - 1 ) ) ;
+	  }
+	debug ( "\n" ) ;
 }
 
 /*
@@ -1147,6 +1224,7 @@
 		for (info->chipwidth = FLASH_CFI_BY8;
 		     info->chipwidth <= info->portwidth;
 		     info->chipwidth <<= 1) {
+		        debug ( "Try port=%d chip=%d\n", info->portwidth, info->chipwidth ) ;
 			flash_write_cmd (info, 0, 0, info->cmd_reset);
 			for (cfi_offset=0; cfi_offset < sizeof(flash_offset_cfi)/sizeof(uint); cfi_offset++) {
 				flash_write_cmd (info, 0, flash_offset_cfi[cfi_offset], FLASH_CMD_CFI);
@@ -1163,6 +1241,19 @@
 						info->portwidth << CFI_FLASH_SHIFT_WIDTH,
 						info->chipwidth << CFI_FLASH_SHIFT_WIDTH);
 					return 1;
+				} else if (flash_isequal (info, 0, 2 * ( FLASH_OFFSET_CFI_RESP ), 'Q')
+					&& flash_isequal (info, 0, 2 * ( FLASH_OFFSET_CFI_RESP + 1 ), 'R')
+					&& flash_isequal (info, 0, 2 * ( FLASH_OFFSET_CFI_RESP + 2 ), 'Y')) {
+					/* RB, Liberte software 2006-02-28. Deal with devices that identify in 16 bit mode but work in 8 bit */
+						info->interface = 0 ;
+						debug ("device interface is %d\n",
+							info->interface);
+						debug ("found port %d chip %d ",
+							info->portwidth, info->chipwidth);
+						debug ("port %d bits chip %d bits\n",
+							info->portwidth << CFI_FLASH_SHIFT_WIDTH,
+							info->chipwidth << CFI_FLASH_SHIFT_WIDTH);
+					return 2;
 				}
 			}
 		}
@@ -1171,9 +1262,14 @@
 	return 0;
 }
 
+#if defined (CONFIG_STB225)
+extern int stb225_bootmode (void);
+#endif
+
 /*
  * The following code cannot be run from FLASH!
  *
+ * @note Do we need to change ALL flash_read_<type>(...) to flash_read_<type>x(..., cfi_type) ?
  */
 ulong flash_get_size (ulong base, int banknum)
 {
@@ -1187,6 +1283,7 @@
 	int erase_region_size;
 	int erase_region_count;
 	int geometry_reversed = 0;
+	int cfi_type = 0;
 
 	info->ext_addr = 0;
 	info->cfi_version = 0;
@@ -1196,20 +1293,34 @@
 
 	info->start[0] = base;
 
-	if (flash_detect_cfi (info)) {
-		info->vendor = flash_read_ushort (info, 0,
-					FLASH_OFFSET_PRIMARY_VENDOR);
-		flash_read_jedec_ids (info);
+#if defined (CONFIG_STB225)
+	/* If we don't have a NOR chip attached, then flash_detect_cfi will crash */
+	/* if DEBUG is not defined */
+	/* To be safe, skip probe if we haven't booted from NOR */
+	{
+		int bootmode = stb225_bootmode();
+		if ((bootmode == BOOTMODE_NOR_8) || (bootmode == BOOTMODE_NOR_16))
+			cfi_type = flash_detect_cfi (info);
+		else
+			cfi_type = 0;
+	}
+#else
+	cfi_type = flash_detect_cfi (info);
+#endif
+
+ 	if ( cfi_type ) {
+		info->vendor = flash_read_ushortx (info, 0, FLASH_OFFSET_PRIMARY_VENDOR, cfi_type);
+ 		flash_read_jedec_ids (info);
 		flash_write_cmd (info, 0, info->cfi_offset, FLASH_CMD_CFI);
-		num_erase_regions = flash_read_uchar (info,
-					FLASH_OFFSET_NUM_ERASE_REGIONS);
-		info->ext_addr = flash_read_ushort (info, 0,
-					FLASH_OFFSET_EXT_QUERY_T_P_ADDR);
+		num_erase_regions = flash_read_ucharx (info,
+					FLASH_OFFSET_NUM_ERASE_REGIONS, cfi_type);
+		info->ext_addr = flash_read_ushortx (info, 0,
+					FLASH_OFFSET_EXT_QUERY_T_P_ADDR, cfi_type);
 		if (info->ext_addr) {
-			info->cfi_version = (ushort) flash_read_uchar (info,
-						info->ext_addr + 3) << 8;
-			info->cfi_version |= (ushort) flash_read_uchar (info,
-						info->ext_addr + 4);
+			info->cfi_version = (ushort) flash_read_ucharx (info,
+						info->ext_addr + 3, cfi_type) << 8;
+			info->cfi_version |= (ushort) flash_read_ucharx (info,
+						info->ext_addr + 4, cfi_type);
 		}
 #ifdef DEBUG
 		flash_printqry (info, 0);
@@ -1222,8 +1333,8 @@
 #ifdef CFG_FLASH_PROTECTION
 			/* read legacy lock/unlock bit from intel flash */
 			if (info->ext_addr) {
-				info->legacy_unlock = flash_read_uchar (info,
-						info->ext_addr + 5) & 0x08;
+				info->legacy_unlock = flash_read_ucharx (info,
+						info->ext_addr + 5, cfi_type) & 0x08;
 			}
 #endif
 			break;
@@ -1243,7 +1354,7 @@
 			}
 			/* CFI >= 1.1, deduct from top/bottom flag */
 			/* note: ext_addr is valid since cfi_version > 0 */
-			if (flash_read_uchar(info, info->ext_addr + 0xf) == 3) {
+			if (flash_read_ucharx(info, info->ext_addr + 0xf, cfi_type) == 3) {
 				geometry_reversed = 1;
 			}
 			break;
@@ -1274,13 +1385,13 @@
 				break;
 			}
 			if (geometry_reversed)
-				tmp = flash_read_long (info, 0,
+				tmp = flash_read_longx (info, 0,
 					       FLASH_OFFSET_ERASE_REGIONS +
-					       (num_erase_regions - 1 - i) * 4);
+					       (num_erase_regions - 1 - i) * 4, cfi_type);
 			else
-				tmp = flash_read_long (info, 0,
+				tmp = flash_read_longx (info, 0,
 					       FLASH_OFFSET_ERASE_REGIONS +
-					       i * 4);
+					       i * 4, cfi_type);
 			erase_region_size =
 				(tmp & 0xffff) ? ((tmp & 0xffff) * 256) : 128;
 			tmp >>= 16;
@@ -1288,6 +1399,10 @@
 			debug ("erase_region_count = %d erase_region_size = %d\n",
 				erase_region_count, erase_region_size);
 			for (j = 0; j < erase_region_count; j++) {
+				if (sect_cnt >= CFG_MAX_FLASH_SECT) {
+					printf("Aborting flash configuration: CFG_MAX_FLASH_SECT is too low!\n");
+					return 0;
+				}
 				info->start[sect_cnt] = sector;
 				sector += (erase_region_size * size_ratio);
 
@@ -1312,15 +1427,15 @@
 
 		info->sector_count = sect_cnt;
 		/* multiply the size by the number of chips */
-		info->size = (1 << flash_read_uchar (info, FLASH_OFFSET_SIZE)) * size_ratio;
-		info->buffer_size = (1 << flash_read_ushort (info, 0, FLASH_OFFSET_BUFFER_SIZE));
-		tmp = 1 << flash_read_uchar (info, FLASH_OFFSET_ETOUT);
-		info->erase_blk_tout = (tmp * (1 << flash_read_uchar (info, FLASH_OFFSET_EMAX_TOUT)));
-		tmp = (1 << flash_read_uchar (info, FLASH_OFFSET_WBTOUT)) *
-			(1 << flash_read_uchar (info, FLASH_OFFSET_WBMAX_TOUT));
+		info->size = (1 << flash_read_ucharx (info, FLASH_OFFSET_SIZE, cfi_type)) * size_ratio;
+		info->buffer_size = (1 << flash_read_ushortx (info, 0, FLASH_OFFSET_BUFFER_SIZE, cfi_type));
+		tmp = 1 << flash_read_ucharx (info, FLASH_OFFSET_ETOUT, cfi_type);
+		info->erase_blk_tout = (tmp * (1 << flash_read_ucharx (info, FLASH_OFFSET_EMAX_TOUT, cfi_type)));
+		tmp = (1 << flash_read_ucharx (info, FLASH_OFFSET_WBTOUT, cfi_type)) *
+			(1 << flash_read_ucharx (info, FLASH_OFFSET_WBMAX_TOUT, cfi_type));
 		info->buffer_write_tout = tmp / 1000 + (tmp % 1000 ? 1 : 0); /* round up when converting to ms */
-		tmp = (1 << flash_read_uchar (info, FLASH_OFFSET_WTOUT)) *
-		      (1 << flash_read_uchar (info, FLASH_OFFSET_WMAX_TOUT));
+		tmp = (1 << flash_read_ucharx (info, FLASH_OFFSET_WTOUT, cfi_type)) *
+		      (1 << flash_read_ucharx (info, FLASH_OFFSET_WMAX_TOUT, cfi_type));
 		info->write_tout = tmp / 1000 + (tmp % 1000 ? 1 : 0); /* round up when converting to ms */
 		info->flash_id = FLASH_MAN_CFI;
 		if ((info->interface == FLASH_CFI_X8X16) && (info->chipwidth == FLASH_CFI_BY8)) {
@@ -1426,6 +1541,8 @@
 {
 	flash_sect_t sector;
 	int cnt;
+	int confirm_command;
+	int clear_status = 0;
 	int retcode;
 	volatile cfiptr_t src;
 	volatile cfiptr_t dst;
@@ -1436,6 +1553,9 @@
 		src.cp = cp;
 		dst.cp = (uchar *) dest;
 		sector = find_sector (info, dest);
+		confirm_command = FLASH_CMD_WRITE_BUFFER_CONFIRM;
+		clear_status = 1;
+
 		flash_write_cmd (info, sector, 0, FLASH_CMD_CLEAR_STATUS);
 		flash_write_cmd (info, sector, 0, FLASH_CMD_WRITE_TO_BUFFER);
 		if ((retcode = flash_status_check (info, sector, info->buffer_write_tout,
@@ -1478,19 +1598,15 @@
 					break;
 				}
 			}
-			flash_write_cmd (info, sector, 0,
-					 FLASH_CMD_WRITE_BUFFER_CONFIRM);
-			retcode = flash_full_status_check (info, sector,
-							   info->buffer_write_tout,
-							   "buffer write");
 		}
-		return retcode;
+		break;
 
 	case CFI_CMDSET_AMD_STANDARD:
 	case CFI_CMDSET_AMD_EXTENDED:
 		src.cp = cp;
 		dst.cp = (uchar *) dest;
 		sector = find_sector (info, dest);
+		confirm_command = AMD_CMD_WRITE_BUFFER_CONFIRM;
 
 		flash_unlock_seq(info,0);
 		flash_write_cmd (info, sector, 0, AMD_CMD_WRITE_TO_BUFFER);
@@ -1519,16 +1635,23 @@
 		default:
 			return ERR_INVAL;
 		}
+		break;
 
-		flash_write_cmd (info, sector, 0, AMD_CMD_WRITE_BUFFER_CONFIRM);
-		retcode = flash_full_status_check (info, sector, info->buffer_write_tout,
-						   "buffer write");
-		return retcode;
-
 	default:
 		debug ("Unknown Command Set\n");
 		return ERR_INVAL;
 	}
+
+	flash_write_cmd (info, sector, 0, confirm_command);
+	retcode = flash_full_status_check (info, sector, info->buffer_write_tout,
+						   "buffer write");
+
+        if (clear_status) {
+		flash_write_cmd (info, sector, 0, FLASH_CMD_CLEAR_STATUS);
+        }
+
+	return retcode;
+
 }
 #endif /* CFG_FLASH_USE_BUFFER_WRITE */
 #endif /* CFG_FLASH_CFI */

===================================================================
--- u-boot-1.2.0/drivers/dataflash.c	(revision 2338)
+++ u-boot-1.2.0/drivers/dataflash.c	(revision 2339)
@@ -20,15 +20,23 @@
 #include <common.h>
 #include <config.h>
 #ifdef CONFIG_HAS_DATAFLASH
+#if !defined( CONFIG_STB220t3 )
 #include <asm/hardware.h>
+#endif
 #include <dataflash.h>
 
 AT91S_DATAFLASH_INFO dataflash_info[CFG_MAX_DATAFLASH_BANKS];
 static AT91S_DataFlash DataFlashInst;
 
-int cs[][CFG_MAX_DATAFLASH_BANKS] = {
+int cs[CFG_MAX_DATAFLASH_BANKS][2] = {
+#if (CFG_MAX_DATAFLASH_BANKS == 2)
 	{CFG_DATAFLASH_LOGIC_ADDR_CS0, 0},	/* Logical adress, CS */
 	{CFG_DATAFLASH_LOGIC_ADDR_CS3, 3}
+#elif (CFG_MAX_DATAFLASH_BANKS == 1)
+	{CFG_DATAFLASH_LOGIC_ADDR_CS0, 0}	/* Logical adress, CS */
+#else
+#error CFG_MAX_DATAFLASH_BANKS value not supported
+#endif
 };
 
 /*define the area offsets*/

===================================================================
--- u-boot-1.2.0/drivers/nand/nand.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand.c	(revision 2339)
@@ -57,20 +57,17 @@
 		mtd->name = NULL;
 		mtd->size = 0;
 	}
-
 }
 
 void nand_init(void)
 {
 	int i;
-	unsigned int size = 0;
+
 	for (i = 0; i < CFG_MAX_NAND_DEVICE; i++) {
 		nand_init_chip(&nand_info[i], &nand_chip[i], base_address[i]);
-		size += nand_info[i].size;
 		if (nand_curr_device == -1)
 			nand_curr_device = i;
 	}
-	printf("%lu MiB\n", size / (1024 * 1024));
 
 #ifdef CFG_NAND_SELECT_DEVICE
 	/*

===================================================================
--- u-boot-1.2.0/drivers/nand/nand_base.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand_base.c	(revision 4312)
@@ -89,13 +89,6 @@
 #endif
 
 /* Define default oob placement schemes for large and small page devices */
-static struct nand_oobinfo nand_oob_8 = {
-	.useecc = MTD_NANDECC_AUTOPLACE,
-	.eccbytes = 3,
-	.eccpos = {0, 1, 2},
-	.oobfree = { {3, 2}, {6, 2} }
-};
-
 static struct nand_oobinfo nand_oob_16 = {
 	.useecc = MTD_NANDECC_AUTOPLACE,
 	.eccbytes = 6,
@@ -113,8 +106,21 @@
 	.oobfree = { {2, 38} }
 };
 
+static struct nand_oobinfo nand_oob_128 = {
+	.useecc = MTD_NANDECC_AUTOPLACE,
+	.eccbytes = 48,
+	.eccpos = {
+		 80,  81,  82,  83,  84,  85,  86,  87,
+		 88,  89,  90,  91,  92,  93,  94,  95,
+		 96,  97,  98,  99, 100, 101, 102, 103,
+		104, 105, 106, 107, 108, 109, 110, 111,
+		112, 113, 114, 115, 116, 117, 118, 119,
+		120, 121, 122, 123, 124, 125, 126, 127},
+	.oobfree = { {2, 78} }
+};
+
 /* This is used for padding purposes in nand_write_oob */
-static u_char ffchars[] = {
+static u_char ffchars[128] = {
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
@@ -123,6 +129,14 @@
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
 	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+	0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
 };
 
 /*
@@ -162,6 +176,51 @@
 
 static void nand_get_device (struct nand_chip *this, struct mtd_info *mtd, int new_state);
 
+#if defined (CONFIG_NAND_DBG_CONTROL)
+/*
+   WARNING: u-boot init code doesn't clear bss section correctly. Explicit
+            init seems to work (either by luck or by forcing variable into
+	    data section). Should really be fixed properly...
+*/
+unsigned int nand_debug_enable = 0;
+
+static char *nand_cmd_to_string (unsigned int cmd)
+{
+	switch (cmd)
+	{
+		case NAND_CMD_READ0	   : return "Read_0";
+		case NAND_CMD_READ1	   : return "Read_1";
+		case NAND_CMD_PAGEPROG	   : return "PgProg";
+		case NAND_CMD_READOOB	   : return "RdOOB ";
+		case NAND_CMD_ERASE1	   : return "Ers_1 ";
+		case NAND_CMD_STATUS	   : return "Status";
+		case NAND_CMD_STATUS_MULTI : return "Stat_M";
+		case NAND_CMD_SEQIN	   : return "SeqIn ";
+		case NAND_CMD_READID	   : return "ReadID";
+		case NAND_CMD_ERASE2	   : return "Ers_2 ";
+		case NAND_CMD_RESET	   : return "Reset ";
+		case NAND_CMD_READSTART    : return "RdStrt";
+		case NAND_CMD_CACHEDPROG   : return "CchPrg";
+
+		default			   : return "UNKNWN";
+	}
+}
+#endif
+
+static void hexdump_local (unsigned char *data, int byte_count)
+{
+	int i;
+
+	for (i = 0; i < byte_count; i++) {
+		if (i % 16 == 0)
+			printf ("\n%08x: ", (unsigned long) data);
+		if (i % 16 == 8)
+			printf ("- ");
+		printf ("%02x ", *data++);
+	}
+	printf ("\n");
+}
+
 /**
  * nand_release_device - [GENERIC] release chip
  * @mtd:	MTD device structure
@@ -427,8 +486,9 @@
 	struct nand_chip *this = mtd->priv;
 	u16 bad;
 
+	page = (int)(ofs >> this->page_shift);
+
 	if (getchip) {
-		page = (int)(ofs >> this->page_shift);
 		chipnr = (int)(ofs >> this->chip_shift);
 
 		/* Grab the lock and see if the device is available */
@@ -436,8 +496,7 @@
 
 		/* Select the NAND device */
 		this->select_chip(mtd, chipnr);
-	} else
-		page = (int) ofs;
+	}
 
 	if (this->options & NAND_BUSWIDTH_16) {
 		this->cmdfunc (mtd, NAND_CMD_READOOB, this->badblockpos & 0xFE, page & this->pagemask);
@@ -524,6 +583,43 @@
 	return nand_isbad_bbt (mtd, ofs, allowbbt);
 }
 
+#if defined (CFG_NAND_BB_REMAP)
+
+#undef NAND_CANAUTOINCR
+#define NAND_CANAUTOINCR(x) 0
+
+static unsigned short block_map[4096];
+static int apply_map = 0;
+static unsigned nand_good_cnt = 0;
+
+unsigned nand_map_block(struct mtd_info *mtd, unsigned offset)
+{
+	struct nand_chip *this = mtd->priv;
+	unsigned block = offset >> this->phys_erase_shift;
+	unsigned new_offset;
+
+	if (block < (sizeof(block_map)/sizeof(block_map[0])))
+		block = block_map[block];
+	new_offset = (block << this->phys_erase_shift) | 
+	             (offset & ((1 << this->phys_erase_shift)-1));
+/*	printf("Mapped %d -> %d\n",offset,new_offset);*/
+	return new_offset;
+}
+
+unsigned nand_map_getsize(struct mtd_info *mtd, unsigned offset, unsigned size)
+{
+	struct nand_chip *this = mtd->priv;
+	unsigned good_size = nand_good_cnt << this->phys_erase_shift;
+
+	if (offset >= good_size) return 0;
+	if ((offset + size) >= good_size) 
+		return mtd->size - nand_map_block(mtd,offset);
+
+	return nand_map_block(mtd,offset+size) - nand_map_block(mtd,offset);
+}
+
+#endif
+
 /**
  * nand_command - [DEFAULT] Send command to NAND device
  * @mtd:	MTD device structure
@@ -538,6 +634,16 @@
 {
 	register struct nand_chip *this = mtd->priv;
 
+#if defined (CFG_NAND_BB_REMAP)
+	if (page_addr >= 0 && apply_map) {
+		unsigned new_page_addr = 
+		    nand_map_block(mtd, page_addr << this->page_shift) >>
+		             this->page_shift;
+/*		printf("Mapped %d -> %d\n",page_addr,new_page_addr);*/
+		page_addr = new_page_addr;
+	}
+#endif
+
 	/* Begin command latch cycle */
 	this->hwcontrol(mtd, NAND_CTL_SETCLE);
 	/*
@@ -649,7 +755,6 @@
 		command = NAND_CMD_READ0;
 	}
 
-
 	/* Begin command latch cycle */
 	this->hwcontrol(mtd, NAND_CTL_SETCLE);
 	/* Write out the command to the device. */
@@ -679,6 +784,26 @@
 		this->hwcontrol(mtd, NAND_CTL_CLRALE);
 	}
 
+#if defined (CONFIG_NAND_DBG_CONTROL)
+	if (nand_debug_enable) {
+		printf ("%s", nand_cmd_to_string (command));
+
+		if ((page_addr == -1) && (column == -1))
+			printf ("\n");
+		else {
+			if (page_addr == -1)
+				printf (" --------");
+			else
+				printf (" %08x", page_addr << this->page_shift);
+
+			if (column == -1)
+				printf ("\n");
+			else
+				printf ("+%d\n", column);
+		}
+	}
+#endif
+
 	/*
 	 * program and erase have their own busy handlers
 	 * status and sequential in needs no delay
@@ -693,7 +818,6 @@
 	case NAND_CMD_STATUS:
 		return;
 
-
 	case NAND_CMD_RESET:
 		if (this->dev_ready)
 			break;
@@ -835,22 +959,26 @@
 #else
 static int nand_wait(struct mtd_info *mtd, struct nand_chip *this, int state)
 {
-	unsigned long	timeo;
+	unsigned long timeo, timeo_start;
+	unsigned long hz = get_tbclk();
 
-	if (state == FL_ERASING)
- 		timeo = (CFG_HZ * 400) / 1000;
+	if (hz > 1000000)
+		timeo = ((hz + 999) / 1000) * 20;	/* 20 msec */
 	else
-		timeo = (CFG_HZ * 20) / 1000;
+		timeo = ((hz * 20) + 999) / 1000;	/* 20 msec */
 
+	if (state == FL_ERASING)
+ 		timeo *= 20;				/* 400 msec */
+
 	if ((state == FL_ERASING) && (this->options & NAND_IS_AND))
 		this->cmdfunc(mtd, NAND_CMD_STATUS_MULTI, -1, -1);
 	else
 		this->cmdfunc(mtd, NAND_CMD_STATUS, -1, -1);
 
-	reset_timer();
+	timeo_start = get_timer(0);
 
 	while (1) {
-		if (get_timer(0) > timeo) {
+		if (get_timer(timeo_start) > timeo) {
 			printf("Timeout!");
 			return 0x01;
 		}
@@ -863,10 +991,11 @@
 				break;
 		}
 	}
+
 #ifdef PPCHAMELON_NAND_TIMER_HACK
 	reset_timer();
 	while (get_timer(0) < 10);
-#endif /*  PPCHAMELON_NAND_TIMER_HACK */
+#endif
 
 	return this->read_byte(mtd);
 }
@@ -891,7 +1020,7 @@
 	u_char *oob_buf,  struct nand_oobinfo *oobsel, int cached)
 {
 	int 	i, status;
-	u_char	ecc_code[32];
+	u_char	ecc_code[64];
 	int	eccmode = oobsel->useecc ? this->eccmode : NAND_ECC_NONE;
 	uint  	*oob_config = oobsel->eccpos;
 	int	datidx = 0, eccidx = 0, eccsteps = this->eccsteps;
@@ -919,6 +1048,12 @@
 				oob_buf[oob_config[eccidx]] = ecc_code[i];
 			datidx += this->eccsize;
 		}
+#if 0
+		if (page == 2048) {
+			printk ("\nforcing bitflip, page %d offset 0: 0x%02x -> 0x%02x\n\n", page, this->data_poi[0], this->data_poi[0] ^ 0x01);
+			this->data_poi[0] ^= 0x01;
+		}
+#endif
 		this->write_buf(mtd, this->data_poi, mtd->oobblock);
 		break;
 	default:
@@ -991,7 +1126,7 @@
 	int 	i, j, datidx = 0, oobofs = 0, res = -EIO;
 	int	eccsteps = this->eccsteps;
 	int	hweccbytes;
-	u_char 	oobdata[64];
+	u_char 	oobdata[NAND_MAX_OOBSIZE];
 
 	hweccbytes = (this->options & NAND_HWECC_SYNDROME) ? (oobsel->eccbytes / eccsteps) : 0;
 
@@ -1112,8 +1247,8 @@
 	int read = 0, oob = 0, ecc_status = 0, ecc_failed = 0;
 	struct nand_chip *this = mtd->priv;
 	u_char *data_poi, *oob_data = oob_buf;
-	u_char ecc_calc[32];
-	u_char ecc_code[32];
+	u_char ecc_calc[64];
+	u_char ecc_code[64];
 	int eccmode, eccsteps;
 	unsigned *oob_config;
 	int	datidx;
@@ -1283,7 +1418,13 @@
 			}
 
 			if (ecc_status == -1) {
-				DEBUG (MTD_DEBUG_LEVEL0, "nand_read_ecc: " "Failed ECC read, page 0x%08x\n", page);
+				DEBUG (MTD_DEBUG_LEVEL0, "nand_read_ecc: " "Failed ECC read, page 0x%08x, step %2d\n", page, i);
+				if (ecc_failed == 0) {
+					hexdump_local (data_poi, mtd->oobblock);
+					printf ("\n");
+					hexdump_local (oob_data, mtd->oobsize);
+					printf ("\n");
+				}
 				ecc_failed++;
 			}
 		}
@@ -1631,7 +1772,7 @@
 
 	/* reject writes, which are not page aligned */
 	if (NOTALIGNED (to) || NOTALIGNED(len)) {
-		printk (KERN_NOTICE "nand_write_ecc: Attempt to write not page aligned data\n");
+		printf (KERN_NOTICE "nand_write_ecc: Attempt to write not page aligned data (to 0x%08x, len 0x%08x)\n", (unsigned int) to, (unsigned int) len);
 		return -EINVAL;
 	}
 
@@ -1644,8 +1785,10 @@
 	this->select_chip(mtd, chipnr);
 
 	/* Check, if it is write protected */
-	if (nand_check_wp(mtd))
+	if (nand_check_wp(mtd)) {
+		printf (KERN_NOTICE "nand_write_ecc: device is write protected\n");
 		goto out;
+	}
 
 	/* if oobsel is NULL, use chip defaults */
 	if (oobsel == NULL)
@@ -1905,13 +2048,13 @@
 
 	/* Do not allow write past end of page */
 	if ((to + total_len) > mtd->size) {
-		DEBUG (MTD_DEBUG_LEVEL0, "nand_writev: Attempted write past end of device\n");
+		DEBUG (MTD_DEBUG_LEVEL0, "nand_writev_ecc: Attempted write past end of device\n");
 		return -EINVAL;
 	}
 
 	/* reject writes, which are not page aligned */
 	if (NOTALIGNED (to) || NOTALIGNED(total_len)) {
-		printk (KERN_NOTICE "nand_write_ecc: Attempt to write not page aligned data\n");
+		printk (KERN_NOTICE "nand_writev_ecc: Attempt to write not page aligned data (to 0x%08x, total_len 0x%08x)\n", (unsigned int) to, (unsigned int) total_len);
 		return -EINVAL;
 	}
 
@@ -2253,6 +2396,36 @@
 	return this->block_markbad(mtd, ofs);
 }
 
+#if defined (CFG_NAND_BB_REMAP)
+void nand_remap_badblocks(struct mtd_info *mtd)
+{
+	unsigned map_size = sizeof(block_map)/sizeof(block_map[0]);
+	unsigned device_blocks = mtd->size / mtd->erasesize;
+        unsigned map_used = map_size < device_blocks ? map_size : device_blocks;
+	unsigned i, off, goodcnt, badcnt;
+
+	if (mtd->erasesize * map_size < mtd->size)
+		printf("NAND: WARNING: only remapping first %d blocks (out of %d)\n",map_size,device_blocks);
+	printf("NAND: Remapping Bad Blocks:");
+	for (i=0,off=0,badcnt=0,goodcnt=0;i<map_used;i++) {
+		if (nand_block_isbad(mtd, i * mtd->erasesize)) {
+			printf("%c%d",badcnt ? ',' : ' ',i);
+			block_map[map_used - (++badcnt)] = i;
+		} else
+			block_map[goodcnt++] = i;
+	}
+	printf("\n");
+	apply_map = 1;
+	nand_good_cnt = goodcnt;
+/*
+	printf("block_map:\n");
+	for (i=0;i<map_used;i++)
+		printf("%d ",block_map[i]);
+	printf("\n");
+*/
+}
+#endif
+
 /**
  * nand_scan - [NAND Interface] Scan for the NAND device
  * @mtd:	MTD device structure
@@ -2267,9 +2440,13 @@
  */
 int nand_scan (struct mtd_info *mtd, int maxchips)
 {
-	int i, j, nand_maf_id, nand_dev_id, busw;
+	int i, j, nand_maf_id, nand_dev_id, busw, ret;
+	char *nand_maf_id_string = NULL;
+	char *nand_dev_id_string = NULL;
 	struct nand_chip *this = mtd->priv;
 
+	printk (KERN_INFO "N");
+
 	/* Get buswidth to select the correct functions*/
 	busw = this->options & NAND_BUSWIDTH_16;
 
@@ -2311,20 +2488,29 @@
 	/* Select the device */
 	this->select_chip(mtd, 0);
 
+	printk (KERN_INFO "A");
+
 	/* Send the command for reading device ID */
 	this->cmdfunc (mtd, NAND_CMD_READID, 0x00, -1);
 
+	printk (KERN_INFO "N");
+
 	/* Read manufacturer and device IDs */
 	nand_maf_id = this->read_byte(mtd);
 	nand_dev_id = this->read_byte(mtd);
 
+	printk (KERN_INFO "D");
+
 	/* Print and store flash device information */
 	for (i = 0; nand_flash_ids[i].name != NULL; i++) {
 
 		if (nand_dev_id != nand_flash_ids[i].id)
 			continue;
 
-		if (!mtd->name) mtd->name = nand_flash_ids[i].name;
+		nand_dev_id_string = nand_flash_ids[i].name;
+		if (!mtd->name)
+			mtd->name = nand_dev_id_string;
+
 		this->chipsize = nand_flash_ids[i].chipsize << 20;
 
 		/* New devices have all the information in additional id bytes */
@@ -2355,12 +2541,34 @@
 			busw = nand_flash_ids[i].options & NAND_BUSWIDTH_16;
 		}
 
+		/* Try to identify manufacturer */
+		for (j = 0; nand_manuf_ids[j].id != 0x0; j++) {
+			if (nand_manuf_ids[j].id == nand_maf_id) {
+				nand_maf_id_string = nand_manuf_ids[j].name;
+				break;
+			}
+		}
+
+		/* NB: leading "NAND" has already been printed */
+		printk (KERN_INFO ": %s %s\n",
+			nand_maf_id_string ? nand_maf_id_string : "UNKNOWN", nand_dev_id_string);
+
+		/* Additional debug if we derived geometry from extended ID bytes... */
+		if (!nand_flash_ids[i].pagesize) {
+			printk ("NAND: blocksize ");
+			print_size (mtd->erasesize, ", ");
+			printk ("pagesize ");
+			print_size (mtd->oobblock, ", ");
+			printk ("oobsize %d, buswidth %dbits\n",
+				mtd->oobsize, (busw == NAND_BUSWIDTH_16) ? 16 : 8);
+		}
+
+		if (mtd->oobsize > NAND_MAX_OOBSIZE)
+			printk (KERN_INFO "\nNAND: ERROR... oobsize greater than NAND_MAX_OOBSIZE (%d) !!\n\n", NAND_MAX_OOBSIZE);
+
 		/* Check, if buswidth is correct. Hardware drivers should set
 		 * this correct ! */
 		if (busw != (this->options & NAND_BUSWIDTH_16)) {
-			printk (KERN_INFO "NAND device: Manufacturer ID:"
-				" 0x%02x, Chip ID: 0x%02x (%s %s)\n", nand_maf_id, nand_dev_id,
-				nand_manuf_ids[i].name , mtd->name);
 			printk (KERN_WARNING
 				"NAND bus width %d instead %d bit\n",
 					(this->options & NAND_BUSWIDTH_16) ? 16 : 8,
@@ -2399,18 +2607,12 @@
 		if (mtd->oobblock > 512 && this->cmdfunc == nand_command)
 			this->cmdfunc = nand_command_lp;
 
-		/* Try to identify manufacturer */
-		for (j = 0; nand_manuf_ids[j].id != 0x0; j++) {
-			if (nand_manuf_ids[j].id == nand_maf_id)
-				break;
-		}
 		break;
 	}
 
-	if (!nand_flash_ids[i].name) {
-#ifndef CFG_NAND_QUIET_TEST
-		printk (KERN_WARNING "No NAND device found!!!\n");
-#endif
+	if (! nand_dev_id_string) {
+		/* NB: leading "NAND" has already been printed */
+		printk (": no device found\n");
 		this->select_chip(mtd, -1);
 		return 1;
 	}
@@ -2468,15 +2670,15 @@
 		/* Select the appropriate default oob placement scheme for
 		 * placement agnostic filesystems */
 		switch (mtd->oobsize) {
-		case 8:
-			this->autooob = &nand_oob_8;
-			break;
 		case 16:
 			this->autooob = &nand_oob_16;
 			break;
 		case 64:
 			this->autooob = &nand_oob_64;
 			break;
+		case 128:
+			this->autooob = &nand_oob_128;
+			break;
 		default:
 			printk (KERN_WARNING "No oob scheme defined for oobsize %d\n",
 				mtd->oobsize);
@@ -2634,7 +2836,11 @@
 	mtd->owner = THIS_MODULE;
 #endif
 	/* Build bad block table */
-	return this->scan_bbt (mtd);
+	ret = this->scan_bbt (mtd);
+#if defined (CFG_NAND_BB_REMAP)
+	nand_remap_badblocks (mtd);
+#endif
+	return ret;
 }
 
 /**

===================================================================
--- u-boot-1.2.0/drivers/nand/nand_bbt.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand_bbt.c	(revision 2339)
@@ -291,10 +291,36 @@
 		from = startblock << (this->bbt_erase_shift - 1);
 	}
 
+//	printf ("%s: startblock %d, real numblocks %d, len %d, db->options 0x%08x\n", __FUNCTION__, startblock, (numblocks / 2), len, bd->options);
+
 	for (i = startblock; i < numblocks;) {
-		nand_read_raw (mtd, buf, from, readlen, ooblen);
+		size_t retlen;
+
+		if (bd->options & NAND_BBT_SCANEMPTY) {
+			/*
+			   We shouldn't read from the data area of a given page unless the
+			   page is known to be within a good block. Therefore reading from
+			   the data area during the bad block scan must be a bug...
+			*/
+			nand_read_raw (mtd, buf, from, readlen, ooblen);
+		}
+		else
+			mtd->read_oob (mtd, from, ooblen, &retlen, buf + readlen);
+
 		for (j = 0; j < len; j++) {
 			if (check_pattern (&buf[j * scanlen], scanlen, mtd->oobblock, bd)) {
+				unsigned int from_lower = (unsigned int) (from >> 0);
+				unsigned int from_upper = (unsigned int) (from >> 32);
+				/*
+				   Crappy u-boot printf doesn't support 'll' qualifier.
+				   The equivalent is 'q', but this has to be explicitely enabled with
+				   CFG_64BIT_VSPRINTF, so we can't rely on it in generic code...
+				*/
+				if (mtd->size > 0xFFFFFFFF)
+					printf ("NAND 0x%08x%08x: bad block\n", from_upper, from_lower);
+				else
+					printf ("NAND 0x%08x: bad block\n", from_lower);
+
 				this->bbt[i >> 3] |= 0x03 << (i & 0x6);
 				break;
 			}

===================================================================
--- u-boot-1.2.0/drivers/nand/nand_ecc.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand_ecc.c	(revision 4312)
@@ -1,14 +1,19 @@
 /*
- * This file contains an ECC algorithm from Toshiba that detects and
- * corrects 1 bit errors in a 256 byte block of data.
+ * This file contains an ECC algorithm that detects and corrects 1 bit
+ * errors in a 256 byte block of data.
  *
  * drivers/mtd/nand/nand_ecc.c
  *
- * Copyright (C) 2000-2004 Steven J. Hill (sjhill@realitydiluted.com)
- *                         Toshiba America Electronics Components, Inc.
+ * Copyright (c) 2008 Koninklijke Philips Electronics NV.
+ *                    Author: Frans Meulenbroeks
  *
- * $Id: nand_ecc.c,v 1.14 2004/06/16 15:34:37 gleixner Exp $
+ * Completely replaces the previous ECC implementation which was written by:
+ *   Steven J. Hill (sjhill@realitydiluted.com)
+ *   Thomas Gleixner (tglx@linutronix.de)
  *
+ * Information on how this algorithm works and how it was developed
+ * can be found in Documentation/mtd/nand_ecc.txt
+ *
  * This file 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 or (at your option) any
@@ -23,221 +28,473 @@
  * with this file; if not, write to the Free Software Foundation, Inc.,
  * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
  *
- * As a special exception, if other files instantiate templates or use
- * macros or inline functions from these files, or you compile these
- * files and link them with other works to produce a work based on these
- * files, these files do not by themselves cause the resulting work to be
- * covered by the GNU General Public License. However the source code for
- * these files must still be made available in accordance with section (3)
- * of the GNU General Public License.
- *
- * This exception does not invalidate any other reasons why a work based on
- * this file might be covered by the GNU General Public License.
  */
 
 #include <common.h>
 
 #if (CONFIG_COMMANDS & CFG_CMD_NAND) && !defined(CFG_NAND_LEGACY)
 
-#include<linux/mtd/mtd.h>
+#include <linux/mtd/mtd.h>
+#include <asm/byteorder.h>
+
+#define printk printf
+#define KERN_ERR	""
+
 /*
- * Pre-calculated 256-way 1 byte column parity
+ * invparity is a 256 byte table that contains the odd parity
+ * for each byte. So if the number of bits in a byte is even,
+ * the array element is 1, and when the number of bits is odd
+ * the array eleemnt is 0.
  */
-static const u_char nand_ecc_precalc_table[] = {
-	0x00, 0x55, 0x56, 0x03, 0x59, 0x0c, 0x0f, 0x5a, 0x5a, 0x0f, 0x0c, 0x59, 0x03, 0x56, 0x55, 0x00,
-	0x65, 0x30, 0x33, 0x66, 0x3c, 0x69, 0x6a, 0x3f, 0x3f, 0x6a, 0x69, 0x3c, 0x66, 0x33, 0x30, 0x65,
-	0x66, 0x33, 0x30, 0x65, 0x3f, 0x6a, 0x69, 0x3c, 0x3c, 0x69, 0x6a, 0x3f, 0x65, 0x30, 0x33, 0x66,
-	0x03, 0x56, 0x55, 0x00, 0x5a, 0x0f, 0x0c, 0x59, 0x59, 0x0c, 0x0f, 0x5a, 0x00, 0x55, 0x56, 0x03,
-	0x69, 0x3c, 0x3f, 0x6a, 0x30, 0x65, 0x66, 0x33, 0x33, 0x66, 0x65, 0x30, 0x6a, 0x3f, 0x3c, 0x69,
-	0x0c, 0x59, 0x5a, 0x0f, 0x55, 0x00, 0x03, 0x56, 0x56, 0x03, 0x00, 0x55, 0x0f, 0x5a, 0x59, 0x0c,
-	0x0f, 0x5a, 0x59, 0x0c, 0x56, 0x03, 0x00, 0x55, 0x55, 0x00, 0x03, 0x56, 0x0c, 0x59, 0x5a, 0x0f,
-	0x6a, 0x3f, 0x3c, 0x69, 0x33, 0x66, 0x65, 0x30, 0x30, 0x65, 0x66, 0x33, 0x69, 0x3c, 0x3f, 0x6a,
-	0x6a, 0x3f, 0x3c, 0x69, 0x33, 0x66, 0x65, 0x30, 0x30, 0x65, 0x66, 0x33, 0x69, 0x3c, 0x3f, 0x6a,
-	0x0f, 0x5a, 0x59, 0x0c, 0x56, 0x03, 0x00, 0x55, 0x55, 0x00, 0x03, 0x56, 0x0c, 0x59, 0x5a, 0x0f,
-	0x0c, 0x59, 0x5a, 0x0f, 0x55, 0x00, 0x03, 0x56, 0x56, 0x03, 0x00, 0x55, 0x0f, 0x5a, 0x59, 0x0c,
-	0x69, 0x3c, 0x3f, 0x6a, 0x30, 0x65, 0x66, 0x33, 0x33, 0x66, 0x65, 0x30, 0x6a, 0x3f, 0x3c, 0x69,
-	0x03, 0x56, 0x55, 0x00, 0x5a, 0x0f, 0x0c, 0x59, 0x59, 0x0c, 0x0f, 0x5a, 0x00, 0x55, 0x56, 0x03,
-	0x66, 0x33, 0x30, 0x65, 0x3f, 0x6a, 0x69, 0x3c, 0x3c, 0x69, 0x6a, 0x3f, 0x65, 0x30, 0x33, 0x66,
-	0x65, 0x30, 0x33, 0x66, 0x3c, 0x69, 0x6a, 0x3f, 0x3f, 0x6a, 0x69, 0x3c, 0x66, 0x33, 0x30, 0x65,
-	0x00, 0x55, 0x56, 0x03, 0x59, 0x0c, 0x0f, 0x5a, 0x5a, 0x0f, 0x0c, 0x59, 0x03, 0x56, 0x55, 0x00
+static const char invparity[256] = {
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0,
+	1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1
 };
 
+/*
+ * bitsperbyte contains the number of bits per byte
+ * this is only used for testing and repairing parity
+ * (a precalculated value slightly improves performance)
+ */
+static const char bitsperbyte[256] = {
+	0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4,
+	1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5,
+	1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7,
+	1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7,
+	2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6,
+	3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7,
+	3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7,
+	4, 5, 5, 6, 5, 6, 6, 7, 5, 6, 6, 7, 6, 7, 7, 8,
+};
 
+/*
+ * addressbits is a lookup table to filter out the bits from the xor-ed
+ * ecc data that identify the faulty location.
+ * this is only used for repairing parity
+ * see the comments in nand_correct_data for more details
+ */
+static const char addressbits[256] = {
+	0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x01, 0x01,
+	0x02, 0x02, 0x03, 0x03, 0x02, 0x02, 0x03, 0x03,
+	0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x01, 0x01,
+	0x02, 0x02, 0x03, 0x03, 0x02, 0x02, 0x03, 0x03,
+	0x04, 0x04, 0x05, 0x05, 0x04, 0x04, 0x05, 0x05,
+	0x06, 0x06, 0x07, 0x07, 0x06, 0x06, 0x07, 0x07,
+	0x04, 0x04, 0x05, 0x05, 0x04, 0x04, 0x05, 0x05,
+	0x06, 0x06, 0x07, 0x07, 0x06, 0x06, 0x07, 0x07,
+	0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x01, 0x01,
+	0x02, 0x02, 0x03, 0x03, 0x02, 0x02, 0x03, 0x03,
+	0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x01, 0x01,
+	0x02, 0x02, 0x03, 0x03, 0x02, 0x02, 0x03, 0x03,
+	0x04, 0x04, 0x05, 0x05, 0x04, 0x04, 0x05, 0x05,
+	0x06, 0x06, 0x07, 0x07, 0x06, 0x06, 0x07, 0x07,
+	0x04, 0x04, 0x05, 0x05, 0x04, 0x04, 0x05, 0x05,
+	0x06, 0x06, 0x07, 0x07, 0x06, 0x06, 0x07, 0x07,
+	0x08, 0x08, 0x09, 0x09, 0x08, 0x08, 0x09, 0x09,
+	0x0a, 0x0a, 0x0b, 0x0b, 0x0a, 0x0a, 0x0b, 0x0b,
+	0x08, 0x08, 0x09, 0x09, 0x08, 0x08, 0x09, 0x09,
+	0x0a, 0x0a, 0x0b, 0x0b, 0x0a, 0x0a, 0x0b, 0x0b,
+	0x0c, 0x0c, 0x0d, 0x0d, 0x0c, 0x0c, 0x0d, 0x0d,
+	0x0e, 0x0e, 0x0f, 0x0f, 0x0e, 0x0e, 0x0f, 0x0f,
+	0x0c, 0x0c, 0x0d, 0x0d, 0x0c, 0x0c, 0x0d, 0x0d,
+	0x0e, 0x0e, 0x0f, 0x0f, 0x0e, 0x0e, 0x0f, 0x0f,
+	0x08, 0x08, 0x09, 0x09, 0x08, 0x08, 0x09, 0x09,
+	0x0a, 0x0a, 0x0b, 0x0b, 0x0a, 0x0a, 0x0b, 0x0b,
+	0x08, 0x08, 0x09, 0x09, 0x08, 0x08, 0x09, 0x09,
+	0x0a, 0x0a, 0x0b, 0x0b, 0x0a, 0x0a, 0x0b, 0x0b,
+	0x0c, 0x0c, 0x0d, 0x0d, 0x0c, 0x0c, 0x0d, 0x0d,
+	0x0e, 0x0e, 0x0f, 0x0f, 0x0e, 0x0e, 0x0f, 0x0f,
+	0x0c, 0x0c, 0x0d, 0x0d, 0x0c, 0x0c, 0x0d, 0x0d,
+	0x0e, 0x0e, 0x0f, 0x0f, 0x0e, 0x0e, 0x0f, 0x0f
+};
+
 /**
- * nand_trans_result - [GENERIC] create non-inverted ECC
- * @reg2:	line parity reg 2
- * @reg3:	line parity reg 3
- * @ecc_code:	ecc
- *
- * Creates non-inverted ECC code from line parity
+ * nand_calculate_ecc - [NAND Interface] Calculate 3-byte ECC for 256/512-byte
+ *			 block
+ * @mtd:	MTD block structure
+ * @buf:	input buffer with raw data
+ * @code:	output buffer with ECC
  */
-static void nand_trans_result(u_char reg2, u_char reg3,
-	u_char *ecc_code)
+static int nand_calculate_ecc_aligned (struct mtd_info *mtd, const unsigned char *buf, unsigned char *code)
 {
-	u_char a, b, i, tmp1, tmp2;
+	int i;
+	const uint32_t *bp = (uint32_t *)buf;
+#if 0
+	/* 256 or 512 bytes/ecc  */
+	const uint32_t eccsize_mult =
+			(((struct nand_chip *)mtd->priv)->ecc.size) >> 8;
+#else
+	const uint32_t eccsize_mult = 1;	/* 1: 256 bytes/ecc, 2: 512 bytes/ecc */
+#endif
+	uint32_t cur;		/* current value in buffer */
+	/* rp0..rp15..rp17 are the various accumulated parities (per byte) */
+	uint32_t rp0, rp1, rp2, rp3, rp4, rp5, rp6, rp7;
+	uint32_t rp8, rp9, rp10, rp11, rp12, rp13, rp14, rp15, rp16;
+	uint32_t rp17;
+	uint32_t par;		/* the cumulative parity for all data */
+	uint32_t tmppar;	/* the cumulative parity for this iteration;
+				   for rp12, rp14 and rp16 at the end of the
+				   loop */
 
-	/* Initialize variables */
-	a = b = 0x80;
-	tmp1 = tmp2 = 0;
+	par = 0;
+	rp4 = 0;
+	rp6 = 0;
+	rp8 = 0;
+	rp10 = 0;
+	rp12 = 0;
+	rp14 = 0;
+	rp16 = 0;
 
-	/* Calculate first ECC byte */
-	for (i = 0; i < 4; i++) {
-		if (reg3 & a)		/* LP15,13,11,9 --> ecc_code[0] */
-			tmp1 |= b;
-		b >>= 1;
-		if (reg2 & a)		/* LP14,12,10,8 --> ecc_code[0] */
-			tmp1 |= b;
-		b >>= 1;
-		a >>= 1;
+	/*
+	 * The loop is unrolled a number of times;
+	 * This avoids if statements to decide on which rp value to update
+	 * Also we process the data by longwords.
+	 * Note: passing unaligned data might give a performance penalty.
+	 * It is assumed that the buffers are aligned.
+	 * tmppar is the cumulative sum of this iteration.
+	 * needed for calculating rp12, rp14, rp16 and par
+	 * also used as a performance improvement for rp6, rp8 and rp10
+	 */
+	for (i = 0; i < eccsize_mult << 2; i++) {
+		cur = *bp++;
+		tmppar = cur;
+		rp4 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp6 ^= tmppar;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp8 ^= tmppar;
+
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		rp6 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp6 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp10 ^= tmppar;
+
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		rp6 ^= cur;
+		rp8 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp6 ^= cur;
+		rp8 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		rp8 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp8 ^= cur;
+
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		rp6 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp6 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+		rp4 ^= cur;
+		cur = *bp++;
+		tmppar ^= cur;
+
+		par ^= tmppar;
+		if ((i & 0x1) == 0)
+			rp12 ^= tmppar;
+		if ((i & 0x2) == 0)
+			rp14 ^= tmppar;
+		if (eccsize_mult == 2 && (i & 0x4) == 0)
+			rp16 ^= tmppar;
 	}
 
-	/* Calculate second ECC byte */
-	b = 0x80;
-	for (i = 0; i < 4; i++) {
-		if (reg3 & a)		/* LP7,5,3,1 --> ecc_code[1] */
-			tmp2 |= b;
-		b >>= 1;
-		if (reg2 & a)		/* LP6,4,2,0 --> ecc_code[1] */
-			tmp2 |= b;
-		b >>= 1;
-		a >>= 1;
+	/*
+	 * handle the fact that we use longword operations
+	 * we'll bring rp4..rp14..rp16 back to single byte entities by
+	 * shifting and xoring first fold the upper and lower 16 bits,
+	 * then the upper and lower 8 bits.
+	 */
+	rp4 ^= (rp4 >> 16);
+	rp4 ^= (rp4 >> 8);
+	rp4 &= 0xff;
+	rp6 ^= (rp6 >> 16);
+	rp6 ^= (rp6 >> 8);
+	rp6 &= 0xff;
+	rp8 ^= (rp8 >> 16);
+	rp8 ^= (rp8 >> 8);
+	rp8 &= 0xff;
+	rp10 ^= (rp10 >> 16);
+	rp10 ^= (rp10 >> 8);
+	rp10 &= 0xff;
+	rp12 ^= (rp12 >> 16);
+	rp12 ^= (rp12 >> 8);
+	rp12 &= 0xff;
+	rp14 ^= (rp14 >> 16);
+	rp14 ^= (rp14 >> 8);
+	rp14 &= 0xff;
+	if (eccsize_mult == 2) {
+		rp16 ^= (rp16 >> 16);
+		rp16 ^= (rp16 >> 8);
+		rp16 &= 0xff;
 	}
 
-	/* Store two of the ECC bytes */
-	ecc_code[0] = tmp1;
-	ecc_code[1] = tmp2;
-}
+	/*
+	 * we also need to calculate the row parity for rp0..rp3
+	 * This is present in par, because par is now
+	 * rp3 rp3 rp2 rp2 in little endian and
+	 * rp2 rp2 rp3 rp3 in big endian
+	 * as well as
+	 * rp1 rp0 rp1 rp0 in little endian and
+	 * rp0 rp1 rp0 rp1 in big endian
+	 * First calculate rp2 and rp3
+	 */
+#ifdef __BIG_ENDIAN
+	rp2 = (par >> 16);
+	rp2 ^= (rp2 >> 8);
+	rp2 &= 0xff;
+	rp3 = par & 0xffff;
+	rp3 ^= (rp3 >> 8);
+	rp3 &= 0xff;
+#else
+	rp3 = (par >> 16);
+	rp3 ^= (rp3 >> 8);
+	rp3 &= 0xff;
+	rp2 = par & 0xffff;
+	rp2 ^= (rp2 >> 8);
+	rp2 &= 0xff;
+#endif
 
-/**
- * nand_calculate_ecc - [NAND Interface] Calculate 3 byte ECC code for 256 byte block
- * @mtd:	MTD block structure
- * @dat:	raw data
- * @ecc_code:	buffer for ECC
- */
-int nand_calculate_ecc(struct mtd_info *mtd, const u_char *dat, u_char *ecc_code)
-{
-	u_char idx, reg1, reg2, reg3;
-	int j;
+	/* reduce par to 16 bits then calculate rp1 and rp0 */
+	par ^= (par >> 16);
+#ifdef __BIG_ENDIAN
+	rp0 = (par >> 8) & 0xff;
+	rp1 = (par & 0xff);
+#else
+	rp1 = (par >> 8) & 0xff;
+	rp0 = (par & 0xff);
+#endif
 
-	/* Initialize variables */
-	reg1 = reg2 = reg3 = 0;
-	ecc_code[0] = ecc_code[1] = ecc_code[2] = 0;
+	/* finally reduce par to 8 bits */
+	par ^= (par >> 8);
+	par &= 0xff;
 
-	/* Build up column parity */
-	for(j = 0; j < 256; j++) {
+	/*
+	 * and calculate rp5..rp15..rp17
+	 * note that par = rp4 ^ rp5 and due to the commutative property
+	 * of the ^ operator we can say:
+	 * rp5 = (par ^ rp4);
+	 * The & 0xff seems superfluous, but benchmarking learned that
+	 * leaving it out gives slightly worse results. No idea why, probably
+	 * it has to do with the way the pipeline in pentium is organized.
+	 */
+	rp5 = (par ^ rp4) & 0xff;
+	rp7 = (par ^ rp6) & 0xff;
+	rp9 = (par ^ rp8) & 0xff;
+	rp11 = (par ^ rp10) & 0xff;
+	rp13 = (par ^ rp12) & 0xff;
+	rp15 = (par ^ rp14) & 0xff;
+	if (eccsize_mult == 2)
+		rp17 = (par ^ rp16) & 0xff;
 
-		/* Get CP0 - CP5 from table */
-		idx = nand_ecc_precalc_table[dat[j]];
-		reg1 ^= (idx & 0x3f);
+	/*
+	 * Finally calculate the ecc bits.
+	 * Again here it might seem that there are performance optimisations
+	 * possible, but benchmarks showed that on the system this is developed
+	 * the code below is the fastest
+	 */
+#ifdef CONFIG_MTD_NAND_ECC_SMC
+	code[0] =
+	    (invparity[rp7] << 7) |
+	    (invparity[rp6] << 6) |
+	    (invparity[rp5] << 5) |
+	    (invparity[rp4] << 4) |
+	    (invparity[rp3] << 3) |
+	    (invparity[rp2] << 2) |
+	    (invparity[rp1] << 1) |
+	    (invparity[rp0]);
+	code[1] =
+	    (invparity[rp15] << 7) |
+	    (invparity[rp14] << 6) |
+	    (invparity[rp13] << 5) |
+	    (invparity[rp12] << 4) |
+	    (invparity[rp11] << 3) |
+	    (invparity[rp10] << 2) |
+	    (invparity[rp9] << 1)  |
+	    (invparity[rp8]);
+#else
+	code[1] =
+	    (invparity[rp7] << 7) |
+	    (invparity[rp6] << 6) |
+	    (invparity[rp5] << 5) |
+	    (invparity[rp4] << 4) |
+	    (invparity[rp3] << 3) |
+	    (invparity[rp2] << 2) |
+	    (invparity[rp1] << 1) |
+	    (invparity[rp0]);
+	code[0] =
+	    (invparity[rp15] << 7) |
+	    (invparity[rp14] << 6) |
+	    (invparity[rp13] << 5) |
+	    (invparity[rp12] << 4) |
+	    (invparity[rp11] << 3) |
+	    (invparity[rp10] << 2) |
+	    (invparity[rp9] << 1)  |
+	    (invparity[rp8]);
+#endif
+	if (eccsize_mult == 1)
+		code[2] =
+		    (invparity[par & 0xf0] << 7) |
+		    (invparity[par & 0x0f] << 6) |
+		    (invparity[par & 0xcc] << 5) |
+		    (invparity[par & 0x33] << 4) |
+		    (invparity[par & 0xaa] << 3) |
+		    (invparity[par & 0x55] << 2) |
+		    3;
+	else
+		code[2] =
+		    (invparity[par & 0xf0] << 7) |
+		    (invparity[par & 0x0f] << 6) |
+		    (invparity[par & 0xcc] << 5) |
+		    (invparity[par & 0x33] << 4) |
+		    (invparity[par & 0xaa] << 3) |
+		    (invparity[par & 0x55] << 2) |
+		    (invparity[rp17] << 1) |
+		    (invparity[rp16] << 0);
+	return 0;
+}
 
-		/* All bit XOR = 1 ? */
-		if (idx & 0x40) {
-			reg3 ^= (u_char) j;
-			reg2 ^= ~((u_char) j);
-		}
+int nand_calculate_ecc (struct mtd_info *mtd, const unsigned char *buf, unsigned char *code)
+{
+	unsigned char align_buf[256];
+
+	if ((((unsigned long) buf) & 0x03) != 0) {
+		printf ("%s: misaligned source buffer !?!\n", __FUNCTION__);
+		memcpy (align_buf, buf, 256);
+		buf = (const unsigned char *) align_buf;
 	}
 
-	/* Create non-inverted ECC code from line parity */
-	nand_trans_result(reg2, reg3, ecc_code);
-
-	/* Calculate final ECC code */
-	ecc_code[0] = ~ecc_code[0];
-	ecc_code[1] = ~ecc_code[1];
-	ecc_code[2] = ((~reg1) << 2) | 0x03;
-	return 0;
+	return nand_calculate_ecc_aligned (mtd, buf, code);
 }
 
 /**
  * nand_correct_data - [NAND Interface] Detect and correct bit error(s)
  * @mtd:	MTD block structure
- * @dat:	raw data read from the chip
+ * @buf:	raw data read from the chip
  * @read_ecc:	ECC from the chip
  * @calc_ecc:	the ECC calculated from raw data
  *
- * Detect and correct a 1 bit error for 256 byte block
+ * Detect and correct a 1 bit error for 256/512 byte block
  */
-int nand_correct_data(struct mtd_info *mtd, u_char *dat, u_char *read_ecc, u_char *calc_ecc)
+int nand_correct_data(struct mtd_info *mtd, unsigned char *buf,
+		      unsigned char *read_ecc, unsigned char *calc_ecc)
 {
-	u_char a, b, c, d1, d2, d3, add, bit, i;
+	unsigned char b0, b1, b2;
+	unsigned char byte_addr, bit_addr;
+#if 0
+	/* 256 or 512 bytes/ecc  */
+	const uint32_t eccsize_mult =
+			(((struct nand_chip *)mtd->priv)->ecc.size) >> 8;
+#else
+	const uint32_t eccsize_mult = 1;	/* 1: 256 bytes/ecc, 2: 512 bytes/ecc */
+#endif
 
-	/* Do error detection */
-	d1 = calc_ecc[0] ^ read_ecc[0];
-	d2 = calc_ecc[1] ^ read_ecc[1];
-	d3 = calc_ecc[2] ^ read_ecc[2];
+	/*
+	 * b0 to b2 indicate which bit is faulty (if any)
+	 * we might need the xor result  more than once,
+	 * so keep them in a local var
+	*/
+#ifdef CONFIG_MTD_NAND_ECC_SMC
+	b0 = read_ecc[0] ^ calc_ecc[0];
+	b1 = read_ecc[1] ^ calc_ecc[1];
+#else
+	b0 = read_ecc[1] ^ calc_ecc[1];
+	b1 = read_ecc[0] ^ calc_ecc[0];
+#endif
+	b2 = read_ecc[2] ^ calc_ecc[2];
 
-	if ((d1 | d2 | d3) == 0) {
-		/* No errors */
-		return 0;
-	}
-	else {
-		a = (d1 ^ (d1 >> 1)) & 0x55;
-		b = (d2 ^ (d2 >> 1)) & 0x55;
-		c = (d3 ^ (d3 >> 1)) & 0x54;
+	/* check if there are any bitfaults */
 
-		/* Found and will correct single bit error in the data */
-		if ((a == 0x55) && (b == 0x55) && (c == 0x54)) {
-			c = 0x80;
-			add = 0;
-			a = 0x80;
-			for (i=0; i<4; i++) {
-				if (d1 & c)
-					add |= a;
-				c >>= 2;
-				a >>= 1;
-			}
-			c = 0x80;
-			for (i=0; i<4; i++) {
-				if (d2 & c)
-					add |= a;
-				c >>= 2;
-				a >>= 1;
-			}
-			bit = 0;
-			b = 0x04;
-			c = 0x80;
-			for (i=0; i<3; i++) {
-				if (d3 & c)
-					bit |= b;
-				c >>= 2;
-				b >>= 1;
-			}
-			b = 0x01;
-			a = dat[add];
-			a ^= (b << bit);
-			dat[add] = a;
-			return 1;
-		} else {
-			i = 0;
-			while (d1) {
-				if (d1 & 0x01)
-					++i;
-				d1 >>= 1;
-			}
-			while (d2) {
-				if (d2 & 0x01)
-					++i;
-				d2 >>= 1;
-			}
-			while (d3) {
-				if (d3 & 0x01)
-					++i;
-				d3 >>= 1;
-			}
-			if (i == 1) {
-				/* ECC Code Error Correction */
-				read_ecc[0] = calc_ecc[0];
-				read_ecc[1] = calc_ecc[1];
-				read_ecc[2] = calc_ecc[2];
-				return 2;
-			}
-			else {
-				/* Uncorrectable Error */
-				return -1;
-			}
-		}
+	/* repeated if statements are slightly more efficient than switch ... */
+	/* ordered in order of likelihood */
+
+	if ((b0 | b1 | b2) == 0)
+		return 0;	/* no error */
+
+	if ((((b0 ^ (b0 >> 1)) & 0x55) == 0x55) &&
+	    (((b1 ^ (b1 >> 1)) & 0x55) == 0x55) &&
+	    ((eccsize_mult == 1 && ((b2 ^ (b2 >> 1)) & 0x54) == 0x54) ||
+	     (eccsize_mult == 2 && ((b2 ^ (b2 >> 1)) & 0x55) == 0x55))) {
+		/* single bit error */
+		/*
+		 * rp17/rp15/13/11/9/7/5/3/1 indicate which byte is the faulty
+		 * byte, cp 5/3/1 indicate the faulty bit.
+		 * A lookup table (called addressbits) is used to filter
+		 * the bits from the byte they are in.
+		 * A marginal optimisation is possible by having three
+		 * different lookup tables.
+		 * One as we have now (for b0), one for b2
+		 * (that would avoid the >> 1), and one for b1 (with all values
+		 * << 4). However it was felt that introducing two more tables
+		 * hardly justify the gain.
+		 *
+		 * The b2 shift is there to get rid of the lowest two bits.
+		 * We could also do addressbits[b2] >> 1 but for the
+		 * performace it does not make any difference
+		 */
+		if (eccsize_mult == 1)
+			byte_addr = (addressbits[b1] << 4) + addressbits[b0];
+		else
+			byte_addr = (addressbits[b2 & 0x3] << 8) +
+				    (addressbits[b1] << 4) + addressbits[b0];
+		bit_addr = addressbits[b2 >> 2];
+		/* flip the bit */
+		buf[byte_addr] ^= (1 << bit_addr);
+
+		printk("\nCorrectable ECC error\n");
+		return 1;
 	}
 
-	/* Should never happen */
+	/* count nr of bits; use table lookup, faster than calculating it */
+	if ((bitsperbyte[b0] + bitsperbyte[b1] + bitsperbyte[b2]) == 1)
+		return 1;	/* error in ecc data; no action needed */
+
+	printk(KERN_ERR "Uncorrectable ECC error\n");
 	return -1;
 }
 

===================================================================
--- u-boot-1.2.0/drivers/nand/nand_ids.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand_ids.c	(revision 2339)
@@ -29,78 +29,82 @@
 *	512	512 Byte page size
 */
 struct nand_flash_dev nand_flash_ids[] = {
-	{"NAND 1MiB 5V 8-bit", 		0x6e, 256, 1, 0x1000, 0},
-	{"NAND 2MiB 5V 8-bit", 		0x64, 256, 2, 0x1000, 0},
-	{"NAND 4MiB 5V 8-bit", 		0x6b, 512, 4, 0x2000, 0},
-	{"NAND 1MiB 3,3V 8-bit", 	0xe8, 256, 1, 0x1000, 0},
-	{"NAND 1MiB 3,3V 8-bit", 	0xec, 256, 1, 0x1000, 0},
-	{"NAND 2MiB 3,3V 8-bit", 	0xea, 256, 2, 0x1000, 0},
-	{"NAND 4MiB 3,3V 8-bit", 	0xd5, 512, 4, 0x2000, 0},
-	{"NAND 4MiB 3,3V 8-bit", 	0xe3, 512, 4, 0x2000, 0},
-	{"NAND 4MiB 3,3V 8-bit", 	0xe5, 512, 4, 0x2000, 0},
-	{"NAND 8MiB 3,3V 8-bit", 	0xd6, 512, 8, 0x2000, 0},
+#if 0
+	{"1MiB 5V 8-bit", 	0x6e, 256, 1, 0x1000, 0},
+	{"2MiB 5V 8-bit", 	0x64, 256, 2, 0x1000, 0},
+	{"4MiB 5V 8-bit", 	0x6b, 512, 4, 0x2000, 0},
+	{"1MiB 3,3V 8-bit", 	0xe8, 256, 1, 0x1000, 0},
+	{"1MiB 3,3V 8-bit", 	0xec, 256, 1, 0x1000, 0},
+	{"2MiB 3,3V 8-bit", 	0xea, 256, 2, 0x1000, 0},
+	{"4MiB 3,3V 8-bit", 	0xd5, 512, 4, 0x2000, 0},
+	{"4MiB 3,3V 8-bit", 	0xe3, 512, 4, 0x2000, 0},
+	{"4MiB 3,3V 8-bit", 	0xe5, 512, 4, 0x2000, 0},
+	{"8MiB 3,3V 8-bit", 	0xd6, 512, 8, 0x2000, 0},
 
-	{"NAND 8MiB 1,8V 8-bit", 	0x39, 512, 8, 0x2000, 0},
-	{"NAND 8MiB 3,3V 8-bit", 	0xe6, 512, 8, 0x2000, 0},
-	{"NAND 8MiB 1,8V 16-bit", 	0x49, 512, 8, 0x2000, NAND_BUSWIDTH_16},
-	{"NAND 8MiB 3,3V 16-bit", 	0x59, 512, 8, 0x2000, NAND_BUSWIDTH_16},
+	{"8MiB 1,8V 8-bit", 	0x39, 512, 8, 0x2000, 0},
+	{"8MiB 3,3V 8-bit", 	0xe6, 512, 8, 0x2000, 0},
+	{"8MiB 1,8V 16-bit", 	0x49, 512, 8, 0x2000, NAND_BUSWIDTH_16},
+	{"8MiB 3,3V 16-bit", 	0x59, 512, 8, 0x2000, NAND_BUSWIDTH_16},
+#endif
 
-	{"NAND 16MiB 1,8V 8-bit", 	0x33, 512, 16, 0x4000, 0},
-	{"NAND 16MiB 3,3V 8-bit", 	0x73, 512, 16, 0x4000, 0},
-	{"NAND 16MiB 1,8V 16-bit", 	0x43, 512, 16, 0x4000, NAND_BUSWIDTH_16},
-	{"NAND 16MiB 3,3V 16-bit", 	0x53, 512, 16, 0x4000, NAND_BUSWIDTH_16},
+	{"16MiB 1,8V 8-bit", 	0x33, 512, 16, 0x4000, 0},
+	{"16MiB 3,3V 8-bit", 	0x73, 512, 16, 0x4000, 0},
+	{"16MiB 1,8V 16-bit", 	0x43, 512, 16, 0x4000, NAND_BUSWIDTH_16},
+	{"16MiB 3,3V 16-bit", 	0x53, 512, 16, 0x4000, NAND_BUSWIDTH_16},
 
-	{"NAND 32MiB 1,8V 8-bit", 	0x35, 512, 32, 0x4000, 0},
-	{"NAND 32MiB 3,3V 8-bit", 	0x75, 512, 32, 0x4000, 0},
-	{"NAND 32MiB 1,8V 16-bit", 	0x45, 512, 32, 0x4000, NAND_BUSWIDTH_16},
-	{"NAND 32MiB 3,3V 16-bit", 	0x55, 512, 32, 0x4000, NAND_BUSWIDTH_16},
+	{"32MiB 1,8V 8-bit", 	0x35, 512, 32, 0x4000, 0},
+	{"32MiB 3,3V 8-bit", 	0x75, 512, 32, 0x4000, 0},
+	{"32MiB 1,8V 16-bit", 	0x45, 512, 32, 0x4000, NAND_BUSWIDTH_16},
+	{"32MiB 3,3V 16-bit", 	0x55, 512, 32, 0x4000, NAND_BUSWIDTH_16},
 
-	{"NAND 64MiB 1,8V 8-bit", 	0x36, 512, 64, 0x4000, 0},
-	{"NAND 64MiB 3,3V 8-bit", 	0x76, 512, 64, 0x4000, 0},
-	{"NAND 64MiB 1,8V 16-bit", 	0x46, 512, 64, 0x4000, NAND_BUSWIDTH_16},
-	{"NAND 64MiB 3,3V 16-bit", 	0x56, 512, 64, 0x4000, NAND_BUSWIDTH_16},
+	{"64MiB 1,8V 8-bit", 	0x36, 512, 64, 0x4000, 0},
+	{"64MiB 3,3V 8-bit", 	0x76, 512, 64, 0x4000, 0},
+	{"64MiB 1,8V 16-bit", 	0x46, 512, 64, 0x4000, NAND_BUSWIDTH_16},
+	{"64MiB 3,3V 16-bit", 	0x56, 512, 64, 0x4000, NAND_BUSWIDTH_16},
 
-	{"NAND 128MiB 1,8V 8-bit", 	0x78, 512, 128, 0x4000, 0},
-	{"NAND 128MiB 3,3V 8-bit", 	0x79, 512, 128, 0x4000, 0},
-	{"NAND 128MiB 1,8V 16-bit", 	0x72, 512, 128, 0x4000, NAND_BUSWIDTH_16},
-	{"NAND 128MiB 3,3V 16-bit", 	0x74, 512, 128, 0x4000, NAND_BUSWIDTH_16},
+	{"128MiB 1,8V 8-bit", 	0x78, 512, 128, 0x4000, 0},
+	{"128MiB 3,3V 8-bit", 	0x79, 512, 128, 0x4000, 0},
+	{"128MiB 1,8V 16-bit", 	0x72, 512, 128, 0x4000, NAND_BUSWIDTH_16},
+	{"128MiB 3,3V 16-bit", 	0x74, 512, 128, 0x4000, NAND_BUSWIDTH_16},
 
-	{"NAND 256MiB 3,3V 8-bit", 	0x71, 512, 256, 0x4000, 0},
+	{"256MiB 3,3V 8-bit", 	0x71, 512, 256, 0x4000, 0},
 
-	{"NAND 512MiB 3,3V 8-bit", 	0xDC, 512, 512, 0x4000, 0},
+#if 0
+	{"512MiB 3,3V 8-bit", 	0xDC, 512, 512, 0x4000, 0},
+#endif
 
 	/* These are the new chips with large page size. The pagesize
 	* and the erasesize is determined from the extended id bytes
 	*/
 	/* 1 Gigabit */
-	{"NAND 128MiB 1,8V 8-bit", 	0xA1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 128MiB 3,3V 8-bit", 	0xF1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 128MiB 1,8V 16-bit", 	0xB1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
-	{"NAND 128MiB 3,3V 16-bit", 	0xC1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"128MiB 1,8V 8-bit", 	0xA1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"128MiB 3,3V 8-bit", 	0xF1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"128MiB 1,8V 16-bit", 	0xB1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"128MiB 3,3V 16-bit", 	0xC1, 0, 128, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
 
 	/* 2 Gigabit */
-	{"NAND 256MiB 1,8V 8-bit", 	0xAA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 256MiB 3,3V 8-bit", 	0xDA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 256MiB 1,8V 16-bit", 	0xBA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
-	{"NAND 256MiB 3,3V 16-bit", 	0xCA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"256MiB 1,8V 8-bit", 	0xAA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"256MiB 3,3V 8-bit", 	0xDA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"256MiB 1,8V 16-bit", 	0xBA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"256MiB 3,3V 16-bit", 	0xCA, 0, 256, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
 
 	/* 4 Gigabit */
-	{"NAND 512MiB 1,8V 8-bit", 	0xAC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 512MiB 3,3V 8-bit", 	0xDC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 512MiB 1,8V 16-bit", 	0xBC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
-	{"NAND 512MiB 3,3V 16-bit", 	0xCC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"512MiB 1,8V 8-bit", 	0xAC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"512MiB 3,3V 8-bit", 	0xDC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"512MiB 1,8V 16-bit", 	0xBC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"512MiB 3,3V 16-bit", 	0xCC, 0, 512, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
 
 	/* 8 Gigabit */
-	{"NAND 1GiB 1,8V 8-bit", 	0xA3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 1GiB 3,3V 8-bit", 	0xD3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 1GiB 1,8V 16-bit", 	0xB3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
-	{"NAND 1GiB 3,3V 16-bit", 	0xC3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"1GiB 1,8V 8-bit", 	0xA3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"1GiB 3,3V 8-bit", 	0xD3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"1GiB 1,8V 16-bit", 	0xB3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"1GiB 3,3V 16-bit", 	0xC3, 0, 1024, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
 
 	/* 16 Gigabit */
-	{"NAND 2GiB 1,8V 8-bit", 	0xA5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 2GiB 3,3V 8-bit", 	0xD5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
-	{"NAND 2GiB 1,8V 16-bit", 	0xB5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
-	{"NAND 2GiB 3,3V 16-bit", 	0xC5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"2GiB 1,8V 8-bit", 	0xA5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"2GiB 3,3V 8-bit", 	0xD5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_NO_AUTOINCR},
+	{"2GiB 1,8V 16-bit", 	0xB5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
+	{"2GiB 3,3V 16-bit", 	0xC5, 0, 2048, 0, NAND_SAMSUNG_LP_OPTIONS | NAND_BUSWIDTH_16 | NAND_NO_AUTOINCR},
 
 	/* Renesas AND 1 Gigabit. Those chips do not support extended id and have a strange page/block layout !
 	 * The chosen minimum erasesize is 4 * 2 * 2048 = 16384 Byte, as those chips have an array of 4 page planes
@@ -123,6 +127,7 @@
 	{NAND_MFR_NATIONAL, "National"},
 	{NAND_MFR_RENESAS, "Renesas"},
 	{NAND_MFR_STMICRO, "ST Micro"},
+	{NAND_MFR_HYNIX, "Hynix"},
 	{0x0, "Unknown"}
 };
 #endif

===================================================================
--- u-boot-1.2.0/drivers/nand/nand_util.c	(revision 2338)
+++ u-boot-1.2.0/drivers/nand/nand_util.c	(revision 3056)
@@ -48,6 +48,11 @@
 #define cpu_to_je16(x) (x)
 #define cpu_to_je32(x) (x)
 
+#define DELTA_PERCENT_MIN_READING	(10)
+#define DELTA_PERCENT_MIN_WRITING	(10)
+#define DELTA_PERCENT_MIN_ERASING	(10)
+
+
 /*****************************************************************************/
 static int nand_block_bad_scrub(struct mtd_info *mtd, loff_t ofs, int getchip)
 {
@@ -75,7 +80,7 @@
 	int isNAND;
 	int bbtest = 1;
 	int result;
-	int percent_complete = -1;
+	int percent_complete = 0;
 	int (*nand_block_bad_old)(struct mtd_info *, loff_t, int) = NULL;
 	const char *mtd_device = meminfo->name;
 
@@ -217,14 +222,14 @@
 			 * steps to reduce the number of messages printed
 			 * on (slow) serial consoles
 			 */
-			if (percent != percent_complete) {
+			if ((percent - percent_complete) >= DELTA_PERCENT_MIN_ERASING) {
 				percent_complete = percent;
 
-				printf("\rErasing at 0x%x -- %3d%% complete.",
+				printf("\rErasing at 0x%08x -- %3d%% complete",
 				       erase.addr, percent);
 
 				if (opts->jffs2 && result == 0)
-					printf(" Cleanmarker written at 0x%x.",
+					printf(", cleanmarker written at 0x%08x",
 					       erase.addr);
 			}
 		}
@@ -242,8 +247,8 @@
 	return 0;
 }
 
-#define MAX_PAGE_SIZE	2048
-#define MAX_OOB_SIZE	64
+#define MAX_PAGE_SIZE	4096
+#define MAX_OOB_SIZE	128
 
 /*
  * buffer array used for writing data
@@ -291,7 +296,7 @@
 	loff_t offs;
 	int readlen;
 	int oobinfochanged = 0;
-	int percent_complete = -1;
+	int percent_complete = 0;
 	struct nand_oobinfo old_oobinfo;
 	ulong mtdoffset = opts->offset;
 	ulong erasesize_blockalign;
@@ -314,9 +319,9 @@
 
 	/* make sure device page sizes are valid */
 	if (!(meminfo->oobsize == 16 && meminfo->oobblock == 512)
-	    && !(meminfo->oobsize == 8 && meminfo->oobblock == 256)
-	    && !(meminfo->oobsize == 64 && meminfo->oobblock == 2048)) {
-		printf("Unknown flash (not normal NAND)\n");
+	    && !(meminfo->oobsize == 64 && meminfo->oobblock == 2048)
+	    && !(meminfo->oobsize == 128 && meminfo->oobblock == 4096)) {
+		printf("%s: Unknown flash (not normal NAND)\n", __FUNCTION__);
 		return -1;
 	}
 
@@ -483,11 +488,11 @@
 			 * steps to reduce the number of messages printed
 			 * on (slow) serial consoles
 			 */
-			if (percent != percent_complete) {
-				printf("\rWriting data at 0x%x "
-				       "-- %3d%% complete.",
+			if ((percent - percent_complete) >= DELTA_PERCENT_MIN_WRITING) {
+				percent_complete = percent;
+				printf("\rWriting data at 0x%08x "
+				       "-- %3d%% complete",
 				       mtdoffset, percent);
-				percent_complete = percent;
 			}
 		}
 
@@ -526,7 +531,7 @@
 	int pagelen;
 	int baderaseblock;
 	int blockstart = -1;
-	int percent_complete = -1;
+	int percent_complete = 0;
 	loff_t offs;
 	size_t readlen;
 	ulong mtdoffset = opts->offset;
@@ -535,9 +540,9 @@
 
 	/* make sure device page sizes are valid */
 	if (!(meminfo->oobsize == 16 && meminfo->oobblock == 512)
-	    && !(meminfo->oobsize == 8 && meminfo->oobblock == 256)
-	    && !(meminfo->oobsize == 64 && meminfo->oobblock == 2048)) {
-		printf("Unknown flash (not normal NAND)\n");
+	    && !(meminfo->oobsize == 64 && meminfo->oobblock == 2048)
+	    && !(meminfo->oobsize == 128 && meminfo->oobblock == 4096)) {
+		printf("%s: Unknown flash (not normal NAND)\n", __FUNCTION__);
 		return -1;
 	}
 
@@ -659,12 +664,11 @@
 			 * steps to reduce the number of messages printed
 			 * on (slow) serial consoles
 			 */
-			if (percent != percent_complete) {
-			if (!opts->quiet)
-				printf("\rReading data from 0x%x "
-				       "-- %3d%% complete.",
+			if ((percent - percent_complete) >= DELTA_PERCENT_MIN_READING) {
+				percent_complete = percent;
+				printf("\rReading data from 0x%08x "
+				       "-- %3d%% complete",
 				       mtdoffset, percent);
-				percent_complete = percent;
 			}
 		}
 

===================================================================
--- u-boot-1.2.0/drivers/smc91111.c	(revision 2338)
+++ u-boot-1.2.0/drivers/smc91111.c	(revision 2339)
@@ -138,8 +138,14 @@
 #define SMC_DEV_NAME "SMC91111"
 #define SMC_PHY_ADDR 0x0000
 #define SMC_ALLOC_MAX_TRY 5
-#define SMC_TX_TIMEOUT 30
 
+/*
+   Warning: (SMC_TX_TIMEOUT * CFG_HZ) must be < ((unsigned long) -1)
+   30 seconds is too long on some systems (e.g. MIPS cores above approx 286 MHz)
+   20 seconds is too long for MIPS cores above approx 429 MHz.
+*/
+#define SMC_TX_TIMEOUT 20
+
 #define SMC_PHY_CLOCK_DELAY 1000
 
 #define ETH_ZLEN 60

===================================================================
--- u-boot-1.2.0/examples/Makefile	(revision 2338)
+++ u-boot-1.2.0/examples/Makefile	(revision 2339)
@@ -34,8 +34,12 @@
 endif
 
 ifeq ($(ARCH),mips)
+ifeq "$(_TMTGTENDIAN)" "el"
+LOAD_ADDR = 0x80200000 -T mipsel.lds
+else
 LOAD_ADDR = 0x80200000 -T mips.lds
 endif
+endif
 
 ifeq ($(ARCH),nios)
 LOAD_ADDR = 0x00800000 -L $(gcclibdir)/m32 -T nios.lds
@@ -161,11 +165,11 @@
 			-L$(gcclibdir) -lgcc
 
 $(SREC):
-$(obj)%.srec:	$(obj)%
+$(obj)%.srec:	$(obj)%.o
 		$(OBJCOPY) -O srec $< $@ 2>/dev/null
 
 $(BIN):
-$(obj)%.bin:	$(obj)%
+$(obj)%.bin:	$(obj)%.o
 		$(OBJCOPY) -O binary $< $@ 2>/dev/null
 
 #########################################################################

===================================================================
--- u-boot-1.2.0/fs/cramfs/cramfs.c	(revision 2338)
+++ u-boot-1.2.0/fs/cramfs/cramfs.c	(revision 2763)
@@ -27,7 +27,7 @@
 #include <common.h>
 #include <malloc.h>
 
-#if (CONFIG_COMMANDS & CFG_CMD_JFFS2)
+#if (CONFIG_COMMANDS & CFG_CMD_JFFS2) && ! defined (CFG_NO_FS_ACCESS)
 
 #include <asm/byteorder.h>
 #include <linux/stat.h>

===================================================================
--- u-boot-1.2.0/include/asm-mips/addrspace.h	(revision 2338)
+++ u-boot-1.2.0/include/asm-mips/addrspace.h	(revision 2339)
@@ -41,18 +41,6 @@
 #endif
 
 /*
- * Returns the uncached address of a sdram address
- */
-#ifndef __ASSEMBLY__
-#if defined(CONFIG_AU1X00) || defined(CONFIG_TB0229)
-/* We use a 36 bit physical address map here and
-   cannot access physical memory directly from core */
-#define UNCACHED_SDRAM(a) (((unsigned long)(a)) | 0x20000000)
-#else	/* !CONFIG_AU1X00 */
-#define UNCACHED_SDRAM(a) PHYSADDR(a)
-#endif	/* CONFIG_AU1X00 */
-#endif	/* __ASSEMBLY__ */
-/*
  * Map an address to a certain kernel segment
  */
 #ifndef __ASSEMBLY__
@@ -68,6 +56,21 @@
 #endif
 
 /*
+ * Returns the uncached address of a sdram address
+ */
+#ifndef __ASSEMBLY__
+#if defined(CONFIG_AU1X00) || defined(CONFIG_TB0229)
+/* We use a 36 bit physical address map here and
+   cannot access physical memory directly from core */
+#define UNCACHED_SDRAM(a) (((unsigned long)(a)) | 0x20000000)
+#elif defined(CONFIG_SOC_PNX833X)
+#define UNCACHED_SDRAM(a) KSEG1ADDR(a)
+#else /* !CONFIG_AU1X00 */
+#define UNCACHED_SDRAM(a) PHYSADDR(a)
+#endif	/* CONFIG_AU1X00 */
+#endif	/* __ASSEMBLY__ */
+
+/*
  * Memory segments (64bit kernel mode addresses)
  */
 #define XKUSEG			0x0000000000000000

===================================================================
--- u-boot-1.2.0/include/asm-mips/global_data.h	(revision 2338)
+++ u-boot-1.2.0/include/asm-mips/global_data.h	(revision 3572)
@@ -45,6 +45,7 @@
 	unsigned long	reloc_off;	/* Relocation Offset */
 	unsigned long	env_addr;	/* Address  of Environment struct */
 	unsigned long	env_valid;	/* Checksum of Environment valid? */
+	unsigned long	addr_sp;	/* initial top of stack */
 	void		**jt;		/* jump table */
 } gd_t;
 

===================================================================
--- u-boot-1.2.0/include/asm-mips/mipsregs.h	(revision 2338)
+++ u-boot-1.2.0/include/asm-mips/mipsregs.h	(revision 2339)
@@ -48,6 +48,7 @@
 #define CP0_CAUSE $13
 #define CP0_EPC $14
 #define CP0_PRID $15
+#define CP0_EBASE $15,1
 #define CP0_CONFIG $16
 #define CP0_LLADDR $17
 #define CP0_WATCHLO $18

===================================================================
--- u-boot-1.2.0/include/common.h	(revision 2338)
+++ u-boot-1.2.0/include/common.h	(revision 3553)
@@ -225,6 +225,7 @@
 char	*getenv	     (char *);
 int	getenv_r     (char *name, char *buf, unsigned len);
 int	saveenv	     (void);
+int	clearenv     (void);
 #ifdef CONFIG_PPC		/* ARM version to be fixed! */
 void inline setenv   (char *, char *);
 #else
@@ -421,6 +422,7 @@
 void	serial_setbrg (void);
 void	serial_putc   (const char);
 void	serial_putc_raw(const char);
+void	serial_puthex32(unsigned int v);
 void	serial_puts   (const char *);
 int	serial_getc   (void);
 int	serial_tstc   (void);

===================================================================
--- u-boot-1.2.0/include/dataflash.h	(revision 2338)
+++ u-boot-1.2.0/include/dataflash.h	(revision 2339)
@@ -34,7 +34,9 @@
 #define _DataFlash_h
 
 
+#if !defined( CONFIG_STB220t3 )
 #include <asm/arch/hardware.h>
+#endif
 #include "config.h"
 
 /*number of protected area*/

===================================================================
--- u-boot-1.2.0/include/environment.h	(revision 2338)
+++ u-boot-1.2.0/include/environment.h	(revision 4572)
@@ -84,17 +84,38 @@
 # endif
 #endif /* CFG_ENV_IS_IN_NAND */
 
+#if defined (CFG_ENV_ACTIVE_COUNT)
+#define ENV_HEADER_ACTIVE_COUNT_SIZE	sizeof(unsigned long)
+#else
+#define ENV_HEADER_ACTIVE_COUNT_SIZE	0
+#endif
 
-#ifdef CFG_REDUNDAND_ENVIRONMENT
-# define ENV_HEADER_SIZE	(sizeof(unsigned long) + 1)
+#define ENV_HEADER_CRC_SIZE		sizeof(unsigned long)
+
+#if defined (CFG_REDUNDAND_ENVIRONMENT)
+#define ENV_HEADER_FLAGS_SIZE		sizeof(unsigned char)
 #else
-# define ENV_HEADER_SIZE	(sizeof(unsigned long))
+#define ENV_HEADER_FLAGS_SIZE		0
 #endif
 
+#define ENV_HEADER_SIZE	(ENV_HEADER_ACTIVE_COUNT_SIZE + ENV_HEADER_CRC_SIZE + ENV_HEADER_FLAGS_SIZE)
 
-#define ENV_SIZE (CFG_ENV_SIZE - ENV_HEADER_SIZE)
+#if defined (CFG_ENV_ACTIVE_SIZE)
+  #if defined (CFG_ENV_IS_IN_FLASH)
+    #error "CFG_ENV_ACTIVE_SIZE not yet supported with CFG_ENV_IS_IN_FLASH"
+  #endif
+  #if (CFG_ENV_ACTIVE_SIZE > CFG_ENV_SIZE)
+    #error "CFG_ENV_ACTIVE_SIZE must be <= CFG_ENV_SIZE"
+  #endif
+  #define ENV_SIZE (CFG_ENV_ACTIVE_SIZE - ENV_HEADER_SIZE)
+#else
+  #define ENV_SIZE (CFG_ENV_SIZE - ENV_HEADER_SIZE)
+#endif
 
 typedef	struct environment_s {
+#ifdef CFG_ENV_ACTIVE_COUNT
+	unsigned long	active_cnt;	/* active boot retry count...	*/
+#endif
 	unsigned long	crc;		/* CRC32 over data bytes	*/
 #ifdef CFG_REDUNDAND_ENVIRONMENT
 	unsigned char	flags;		/* active/obsolete flags	*/

===================================================================
--- u-boot-1.2.0/include/linux/mtd/mtd-abi.h	(revision 2338)
+++ u-boot-1.2.0/include/linux/mtd/mtd-abi.h	(revision 3050)
@@ -93,7 +93,7 @@
 	uint32_t useecc;
 	uint32_t eccbytes;
 	uint32_t oobfree[8][2];
-	uint32_t eccpos[32];
+	uint32_t eccpos[48];
 };
 
 #endif /* __MTD_ABI_H__ */

===================================================================
--- u-boot-1.2.0/include/linux/mtd/nand.h	(revision 2338)
+++ u-boot-1.2.0/include/linux/mtd/nand.h	(revision 3296)
@@ -64,6 +64,7 @@
 /* Read raw data from the device without ECC */
 extern int nand_read_raw (struct mtd_info *mtd, uint8_t *buf, loff_t from, size_t len, size_t ooblen);
 
+extern unsigned int nand_debug_enable;
 
 /* This constant declares the max. oobsize / page, which
  * is supported now. If you add a chip with bigger oobsize/page
@@ -348,6 +349,7 @@
 #define NAND_MFR_NATIONAL	0x8f
 #define NAND_MFR_RENESAS	0x07
 #define NAND_MFR_STMICRO	0x20
+#define NAND_MFR_HYNIX		0xAD
 
 /**
  * struct nand_flash_dev - NAND Flash Device ID Structure

===================================================================
--- u-boot-1.2.0/include/linux/mtd/nand_ids.h	(revision 2338)
+++ u-boot-1.2.0/include/linux/mtd/nand_ids.h	(revision 2339)
@@ -32,29 +32,9 @@
 #error This module is for the legacy NAND support
 #endif
 
-static struct nand_flash_dev nand_flash_ids[] = {
-	{"Toshiba TC5816BDC",     NAND_MFR_TOSHIBA, 0x64, 21, 1, 2, 0x1000, 0},
-	{"Toshiba TC5832DC",      NAND_MFR_TOSHIBA, 0x6b, 22, 0, 2, 0x2000, 0},
-	{"Toshiba TH58V128DC",    NAND_MFR_TOSHIBA, 0x73, 24, 0, 2, 0x4000, 0},
-	{"Toshiba TC58256FT/DC",  NAND_MFR_TOSHIBA, 0x75, 25, 0, 2, 0x4000, 0},
-	{"Toshiba TH58512FT",     NAND_MFR_TOSHIBA, 0x76, 26, 0, 3, 0x4000, 0},
-	{"Toshiba TC58V32DC",     NAND_MFR_TOSHIBA, 0xe5, 22, 0, 2, 0x2000, 0},
-	{"Toshiba TC58V64AFT/DC", NAND_MFR_TOSHIBA, 0xe6, 23, 0, 2, 0x2000, 0},
-	{"Toshiba TC58V16BDC",    NAND_MFR_TOSHIBA, 0xea, 21, 1, 2, 0x1000, 0},
-	{"Toshiba TH58100FT",     NAND_MFR_TOSHIBA, 0x79, 27, 0, 3, 0x4000, 0},
-	{"Samsung KM29N16000",    NAND_MFR_SAMSUNG, 0x64, 21, 1, 2, 0x1000, 0},
-	{"Samsung unknown 4Mb",   NAND_MFR_SAMSUNG, 0x6b, 22, 0, 2, 0x2000, 0},
-	{"Samsung KM29U128T",     NAND_MFR_SAMSUNG, 0x73, 24, 0, 2, 0x4000, 0},
-	{"Samsung KM29U256T",     NAND_MFR_SAMSUNG, 0x75, 25, 0, 2, 0x4000, 0},
-	{"Samsung unknown 64Mb",  NAND_MFR_SAMSUNG, 0x76, 26, 0, 3, 0x4000, 0},
-	{"Samsung KM29W32000",    NAND_MFR_SAMSUNG, 0xe3, 22, 0, 2, 0x2000, 0},
-	{"Samsung unknown 4Mb",   NAND_MFR_SAMSUNG, 0xe5, 22, 0, 2, 0x2000, 0},
-	{"Samsung KM29U64000",    NAND_MFR_SAMSUNG, 0xe6, 23, 0, 2, 0x2000, 0},
-	{"Samsung KM29W16000",    NAND_MFR_SAMSUNG, 0xea, 21, 1, 2, 0x1000, 0},
-	{"Samsung K9F5616Q0C",    NAND_MFR_SAMSUNG, 0x45, 25, 0, 2, 0x4000, 1},
-	{"Samsung K9K1216Q0C",    NAND_MFR_SAMSUNG, 0x46, 26, 0, 3, 0x4000, 1},
-	{"Samsung K9F1G08U0M",    NAND_MFR_SAMSUNG, 0xf1, 27, 0, 2, 0, 0},
-	{NULL,}
-};
+extern struct nand_flash_dev nand_flash_ids[];
+/*extern struct nand_flash_dev *nand_flash_ids;*/
 
+extern void relocate_nand_flash_ids(unsigned long offset);
+
 #endif /* __LINUX_MTD_NAND_IDS_H */

===================================================================
--- u-boot-1.2.0/include/version.h	(revision 2338)
+++ u-boot-1.2.0/include/version.h	(revision 2339)
@@ -23,6 +23,15 @@
 
 #ifndef	__VERSION_H__
 #define	__VERSION_H__
+#ifdef GENERATED_CONFIG
+#ifndef STR
+#define __STR(x) #x
+#define STR(x) __STR(x)
+#endif
+#include STR(GENERATED_CONFIG.h)
+#else
+#define CONFIG_VERSION ""
+#endif
 
 #include "version_autogenerated.h"
 

===================================================================
--- u-boot-1.2.0/lib_generic/Makefile	(revision 2338)
+++ u-boot-1.2.0/lib_generic/Makefile	(revision 3564)
@@ -30,6 +30,8 @@
 	  crc32.o ctype.o display_options.o ldiv.o \
 	  string.o vsprintf.o zlib.o
 
+COBJS	+= aimage_uboot.o bl_image_db.o sha1.o
+
 SRCS 	:= $(COBJS:.o=.c)
 OBJS	:= $(addprefix $(obj),$(COBJS))
 

===================================================================
--- u-boot-1.2.0/lib_generic/crc32.c	(revision 2338)
+++ u-boot-1.2.0/lib_generic/crc32.c	(revision 4526)
@@ -150,30 +150,7 @@
 #define DO8(buf)  DO4(buf); DO4(buf);
 
 /* ========================================================================= */
-uLong ZEXPORT crc32(crc, buf, len)
-    uLong crc;
-    const Bytef *buf;
-    uInt len;
-{
-#ifdef DYNAMIC_CRC_TABLE
-    if (crc_table_empty)
-      make_crc_table();
-#endif
-    crc = crc ^ 0xffffffffL;
-    while (len >= 8)
-    {
-      DO8(buf);
-      len -= 8;
-    }
-    if (len) do {
-      DO1(buf);
-    } while (--len);
-    return crc ^ 0xffffffffL;
-}
 
-#if (CONFIG_COMMANDS & CFG_CMD_JFFS2) || \
-	((CONFIG_COMMANDS & CFG_CMD_NAND) && !defined(CFG_NAND_LEGACY))
-
 /* No ones complement version. JFFS2 (and other things ?)
  * don't use ones compliment in their CRC calculations.
  */
@@ -195,4 +172,11 @@
     return crc;
 }
 
-#endif	/* CFG_CMD_JFFS2 */
+uLong ZEXPORT crc32(uLong crc, const Bytef *buf, uInt len)
+{
+    crc = crc ^ 0xffffffffL;
+    crc = crc32_no_comp (crc, buf, len);
+    crc = crc ^ 0xffffffffL;
+    return crc;
+}
+

===================================================================
--- u-boot-1.2.0/lib_generic/display_options.c	(revision 2338)
+++ u-boot-1.2.0/lib_generic/display_options.c	(revision 3554)
@@ -59,7 +59,7 @@
 		n += 1;
 	}
 
-	printf ("%2ld", n);
+	printf ("%ld", n);
 	if (m) {
 		printf (".%ld", m);
 	}

===================================================================
--- u-boot-1.2.0/lib_generic/string.c	(revision 2338)
+++ u-boot-1.2.0/lib_generic/string.c	(revision 4501)
@@ -403,12 +403,48 @@
  */
 void * memset(void * s,int c,size_t count)
 {
+#if 0
 	char *xs = (char *) s;
 
 	while (count--)
 		*xs++ = c;
 
 	return s;
+#else
+	unsigned int c32;
+	unsigned long addr = (unsigned long) s;
+
+	c32 = (c & 0xFF);
+	c32 |= (c32 << 8);
+	c32 |= (c32 << 16);
+
+	while ((addr % 16) && count) {
+		*((unsigned char *) addr) = c32;
+		count--;
+		addr++;
+	}
+
+	while (count >= 32) {
+		*((unsigned int *) (addr + 0)) = c32;
+		*((unsigned int *) (addr + 4)) = c32;
+		*((unsigned int *) (addr + 8)) = c32;
+		*((unsigned int *) (addr + 12)) = c32;
+		*((unsigned int *) (addr + 16)) = c32;
+		*((unsigned int *) (addr + 20)) = c32;
+		*((unsigned int *) (addr + 24)) = c32;
+		*((unsigned int *) (addr + 28)) = c32;
+		count -= 32;
+		addr += 32;
+	}
+
+	while (count) {
+		*((unsigned char *) addr) = c32;
+		count--;
+		addr++;
+	}
+
+	return s;
+#endif
 }
 #endif
 
@@ -427,12 +463,7 @@
  */
 char * bcopy(const char * src, char * dest, int count)
 {
-	char *tmp = dest;
-
-	while (count--)
-		*tmp++ = *src++;
-
-	return dest;
+	return memcpy (dest, src, count);
 }
 #endif
 
@@ -448,12 +479,61 @@
  */
 void * memcpy(void * dest,const void *src,size_t count)
 {
+#if 0
 	char *tmp = (char *) dest, *s = (char *) src;
 
 	while (count--)
 		*tmp++ = *s++;
 
 	return dest;
+#else
+
+	unsigned long d = (unsigned long) dest;
+	unsigned long s = (unsigned long) src;
+	unsigned long s_end = s + count;
+	unsigned int tmp1, tmp2, tmp3, tmp4;
+
+	while ((s % 4) && ((s_end - s) >= 1)) {
+		tmp1 = *((unsigned char *) s);
+		*((unsigned char *) d) = tmp1;
+		s++;
+		d++;
+	}
+
+	if ((d % 4) == 0) {
+		while ((s_end - s) >= 32) {
+			tmp1 = *((unsigned int *) (s + 0));
+			tmp2 = *((unsigned int *) (s + 4));
+			tmp3 = *((unsigned int *) (s + 8));
+			tmp4 = *((unsigned int *) (s + 12));
+			*((unsigned int *) (d + 0)) = tmp1;
+			*((unsigned int *) (d + 4)) = tmp2;
+			*((unsigned int *) (d + 8)) = tmp3;
+			*((unsigned int *) (d + 12)) = tmp4;
+			tmp1 = *((unsigned int *) (s + 16));
+			tmp2 = *((unsigned int *) (s + 20));
+			tmp3 = *((unsigned int *) (s + 24));
+			tmp4 = *((unsigned int *) (s + 28));
+			*((unsigned int *) (d + 16)) = tmp1;
+			*((unsigned int *) (d + 20)) = tmp2;
+			*((unsigned int *) (d + 24)) = tmp3;
+			*((unsigned int *) (d + 28)) = tmp4;
+			s += 32;
+			d += 32;
+		}
+	}
+
+	while ((s_end - s) >= 1) {
+		tmp1 = *((unsigned char *) s);
+		*((unsigned char *) d) = tmp1;
+		s++;
+		d++;
+	}
+
+	return dest;
+
+#endif
+
 }
 #endif
 

===================================================================
--- u-boot-1.2.0/lib_mips/Makefile	(revision 2338)
+++ u-boot-1.2.0/lib_mips/Makefile	(revision 2339)
@@ -25,7 +25,11 @@
 
 LIB	= $(obj)lib$(ARCH).a
 
-SOBJS	=
+#
+# Fixme: Including sha1_mips32r2.o should depend on target CPU being
+#        mips32r2 ISA capable...
+#
+SOBJS	= sha1_mips32r2.o
 
 COBJS	= board.o time.o mips_linux.o
 

===================================================================
--- u-boot-1.2.0/lib_mips/board.c	(revision 2338)
+++ u-boot-1.2.0/lib_mips/board.c	(revision 6611)
@@ -29,6 +29,14 @@
 #include <net.h>
 #include <environment.h>
 
+#if (CONFIG_COMMANDS & CFG_CMD_NAND)
+void nand_init (void);
+#endif
+
+#if defined (CONFIG_SPLASH_SCREEN)
+extern int do_splash_noargs (void);
+#endif
+
 DECLARE_GLOBAL_DATA_PTR;
 
 #if ( ((CFG_ENV_ADDR+CFG_ENV_SIZE) < CFG_MONITOR_BASE) || \
@@ -42,17 +50,17 @@
 #undef DEBUG
 
 extern int timer_init(void);
+extern int setup_miu(void);
 
-extern int incaip_set_cpuclk(void);
-
 extern ulong uboot_end_data;
 extern ulong uboot_end;
 
 ulong monitor_flash_len;
 
 const char version_string[] =
-	U_BOOT_VERSION" (" __DATE__ " - " __TIME__ ")";
+U_BOOT_VERSION" "CONFIG_VERSION" (" __DATE__ " - " __TIME__ ")";
 
+
 static char *failed = "*** failed ***\n";
 
 /*
@@ -74,9 +82,11 @@
 	mem_malloc_start = dest_addr - TOTAL_MALLOC_LEN;
 	mem_malloc_brk = mem_malloc_start;
 
+#if 0
 	memset ((void *) mem_malloc_start,
 		0,
 		mem_malloc_end - mem_malloc_start);
+#endif
 }
 
 void *sbrk (ptrdiff_t increment)
@@ -91,7 +101,6 @@
 	return ((void *) old);
 }
 
-
 static int init_func_ram (void)
 {
 #ifdef	CONFIG_BOARD_TYPES
@@ -99,7 +108,7 @@
 #else
 	int board_type = 0;	/* use dummy arg */
 #endif
-	puts ("DRAM:  ");
+	puts ("DRAM: ");
 
 	if ((gd->ram_size = initdram (board_type)) > 0) {
 		print_size (gd->ram_size, "\n");
@@ -111,28 +120,31 @@
 
 static int display_banner(void)
 {
-
-	printf ("\n\n%s\n\n", version_string);
-	return (0);
+	/*
+	   Warning: runs before relocation (ie without final stack) so printf maybe unsafe...
+	*/
+	puts ("\n\n");
+	puts (version_string);
+	puts ("\n\n");
+#ifdef BUILDNAME
+	puts ("Build name: " BUILDNAME " \n\n");
+#endif
+	return 0;
 }
 
+#ifndef CFG_NO_FLASH
 static void display_flash_config(ulong size)
 {
-	puts ("Flash: ");
+	puts ("NOR: ");
 	print_size (size, "\n");
 }
+#endif
 
-
 static int init_baudrate (void)
 {
-	char tmp[64];	/* long enough for environment variables */
-	int i = getenv_r ("baudrate", tmp, sizeof (tmp));
-
-	gd->baudrate = (i > 0)
-			? (int) simple_strtoul (tmp, NULL, 10)
-			: CONFIG_BAUDRATE;
-
-	return (0);
+	/* Don't try to read environment before relocation. */
+	gd->baudrate = CONFIG_BAUDRATE;
+	return 0;
 }
 
 
@@ -160,10 +172,10 @@
 
 init_fnc_t *init_sequence[] = {
 	timer_init,
-	env_init,		/* initialize environment */
-#ifdef CONFIG_INCA_IP
-	incaip_set_cpuclk,	/* set cpu clock according to environment variable */
+#ifdef CONFIG_STB22X
+	setup_miu,
 #endif
+	env_init,		/* initialize environment (FIXME: move this to after relocation) */
 	init_baudrate,		/* initialze baudrate settings */
 	serial_init,		/* serial communications setup */
 	console_init_f,
@@ -173,17 +185,13 @@
 	NULL,
 };
 
-
-void board_init_f(ulong bootflag)
+void board_init_f (ulong bootflag)
 {
 	gd_t gd_data, *id;
 	bd_t *bd;
 	init_fnc_t **init_fnc_ptr;
 	ulong addr, addr_sp, len = (ulong)&uboot_end - CFG_MONITOR_BASE;
 	ulong *s;
-#ifdef CONFIG_PURPLE
-	void copy_code (ulong);
-#endif
 
 	/* Pointer is writable since we allocated a register for it.
 	 */
@@ -261,6 +269,7 @@
 	*s-- = 0;
 	*s-- = 0;
 	addr_sp = (ulong)s;
+	gd->addr_sp = addr_sp;
 	debug ("Stack Pointer at: %08lx\n", addr_sp);
 
 	/*
@@ -272,13 +281,6 @@
 
 	memcpy (id, (void *)gd, sizeof (gd_t));
 
-	/* On the purple board we copy the code in a special way
-	 * in order to solve flash problems
-	 */
-#ifdef CONFIG_PURPLE
-	copy_code(addr);
-#endif
-
 	relocate_code (addr_sp, id, addr);
 
 	/* NOTREACHED - relocate_code() does not return */
@@ -296,7 +298,9 @@
 void board_init_r (gd_t *id, ulong dest_addr)
 {
 	cmd_tbl_t *cmdtp;
+#ifndef CFG_NO_FLASH
 	ulong size;
+#endif
 	extern void malloc_bin_reloc (void);
 #ifndef CFG_ENV_IS_NOWHERE
 	extern char * env_name_spec;
@@ -347,11 +351,18 @@
 	env_name_spec += gd->reloc_off;
 #endif
 
+	/* initialize malloc() area */
+	mem_malloc_init();
+	malloc_bin_reloc();
+
+#ifndef CFG_NO_FLASH
 	/* configure available FLASH banks */
 	size = flash_init();
 	display_flash_config (size);
+#endif
 
 	bd = gd->bd;
+#ifndef CFG_NO_FLASH
 	bd->bi_flashstart = CFG_FLASH_BASE;
 	bd->bi_flashsize = size;
 #if CFG_MONITOR_BASE == CFG_FLASH_BASE
@@ -359,16 +370,31 @@
 #else
 	bd->bi_flashoffset = 0;
 #endif
+#else
+	bd->bi_flashstart = 0;
+	bd->bi_flashsize = 0;
+	bd->bi_flashoffset = 0;
+#endif
 
-	/* initialize malloc() area */
-	mem_malloc_init();
-	malloc_bin_reloc();
+#if (CONFIG_COMMANDS & CFG_CMD_NAND)
+	nand_init();
+#endif
 
 	/* relocate environment function pointers etc. */
 	env_relocate();
 
 	/* board MAC address */
 	s = getenv ("ethaddr");
+#ifdef CONFIG_ETHADDR
+#ifndef __STR
+#define __STR(x) #x
+#endif
+#ifndef STR
+#define STR(x) __STR(x)
+#endif
+	if (!s)
+		s = STR(CONFIG_ETHADDR);
+#endif
 	for (i = 0; i < 6; ++i) {
 		bd->bi_enetaddr[i] = s ? simple_strtoul (s, &e, 16) : 0;
 		if (s)
@@ -412,11 +438,70 @@
 
 #if (CONFIG_COMMANDS & CFG_CMD_NET)
 #if defined(CONFIG_NET_MULTI)
-	puts ("Net:   ");
+	puts ("Net: ");
 #endif
 	eth_initialize(gd->bd);
 #endif
 
+#if (CONFIG_COMMANDS & CFG_CMD_IDE)
+	puts("IDE: ");
+	ide_init();
+#endif /* CFG_CMD_IDE */
+
+#if defined (CONFIG_STB225) && (CONFIG_STB225 == 1)
+	printf ("Board Opts:"
+#if defined (STB225_ETHERNET_OSCILLATOR)	/* if defined, eth phy has a dedicated oscillator (if not, we must output 25 MHz from PLLout pin) */
+		" EthOsc"
+#endif
+#if defined (STB225_SCART_OUTPUT_MODE)
+		" SCART"
+#endif
+#if defined (STB225_HDMI_OUTPUT_MODE)
+		" HDMI"
+#endif
+#if defined (CONFIG_SPLASH_SCREEN)
+  #if (STB225_DISPLAY_MODE == DISPLAY_MODE_NTSC)
+		" NTSC"
+  #elif (STB225_DISPLAY_MODE == DISPLAY_MODE_PAL)
+		" PAL"
+  #elif (STB225_DISPLAY_MODE == DISPLAY_MODE_480P)
+		" 480p"
+  #elif (STB225_DISPLAY_MODE == DISPLAY_MODE_576P)
+		" 576p"
+  #elif (STB225_DISPLAY_MODE == DISPLAY_MODE_720P)
+		" 720p"
+  #else
+  #error "STB225_DISPLAY_MODE not recognised"
+  #endif
+#endif
+#if ! defined (NAND_SUPPORTS_READY_SIGNAL)
+		" NO_NAND_RDY"
+#endif
+		"\n");
+#endif
+
+#if defined (CONFIG_SPLASH_SCREEN)
+	do_splash_noargs();
+#elif defined (CONFIG_STB225) && (CONFIG_STB225 == 1)
+	/* Release hardware block resets */
+	*((volatile unsigned int *) 0xb7e08004) = 0x77ffffff;
+	*((volatile unsigned int *) 0xb7e08014) = 0x0000007f;
+	udelay (20);
+
+	/* Enable i2s output clock. Must be done before HDMI setup, but
+	 * hopefully quite safe to do here even if HDMI is not enabled.
+	 */
+	*((volatile unsigned int *) 0xb7e290c4) = 0x00;
+#endif
+
+	/*
+	   timer_init() is called very early in the u-boot startup sequence and
+	   initialises the value returned by 'get_ticks()' to 0. Therefore, at
+	   this point, get_ticks() gives the number of timer ticks comsumed by
+	   u-boot driver initialisation.
+	*/
+	printf ("u-boot startup time so far: %d msec\n", (unsigned int) (get_ticks() / (get_tbclk() / 1000)));
+
 	/* main_loop() can return to retry autoboot, if so just run it again. */
 	for (;;) {
 		main_loop ();

===================================================================
--- u-boot-1.2.0/lib_mips/mips_linux.c	(revision 2338)
+++ u-boot-1.2.0/lib_mips/mips_linux.c	(revision 3694)
@@ -94,7 +94,7 @@
 		checksum = ntohl (hdr->ih_hcrc);
 		hdr->ih_hcrc = 0;
 
-		if (crc32 (0, (uchar *) data, len) != checksum) {
+		if (crc32 (0, (unsigned char *) data, len) != checksum) {
 			printf ("Bad Header Checksum\n");
 			SHOW_BOOT_PROGRESS (-11);
 			do_reset (cmdtp, flag, argc, argv);
@@ -111,7 +111,7 @@
 			ulong csum = 0;
 
 			printf ("   Verifying Checksum ... ");
-			csum = crc32 (0, (uchar *) data, len);
+			csum = crc32 (0, (unsigned char *) data, len);
 			if (csum != ntohl (hdr->ih_dcrc)) {
 				printf ("Bad Data CRC\n");
 				SHOW_BOOT_PROGRESS (-12);
@@ -210,8 +210,12 @@
 	sprintf (env_buf, "0x%X", (uint) (gd->bd->bi_flashsize));
 	linux_env_set ("flash_size", env_buf);
 
+	/* looks like we have to flush caches here - probably because
+	   of some accesses are via KSEG0, and others via KSEG1 */
+	flush_cache(gd->bd->bi_boot_params, CFG_BOOTPARAMS_LEN);
+	
 	/* we assume that the kernel is in place */
-	printf ("\nStarting kernel ...\n\n");
+	puts ("\nStarting kernel ...\n\n");
 
 	theKernel (linux_argc, linux_argv, linux_env, 0);
 }

===================================================================
--- u-boot-1.2.0/lib_mips/time.c	(revision 2338)
+++ u-boot-1.2.0/lib_mips/time.c	(revision 2339)
@@ -55,27 +55,35 @@
 	return 0;
 }
 
+#if 0
 void reset_timer(void)
 {
 	mips_count_set(0);
 }
+#endif
 
 ulong get_timer(ulong base)
 {
 	return mips_count_get() - base;
 }
 
+#if 0
 void set_timer(ulong t)
 {
 	mips_count_set(t);
 }
+#endif
 
 void udelay (unsigned long usec)
 {
 	ulong tmo;
 	ulong start = get_timer(0);
 
-	tmo = usec * (CFG_HZ / 1000000);
+#if defined (CFG_SYSCLK_MHZ)
+	tmo = usec * CFG_SYSCLK_MHZ;
+#else
+	tmo = usec * (CFG_SYSCLK_HZ / 1000000);
+#endif
 	while ((ulong)((mips_count_get() - start)) < tmo)
 		/*NOP*/;
 }
@@ -95,5 +103,5 @@
  */
 ulong get_tbclk(void)
 {
-	return CFG_HZ;
+	return CFG_SYSCLK_HZ;
 }

===================================================================
--- u-boot-1.2.0/net/eth.c	(revision 2338)
+++ u-boot-1.2.0/net/eth.c	(revision 3694)
@@ -52,6 +52,8 @@
 extern int rtl8169_initialize(bd_t*);
 extern int scc_initialize(bd_t*);
 extern int skge_initialize(bd_t*);
+extern int ip3902_initialize(bd_t*);
+extern int smsc911x_initialize(bd_t*);
 extern int tsec_initialize(bd_t*, int, char *);
 extern int npe_initialize(bd_t *);
 extern int uec_initialize(int);
@@ -255,6 +257,12 @@
 #if defined(CONFIG_RTL8169)
 	rtl8169_initialize(bis);
 #endif
+#if defined(CONFIG_IP3902)
+	ip3902_initialize(bis);
+#endif
+#if defined(CONFIG_SMSC911X)
+	smsc911x_initialize(bis);
+#endif
 
 	if (!eth_devices) {
 		puts ("No ethernet found.\n");
@@ -488,6 +496,12 @@
 #if defined(CONFIG_NETARM)
 	ns7520_miiphy_initialize(bis);
 #endif
+#if defined(CONFIG_DRIVER_SMSC911X)
+	/* Not the best option, since eth_init() will be called twice.
+	   However, this is an easy way to make ethaddr to be written
+	   to hardware even if ethernet will not be used by bootloader. */
+	eth_init(bis);
+#endif
 	return 0;
 }
 #endif

===================================================================
--- u-boot-1.2.0/net/tftp.c	(revision 2338)
+++ u-boot-1.2.0/net/tftp.c	(revision 2339)
@@ -15,7 +15,11 @@
 #if (CONFIG_COMMANDS & CFG_CMD_NET)
 
 #define WELL_KNOWN_PORT	69		/* Well known TFTP port #		*/
+#ifdef CFG_TFTP_TIMEOUT
+#define TIMEOUT		CFG_TFTP_TIMEOUT
+#else
 #define TIMEOUT		5		/* Seconds to timeout for a lost pkt	*/
+#endif
 #ifndef	CONFIG_NET_RETRY_COUNT
 # define TIMEOUT_COUNT	10		/* # of timeouts before giving up  */
 #else

