All of lore.kernel.org
 help / color / mirror / Atom feed
* [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support
@ 2013-04-11  0:45 Mike Dunn
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device Mike Dunn
                   ` (7 more replies)
  0 siblings, 8 replies; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

Hi,

This patchset adds support for the Palm Treo 680 smartphone.  I had to make some
minor tweaks to u-boot to get things working.  Most of these changes are small,
and most only touch the pxa arch.

Thanks for looking.

Changelog:
v2:
  - tabs removed in #defines in palmtreo680.h
  - use '__weak' macro in pxa_lcd
  - remove externs from function prototypes in bitrev.h
  - remove commented-out code from docg4.c
  - the CONFIG_SYS_LCD_PXA_NO_L_BIAS patch was removed; the same result
    is accomplished by re-configuring the L_BIAS gpio in the board-specific
    lcd_enable(), which runs after the driver initialization
  - userland utility for programming u-boot to flash moved to tools/palmtreo680
  - commit message for patches that add bitrev library and docg4 driver contain
    the commit and linux version for when the code was added to linux

Mike Dunn (7):
  pxa_lcd: add the ACX544AKN lcd device
  pxa_lcd: make lcd_enable() a weak pointer
  pxa27x_udc: remove call to unimplemented set_GPIO_mode()
  arm: bootm: call udc_disable()before booting linux
  lib: import bitrev library from the linux kernel
  mtd: nand: add driver for diskonchip g4 nand flash
  add support for palm treo 680 board

 CREDITS                                  |    4 +
 MAINTAINERS                              |    3 +
 arch/arm/include/asm/arch-pxa/hardware.h |   11 -
 arch/arm/include/asm/bootm.h             |    1 +
 arch/arm/lib/bootm.c                     |    1 +
 board/palmtreo680/Makefile               |   34 +
 board/palmtreo680/palmtreo680.c          |  179 +++++
 board/palmtreo680/palmtreo680_spl.lds    |   51 ++
 boards.cfg                               |    1 +
 doc/README.palmtreo680                   |  570 ++++++++++++++++
 drivers/mtd/nand/Makefile                |    2 +
 drivers/mtd/nand/docg4.c                 | 1034 ++++++++++++++++++++++++++++++
 drivers/mtd/nand/docg4_spl.c             |  221 +++++++
 drivers/usb/gadget/pxa27x_udc.c          |    4 +-
 drivers/video/pxa_lcd.c                  |   34 +-
 include/configs/palmtreo680.h            |  296 +++++++++
 include/linux/bitrev.h                   |   23 +
 include/linux/mtd/docg4.h                |  134 ++++
 lib/Makefile                             |    1 +
 lib/bitrev.c                             |   59 ++
 tools/palmtreo680/flash_u-boot.c         |  177 +++++
 21 files changed, 2827 insertions(+), 13 deletions(-)
 create mode 100644 board/palmtreo680/Makefile
 create mode 100644 board/palmtreo680/palmtreo680.c
 create mode 100644 board/palmtreo680/palmtreo680_spl.lds
 create mode 100644 doc/README.palmtreo680
 create mode 100644 drivers/mtd/nand/docg4.c
 create mode 100644 drivers/mtd/nand/docg4_spl.c
 create mode 100644 include/configs/palmtreo680.h
 create mode 100644 include/linux/bitrev.h
 create mode 100644 include/linux/mtd/docg4.h
 create mode 100644 lib/bitrev.c
 create mode 100644 tools/palmtreo680/flash_u-boot.c

-- 
1.7.8.6

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:14   ` Marek Vasut
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer Mike Dunn
                   ` (6 subsequent siblings)
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

This adds the definitions required to support the LCD device on the Palm Treo
680.

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 drivers/video/pxa_lcd.c |   32 ++++++++++++++++++++++++++++++++
 1 files changed, 32 insertions(+), 0 deletions(-)

diff --git a/drivers/video/pxa_lcd.c b/drivers/video/pxa_lcd.c
index b40ec36..d5fbe7b 100644
--- a/drivers/video/pxa_lcd.c
+++ b/drivers/video/pxa_lcd.c
@@ -248,6 +248,38 @@ vidinfo_t panel_info = {
 };
 #endif /* CONFIG_ACX517AKN */
 
+#ifdef CONFIG_ACX544AKN
+
+# define LCD_BPP	LCD_COLOR16
+
+/* you have to set lccr0 and lccr3 (including pcd) */
+# define REG_LCCR0	0x003008f9
+# define REG_LCCR3	0x04700007 /* 16bpp */
+
+vidinfo_t panel_info = {
+	.vl_col		= 320,
+	.vl_row		= 320,
+	.vl_width	= 320,
+	.vl_height	= 320,
+	.vl_clkp	= CONFIG_SYS_LOW,
+	.vl_oep		= CONFIG_SYS_LOW,
+	.vl_hsp		= CONFIG_SYS_LOW,
+	.vl_vsp		= CONFIG_SYS_LOW,
+	.vl_dp		= CONFIG_SYS_LOW,
+	.vl_bpix	= LCD_BPP,
+	.vl_lbw		= 0,
+	.vl_splt	= 0,
+	.vl_clor	= 1,
+	.vl_tft		= 1,
+	.vl_hpw		= 0x05,
+	.vl_blw		= 0x13,
+	.vl_elw		= 0x08,
+	.vl_vpw		= 0x02,
+	.vl_bfw		= 0x07,
+	.vl_efw		= 0x05,
+};
+#endif /* CONFIG_ACX544AKN */
+
 /*----------------------------------------------------------------------*/
 
 #ifdef CONFIG_LQ038J7DH53
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:15   ` Marek Vasut
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode() Mike Dunn
                   ` (5 subsequent siblings)
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

Make lcd_init() a weak pointer so that boards can overload it if necessary.  The
palmtreo680 board needs to wiggle some gpios and configure the pwm controller in
order to get the lcd and its backlight working.

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 drivers/video/pxa_lcd.c |    2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/drivers/video/pxa_lcd.c b/drivers/video/pxa_lcd.c
index d5fbe7b..5e4c685 100644
--- a/drivers/video/pxa_lcd.c
+++ b/drivers/video/pxa_lcd.c
@@ -410,7 +410,7 @@ void lcd_initcolregs (void)
 #endif /* LCD_MONOCHROME */
 
 /*----------------------------------------------------------------------*/
-void lcd_enable (void)
+__weak void lcd_enable(void)
 {
 }
 
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode()
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device Mike Dunn
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:16   ` Marek Vasut
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux Mike Dunn
                   ` (4 subsequent siblings)
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

If CONFIG_USB_DEV_PULLUP_GPIO is defined, a link error occurs because the
set_GPIO_mode() helper function is not implemented.  This function doesn't do
much except make the code a little more readable, so I just manually coded its
equivalent and removed the prototype from the header file.  It is invoked no
where else in the code.

While I was at it, I noticed that two other function prototypes in the same
header file are also neither implemented nor invoked anywhere, so I removed them
as well.

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 arch/arm/include/asm/arch-pxa/hardware.h |   11 -----------
 drivers/usb/gadget/pxa27x_udc.c          |    4 +++-
 2 files changed, 3 insertions(+), 12 deletions(-)

diff --git a/arch/arm/include/asm/arch-pxa/hardware.h b/arch/arm/include/asm/arch-pxa/hardware.h
index 44b800f..2397bce 100644
--- a/arch/arm/include/asm/arch-pxa/hardware.h
+++ b/arch/arm/include/asm/arch-pxa/hardware.h
@@ -77,17 +77,6 @@
 #define GPIO_FALLING_EDGE	1
 #define GPIO_RISING_EDGE	2
 #define GPIO_BOTH_EDGES		3
-extern void set_GPIO_IRQ_edge( int gpio_nr, int edge_mask );
-
-/*
- * Handy routine to set GPIO alternate functions
- */
-extern void set_GPIO_mode( int gpio_mode );
-
-/*
- * return current lclk frequency in units of 10kHz
- */
-extern unsigned int get_lclk_frequency_10khz(void);
 
 #endif
 
diff --git a/drivers/usb/gadget/pxa27x_udc.c b/drivers/usb/gadget/pxa27x_udc.c
index 4c00081..71cc0f2 100644
--- a/drivers/usb/gadget/pxa27x_udc.c
+++ b/drivers/usb/gadget/pxa27x_udc.c
@@ -610,7 +610,9 @@ void udc_connect(void)
 
 #ifdef CONFIG_USB_DEV_PULLUP_GPIO
 	/* Turn on the USB connection by enabling the pullup resistor */
-	set_GPIO_mode(CONFIG_USB_DEV_PULLUP_GPIO | GPIO_OUT);
+	writel(readl(GPDR(CONFIG_USB_DEV_PULLUP_GPIO))
+		     | GPIO_bit(CONFIG_USB_DEV_PULLUP_GPIO),
+	       GPDR(CONFIG_USB_DEV_PULLUP_GPIO));
 	writel(GPIO_bit(CONFIG_USB_DEV_PULLUP_GPIO), GPSR(CONFIG_USB_DEV_PULLUP_GPIO));
 #else
 	/* Host port 2 transceiver D+ pull up enable */
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
                   ` (2 preceding siblings ...)
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode() Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:18   ` Marek Vasut
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel Mike Dunn
                   ` (3 subsequent siblings)
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

On the pxa270, if the udc device is not disabled before jumping to linux, the
device fails to initialize in linux because it was left in a running state, and
the linux driver assumes that it is in a disabled state.

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---

Arguably, this is a bug in the linux driver, but it seemed pretty simple and
benign to just disable it in u-boot.  I'll also send a patch to upstream kernel
to fix its driver.

 arch/arm/include/asm/bootm.h |    1 +
 arch/arm/lib/bootm.c         |    1 +
 2 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/arch/arm/include/asm/bootm.h b/arch/arm/include/asm/bootm.h
index db2ff94..68189cc 100644
--- a/arch/arm/include/asm/bootm.h
+++ b/arch/arm/include/asm/bootm.h
@@ -21,6 +21,7 @@
 
 #ifdef CONFIG_USB_DEVICE
 extern void udc_disconnect(void);
+extern void udc_disable(void);
 #endif
 
 #endif
diff --git a/arch/arm/lib/bootm.c b/arch/arm/lib/bootm.c
index f3b30c5..6daa7bf 100644
--- a/arch/arm/lib/bootm.c
+++ b/arch/arm/lib/bootm.c
@@ -105,6 +105,7 @@ static void announce_and_cleanup(void)
 
 #ifdef CONFIG_USB_DEVICE
 	udc_disconnect();
+	udc_disable();
 #endif
 	cleanup_before_linux();
 }
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
                   ` (3 preceding siblings ...)
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:19   ` Marek Vasut
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash Mike Dunn
                   ` (2 subsequent siblings)
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

This patch adds the bitrev library from the linux kernel.  This is a simple
algorithm that uses an 8 bit look-up table to reverse the bits in data types of
8, 16, or 32 bit widths.  The docg4 nand flash driver uses it.

[port from linux kernel 2.6.20 commit a5cfc1ec58a07074dacb6aa8c79eff864c966d12]

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 include/linux/bitrev.h |   23 ++++++++++++++++++
 lib/Makefile           |    1 +
 lib/bitrev.c           |   59 ++++++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 83 insertions(+), 0 deletions(-)
 create mode 100644 include/linux/bitrev.h
 create mode 100644 lib/bitrev.c

diff --git a/include/linux/bitrev.h b/include/linux/bitrev.h
new file mode 100644
index 0000000..a61d956
--- /dev/null
+++ b/include/linux/bitrev.h
@@ -0,0 +1,23 @@
+/*
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ * Based on bitrev from the Linux kernel, by Akinobu Mita
+ */
+
+#ifndef _LINUX_BITREV_H
+#define _LINUX_BITREV_H
+
+#include <linux/types.h>
+
+extern u8 const byte_rev_table[256];
+
+static inline u8 bitrev8(u8 byte)
+{
+	return byte_rev_table[byte];
+}
+
+u16 bitrev16(u16 in);
+u32 bitrev32(u32 in);
+
+#endif /* _LINUX_BITREV_H */
diff --git a/lib/Makefile b/lib/Makefile
index 1bfd3ee..b4aaae9 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -55,6 +55,7 @@ COBJS-$(CONFIG_SHA1) += sha1.o
 COBJS-$(CONFIG_SHA256) += sha256.o
 COBJS-y	+= strmhz.o
 COBJS-$(CONFIG_RBTREE)	+= rbtree.o
+COBJS-$(CONFIG_BITREVERSE) += bitrev.o
 endif
 
 ifdef CONFIG_SPL_BUILD
diff --git a/lib/bitrev.c b/lib/bitrev.c
new file mode 100644
index 0000000..160021a
--- /dev/null
+++ b/lib/bitrev.c
@@ -0,0 +1,59 @@
+/*
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ * Based on bitrev from the Linux kernel, by Akinobu Mita
+ */
+
+
+#include <linux/types.h>
+#include <linux/bitrev.h>
+
+const u8 byte_rev_table[256] = {
+	0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0,
+	0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0,
+	0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8,
+	0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8,
+	0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4,
+	0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4,
+	0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec,
+	0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc,
+	0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2,
+	0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2,
+	0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea,
+	0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa,
+	0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6,
+	0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6,
+	0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee,
+	0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe,
+	0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1,
+	0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1,
+	0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9,
+	0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9,
+	0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5,
+	0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5,
+	0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed,
+	0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd,
+	0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3,
+	0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3,
+	0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb,
+	0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb,
+	0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7,
+	0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7,
+	0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef,
+	0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff,
+};
+
+u16 bitrev16(u16 x)
+{
+	return (bitrev8(x & 0xff) << 8) | bitrev8(x >> 8);
+}
+
+/**
+ * bitrev32 - reverse the order of bits in a u32 value
+ * @x: value to be bit-reversed
+ */
+u32 bitrev32(u32 x)
+{
+	return (bitrev16(x & 0xffff) << 16) | bitrev16(x >> 16);
+}
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
                   ` (4 preceding siblings ...)
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:19   ` Marek Vasut
  2013-04-11 21:00   ` Scott Wood
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board Mike Dunn
  2013-04-14 17:44 ` [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Marek Vasut
  7 siblings, 2 replies; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

This patch adds a driver for the diskonchip G4 nand flash device.  It is based
on the driver from the linux kernel.

This also includes a separate SPL driver.  A separate SPL driver is used because
the device operates in a different mode (reliable mode) when loading a boot
image, and also because the storage format of the boot image is different from
normal data (pages are stored redundantly).  The SPL driver basically mimics how
a typical IPL reads data from the device.  The special operating mode and
storage format are used to compensate for the fact that the IPL does not contain
the BCH ecc decoding algorithm (due to size constraints).  Although the u-boot
SPL *could* use ecc, it operates like an IPL for the sake of simplicity and
uniformity, since the IPL and SPL share the task of loading the u-boot image.
As a side benefit, the SPL driver is very small.

[port from linux kernel 3.4 commit 570469f3bde7f71cc1ece07a18d54a05b6a8775d]

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 drivers/mtd/nand/Makefile    |    2 +
 drivers/mtd/nand/docg4.c     | 1035 ++++++++++++++++++++++++++++++++++++++++++
 drivers/mtd/nand/docg4_spl.c |  222 +++++++++
 include/linux/mtd/docg4.h    |  134 ++++++
 4 files changed, 1393 insertions(+), 0 deletions(-)
 create mode 100644 drivers/mtd/nand/docg4.c
 create mode 100644 drivers/mtd/nand/docg4_spl.c
 create mode 100644 include/linux/mtd/docg4.h

diff --git a/drivers/mtd/nand/Makefile b/drivers/mtd/nand/Makefile
index c77c0c4..1bcf43c 100644
--- a/drivers/mtd/nand/Makefile
+++ b/drivers/mtd/nand/Makefile
@@ -34,6 +34,7 @@ NORMAL_DRIVERS=y
 endif
 
 COBJS-$(CONFIG_SPL_NAND_AM33XX_BCH) += am335x_spl_bch.o
+COBJS-$(CONFIG_SPL_NAND_DOCG4) += docg4_spl.o
 COBJS-$(CONFIG_SPL_NAND_SIMPLE) += nand_spl_simple.o
 COBJS-$(CONFIG_SPL_NAND_LOAD) += nand_spl_load.o
 COBJS-$(CONFIG_SPL_NAND_ECC) += nand_ecc.o
@@ -78,6 +79,7 @@ COBJS-$(CONFIG_NAND_SPEAR) += spr_nand.o
 COBJS-$(CONFIG_TEGRA_NAND) += tegra_nand.o
 COBJS-$(CONFIG_NAND_OMAP_GPMC) += omap_gpmc.o
 COBJS-$(CONFIG_NAND_PLAT) += nand_plat.o
+COBJS-$(CONFIG_NAND_DOCG4) += docg4.o
 
 else  # minimal SPL drivers
 
diff --git a/drivers/mtd/nand/docg4.c b/drivers/mtd/nand/docg4.c
new file mode 100644
index 0000000..c5c4ee0
--- /dev/null
+++ b/drivers/mtd/nand/docg4.c
@@ -0,0 +1,1035 @@
+/*
+ * drivers/mtd/nand/docg4.c
+ *
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ * mtd nand driver for M-Systems DiskOnChip G4
+ *
+ * Tested on the Palm Treo 680.  The G4 is also present on Toshiba Portege, Asus
+ * P526, some HTC smartphones (Wizard, Prophet, ...), O2 XDA Zinc, maybe others.
+ * Should work on these as well.  Let me know!
+ *
+ * TODO:
+ *
+ *  Mechanism for management of password-protected areas
+ *
+ *  Hamming ecc when reading oob only
+ *
+ *  According to the M-Sys documentation, this device is also available in a
+ *  "dual-die" configuration having a 256MB capacity, but no mechanism for
+ *  detecting this variant is documented.  Currently this driver assumes 128MB
+ *  capacity.
+ *
+ *  Support for multiple cascaded devices ("floors").  Not sure which gadgets
+ *  contain multiple G4s in a cascaded configuration, if any.
+ *
+ */
+
+
+#include <common.h>
+#include <asm/arch/hardware.h>
+#include <asm/io.h>
+#include <asm/bitops.h>
+#include <asm/errno.h>
+#include <malloc.h>
+#include <nand.h>
+#include <linux/bch.h>
+#include <linux/bitrev.h>
+#include <linux/mtd/docg4.h>
+
+/*
+ * The device has a nop register which M-Sys claims is for the purpose of
+ * inserting precise delays.  But beware; at least some operations fail if the
+ * nop writes are replaced with a generic delay!
+ */
+static inline void write_nop(void __iomem *docptr)
+{
+	writew(0, docptr + DOC_NOP);
+}
+
+
+static int poll_status(void __iomem *docptr)
+{
+	/*
+	 * Busy-wait for the FLASHREADY bit to be set in the FLASHCONTROL
+	 * register.  Operations known to take a long time (e.g., block erase)
+	 * should sleep for a while before calling this.
+	 */
+
+	uint8_t flash_status;
+
+	/* hardware quirk requires reading twice initially */
+	flash_status = readb(docptr + DOC_FLASHCONTROL);
+
+	do {
+		flash_status = readb(docptr + DOC_FLASHCONTROL);
+	} while (!(flash_status & DOC_CTRL_FLASHREADY));
+
+	return 0;
+}
+
+static void write_addr(void __iomem *docptr, uint32_t docg4_addr)
+{
+	/* write the four address bytes packed in docg4_addr to the device */
+
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+}
+
+
+#ifdef DEBUG_DOCG4
+#define dbg(format, arg...) printf("DEBUG: " format, ##arg)
+#else
+#define dbg(format, arg...) do {} while (0)
+#endif
+
+/*
+ * This is a module parameter in the linux kernel version of this driver.  It is
+ * hard-coded to 'off' for u-boot.  This driver uses oob to mark bad blocks.
+ * This can be problematic when dealing with data not intended for the mtd/nand
+ * subsystem.  For example, on boards that boot from the docg4 and use the IPL
+ * to load an spl + u-boot image, the blocks containing the image will be
+ * reported as "bad" because the oob of the first page of each block contains a
+ * magic number that the IPL looks for, which causes the badblock scan to
+ * erroneously add them to the bad block table.  To erase such a block, use
+ * u-boot's 'nand scrub'.  scrub is safe for the docg4.  The device does have a
+ * factory bad block table, but it is read-only, and is used in conjunction with
+ * oob bad block markers that are written by mtd/nand when a block is deemed to
+ * be bad.  To read data from "bad" blocks, use 'read.raw'.  Unfortunately,
+ * read.raw does not use ecc, which would still work fine on such misidentified
+ * bad blocks.  TODO: u-boot nand utilities need the ability to ignore bad
+ * blocks.
+ */
+static const int ignore_badblocks; /* remains false */
+
+struct docg4_priv {
+	int status;
+	struct {
+		unsigned int command;
+		int column;
+		int page;
+	} last_command;
+	uint8_t oob_buf[16];
+	uint8_t ecc_buf[7];
+	int oob_page;
+	struct bch_control *bch;
+};
+/*
+ * Oob bytes 0 - 6 are available to the user.
+ * Byte 7 is hamming ecc for first 7 bytes.  Bytes 8 - 14 are hw-generated ecc.
+ * Byte 15 (the last) is used by the driver as a "page written" flag.
+ */
+static struct nand_ecclayout docg4_oobinfo = {
+	.eccbytes = 9,
+	.eccpos = {7, 8, 9, 10, 11, 12, 13, 14, 15},
+	.oobavail = 7,
+	.oobfree = { {0, 7} }
+};
+
+static void reset(void __iomem *docptr)
+{
+	/* full device reset */
+
+	writew(DOC_ASICMODE_RESET | DOC_ASICMODE_MDWREN, docptr + DOC_ASICMODE);
+	writew(~(DOC_ASICMODE_RESET | DOC_ASICMODE_MDWREN),
+	       docptr + DOC_ASICMODECONFIRM);
+	write_nop(docptr);
+
+	writew(DOC_ASICMODE_NORMAL | DOC_ASICMODE_MDWREN,
+	       docptr + DOC_ASICMODE);
+	writew(~(DOC_ASICMODE_NORMAL | DOC_ASICMODE_MDWREN),
+	       docptr + DOC_ASICMODECONFIRM);
+
+	writew(DOC_ECCCONF1_ECC_ENABLE, docptr + DOC_ECCCONF1);
+
+	poll_status(docptr);
+}
+
+static void docg4_select_chip(struct mtd_info *mtd, int chip)
+{
+	/*
+	 * Select among multiple cascaded chips ("floors").  Multiple floors are
+	 * not yet supported, so the only valid non-negative value is 0.
+	 */
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+
+	if (chip < 0)
+		return;		/* deselected */
+
+	if (chip > 0)
+		printf("multiple floors currently unsupported\n");
+
+	writew(0, docptr + DOC_DEVICESELECT);
+}
+
+static void read_hw_ecc(void __iomem *docptr, uint8_t *ecc_buf)
+{
+	/* read the 7 hw-generated ecc bytes */
+
+	int i;
+	for (i = 0; i < 7; i++) { /* hw quirk; read twice */
+		ecc_buf[i] = readb(docptr + DOC_BCH_SYNDROM(i));
+		ecc_buf[i] = readb(docptr + DOC_BCH_SYNDROM(i));
+	}
+}
+
+static int correct_data(struct mtd_info *mtd, uint8_t *buf, int page)
+{
+	/*
+	 * Called after a page read when hardware reports bitflips.
+	 * Up to four bitflips can be corrected.
+	 */
+
+	struct nand_chip *nand = mtd->priv;
+	struct docg4_priv *doc = nand->priv;
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	int i, numerrs;
+	unsigned int errpos[4];
+	const uint8_t blank_read_hwecc[8] = {
+		0xcf, 0x72, 0xfc, 0x1b, 0xa9, 0xc7, 0xb9, 0 };
+
+	read_hw_ecc(docptr, doc->ecc_buf); /* read 7 hw-generated ecc bytes */
+
+	/* check if read error is due to a blank page */
+	if (!memcmp(doc->ecc_buf, blank_read_hwecc, 7))
+		return 0;	/* yes */
+
+	/* skip additional check of "written flag" if ignore_badblocks */
+	if (!ignore_badblocks) {
+		/*
+		 * If the hw ecc bytes are not those of a blank page, there's
+		 * still a chance that the page is blank, but was read with
+		 * errors.  Check the "written flag" in last oob byte, which
+		 * is set to zero when a page is written.  If more than half
+		 * the bits are set, assume a blank page.  Unfortunately, the
+		 * bit flips(s) are not reported in stats.
+		 */
+
+		if (doc->oob_buf[15]) {
+			int bit, numsetbits = 0;
+			unsigned long written_flag = doc->oob_buf[15];
+
+			for (bit = 0; bit < 8; bit++) {
+				if (written_flag & 0x01)
+					numsetbits++;
+				written_flag >>= 1;
+			}
+			if (numsetbits > 4) { /* assume blank */
+				printf("errors in blank page at offset %08x\n",
+				       page * DOCG4_PAGE_SIZE);
+				return 0;
+			}
+		}
+	}
+
+	/*
+	 * The hardware ecc unit produces oob_ecc ^ calc_ecc.  The kernel's bch
+	 * algorithm is used to decode this.  However the hw operates on page
+	 * data in a bit order that is the reverse of that of the bch alg,
+	 * requiring that the bits be reversed on the result.  Thanks to Ivan
+	 * Djelic for his analysis!
+	 */
+	for (i = 0; i < 7; i++)
+		doc->ecc_buf[i] = bitrev8(doc->ecc_buf[i]);
+
+	numerrs = decode_bch(doc->bch, NULL, DOCG4_USERDATA_LEN, NULL,
+			     doc->ecc_buf, NULL, errpos);
+
+	if (numerrs == -EBADMSG) {
+		printf("uncorrectable errors at offset %08x\n",
+		       page * DOCG4_PAGE_SIZE);
+		return -EBADMSG;
+	}
+
+	BUG_ON(numerrs < 0);	/* -EINVAL, or anything other than -EBADMSG */
+
+	/* undo last step in BCH alg (modulo mirroring not needed) */
+	for (i = 0; i < numerrs; i++)
+		errpos[i] = (errpos[i] & ~7)|(7-(errpos[i] & 7));
+
+	/* fix the errors */
+	for (i = 0; i < numerrs; i++) {
+		/* ignore if error within oob ecc bytes */
+		if (errpos[i] > DOCG4_USERDATA_LEN * 8)
+			continue;
+
+		/* if error within oob area preceeding ecc bytes... */
+		if (errpos[i] > DOCG4_PAGE_SIZE * 8)
+			__change_bit(errpos[i] - DOCG4_PAGE_SIZE * 8,
+				     (unsigned long *)doc->oob_buf);
+
+		else    /* error in page data */
+			__change_bit(errpos[i], (unsigned long *)buf);
+	}
+
+	printf("%d error(s) corrected at offset %08x\n",
+	       numerrs, page * DOCG4_PAGE_SIZE);
+
+	return numerrs;
+}
+
+static int read_progstatus(struct docg4_priv *doc, void __iomem *docptr)
+{
+	/*
+	 * This apparently checks the status of programming.  Done after an
+	 * erasure, and after page data is written.  On error, the status is
+	 * saved, to be later retrieved by the nand infrastructure code.
+	 */
+
+	/* status is read from the I/O reg */
+	uint16_t status1 = readw(docptr + DOC_IOSPACE_DATA);
+	uint16_t status2 = readw(docptr + DOC_IOSPACE_DATA);
+	uint16_t status3 = readw(docptr + DOCG4_MYSTERY_REG);
+
+	dbg(doc->dev, "docg4: %s: %02x %02x %02x\n",
+	    __func__, status1, status2, status3);
+
+	if (status1 != DOCG4_PROGSTATUS_GOOD ||
+	    status2 != DOCG4_PROGSTATUS_GOOD_2 ||
+	    status3 != DOCG4_PROGSTATUS_GOOD_2) {
+		doc->status = NAND_STATUS_FAIL;
+		printf("read_progstatus failed: %02x, %02x, %02x\n",
+		       status1, status2, status3);
+		return -EIO;
+	}
+	return 0;
+}
+
+static int pageprog(struct mtd_info *mtd)
+{
+	/*
+	 * Final step in writing a page.  Writes the contents of its
+	 * internal buffer out to the flash array, or some such.
+	 */
+
+	struct nand_chip *nand = mtd->priv;
+	struct docg4_priv *doc = nand->priv;
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	int retval = 0;
+
+	dbg(doc->dev, "docg4: %s\n", __func__);
+
+	writew(DOCG4_SEQ_PAGEPROG, docptr + DOC_FLASHSEQUENCE);
+	writew(DOC_CMD_PROG_CYCLE2, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/* Just busy-wait; usleep_range() slows things down noticeably. */
+	poll_status(docptr);
+
+	writew(DOCG4_SEQ_FLUSH, docptr + DOC_FLASHSEQUENCE);
+	writew(DOCG4_CMD_FLUSH, docptr + DOC_FLASHCOMMAND);
+	writew(DOC_ECCCONF0_READ_MODE | 4, docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	retval = read_progstatus(doc, docptr);
+	writew(0, docptr + DOC_DATAEND);
+	write_nop(docptr);
+	poll_status(docptr);
+	write_nop(docptr);
+
+	return retval;
+}
+
+static void sequence_reset(void __iomem *docptr)
+{
+	/* common starting sequence for all operations */
+
+	writew(DOC_CTRL_UNKNOWN | DOC_CTRL_CE, docptr + DOC_FLASHCONTROL);
+	writew(DOC_SEQ_RESET, docptr + DOC_FLASHSEQUENCE);
+	writew(DOC_CMD_RESET, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+	poll_status(docptr);
+	write_nop(docptr);
+}
+
+static void read_page_prologue(void __iomem *docptr, uint32_t docg4_addr)
+{
+	/* first step in reading a page */
+
+	sequence_reset(docptr);
+
+	writew(DOCG4_SEQ_PAGE_READ, docptr + DOC_FLASHSEQUENCE);
+	writew(DOCG4_CMD_PAGE_READ, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+
+	write_addr(docptr, docg4_addr);
+
+	write_nop(docptr);
+	writew(DOCG4_CMD_READ2, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	poll_status(docptr);
+}
+
+static void write_page_prologue(void __iomem *docptr, uint32_t docg4_addr)
+{
+	/* first step in writing a page */
+
+	sequence_reset(docptr);
+	writew(DOCG4_SEQ_PAGEWRITE, docptr + DOC_FLASHSEQUENCE);
+	writew(DOCG4_CMD_PAGEWRITE, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_addr(docptr, docg4_addr);
+	write_nop(docptr);
+	write_nop(docptr);
+	poll_status(docptr);
+}
+
+static uint32_t mtd_to_docg4_address(int page, int column)
+{
+	/*
+	 * Convert mtd address to format used by the device, 32 bit packed.
+	 *
+	 * Some notes on G4 addressing... The M-Sys documentation on this device
+	 * claims that pages are 2K in length, and indeed, the format of the
+	 * address used by the device reflects that.  But within each page are
+	 * four 512 byte "sub-pages", each with its own oob data that is
+	 * read/written immediately after the 512 bytes of page data.  This oob
+	 * data contains the ecc bytes for the preceeding 512 bytes.
+	 *
+	 * Rather than tell the mtd nand infrastructure that page size is 2k,
+	 * with four sub-pages each, we engage in a little subterfuge and tell
+	 * the infrastructure code that pages are 512 bytes in size.  This is
+	 * done because during the course of reverse-engineering the device, I
+	 * never observed an instance where an entire 2K "page" was read or
+	 * written as a unit.  Each "sub-page" is always addressed individually,
+	 * its data read/written, and ecc handled before the next "sub-page" is
+	 * addressed.
+	 *
+	 * This requires us to convert addresses passed by the mtd nand
+	 * infrastructure code to those used by the device.
+	 *
+	 * The address that is written to the device consists of four bytes: the
+	 * first two are the 2k page number, and the second is the index into
+	 * the page.  The index is in terms of 16-bit half-words and includes
+	 * the preceeding oob data, so e.g., the index into the second
+	 * "sub-page" is 0x108, and the full device address of the start of mtd
+	 * page 0x201 is 0x00800108.
+	 */
+	int g4_page = page / 4;	                      /* device's 2K page */
+	int g4_index = (page % 4) * 0x108 + column/2; /* offset into page */
+	return (g4_page << 16) | g4_index;	      /* pack */
+}
+
+static void docg4_command(struct mtd_info *mtd, unsigned command, int column,
+			  int page_addr)
+{
+	/* handle standard nand commands */
+
+	struct nand_chip *nand = mtd->priv;
+	struct docg4_priv *doc = nand->priv;
+	uint32_t g4_addr = mtd_to_docg4_address(page_addr, column);
+
+	dbg(doc->dev, "%s %x, page_addr=%x, column=%x\n",
+	    __func__, command, page_addr, column);
+
+	/*
+	 * Save the command and its arguments.  This enables emulation of
+	 * standard flash devices, and also some optimizations.
+	 */
+	doc->last_command.command = command;
+	doc->last_command.column = column;
+	doc->last_command.page = page_addr;
+
+	switch (command) {
+	case NAND_CMD_RESET:
+		reset(CONFIG_SYS_NAND_BASE);
+		break;
+
+	case NAND_CMD_READ0:
+		read_page_prologue(CONFIG_SYS_NAND_BASE, g4_addr);
+		break;
+
+	case NAND_CMD_STATUS:
+		/* next call to read_byte() will expect a status */
+		break;
+
+	case NAND_CMD_SEQIN:
+		write_page_prologue(CONFIG_SYS_NAND_BASE, g4_addr);
+
+		/* hack for deferred write of oob bytes */
+		if (doc->oob_page == page_addr)
+			memcpy(nand->oob_poi, doc->oob_buf, 16);
+		break;
+
+	case NAND_CMD_PAGEPROG:
+		pageprog(mtd);
+		break;
+
+	/* we don't expect these, based on review of nand_base.c */
+	case NAND_CMD_READOOB:
+	case NAND_CMD_READID:
+	case NAND_CMD_ERASE1:
+	case NAND_CMD_ERASE2:
+		printf("docg4_command: unexpected nand command 0x%x\n",
+		       command);
+		break;
+	}
+}
+
+static void docg4_read_buf(struct mtd_info *mtd, uint8_t *buf, int len)
+{
+	int i;
+	struct nand_chip *nand = mtd->priv;
+	uint16_t *p = (uint16_t *)buf;
+	len >>= 1;
+
+	for (i = 0; i < len; i++)
+		p[i] = readw(nand->IO_ADDR_R);
+}
+
+static int docg4_read_oob(struct mtd_info *mtd, struct nand_chip *nand,
+			  int page, int sndcmd)
+{
+	struct docg4_priv *doc = nand->priv;
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	uint16_t status;
+
+	dbg(doc->dev, "%s: page %x\n", __func__, page);
+
+	/*
+	 * Oob bytes are read as part of a normal page read.  If the previous
+	 * nand command was a read of the page whose oob is now being read, just
+	 * copy the oob bytes that we saved in a local buffer and avoid a
+	 * separate oob read.
+	 */
+	if (doc->last_command.command == NAND_CMD_READ0 &&
+	    doc->last_command.page == page) {
+		memcpy(nand->oob_poi, doc->oob_buf, 16);
+		return 0;
+	}
+
+	/*
+	 * Separate read of oob data only.
+	 */
+	docg4_command(mtd, NAND_CMD_READ0, nand->ecc.size, page);
+
+	writew(DOC_ECCCONF0_READ_MODE | DOCG4_OOB_SIZE, docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/* the 1st byte from the I/O reg is a status; the rest is oob data */
+	status = readw(docptr + DOC_IOSPACE_DATA);
+	if (status & DOCG4_READ_ERROR) {
+		printf("docg4_read_oob failed: status = 0x%02x\n", status);
+		return -EIO;
+	}
+
+	dbg(doc->dev, "%s: status = 0x%x\n", __func__, status);
+
+	docg4_read_buf(mtd, nand->oob_poi, 16);
+
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	writew(0, docptr + DOC_DATAEND);
+	write_nop(docptr);
+
+	return 0;
+}
+
+static int docg4_write_oob(struct mtd_info *mtd, struct nand_chip *nand,
+			   int page)
+{
+	/*
+	 * Writing oob-only is not really supported, because MLC nand must write
+	 * oob bytes at the same time as page data.  Nonetheless, we save the
+	 * oob buffer contents here, and then write it along with the page data
+	 * if the same page is subsequently written.  This allows user space
+	 * utilities that write the oob data prior to the page data to work
+	 * (e.g., nandwrite).  The disdvantage is that, if the intention was to
+	 * write oob only, the operation is quietly ignored.  Also, oob can get
+	 * corrupted if two concurrent processes are running nandwrite.
+	 */
+
+	/* note that bytes 7..14 are hw generated hamming/ecc and overwritten */
+	struct docg4_priv *doc = nand->priv;
+	doc->oob_page = page;
+	memcpy(doc->oob_buf, nand->oob_poi, 16);
+	return 0;
+}
+
+static int docg4_block_neverbad(struct mtd_info *mtd, loff_t ofs, int getchip)
+{
+	/* only called when module_param ignore_badblocks is set */
+	return 0;
+}
+
+static void docg4_write_buf16(struct mtd_info *mtd, const uint8_t *buf, int len)
+{
+	int i;
+	struct nand_chip *nand = mtd->priv;
+	uint16_t *p = (uint16_t *)buf;
+	len >>= 1;
+
+	for (i = 0; i < len; i++)
+		writew(p[i], nand->IO_ADDR_W);
+}
+
+static void write_page(struct mtd_info *mtd, struct nand_chip *nand,
+		       const uint8_t *buf, int use_ecc)
+{
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	uint8_t ecc_buf[8];
+
+	writew(DOC_ECCCONF0_ECC_ENABLE |
+	       DOC_ECCCONF0_UNKNOWN |
+	       DOCG4_BCH_SIZE,
+	       docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+
+	/* write the page data */
+	docg4_write_buf16(mtd, buf, DOCG4_PAGE_SIZE);
+
+	/* oob bytes 0 through 5 are written to I/O reg */
+	docg4_write_buf16(mtd, nand->oob_poi, 6);
+
+	/* oob byte 6 written to a separate reg */
+	writew(nand->oob_poi[6], docptr + DOCG4_OOB_6_7);
+
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/* write hw-generated ecc bytes to oob */
+	if (likely(use_ecc)) {
+		/* oob byte 7 is hamming code */
+		uint8_t hamming = readb(docptr + DOC_HAMMINGPARITY);
+		hamming = readb(docptr + DOC_HAMMINGPARITY); /* 2nd read */
+		writew(hamming, docptr + DOCG4_OOB_6_7);
+		write_nop(docptr);
+
+		/* read the 7 bch bytes from ecc regs */
+		read_hw_ecc(docptr, ecc_buf);
+		ecc_buf[7] = 0;         /* clear the "page written" flag */
+	}
+
+	/* write user-supplied bytes to oob */
+	else {
+		writew(nand->oob_poi[7], docptr + DOCG4_OOB_6_7);
+		write_nop(docptr);
+		memcpy(ecc_buf, &nand->oob_poi[8], 8);
+	}
+
+	docg4_write_buf16(mtd, ecc_buf, 8);
+	write_nop(docptr);
+	write_nop(docptr);
+	writew(0, docptr + DOC_DATAEND);
+	write_nop(docptr);
+}
+
+static void docg4_write_page_raw(struct mtd_info *mtd, struct nand_chip *nand,
+				 const uint8_t *buf)
+{
+	return write_page(mtd, nand, buf, 0);
+}
+
+static void docg4_write_page(struct mtd_info *mtd, struct nand_chip *nand,
+			     const uint8_t *buf)
+{
+	return write_page(mtd, nand, buf, 1);
+}
+
+static int read_page(struct mtd_info *mtd, struct nand_chip *nand,
+		     uint8_t *buf, int page, int use_ecc)
+{
+	struct docg4_priv *doc = nand->priv;
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	uint16_t status, edc_err, *buf16;
+
+	writew(DOC_ECCCONF0_READ_MODE |
+	       DOC_ECCCONF0_ECC_ENABLE |
+	       DOC_ECCCONF0_UNKNOWN |
+	       DOCG4_BCH_SIZE,
+	       docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/* the 1st byte from the I/O reg is a status; the rest is page data */
+	status = readw(docptr + DOC_IOSPACE_DATA);
+	if (status & DOCG4_READ_ERROR) {
+		printf("docg4_read_page: bad status: 0x%02x\n", status);
+		writew(0, docptr + DOC_DATAEND);
+		return -EIO;
+	}
+
+	docg4_read_buf(mtd, buf, DOCG4_PAGE_SIZE); /* read the page data */
+
+	/* first 14 oob bytes read from I/O reg */
+	docg4_read_buf(mtd, nand->oob_poi, 14);
+
+	/* last 2 read from another reg */
+	buf16 = (uint16_t *)(nand->oob_poi + 14);
+	*buf16 = readw(docptr + DOCG4_MYSTERY_REG);
+
+	/*
+	 * Diskonchips read oob immediately after a page read.  Mtd
+	 * infrastructure issues a separate command for reading oob after the
+	 * page is read.  So we save the oob bytes in a local buffer and just
+	 * copy it if the next command reads oob from the same page.
+	 */
+	memcpy(doc->oob_buf, nand->oob_poi, 16);
+
+	write_nop(docptr);
+
+	if (likely(use_ecc)) {
+		/* read the register that tells us if bitflip(s) detected  */
+		edc_err = readw(docptr + DOC_ECCCONF1);
+		edc_err = readw(docptr + DOC_ECCCONF1);
+
+		/* If bitflips are reported, attempt to correct with ecc */
+		if (edc_err & DOC_ECCCONF1_BCH_SYNDROM_ERR) {
+			int bits_corrected = correct_data(mtd, buf, page);
+			if (bits_corrected == -EBADMSG)
+				mtd->ecc_stats.failed++;
+			else
+				mtd->ecc_stats.corrected += bits_corrected;
+		}
+	}
+
+	writew(0, docptr + DOC_DATAEND);
+	return 0;
+}
+
+
+static int docg4_read_page_raw(struct mtd_info *mtd, struct nand_chip *nand,
+			       uint8_t *buf, int page)
+{
+	return read_page(mtd, nand, buf, page, 0);
+}
+
+static int docg4_read_page(struct mtd_info *mtd, struct nand_chip *nand,
+			   uint8_t *buf, int page)
+{
+	return read_page(mtd, nand, buf, page, 1);
+}
+
+static void docg4_erase_block(struct mtd_info *mtd, int page)
+{
+	struct nand_chip *nand = mtd->priv;
+	struct docg4_priv *doc = nand->priv;
+	void __iomem *docptr = CONFIG_SYS_NAND_BASE;
+	uint16_t g4_page;
+
+	dbg(doc->dev, "%s: page %04x\n", __func__, page);
+
+	sequence_reset(docptr);
+
+	writew(DOCG4_SEQ_BLOCKERASE, docptr + DOC_FLASHSEQUENCE);
+	writew(DOC_CMD_PROG_BLOCK_ADDR, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+
+	/* only 2 bytes of address are written to specify erase block */
+	g4_page = (uint16_t)(page / 4);  /* to g4's 2k page addressing */
+	writeb(g4_page & 0xff, docptr + DOC_FLASHADDRESS);
+	g4_page >>= 8;
+	writeb(g4_page & 0xff, docptr + DOC_FLASHADDRESS);
+	write_nop(docptr);
+
+	/* start the erasure */
+	writew(DOC_CMD_ERASECYCLE2, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	poll_status(docptr);
+	writew(DOCG4_SEQ_FLUSH, docptr + DOC_FLASHSEQUENCE);
+	writew(DOCG4_CMD_FLUSH, docptr + DOC_FLASHCOMMAND);
+	writew(DOC_ECCCONF0_READ_MODE | 4, docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	read_progstatus(doc, docptr);
+
+	writew(0, docptr + DOC_DATAEND);
+	write_nop(docptr);
+	poll_status(docptr);
+	write_nop(docptr);
+}
+
+static int read_factory_bbt(struct mtd_info *mtd)
+{
+	/*
+	 * The device contains a read-only factory bad block table.  Read it and
+	 * update the memory-based bbt accordingly.
+	 */
+
+	struct nand_chip *nand = mtd->priv;
+	uint32_t g4_addr = mtd_to_docg4_address(DOCG4_FACTORY_BBT_PAGE, 0);
+	uint8_t *buf;
+	int i, block, status;
+
+	buf = kzalloc(DOCG4_PAGE_SIZE, GFP_KERNEL);
+	if (buf == NULL)
+		return -ENOMEM;
+
+	read_page_prologue(CONFIG_SYS_NAND_BASE, g4_addr);
+	status = docg4_read_page(mtd, nand, buf, DOCG4_FACTORY_BBT_PAGE);
+	if (status)
+		goto exit;
+
+	/*
+	 * If no memory-based bbt was created, exit.  This will happen if module
+	 * parameter ignore_badblocks is set.  Then why even call this function?
+	 * For an unknown reason, block erase always fails if it's the first
+	 * operation after device power-up.  The above read ensures it never is.
+	 * Ugly, I know.
+	 */
+	if (nand->bbt == NULL)  /* no memory-based bbt */
+		goto exit;
+
+	/*
+	 * Parse factory bbt and update memory-based bbt.  Factory bbt format is
+	 * simple: one bit per block, block numbers increase left to right (msb
+	 * to lsb).  Bit clear means bad block.
+	 */
+	for (i = block = 0; block < DOCG4_NUMBLOCKS; block += 8, i++) {
+		int bitnum;
+		uint8_t mask;
+		for (bitnum = 0, mask = 0x80;
+		     bitnum < 8; bitnum++, mask >>= 1) {
+			if (!(buf[i] & mask)) {
+				int badblock = block + bitnum;
+				nand->bbt[badblock / 4] |=
+					0x03 << ((badblock % 4) * 2);
+				mtd->ecc_stats.badblocks++;
+				printf("factory-marked bad block: %d\n",
+				       badblock);
+			}
+		}
+	}
+ exit:
+	kfree(buf);
+	return status;
+}
+
+static int docg4_block_markbad(struct mtd_info *mtd, loff_t ofs)
+{
+	/*
+	 * Mark a block as bad.  Bad blocks are marked in the oob area of the
+	 * first page of the block.  The default scan_bbt() in the nand
+	 * infrastructure code works fine for building the memory-based bbt
+	 * during initialization, as does the nand infrastructure function that
+	 * checks if a block is bad by reading the bbt.  This function replaces
+	 * the nand default because writes to oob-only are not supported.
+	 */
+
+	int ret, i;
+	uint8_t *buf;
+	struct nand_chip *nand = mtd->priv;
+	struct nand_bbt_descr *bbtd = nand->badblock_pattern;
+	int block = (int)(ofs >> nand->bbt_erase_shift);
+	int page = (int)(ofs >> nand->page_shift);
+	uint32_t g4_addr = mtd_to_docg4_address(page, 0);
+
+	dbg(doc->dev, "%s: %08llx\n", __func__, ofs);
+
+	if (unlikely(ofs & (DOCG4_BLOCK_SIZE - 1)))
+		printf("%s: ofs %llx not start of block!\n",
+		       __func__, ofs);
+
+	/* allocate blank buffer for page data */
+	buf = kzalloc(DOCG4_PAGE_SIZE, GFP_KERNEL);
+	if (buf == NULL)
+		return -ENOMEM;
+
+	/* update bbt in memory */
+	nand->bbt[block / 4] |= 0x01 << ((block & 0x03) * 2);
+
+	/* write bit-wise negation of pattern to oob buffer */
+	memset(nand->oob_poi, 0xff, mtd->oobsize);
+	for (i = 0; i < bbtd->len; i++)
+		nand->oob_poi[bbtd->offs + i] = ~bbtd->pattern[i];
+
+	/* write first page of block */
+	write_page_prologue(CONFIG_SYS_NAND_BASE, g4_addr);
+	docg4_write_page(mtd, nand, buf);
+	ret = pageprog(mtd);
+	if (!ret)
+		mtd->ecc_stats.badblocks++;
+
+	kfree(buf);
+
+	return ret;
+}
+
+static uint8_t docg4_read_byte(struct mtd_info *mtd)
+{
+	struct nand_chip *nand = mtd->priv;
+	struct docg4_priv *doc = nand->priv;
+
+	dbg(doc->dev, "%s\n", __func__);
+
+	if (doc->last_command.command == NAND_CMD_STATUS) {
+		int status;
+
+		/*
+		 * Previous nand command was status request, so nand
+		 * infrastructure code expects to read the status here.  If an
+		 * error occurred in a previous operation, report it.
+		 */
+		doc->last_command.command = 0;
+
+		if (doc->status) {
+			status = doc->status;
+			doc->status = 0;
+		}
+
+		/* why is NAND_STATUS_WP inverse logic?? */
+		else
+			status = NAND_STATUS_WP | NAND_STATUS_READY;
+
+		return status;
+	}
+
+	printf("unexpectd call to read_byte()\n");
+
+	return 0;
+}
+
+static int docg4_wait(struct mtd_info *mtd, struct nand_chip *nand)
+{
+	struct docg4_priv *doc = nand->priv;
+	int status = NAND_STATUS_WP;       /* inverse logic?? */
+	dbg(doc->dev, "%s...\n", __func__);
+
+	/* report any previously unreported error */
+	if (doc->status) {
+		status |= doc->status;
+		doc->status = 0;
+		return status;
+	}
+
+	status |= poll_status(CONFIG_SYS_NAND_BASE);
+	return status;
+}
+
+int docg4_nand_init(struct mtd_info *mtd, struct nand_chip *nand, int devnum)
+{
+	uint16_t id1, id2;
+	struct docg4_priv *docg4;
+	int retval;
+
+	docg4 = kzalloc(sizeof(*docg4), GFP_KERNEL);
+	if (!docg4)
+		return -1;
+
+	mtd->priv = nand;
+	nand->priv = docg4;
+
+	/* These must be initialized here because the docg4 is non-standard
+	 * and doesn't produce an id that the nand code can use to look up
+	 * these values (nand_scan_ident() not called).
+	 */
+	mtd->size = DOCG4_CHIP_SIZE;
+	mtd->name = "Msys_Diskonchip_G4";
+	mtd->writesize = DOCG4_PAGE_SIZE;
+	mtd->erasesize = DOCG4_BLOCK_SIZE;
+	mtd->oobsize = DOCG4_OOB_SIZE;
+
+	nand->IO_ADDR_R =
+		(void __iomem *)CONFIG_SYS_NAND_BASE + DOC_IOSPACE_DATA;
+	nand->IO_ADDR_W = nand->IO_ADDR_R;
+	nand->chipsize = DOCG4_CHIP_SIZE;
+	nand->chip_shift = DOCG4_CHIP_SHIFT;
+	nand->bbt_erase_shift = DOCG4_ERASE_SHIFT;
+	nand->phys_erase_shift = DOCG4_ERASE_SHIFT;
+	nand->chip_delay = 20;
+	nand->page_shift = DOCG4_PAGE_SHIFT;
+	nand->pagemask = 0x3ffff;
+	nand->badblockpos = NAND_LARGE_BADBLOCK_POS;
+	nand->badblockbits = 8;
+	nand->ecc.layout = &docg4_oobinfo;
+	nand->ecc.mode = NAND_ECC_HW_SYNDROME;
+	nand->ecc.size = DOCG4_PAGE_SIZE;
+	nand->ecc.prepad = 8;
+	nand->ecc.bytes	= 8;
+	nand->options =
+		NAND_BUSWIDTH_16 | NAND_NO_SUBPAGE_WRITE | NAND_NO_AUTOINCR;
+	nand->controller = &nand->hwcontrol;
+
+	/* methods */
+	nand->cmdfunc = docg4_command;
+	nand->waitfunc = docg4_wait;
+	nand->select_chip = docg4_select_chip;
+	nand->read_byte = docg4_read_byte;
+	nand->block_markbad = docg4_block_markbad;
+	nand->read_buf = docg4_read_buf;
+	nand->write_buf = docg4_write_buf16;
+	nand->scan_bbt = nand_default_bbt;
+	nand->erase_cmd = docg4_erase_block;
+	nand->ecc.read_page = docg4_read_page;
+	nand->ecc.write_page = docg4_write_page;
+	nand->ecc.read_page_raw = docg4_read_page_raw;
+	nand->ecc.write_page_raw = docg4_write_page_raw;
+	nand->ecc.read_oob = docg4_read_oob;
+	nand->ecc.write_oob = docg4_write_oob;
+
+	/*
+	 * The way the nand infrastructure code is written, a memory-based bbt
+	 * is not created if NAND_SKIP_BBTSCAN is set.  With no memory bbt,
+	 * nand->block_bad() is used.  So when ignoring bad blocks, we skip the
+	 * scan and define a dummy block_bad() which always returns 0.
+	 */
+	if (ignore_badblocks) {
+		nand->options |= NAND_SKIP_BBTSCAN;
+		nand->block_bad	= docg4_block_neverbad;
+	}
+
+	reset(CONFIG_SYS_NAND_BASE);
+
+	/* check for presence of g4 chip by reading id registers */
+	id1 = readw(CONFIG_SYS_NAND_BASE + DOC_CHIPID);
+	id1 = readw(CONFIG_SYS_NAND_BASE + DOCG4_MYSTERY_REG);
+	id2 = readw(CONFIG_SYS_NAND_BASE + DOC_CHIPID_INV);
+	id2 = readw(CONFIG_SYS_NAND_BASE + DOCG4_MYSTERY_REG);
+	if (id1 != DOCG4_IDREG1_VALUE || id2 != DOCG4_IDREG2_VALUE)
+		return -1;
+
+	/* initialize bch algorithm */
+	docg4->bch = init_bch(DOCG4_M, DOCG4_T, DOCG4_PRIMITIVE_POLY);
+	if (docg4->bch == NULL)
+		return -1;
+
+	retval = nand_scan_tail(mtd);
+	if (retval)
+		return -1;
+
+	/*
+	 * Scan for bad blocks and create bbt here, then add the factory-marked
+	 * bad blocks to the bbt.
+	 */
+	nand->scan_bbt(mtd);
+	nand->options |= NAND_BBT_SCANNED;
+	retval = read_factory_bbt(mtd);
+	if (retval)
+		return -1;
+
+	retval = nand_register(devnum);
+	if (retval)
+		return -1;
+
+	return 0;
+}
diff --git a/drivers/mtd/nand/docg4_spl.c b/drivers/mtd/nand/docg4_spl.c
new file mode 100644
index 0000000..95e856c
--- /dev/null
+++ b/drivers/mtd/nand/docg4_spl.c
@@ -0,0 +1,222 @@
+/*
+ * SPL driver for Diskonchip G4 nand flash
+ *
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ *
+ * This driver basically mimics the load functionality of a typical IPL (initial
+ * program loader) resident in the 2k NOR-like region of the docg4 that is
+ * mapped to the reset vector.  It allows the u-boot SPL to continue loading if
+ * the IPL loads a fixed number of flash blocks that is insufficient to contain
+ * the entire u-boot image.  In this case, a concatenated spl + u-boot image is
+ * written at the flash offset from which the IPL loads an image, and when the
+ * IPL jumps to the SPL, the SPL resumes loading where the IPL left off.  See
+ * the palmtreo680 for an example.
+ *
+ * This driver assumes that the data was written to the flash using the device's
+ * "reliable" mode, and also assumes that each 512 byte page is stored
+ * redundantly in the subsequent page.  This storage format is likely to be used
+ * by all boards that boot from the docg4.  The format compensates for the lack
+ * of ecc in the IPL.
+ *
+ * Reliable mode reduces the capacity of a block by half, and the redundant
+ * pages reduce it by half again.  As a result, the normal 256k capacity of a
+ * block is reduced to 64k for the purposes of the IPL/SPL.
+ */
+
+#include <asm/io.h>
+#include <linux/mtd/docg4.h>
+
+/* forward declarations */
+static inline void write_nop(void __iomem *docptr);
+static int poll_status(void __iomem *docptr);
+static void write_addr(void __iomem *docptr, uint32_t docg4_addr);
+static void address_sequence(unsigned int g4_page, unsigned int g4_index,
+			     void __iomem *docptr);
+static int docg4_load_block_reliable(uint32_t flash_offset, void *dest_addr);
+
+int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
+{
+	void *load_addr = dst;
+	uint32_t flash_offset = offs;
+	const unsigned int block_count =
+		(size + DOCG4_BLOCK_CAPACITY_SPL - 1)
+		/ DOCG4_BLOCK_CAPACITY_SPL;
+	int i;
+
+	for (i = 0; i < block_count; i++) {
+		int ret = docg4_load_block_reliable(flash_offset, load_addr);
+		if (ret)
+			return ret;
+		load_addr += DOCG4_BLOCK_CAPACITY_SPL;
+		flash_offset += DOCG4_BLOCK_SIZE;
+	}
+	return 0;
+}
+
+static inline void write_nop(void __iomem *docptr)
+{
+	writew(0, docptr + DOC_NOP);
+}
+
+static int poll_status(void __iomem *docptr)
+{
+	/*
+	 * Busy-wait for the FLASHREADY bit to be set in the FLASHCONTROL
+	 * register.  Operations known to take a long time (e.g., block erase)
+	 * should sleep for a while before calling this.
+	 */
+
+	uint8_t flash_status;
+
+	/* hardware quirk requires reading twice initially */
+	flash_status = readb(docptr + DOC_FLASHCONTROL);
+
+	do {
+		flash_status = readb(docptr + DOC_FLASHCONTROL);
+	} while (!(flash_status & DOC_CTRL_FLASHREADY));
+
+	return 0;
+}
+
+static void write_addr(void __iomem *docptr, uint32_t docg4_addr)
+{
+	/* write the four address bytes packed in docg4_addr to the device */
+
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+	docg4_addr >>= 8;
+	writeb(docg4_addr & 0xff, docptr + DOC_FLASHADDRESS);
+}
+
+static void address_sequence(unsigned int g4_page, unsigned int g4_index,
+			     void __iomem *docptr)
+{
+	writew(DOCG4_SEQ_PAGE_READ, docptr + DOC_FLASHSEQUENCE);
+	writew(DOCG4_CMD_PAGE_READ, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_addr(docptr, ((uint32_t)g4_page << 16) | g4_index);
+	write_nop(docptr);
+}
+
+static int docg4_load_block_reliable(uint32_t flash_offset, void *dest_addr)
+{
+	void __iomem *docptr = (void *)CONFIG_SYS_NAND_BASE;
+	unsigned int g4_page = flash_offset >> 11; /* 2k page */
+	const unsigned int last_g4_page = g4_page + 0x80; /* last in block */
+	int g4_index = 0;
+	uint16_t flash_status;
+	uint16_t *buf;
+	uint16_t discard, magic_high, magic_low;
+
+	/* flash_offset must be aligned to the start of a block */
+	if (flash_offset & 0x3ffff)
+		return -1;
+
+	writew(DOC_SEQ_RESET, docptr + DOC_FLASHSEQUENCE);
+	writew(DOC_CMD_RESET, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+	poll_status(docptr);
+	write_nop(docptr);
+	writew(0x45, docptr + DOC_FLASHSEQUENCE);
+	writew(0xa3, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	writew(0x22, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+
+	/* read 1st 4 oob bytes of first subpage of block */
+	address_sequence(g4_page, 0x0100, docptr); /* index at oob */
+	write_nop(docptr);
+	flash_status = readw(docptr + DOC_FLASHCONTROL);
+	flash_status = readw(docptr + DOC_FLASHCONTROL);
+	if (flash_status & 0x06) /* sequence or protection errors */
+		return -1;
+	writew(DOCG4_CMD_READ2, docptr + DOC_FLASHCOMMAND);
+	write_nop(docptr);
+	write_nop(docptr);
+	poll_status(docptr);
+	writew(DOC_ECCCONF0_READ_MODE | 4, docptr + DOC_ECCCONF0);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/*
+	 * Here we read the first four oob bytes of the first page of the block.
+	 * The IPL on the palmtreo680 requires that this contain a 32 bit magic
+	 * number, or the load aborts.  We'll ignore it.
+	 */
+	discard = readw(docptr + 0x103c); /* hw quirk; 1st read discarded */
+	magic_low = readw(docptr + 0x103c);
+	magic_high = readw(docptr + DOCG4_MYSTERY_REG);
+	writew(0, docptr + DOC_DATAEND);
+	write_nop(docptr);
+	write_nop(docptr);
+
+	/* load contents of block to memory */
+	buf = (uint16_t *)dest_addr;
+	do {
+		int i;
+
+		address_sequence(g4_page, g4_index, docptr);
+		writew(DOCG4_CMD_READ2,
+		       docptr + DOC_FLASHCOMMAND);
+		write_nop(docptr);
+		write_nop(docptr);
+		poll_status(docptr);
+		writew(DOC_ECCCONF0_READ_MODE |
+		       DOC_ECCCONF0_ECC_ENABLE |
+		       DOCG4_BCH_SIZE,
+		       docptr + DOC_ECCCONF0);
+		write_nop(docptr);
+		write_nop(docptr);
+		write_nop(docptr);
+		write_nop(docptr);
+		write_nop(docptr);
+
+		/* read the 512 bytes of page data, 2 bytes at a time */
+		discard = readw(docptr + 0x103c);
+		for (i = 0; i < 256; i++)
+			*buf++ = readw(docptr + 0x103c);
+
+		/* read oob, but discard it */
+		for (i = 0; i < 7; i++)
+			discard = readw(docptr + 0x103c);
+		discard = readw(docptr + DOCG4_OOB_6_7);
+		discard = readw(docptr + DOCG4_OOB_6_7);
+
+		writew(0, docptr + DOC_DATAEND);
+		write_nop(docptr);
+		write_nop(docptr);
+
+		if (!(g4_index & 0x100)) {
+			/* not redundant subpage read; check for ecc error */
+			write_nop(docptr);
+			flash_status = readw(docptr + DOC_ECCCONF1);
+			flash_status = readw(docptr + DOC_ECCCONF1);
+			if (flash_status & 0x80) { /* ecc error */
+				g4_index += 0x108; /* read redundant subpage */
+				buf -= 256;        /* back up ram ptr */
+				continue;
+			} else                       /* no ecc error */
+				g4_index += 0x210; /* skip redundant subpage */
+		} else  /* redundant page was just read; skip ecc error check */
+			g4_index += 0x108;
+
+		if (g4_index == 0x420) { /* finished with 2k page */
+			g4_index = 0;
+			g4_page += 2; /* odd-numbered 2k pages skipped */
+		}
+
+	} while (g4_page != last_g4_page); /* while still on same block */
+
+	return 0;
+}
diff --git a/include/linux/mtd/docg4.h b/include/linux/mtd/docg4.h
new file mode 100644
index 0000000..982f5ad
--- /dev/null
+++ b/include/linux/mtd/docg4.h
@@ -0,0 +1,134 @@
+/*
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ */
+
+#ifndef __DOCG4_H__
+#define __DOCG4_H__
+
+#include <common.h>
+#include <linux/mtd/nand.h>
+
+extern int docg4_nand_init(struct mtd_info *mtd,
+			   struct nand_chip *nand, int devnum);
+
+/* SPL-related definitions */
+#define DOCG4_IPL_LOAD_BLOCK_COUNT 2  /* number of blocks that IPL loads */
+#define DOCG4_BLOCK_CAPACITY_SPL 0x10000 /* reliable mode; redundant pages */
+
+#define DOC_IOSPACE_DATA		0x0800
+
+/* register offsets */
+#define DOC_CHIPID			0x1000
+#define DOC_DEVICESELECT		0x100a
+#define DOC_ASICMODE			0x100c
+#define DOC_DATAEND			0x101e
+#define DOC_NOP				0x103e
+
+#define DOC_FLASHSEQUENCE		0x1032
+#define DOC_FLASHCOMMAND		0x1034
+#define DOC_FLASHADDRESS		0x1036
+#define DOC_FLASHCONTROL		0x1038
+#define DOC_ECCCONF0			0x1040
+#define DOC_ECCCONF1			0x1042
+#define DOC_HAMMINGPARITY		0x1046
+#define DOC_BCH_SYNDROM(idx)		(0x1048 + idx)
+
+#define DOC_ASICMODECONFIRM		0x1072
+#define DOC_CHIPID_INV			0x1074
+#define DOC_POWERMODE			0x107c
+
+#define DOCG4_MYSTERY_REG		0x1050
+
+/* apparently used only to write oob bytes 6 and 7 */
+#define DOCG4_OOB_6_7			0x1052
+
+/* DOC_FLASHSEQUENCE register commands */
+#define DOC_SEQ_RESET			0x00
+#define DOCG4_SEQ_PAGE_READ		0x03
+#define DOCG4_SEQ_FLUSH			0x29
+#define DOCG4_SEQ_PAGEWRITE		0x16
+#define DOCG4_SEQ_PAGEPROG		0x1e
+#define DOCG4_SEQ_BLOCKERASE		0x24
+
+/* DOC_FLASHCOMMAND register commands */
+#define DOCG4_CMD_PAGE_READ             0x00
+#define DOC_CMD_ERASECYCLE2		0xd0
+#define DOCG4_CMD_FLUSH                 0x70
+#define DOCG4_CMD_READ2                 0x30
+#define DOC_CMD_PROG_BLOCK_ADDR		0x60
+#define DOCG4_CMD_PAGEWRITE		0x80
+#define DOC_CMD_PROG_CYCLE2		0x10
+#define DOC_CMD_RESET			0xff
+
+/* DOC_POWERMODE register bits */
+#define DOC_POWERDOWN_READY		0x80
+
+/* DOC_FLASHCONTROL register bits */
+#define DOC_CTRL_CE			0x10
+#define DOC_CTRL_UNKNOWN		0x40
+#define DOC_CTRL_FLASHREADY		0x01
+
+/* DOC_ECCCONF0 register bits */
+#define DOC_ECCCONF0_READ_MODE		0x8000
+#define DOC_ECCCONF0_UNKNOWN		0x2000
+#define DOC_ECCCONF0_ECC_ENABLE	        0x1000
+#define DOC_ECCCONF0_DATA_BYTES_MASK	0x07ff
+
+/* DOC_ECCCONF1 register bits */
+#define DOC_ECCCONF1_BCH_SYNDROM_ERR	0x80
+#define DOC_ECCCONF1_ECC_ENABLE         0x07
+#define DOC_ECCCONF1_PAGE_IS_WRITTEN	0x20
+
+/* DOC_ASICMODE register bits */
+#define DOC_ASICMODE_RESET		0x00
+#define DOC_ASICMODE_NORMAL		0x01
+#define DOC_ASICMODE_POWERDOWN		0x02
+#define DOC_ASICMODE_MDWREN		0x04
+#define DOC_ASICMODE_BDETCT_RESET	0x08
+#define DOC_ASICMODE_RSTIN_RESET	0x10
+#define DOC_ASICMODE_RAM_WE		0x20
+
+/* good status values read after read/write/erase operations */
+#define DOCG4_PROGSTATUS_GOOD          0x51
+#define DOCG4_PROGSTATUS_GOOD_2        0xe0
+
+/*
+ * On read operations (page and oob-only), the first byte read from I/O reg is a
+ * status.  On error, it reads 0x73; otherwise, it reads either 0x71 (first read
+ * after reset only) or 0x51, so bit 1 is presumed to be an error indicator.
+ */
+#define DOCG4_READ_ERROR           0x02 /* bit 1 indicates read error */
+
+/* anatomy of the device */
+#define DOCG4_CHIP_SIZE        0x8000000
+#define DOCG4_PAGE_SIZE        0x200
+#define DOCG4_PAGES_PER_BLOCK  0x200
+#define DOCG4_BLOCK_SIZE       (DOCG4_PAGES_PER_BLOCK * DOCG4_PAGE_SIZE)
+#define DOCG4_NUMBLOCKS        (DOCG4_CHIP_SIZE / DOCG4_BLOCK_SIZE)
+#define DOCG4_OOB_SIZE         0x10
+#define DOCG4_CHIP_SHIFT       27    /* log_2(DOCG4_CHIP_SIZE) */
+#define DOCG4_PAGE_SHIFT       9     /* log_2(DOCG4_PAGE_SIZE) */
+#define DOCG4_ERASE_SHIFT      18    /* log_2(DOCG4_BLOCK_SIZE) */
+
+/* all but the last byte is included in ecc calculation */
+#define DOCG4_BCH_SIZE         (DOCG4_PAGE_SIZE + DOCG4_OOB_SIZE - 1)
+
+#define DOCG4_USERDATA_LEN     520 /* 512 byte page plus 8 oob avail to user */
+
+/* expected values from the ID registers */
+#define DOCG4_IDREG1_VALUE     0x0400
+#define DOCG4_IDREG2_VALUE     0xfbff
+
+/* primitive polynomial used to build the Galois field used by hw ecc gen */
+#define DOCG4_PRIMITIVE_POLY   0x4443
+
+#define DOCG4_M                14  /* Galois field is of order 2^14 */
+#define DOCG4_T                4   /* BCH alg corrects up to 4 bit errors */
+
+#define DOCG4_FACTORY_BBT_PAGE 16 /* page where read-only factory bbt lives */
+
+#endif	/* __DOCG4_H__ */
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
                   ` (5 preceding siblings ...)
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash Mike Dunn
@ 2013-04-11  0:45 ` Mike Dunn
  2013-04-11 19:20   ` Marek Vasut
  2013-04-14 17:44 ` [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Marek Vasut
  7 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-11  0:45 UTC (permalink / raw)
  To: u-boot

A quick overview of u-boot implementation on the treo 680...

The treo 680 has a Diskonchip G4 nand flash chip.  This device has a 2k region
that maps to the system bus at the reset vector in a NOR-like fashion so that it
can be used as the boot device.  The phone is shipped with this 2k region
configured as write-protected (can't be modified) and programmed with an initial
program loader (IPL).  At power-up, this IPL loads the contents of two flash
blocks to SDRAM and jumps to it.  The capacity of the two blocks is not large
enough to hold all of u-boot, so a u-boot SPL is used.  To conserve flash space,
these two blocks and the necessary number of subsequent blocks are programmed
with a concatenated spl + u-boot image.  That way, the IPL will also load a
portion of u-boot proper, and when the spl runs, it relocates the portion of
u-boot that the IPL has already loaded, and then resumes loading the remaining
part of u-boot before jumping to it.

The default_environment is used (CONFIG_ENV_IS_NOWHERE) because I didn't think
that having a writable environment was worth the cost of a flash block, although
adding it would be straightforward.  I abuse the CONFIG_EXTRA_ENV_SETTINGS
option to specify the usbtty for the console (CONFIG_SYS_CONSOLE_IS_IN_ENV).

Support for the LCD is included, but currently it is only useful for displaying
the u-boot splash screen.  But if u-boot is built without the usbtty console, it
does display the auto-boot progress nicely.

Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
---
 CREDITS                               |    4 +
 MAINTAINERS                           |    3 +
 board/palmtreo680/Makefile            |   34 ++
 board/palmtreo680/palmtreo680.c       |  179 +++++++++++
 board/palmtreo680/palmtreo680_spl.lds |   51 +++
 boards.cfg                            |    1 +
 doc/README.palmtreo680                |  570 +++++++++++++++++++++++++++++++++
 include/configs/palmtreo680.h         |  295 +++++++++++++++++
 tools/palmtreo680/flash_u-boot.c      |  177 ++++++++++
 9 files changed, 1314 insertions(+), 0 deletions(-)
 create mode 100644 board/palmtreo680/Makefile
 create mode 100644 board/palmtreo680/palmtreo680.c
 create mode 100644 board/palmtreo680/palmtreo680_spl.lds
 create mode 100644 doc/README.palmtreo680
 create mode 100644 include/configs/palmtreo680.h
 create mode 100644 tools/palmtreo680/flash_u-boot.c

diff --git a/CREDITS b/CREDITS
index 7c1458f..3b657e9 100644
--- a/CREDITS
+++ b/CREDITS
@@ -124,6 +124,10 @@ N: James F. Dougherty
 E: jfd at GigabitNetworks.COM
 D: Port to the MOUSSE board
 
+N: Mike Dunn
+E: mikedunn at newsguy.com
+D: Palmtreo680 board, docg4 nand flash driver
+
 N: Dave Ellis
 E: DGE at sixnetio.com
 D: EEPROM Speedup, SXNI855T port
diff --git a/MAINTAINERS b/MAINTAINERS
index 1614b91..db62af1 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -650,6 +650,9 @@ Wolfgang Denk <wd@denx.de>
 	imx27lite	i.MX27
 	qong		i.MX31
 
+Mike Dunn <mikedunn@newsguy.com>
+	palmtreo680	pxa270
+
 Kristoffer Ericson <kristoffer.ericson@gmail.com>
 
 	jornada	SA1110
diff --git a/board/palmtreo680/Makefile b/board/palmtreo680/Makefile
new file mode 100644
index 0000000..34ffb99
--- /dev/null
+++ b/board/palmtreo680/Makefile
@@ -0,0 +1,34 @@
+#
+# Palm Treo680 Support
+#
+# Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+#
+# This file is released under the terms of GPL v2 and any later version.
+# See the file COPYING in the root directory of the source tree for details.
+
+include $(TOPDIR)/config.mk
+
+LIB	= $(obj)lib$(BOARD).o
+
+COBJS	:= palmtreo680.o
+
+SRCS	:= $(COBJS:.o=.c)
+OBJS	:= $(addprefix $(obj),$(COBJS))
+
+$(LIB):	$(obj).depend $(OBJS)
+	$(call cmd_link_o_target, $(OBJS))
+
+clean:
+	rm -f $(OBJS)
+
+distclean:	clean
+	rm -f $(LIB) core *.bak $(obj).depend
+
+#########################################################################
+
+# defines $(obj).depend target
+include $(SRCTREE)/rules.mk
+
+sinclude $(obj).depend
+
+#########################################################################
diff --git a/board/palmtreo680/palmtreo680.c b/board/palmtreo680/palmtreo680.c
new file mode 100644
index 0000000..c23c570
--- /dev/null
+++ b/board/palmtreo680/palmtreo680.c
@@ -0,0 +1,179 @@
+/*
+ * Palm Treo 680 Support
+ *
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ */
+
+#include <common.h>
+#include <command.h>
+#include <serial.h>
+#include <nand.h>
+#include <malloc.h>
+#include <asm/arch/pxa-regs.h>
+#include <asm/arch-pxa/pxa.h>
+#include <asm/arch-pxa/regs-mmc.h>
+#include <asm/io.h>
+#include <asm/global_data.h>
+#include <u-boot/crc.h>
+#include <linux/mtd/docg4.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+static struct nand_chip docg4_nand_chip;
+
+int board_init(void)
+{
+	/* We have RAM, disable cache */
+	dcache_disable();
+	icache_disable();
+
+	gd->bd->bi_arch_number = MACH_TYPE_TREO680;
+	gd->bd->bi_boot_params = 0xa0000100;
+
+	return 0;
+}
+
+int dram_init(void)
+{
+	/* IPL initializes SDRAM (we're already running from it) */
+	gd->ram_size = PHYS_SDRAM_1_SIZE;
+	return 0;
+}
+
+#ifdef CONFIG_LCD
+void lcd_enable(void)
+{
+	/*
+	 * Undo the L_BIAS / gpio77 pin configuration performed by the pxa lcd
+	 * driver code.  We need it as an output gpio.
+	 */
+	writel((readl(GAFR2_L) & ~(0xc << 24)), GAFR2_L);
+
+	/* power-up and enable the lcd */
+	writel(0x00400000, GPSR(86)); /* enable; drive high */
+	writel(0x00002000, GPSR(77)); /* power; drive high */
+	writel(0x02000000, GPCR(25)); /* enable_n; drive low */
+
+	/* turn on LCD backlight and configure PWM for reasonable brightness */
+	writel(0x00, PWM_CTRL0);
+	writel(0x1b1, PWM_PERVAL0);
+	writel(0xfd, PWM_PWDUTY0);
+	writel(0x00000040, GPSR(38)); /*  backlight power on */
+}
+#endif
+
+#ifdef CONFIG_MMC
+int board_mmc_init(bd_t *bis)
+{
+	writel(0x00000400, GPSR(42)); /* power on */
+	return pxa_mmc_register(0);
+}
+#endif
+
+void board_nand_init(void)
+{
+	/* we have one 128M diskonchip G4  */
+
+	struct mtd_info *mtd = &nand_info[0];
+	struct nand_chip *nand = &docg4_nand_chip;
+	if (docg4_nand_init(mtd, nand, 0))
+		hang();
+}
+
+#ifdef CONFIG_SPL_BUILD
+void *memcpy(void *dest, const void *src, size_t count)
+{
+	unsigned long *dl = (unsigned long *)dest, *sl = (unsigned long *)src;
+	char *d8, *s8;
+
+	if (src == dest)
+		return dest;
+
+	/* while all data is aligned (common case), copy a word@a time */
+	if ((((ulong)dest | (ulong)src) & (sizeof(*dl) - 1)) == 0) {
+		while (count >= sizeof(*dl)) {
+			*dl++ = *sl++;
+			count -= sizeof(*dl);
+		}
+	}
+	/* copy the reset one byte at a time */
+	d8 = (char *)dl;
+	s8 = (char *)sl;
+	while (count--)
+		*d8++ = *s8++;
+
+	return dest;
+}
+
+
+void nand_boot(void)
+{
+	__attribute__((noreturn)) void (*uboot)(void);
+
+	extern const void *_start, *_end;   /* boundaries of spl in memory */
+
+	/* size of spl; ipl loads this, and then a portion of u-boot */
+	const size_t spl_image_size = ((size_t)&_end - (size_t)&_start);
+
+	/* the flash offset of the blocks that are loaded by the spl */
+	const uint32_t spl_load_offset = CONFIG_SYS_NAND_U_BOOT_OFFS +
+		DOCG4_IPL_LOAD_BLOCK_COUNT * DOCG4_BLOCK_SIZE;
+
+	/* total number of bytes loaded by IPL */
+	const size_t ipl_load_size =
+		DOCG4_IPL_LOAD_BLOCK_COUNT * DOCG4_BLOCK_CAPACITY_SPL;
+
+	/* number of bytes of u-boot proper that was loaded by the IPL */
+	const size_t ipl_uboot_load_size = ipl_load_size - spl_image_size;
+
+	/* number of remaining bytes of u-boot that the SPL must load */
+	const size_t spl_load_size =
+		CONFIG_SYS_NAND_U_BOOT_SIZE - ipl_load_size;
+
+	/* memory address where we resume loading u-boot */
+	void *const load_addr =
+		(void *)(CONFIG_SYS_NAND_U_BOOT_DST + ipl_uboot_load_size);
+
+	/*
+	 * Copy the portion of u-boot already read from flash by the IPL to its
+	 * correct load address.
+	 */
+	memcpy((void *)CONFIG_SYS_NAND_U_BOOT_DST, &_end, ipl_uboot_load_size);
+
+	/*
+	 * Resume loading u-boot where the IPL left off.
+	 */
+	nand_spl_load_image(spl_load_offset, spl_load_size, load_addr);
+
+#ifdef CONFIG_NAND_ENV_DST
+	nand_spl_load_image(CONFIG_ENV_OFFSET, CONFIG_ENV_SIZE,
+			    (void *)CONFIG_NAND_ENV_DST);
+
+#ifdef CONFIG_ENV_OFFSET_REDUND
+	nand_spl_load_image(CONFIG_ENV_OFFSET_REDUND, CONFIG_ENV_SIZE,
+			    (void *)CONFIG_NAND_ENV_DST + CONFIG_ENV_SIZE);
+#endif
+#endif
+	/*
+	 * Jump to U-Boot image
+	 */
+	uboot = (void *)CONFIG_SYS_NAND_U_BOOT_START;
+	(*uboot)();
+}
+
+void board_init_f(ulong bootflag)
+{
+	nand_boot();
+}
+
+void hang(void)
+{
+	for (;;) {
+	}
+}
+
+#endif  /* CONFIG_SPL_BUILD */
diff --git a/board/palmtreo680/palmtreo680_spl.lds b/board/palmtreo680/palmtreo680_spl.lds
new file mode 100644
index 0000000..3e94311
--- /dev/null
+++ b/board/palmtreo680/palmtreo680_spl.lds
@@ -0,0 +1,51 @@
+/*
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ * This file is a slight modification to the default pxa link script.  The '*'
+ * wildcard is added to the section names to consolidate all the sections
+ * created by the -ffunction-sections and -fdata-sections compiler flags.
+ */
+
+
+OUTPUT_FORMAT("elf32-littlearm", "elf32-littlearm", "elf32-littlearm")
+OUTPUT_ARCH(arm)
+ENTRY(_start)
+SECTIONS
+{
+	. = 0x00000000;
+
+	. = ALIGN(4);
+	.text :
+	{
+		arch/arm/cpu/pxa/start.o	(.text)
+		*(.text*)
+	}
+
+	. = ALIGN(4);
+	.rodata : { *(SORT_BY_ALIGNMENT(SORT_BY_NAME(.rodata*))) }
+
+	. = ALIGN(4);
+	.data : {
+		*(.data*)
+	}
+
+	. = ALIGN(4);
+
+	. = .;
+	__u_boot_cmd_start = .;
+	.u_boot_cmd : { *(.u_boot_cmd) }
+	__u_boot_cmd_end = .;
+
+	_end = .;
+
+	/* internal SRAM is used for the SPL's bss */
+	.bss 0x5c000000 : {
+		__bss_start = .;
+		*(.bss*)
+		 . = ALIGN(4);
+		__bss_end = .;
+	}
+}
diff --git a/boards.cfg b/boards.cfg
index 5fc70be..72a9440 100644
--- a/boards.cfg
+++ b/boards.cfg
@@ -331,6 +331,7 @@ h2200                        arm         pxa
 lubbock                      arm         pxa
 palmld                       arm         pxa
 palmtc                       arm         pxa
+palmtreo680                  arm         pxa
 polaris                      arm         pxa         trizepsiv           -              -           trizepsiv:POLARIS
 pxa255_idp                   arm         pxa
 trizepsiv                    arm         pxa
diff --git a/doc/README.palmtreo680 b/doc/README.palmtreo680
new file mode 100644
index 0000000..e4a9305
--- /dev/null
+++ b/doc/README.palmtreo680
@@ -0,0 +1,570 @@
+
+README for the Palm Treo 680.
+
+Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+
+You may reproduce the contents of this file entirely or in part, but please
+credit me by name if you do.  Thanks.
+
+
+Intro
+=====
+
+Yes, you can program u-boot onto the flash of your Palm Treo 680 so that u-boot
+(then Linux, Android, ...) runs at power-up.  This document describes how, and
+gives some implementation details on this port of u-boot.
+
+But first, I probably don't need to tell you that after doing this, your phone
+will no longer run PalmOS.  You *may* be able to later restore your phone to its
+original state by creating a backup image of the flash before writing u-boot
+(details below), but this is not heavily tested and should not be relied upon.
+There is also the possibility that something may go wrong during the process of
+programming u-boot, leaving you with a bricked phone.  If you follow these
+instructions carefully this chance will be minimized, but I do not recommend
+that you program u-boot onto a phone that you can not afford to lose, and
+certainly not one that contains important data that is not backed up elsewhere.
+I AM NOT RESPONSIBLE FOR THE LOSS OF YOUR PHONE.  DO THIS AT YOUR OWN RISK.
+Having said that, feel free to send me a note cursing me out if something does
+go wrong, but please tell me what happened exactly.  For that matter, I'd love
+to hear from you if you succeed.
+
+To program u-boot to your flash, you will need to boot the Linux kernel on your
+phone using a PalmOS bootloader such as cocoboot.  The details of building and
+running Linux on your Treo (cross-compiling, creating a root filesystem,
+configuring the kernel, etc) are beyond the scope of this document.
+
+
+
+Hardware Prerequisites
+======================
+
+A Palm Treo 680:
+  (dugh)
+
+A Palm usb cable:
+  You'll need this to establish a usbtty console connection to u-boot from a
+  desktop PC.  Currently there is no support in u-boot for the pxa27x keypad
+  (coming soon), so a serial link must be used for the console.
+  These cables are still widely available if you don't already have one.
+
+A Linux desktop PC.
+  You may be able to use Windows for the u-boot console if you have a usb driver
+  that is compatible with the Linux usbserial driver, but for programming u-boot
+  to flash, you'll really want to use a Linux PC.
+
+
+
+Treo-side Software Prerequisites
+================================
+
+Linux bootloader for PalmOS:
+
+  Cocoboot is the only one I'm aware of.  If you don't already have this, you
+  can download it from
+  https://download.enlightenment.org/misc/Illume/Treo-650/2008-11-13/sdcard-base.tar.gz
+  which is a compressed tar archive of the contents of an sd card containing
+  cocoboot.  Use mkdosfs to create a fat16 filesystem on the first primary
+  partition of the card, mount the partition, and extract the tar file to it.
+  You will probably need to edit the cocoboot.conf file to customize the
+  parameters passed to the kernel.
+
+
+
+Linux kernel:
+
+  The kernel on the Treo 680 is still a little rough around the edges, and the
+  official kernel frequently breaks on the Treo :(  A development kernel
+  specifically for the Treo 680 can be found on github:
+    http://github.com/mike-dunn/linux-treo680
+  The master branch of this tree has been tested on the Treo, and I recommend
+  using this kernel for programming u-boot.  As of this writing, there may be a
+  bug in the docg4 nand flash driver that sometimes causes block erasures to
+  fail.  This has been fixed in the above tree.
+
+  If you choose to use the official kernel, it must contain the docg4 driver that
+  includes the reliable_mode module parameter.  This was a later enhancement to
+  the driver, and was merged to the kernel as of v3.8.  Do not try to use an
+  earlier kernel that contains the docg4 driver without support for writing in
+  reliable mode.  If you try to program u-boot to flash with the docg4 driver
+  loaded without the reliable_mode parameter enabled, you *will* brick your
+  phone!
+
+  For the purpose of programming u-boot to flash, the following options must be
+  enabled in the Treo kernel's .config:
+
+     CONFIG_MTD=y
+     CONFIG_MTD_CMDLINE_PARTS=y
+     CONFIG_MTD_CHAR=y
+     CONFIG_MTD_NAND_DOCG4=m
+
+  Note that the docg4 nand driver is configured as a module, because we will
+  want to load and unload it with reliable_mode enabled or disabled as needed.
+
+  You will also need to specify mtd partitions on the kernel command line.  In
+  the instructions that follow, we will assume that the flash blocks to which
+  u-boot will be programmed are defined by the second partition on the device.
+  The u-boot config file (include/configs/palmtreo680.h) places the u-boot image
+  at the start of block 6 (offset 0x180000), which is the first writable
+  (non-protected) block on the flash (this is also where the PalmOS SPL starts).
+  The u-boot image occupies four blocks, so to create the u-boot partition, pass
+  this command line to the kernel:
+    mtdparts=Msys_Diskonchip_G4:1536k(protected_part)ro,1024k(bootloader_part),-(filesys_part)
+  This will create three partitions:
+    protected_part: the first six blocks, which are read-only
+    bootloader_part: the next four blocks, for the u-boot image
+    filesys_part: the remainder of the device
+  The mtdchar kernel device driver will use device nodes /dev/mtd0, /dev/mtd1,
+  and /dev/mtd2 for these partitions, respectively.  Ensure that your root file
+  system at least has /dev/mtd1 if you are not running udev or mdev.
+
+
+Userspace Utilities:
+
+  In addition to everything necessary to provide a useful userspace environment
+  (busybox is indispensable, of course), you will need the mtd-utils package on
+  your root filesystem.  I use version 1.5.0 of mtd-utils, and I suggest you use
+  this version as well, or at leat a version very close to this one, as
+  mtd-utils has tended to be fluid.
+
+  Note that busybox includes a version of mtd-utils.  These are deficient and
+  should not be used.  When you run one of these utilities (nanddump, etc),
+  ensure you are invoking the separate executable from mtd-utils, and not the
+  one built into busybox.  I recommend that you configure busybox with its
+  mtd-utils disabled to avoid any possibility of confusion.
+
+  You will also need to cross-compile the userspace Linux utility in
+  tools/palmtreo680/flash_u-boot.c, which we will run on the Treo to perform the
+  actual write of the u-boot image to flash.  This utility links against libmtd
+  from the mtd-utils package.
+
+
+
+Desktop PC-side Software Prerequisites
+======================================
+
+Terminal emulator application:
+  minicom, kermit, etc.
+
+
+Linux kernel:
+  Compiled with CONFIG_USB_SERIAL enabled.  Build this as a module.
+
+
+
+Recommended (Not directly related to u-boot)
+============================================
+
+Working directly on the Treo's tiny screen and keypad is difficult and
+error-prone.  I recommend that you log into the Linux kernel running on your
+Treo from your desktop PC using ethernet over usb.  The desktop's kernel must be
+configured with CONFIG_USB_USBNET, CONFIG_USB_NET_CDCETHER, and
+CONFIG_USB_NET_CDC_SUBSET.  The Treo's kernel will need CONFIG_USB_ETH, and its
+init script will need to start an ssh daemon like dropbear.  Note that the usb0
+network interface will not appear on the desktop PC until the Treo kernel's usb
+ethernet gadget driver has initialized.  You must wait for this to occur (watch
+the PC's kernel log) before you can assign usb0 an ip address and log in to the
+Treo.  If you also build the Treo's kernel with CONFIG_IP_PNP enabled, you can
+pass its ip address on the kernel command line, and obviate the need to
+initialize the network interface in your init script.
+
+Having the Palm usb cable connected to the host has the added benefit of keeping
+power supplied to your Treo, reducing the drain on the battery.  If something
+goes wrong while you're programming u-boot to the flash, you will have lots of
+time to correct it before the battery dies.
+
+I have encountered a situation where the kernel is sometimes unable to mount a
+root filesystem on the mmc card due to the mmc controller not coming up in time,
+(and CONFIG_MMC_UNSAFE_RESUME doesn't seem to help) so I recommend that you
+build a minimal root filesystem into the kernel using the kernel's initramfs
+feature (CONFIG_BLK_DEV_INITRD).  If you want your root filesystem on the mmc
+card, your init script can mount and switch_root to the mmc card after a short
+sleep.  But keep in mind that in this case you won't be able to use an mmc card
+to transfer files between your desktop and the Treo.  Another option for
+transfering files is to mount an nfs filesystem exported by the desktop PC.  For
+greatest convenience, you can export the root filesystem itself from your
+desktop PC and switch_root to it in your init script.  This will work if your
+init script contains a loop that waits for you to initialize the usb0 network
+interface on the desktop PC; e.g., loop while a ping to the desktop PC returns
+an error.  After the loop exits, do the nfs mount and call switch_root.  (You
+can not use the kernel nfsroot feature because the network will not be up when
+the kernel expects it to be; i.e., not until you configure the usb0 interface on
+the desktop.)  Use the nfs 'nolock' option when mounting to avoid the need to
+run a portmapper like rpcbind.
+
+
+
+Preliminaries
+=============
+
+Once Linux is running on your Treo, you may want to perform a few sanity checks
+before programming u-boot.  If you are impatient and reckless, you may skip this
+section, but see disclaimer at the top of this file!
+
+Load the docg4 driver (you did build this as a module, right?):
+
+  $ modprobe docg4 ignore_badblocks=1 reliable_mode=1
+
+We tell the driver to use the docg4's "reliable mode" when writing because this
+is the format required by the initial program loader (IPL), which runs from
+power-up and loads the first portion of u-boot.  We must ignore bad blocks
+because linux mtd uses out-of-band (oob) bytes to mark bad blocks, which will
+cause the blocks written by PalmOS to be misidentified as "bad" by libmtd.
+
+Check the kernel log to ensure that all's well:
+
+  $ dmesg | tail
+   	      <... snip ...>
+  docg4 docg4: NAND device: 128MiB Diskonchip G4 detected
+  3 cmdlinepart partitions found on MTD device Msys_Diskonchip_G4
+  Creating 3 MTD partitions on "Msys_Diskonchip_G4":
+  0x000000000000-0x000000180000 : "protected_part"
+  0x000000180000-0x000000280000 : "bootloader_part"
+  0x000000280000-0x000008000000 : "filesys_part"
+
+Ensure that the partition boundaries are as shown.  (If no partitions are shown,
+did you remember to pass them to the kernel on the command line?)  We will write
+u-boot to bootloader_part, which starts at offset 0x180000 (block 6) and spans 4
+256k blocks.  This partition is accessed through the device node /dev/mtd1.
+
+The docg4 contains a read-only table that identifies blocks that were marked as
+bad at the factory.  This table is in the page at offset 0x2000, which is within
+the partition protected_part (/dev/mtd0).  There is a slight chance that one or
+more of the four blocks that we will use for u-boot is listed in the table, so
+use nanddump to inspect the table to see if this is the case:
+
+  $ nanddump -p -l 512 -s 0x2000 -o /dev/mtd0
+  ECC failed: 0
+  ECC corrected: 0
+  Number of bad blocks: 0
+  Number of bbt blocks: 0
+  Block size 262144, page size 512, OOB size 16
+  Dumping data starting at 0x00002000 and ending at 0x00002200...
+  0x00002000: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+   	      <... snip ...>
+
+The format of the table is simple: one bit per block, with block numbers
+increasing from left to right, starting with block 0 as the most significant bit
+of the first byte.  A bit will be clear if the corresponding block is bad.  We
+want to use blocks 6 throgh 9, so both of the two least significant bits of the
+first byte must be set, as must the two most significant bits of the second
+byte.  If this is not true in your case (you are very unlucky), you should use
+the first contiguous set of four good blocks after block 6, and adjust the
+partition boundaries accordingly.  You will also have to change the value of
+CONFIG_SYS_NAND_U_BOOT_OFFS in include/configs/palmtreo680.h and recompile
+u-boot.  Because the two blocks loaded by the IPL do not have to be contiguous,
+but our SPL expects them to be, you will need to erase any good blocks that are
+at an offset prior to CONFIG_SYS_NAND_U_BOOT_OFFS, so that the IPL does not find
+the magic number in oob and load it (details below).  Once you have done all
+this, the instructions in this file still apply, except that the instructions
+below for restoring the original PalmOS block contents may not work.
+
+Next, use nanddump to verify that the PalmOS SPL is where we expect it to be.
+The SPL can be identified by a magic number in the oob bytes of the first page
+of each of the two blocks containing the SPL image.  Pages are 512 bytes in
+size, so to dump the first page, plus the oob:
+
+  $ nanddump -p -l 512 -s 0 -o /dev/mtd1
+  ECC failed: 0
+  ECC corrected: 0
+  Number of bad blocks: 0
+  Number of bbt blocks: 0
+  Block size 262144, page size 512, OOB size 16
+  Dumping data starting at 0x00000000 and ending at 0x00000200...
+  0x00000000: 0a 00 00 ea 00 00 00 00 00 00 00 00 00 00 00 00
+   	      <... snip ...>
+  0x000001f0: 13 4c 21 60 13 4d 2a 69 13 4b 29 69 89 1a 99 42
+    OOB Data: 42 49 50 4f 30 30 30 10 3a e2 00 92 be a0 11 ff
+
+Verify that the first seven bytes of oob data match those in the above line.
+(This is ASCII "BIPO000".)
+
+Do the same for the next block:
+  $ nanddump -p -l 512 -s 0x40000 -o /dev/mtd1
+
+The first seven oob bytes in last line should read:
+
+    OOB Data: 42 49 50 4f 30 30 31 81 db 8e 8f 46 07 9b 59 ff
+
+(This is ASCII "BIPO001".)
+
+For additional assurance, verify that the next block does *not* contain SPL
+data.
+
+  $ nanddump -p -l 512 -s 0x80000 -o /dev/mtd1
+
+It doesn't matter what the oob contains, as long as the first four bytes are
+*not* ASCII "BIPO".  PalmOS should only be using two blocks for the SPL
+(although we will need four for u-boot).
+
+If you want, you can back up the contents of bootloader_part to a file.  You may
+be able to restore it later, if desired (see "Restoring PalmOS" below).
+
+  $ nanddump -l 0x100000 -s 0 -o -f bootloader_part.orig /dev/mtd1
+
+nanddump will spew voluminous warnings about uncorrectable ecc errors.  This is
+a consequence of reading pages that were written in reliable mode, and is
+expected (these should all occur on pages in odd-numbered 2k regions; i.e.,
+0x800, 0xa00, 0xc00, 0xe00, 0x1800, 0x1a00, ...).  The size of the file
+bootloader_part.orig should be 1081344, which is 2048 pages, each of size 512
+plus 16 oob bytes.  If you are using initramfs for the root filesystem, don't
+forget to copy the file to permanent storage, such as an mmc card.
+
+If all of the above went well, you can now program u-boot.
+
+
+
+Programming u-boot
+==================
+
+Our u-boot includes a small SPL (secondary program loader) that must be
+prepended to u-boot proper.  From the base u-boot source directory on your
+desktop PC:
+
+  $ cat spl/u-boot-spl.bin u-boot.bin > u-boot-concat.bin
+
+cd to the tools/palmtreo680/ directory, and cross-compile flash_u-boot.c for the
+Treo:
+
+  $(CC) -o flash_u-boot $(CFLAGS) $(INCLUDEPATH) $(LIBPATH) flash_u-boot.c -lmtd
+
+Substitute variable values from your cross-compilation environment as
+appropriate.  Note that it links to libmtd from mtd-utils, and this must be
+included in $(LIBPATH) and $(INCLUDEPATH).
+
+Transfer u-boot-concat.bin and the compiled flash_u-boot utility to the Treo's
+root filesystem.  On the Treo, cd to the directory where these files were
+placed.
+
+Load the docg4 driver if you have not already done so.
+
+  $ modprobe docg4 ignore_badblocks=1 reliable_mode=1
+
+Erase the blocks to which we will write u-boot.
+
+  $ flash_erase /dev/mtd1 0x00 4
+
+We can now program the flash.
+
+  ./flash_u-boot u-boot-concat.bin /dev/mtd1
+
+You can use nanddump (see above) to verify that the data was written.  This
+time, "BIPO" should be seen in the first four oob bytes of the first page of all
+four blocks in /dev/mtd1; i.e., at offsets 0x00000, 0x40000, 0x80000, 0xc0000.
+
+Shutdown linux, remove and re-insert the battery, hold your breath...
+
+
+
+Enjoying u-boot
+===============
+
+After you insert the battery, the u-boot splash screen should appear on the lcd
+after a few seconds.  With the usb cable connecting the Treo to your PC, in the
+kernel log of your PC you should see
+
+  <6>usb 3-1: New USB device found, idVendor=0525, idProduct=a4a6
+  <6>usb 3-1: New USB device strings: Mfr=1, Product=2, SerialNumber=3
+  <6>usb 3-1: Product: U-Boot 2013.01-00167-gd62ef56-dirty
+  <6>usb 3-1: Manufacturer: Das U-Boot
+
+Load the usbserial module on your desktop PC:
+
+  $ modprobe usbserial vendor=0x0525 product=0xa4a6
+
+and run your favorite terminal emulation utility (minicom, kermit, etc) with the
+serial device set to /dev/ttyUSB0 (assuming this is your only usb serial
+device).  You should be at the u-boot console (type 'help').
+
+There is not much that is unique about using u-boot on the palm treo 680.
+Kernels can be loaded from mmc, flash, and from the desktop PC via kermit.  You
+can expand the size of the second partition on the flash to contain a kernel, or
+else put the kernel(s) in their own partition.
+
+Nand commands work as expected, with the excepton that blocks not written by the
+linux mtd subsystem may be misidentified by the u-boot docg4 driver as "bad" if
+they contain data in the oob bytes.  This will be the case for the blocks
+containing the u-boot image, for example.  To work around this, use 'nand scrub'
+to erase these blocks, and 'nand read.raw' to read them.  (It would be useful if
+u-boot's nand commands provided a way to explicitly ignore "bad" blocks, because
+read.raw does not perform ecc.)
+
+Currently u-boot itself can only be programmed to flash from Linux; there is no
+support for reliable mode in u-boot's docg4 flash driver.  This should be
+corrected soon.
+
+
+
+Customizing
+===========
+
+If you change u-boot's configuration significantly (adding or removing
+features), you may have to adjust the value of CONFIG_SYS_NAND_U_BOOT_SIZE.
+This is the size of the concatenated spl + u-boot image, and tells the SPL how
+many flash blocks it needs to load.  It will be rounded up to the next 64k
+boundary (the spl flash block capacity), so it does not have to be exact, but
+you must ensure that it is not less than the actual image size.  If it is larger
+than the image, blocks may be needlessly loaded, but if too small, u-boot may
+only be partially loaded, resulting in a boot failure (bricked phone), so better
+to be too large.  The flash_u-boot utility will work with any size image and
+write the required number of blocks, provided that the partition is large
+enough.
+
+As the first writable block on the device, block 6 seems to make the most sense
+as the flash offset for writing u-boot (and this is where PalmOS places its
+SPL).  But you can place it elsewhere if you like.  If you do, you need to
+adjust CONFIG_SYS_NAND_U_BOOT_OFFS accordingly, and you must ensure that blocks
+preceeding the ones containing u-boot do *not* have the magic number in oob (the
+IPL looks for this).  In other words, make sure that any blocks that previously
+contained the u-boot image or PalmOS SPL are erased (and optionally written with
+something else) so that the IPL does not load it.  Also make sure that the new
+u-boot starting offset is at the start of a flash partition (check the kernel
+log after loading the docg4 driver), and pass the corresponding mtd device file
+to the flash_u-boot utility.
+
+The u-boot built-in default environment is used because a writable environment
+in flash did not seem worth the cost of a 256k flash block.  But adding this
+should be straightforward.
+
+
+
+Details on the SPL
+==================
+
+The docg4 features a 2k region at the start of its address space that interfaces
+to the system bus like a NOR flash.  This allows the docg4 to function as a boot
+ROM.  The Treo 680 uses this feature.  The contents of this 2k region are
+protected and can not be reprogrammed (at least I don't know how to do it).
+Fortunately, the code it contains does what we need to do, at least partially.
+After some essential hardware initialization (like the SDRAM controller), it
+runs an IPL (initial program loader) that copies 128K (no more, no less) to a
+fixed address in SDRAM and then jumps to it.  128K is too small for u-boot, so
+we use it to load a u-boot SPL.  But since our SPL only occupies a little over
+1k, we can economize on flash usage by having the IPL load a portion of u-boot
+proper as well.  We let the IPL load two blocks of a concatenated spl + u-boot
+image, and because the SPL is placed before u-boot proper, the IPL jumps to the
+SPL, which copies to its correct SDRAM address the portion of u-boot that the
+IPL has already loaded, and then loads the remaining u-boot blocks.
+
+
+
+The docg4's "reliable mode"
+===========================
+
+This is a special mode of operation of the hardware whereby consecutive pairs of
+2k regions are used in parallel (in some fashion) to store 2k of data.  In other
+words, the normal capacity is halved, but the data integrity is improved.  In
+this mode, the data is read or written from pages in even-numbered 2k regions
+(regions starting at 0x000, 0x1000, 0x2000, ...), and the odd-numbered 2k
+regions (regions starting at 0x800, 0x1800, 0x2800, ...) are transparently used
+in parallel.  In reliable mode, the odd-numbered 2k regions are not meant to be
+read or written directly.
+
+Reliable mode is used by the IPL because there is not enough space in its 2k
+footprint to implement the BCH ecc algorithm.  Data that is read while reliable
+mode is enabled must have been written in reliable mode, or the read fails.
+However, data written in reliable mode can also be read in normal mode (just not
+as reliably), but only from the even-numbered 2k regions; the odd-numbered 2k
+regions appear to contain junk, and will generate ecc errors.  When the IPL and
+SPL read from flash, the odd-numbered 2k regions are explicitly skipped.  The
+same is true for the flash_u-boot utility when it writes the u-boot image in
+reliable mode.
+
+The docg4 Linux driver supports writing in reliable mode (it is enabled by the
+module parameter), but not reading.  However, the u-boot docg4_spl driver does
+read in reliable mode, in the same fashion as the IPL.
+
+
+
+Details on the IPL and its data format
+======================================
+
+Starting from block 5 and counting upward, the IPL will search for and load the
+first two blocks it finds that contain a magic number in the oob of the first
+page of the block.  The contents are loaded to SDRAM starting at address
+0xa1700000.  After two blocks have been loaded, it jumps to 0xa1700000.  The
+number of blocks loaded and the load address in SDRAM are hard-coded; only the
+flash offset of the blocks can vary at run-time (based on the presence of the
+magic number).
+
+In addition to using the docg4's reliable mode, the IPL expects each 512 byte
+page to be written redundantly in the subsequent page.  The hardware is capable
+of detecting bit errors (but not correcting them), and if a bit error is
+detected when a page is read, the page contents are discarded and the subsequent
+page is read.
+
+Reliable mode reduces the capacity of a block by half, and the redundant pages
+reduce it by half again.  As a result, the normal 256k capacity of a block is
+reduced to 64k for the purposes of the IPL/SPL.
+
+For the sake of simplicity and uniformity, the SPL mimics the operation of the
+IPL, and expects the image to be stored in the same format.
+
+
+
+Restoring PalmOS
+================
+
+If you backed up the contents of bootloader_part flash partition earlier, you
+should be able to restore it with the shell script shown below.  The first two
+blocks of data contain the PalmOS SPL and were written in reliable mode, whereas
+the next two blocks were written in normal mode, so the script has to load and
+unload the docg4 driver.  Make sure that the mtd-utils nandwrite and flash_erase
+are in your path (and are not those from busybox).  Also double-check that the
+backup image file bootloader_part.orig is exactly 1081344 bytes in length.  If
+not, it was not backed up correctly.  Run the script as:
+
+  ./restore_bootpart bootloader_part.orig /dev/mtd1
+
+The script will take a minute or so to run.  When it finishes, you may want to
+verify with nanddump that the data looks correct before you cycle power, because
+if the backup or restore failed, your phone will be bricked.  Note that as a
+consequence of reliable mode, the odd-numbered 2k regions in the first two
+blocks will not exactly match the contents of the backup file (so unfortunately
+we can't simply dump the flash contents to a file and do a binary diff with the
+original back-up image to verify that it was restored correctly).  Also,
+nanddump will report uncorrectable ecc errors when it reads those regions.
+
+#!/bin/sh
+
+if [ $# -ne 2 ]; then
+    echo "usage: $0: <image file> <mtd device node>"
+    exit 1
+fi
+
+# reliable mode used for the first two blocks
+modprobe -r docg4
+modprobe docg4 ignore_badblocks=1 reliable_mode=1 || exit 1
+
+# erase all four blocks
+flash_erase $2 0 4
+
+# Program the first two blocks in reliable mode.
+# 2k (4 pages) is written at a time, skipping alternate 2k regions
+# Note that "2k" is 2112 bytes, including 64 oob bytes
+file_ofs=0
+flash_ofs=0
+page=0
+while [ $page -ne 1024 ]; do
+    dd if=$1 bs=2112 skip=$file_ofs count=1 | nandwrite -o -n -s $flash_ofs $2 - || exit 1
+    file_ofs=$((file_ofs+2))
+    flash_ofs=$((flash_ofs+0x1000))
+    page=$((page+8))
+done;
+
+# normal mode used for the next two blocks
+modprobe -r docg4
+modprobe docg4 ignore_badblocks=1 || exit 1
+dd if=$1 bs=1 skip=$file_ofs count=540672 | nandwrite -o -n -s 0x80000 $2 - || exit 1
+modprobe -r docg4
+
+
+TODO
+====
+
+  - Keypad support.
+  - Interactive boot menu using keypad and lcd.
+  - Add reliable mode support to the u-boot docg4 driver.
+  - U-boot command that will write a new image to the bootloader partition in
+    flash.
+  - Linux FTD support.
+
diff --git a/include/configs/palmtreo680.h b/include/configs/palmtreo680.h
new file mode 100644
index 0000000..e785900
--- /dev/null
+++ b/include/configs/palmtreo680.h
@@ -0,0 +1,295 @@
+/*
+ * Palm Treo 680 configuration file
+ *
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ */
+
+#ifndef	__CONFIG_H
+#define	__CONFIG_H
+
+/*
+ * High Level Board Configuration Options
+ */
+#define CONFIG_CPU_PXA27X               1
+#define CONFIG_PALMTREO680              1
+
+
+#define CONFIG_SYS_MALLOC_LEN           (4096*1024)
+
+#define CONFIG_LZMA
+
+/*
+ * Serial Console Configuration
+ */
+#define CONFIG_PXA_SERIAL
+#define CONFIG_FFUART                   1
+#define CONFIG_BAUDRATE                 9600
+#define CONFIG_SYS_BAUDRATE_TABLE       { 9600, 19200, 38400, 57600, 115200 }
+#define CONFIG_CONS_INDEX               3
+
+/* we have nand (although technically nand *is* flash...) */
+#define CONFIG_SYS_NO_FLASH
+
+#define CONFIG_LCD
+/* #define CONFIG_KEYBOARD */  /* TODO */
+
+/*
+ * Bootloader Components Configuration
+ */
+#include <config_cmd_default.h>
+#undef  CONFIG_CMD_FPGA
+#undef  CONFIG_CMD_LOADS
+#undef  CONFIG_CMD_NET
+#undef  CONFIG_CMD_NFS
+#undef  CONFIG_CMD_IMLS
+#undef  CONFIG_CMD_FLASH
+#undef  CONFIG_CMD_SETGETDCR
+#undef  CONFIG_CMD_SOURCE
+#undef  CONFIG_CMD_XIMG
+
+#define CONFIG_CMD_ENV
+#define CONFIG_CMD_MMC
+#define CONFIG_CMD_NAND
+
+#define CONFIG_CMDLINE_TAG
+#define CONFIG_SETUP_MEMORY_TAGS
+
+#define CONFIG_MACH_TYPE                1230
+
+
+/*
+ * MMC Card Configuration
+ */
+#ifdef CONFIG_CMD_MMC
+#define CONFIG_MMC
+#define CONFIG_GENERIC_MMC
+#define CONFIG_PXA_MMC_GENERIC
+
+#define CONFIG_CMD_FAT
+#define CONFIG_CMD_EXT2
+#define CONFIG_DOS_PARTITION
+#endif
+
+/*
+ * LCD
+ */
+#ifdef CONFIG_LCD
+#define CONFIG_PXA_LCD
+#define CONFIG_ACX544AKN
+#define CONFIG_LCD_LOGO
+#define CONFIG_SYS_LCD_PXA_NO_L_BIAS /* don't configure GPIO77 as L_BIAS */
+#define LCD_BPP LCD_COLOR16
+#define CONFIG_FB_ADDR 0x5c000000    /* internal SRAM */
+#define CONFIG_CMD_BMP
+#define CONFIG_SPLASH_SCREEN         /* requires "splashimage" env var */
+#define CONFIG_SPLASH_SCREEN_ALIGN   /* requires "splashpos" env var */
+#define CONFIG_VIDEO_BMP_GZIP
+#define CONFIG_SYS_VIDEO_LOGO_MAX_SIZE  (2 << 20)
+
+#endif
+
+/*
+ * KGDB
+ */
+#ifdef CONFIG_CMD_KGDB
+#define CONFIG_KGDB_BAUDRATE            230400  /* kgdb serial port speed */
+#define CONFIG_KGDB_SER_INDEX           2       /* which serial port to use */
+#endif
+
+/*
+ * HUSH Shell Configuration
+ */
+#define CONFIG_SYS_HUSH_PARSER          1
+#define CONFIG_SYS_PROMPT_HUSH_PS2      "> "
+
+#define CONFIG_SYS_LONGHELP
+#ifdef CONFIG_SYS_HUSH_PARSER
+#define CONFIG_SYS_PROMPT               "$ "
+#else
+#define CONFIG_SYS_PROMPT               "=> "
+#endif
+#define CONFIG_SYS_CBSIZE               256
+#define CONFIG_SYS_PBSIZE               \
+	(CONFIG_SYS_CBSIZE+sizeof(CONFIG_SYS_PROMPT)+16)
+#define CONFIG_SYS_MAXARGS              16
+#define CONFIG_SYS_BARGSIZE             CONFIG_SYS_CBSIZE
+#define CONFIG_SYS_DEVICE_NULLDEV       1
+
+/*
+ * Clock Configuration
+ */
+#undef  CONFIG_SYS_CLKS_IN_HZ
+#define CONFIG_SYS_HZ                   1000 /* decrementer freq: 1 ms ticks */
+#define CONFIG_SYS_CPUSPEED             0x210           /* 416MHz ; N=2,L=16 */
+
+/*
+ * Stack sizes
+ */
+#define CONFIG_STACKSIZE                (128*1024)      /* regular stack */
+#ifdef CONFIG_USE_IRQ
+#define CONFIG_STACKSIZE_IRQ            (4*1024)        /* IRQ stack */
+#define CONFIG_STACKSIZE_FIQ            (4*1024)        /* FIQ stack */
+#endif
+
+/*
+ * DRAM Map
+ */
+#define CONFIG_NR_DRAM_BANKS            1               /* 1 bank of DRAM */
+#define PHYS_SDRAM_1                    0xa0000000      /* SDRAM Bank #1 */
+#define PHYS_SDRAM_1_SIZE               0x04000000      /* 64 MB */
+
+#define CONFIG_SYS_DRAM_BASE            0xa0000000
+#define CONFIG_SYS_DRAM_SIZE            0x04000000      /* 64 MB DRAM */
+
+#define CONFIG_SYS_MEMTEST_START        0xa0400000      /* memtest works on */
+#define CONFIG_SYS_MEMTEST_END          0xa0800000      /* 4 ... 8 MB in DRAM */
+#define CONFIG_SYS_LOAD_ADDR            CONFIG_SYS_DRAM_BASE
+#define CONFIG_SYS_SDRAM_BASE           PHYS_SDRAM_1
+
+
+
+/*
+ * GPIO settings
+ */
+#define CONFIG_SYS_GAFR0_L_VAL  0x0E000000
+#define CONFIG_SYS_GAFR0_U_VAL  0xA500001A
+#define CONFIG_SYS_GAFR1_L_VAL  0x60000002
+#define CONFIG_SYS_GAFR1_U_VAL  0xAAA07959
+#define CONFIG_SYS_GAFR2_L_VAL  0x02AAAAAA
+#define CONFIG_SYS_GAFR2_U_VAL  0x41440F08
+#define CONFIG_SYS_GAFR3_L_VAL  0x56AA95FF
+#define CONFIG_SYS_GAFR3_U_VAL  0x00001401
+#define CONFIG_SYS_GPCR0_VAL    0x1FF80400
+#define CONFIG_SYS_GPCR1_VAL    0x03003FC1
+#define CONFIG_SYS_GPCR2_VAL    0x01C1E000
+#define CONFIG_SYS_GPCR3_VAL    0x01C1E000
+#define CONFIG_SYS_GPDR0_VAL    0xCFF90400
+#define CONFIG_SYS_GPDR1_VAL    0xFB22BFC1
+#define CONFIG_SYS_GPDR2_VAL    0x93CDFFDF
+#define CONFIG_SYS_GPDR3_VAL    0x0069FF81
+#define CONFIG_SYS_GPSR0_VAL    0x02000018
+#define CONFIG_SYS_GPSR1_VAL    0x00000000
+#define CONFIG_SYS_GPSR2_VAL    0x000C0000
+#define CONFIG_SYS_GPSR3_VAL    0x00080000
+
+#define CONFIG_SYS_PSSR_VAL     0x30
+
+/*
+ * Clock settings
+ */
+#define CONFIG_SYS_CKEN         0x01ffffff
+#define CONFIG_SYS_CCCR         0x02000210
+
+/*
+ * Memory settings
+ */
+#define CONFIG_SYS_MSC0_VAL     0x7ff844c8
+#define CONFIG_SYS_MSC1_VAL     0x7ff86ab4
+#define CONFIG_SYS_MSC2_VAL     0x7ff87ff8
+#define CONFIG_SYS_MDCNFG_VAL   0x0B880acd
+#define CONFIG_SYS_MDREFR_VAL   0x201fa031
+#define CONFIG_SYS_MDMRS_VAL    0x00320032
+#define CONFIG_SYS_FLYCNFG_VAL  0x00000000
+#define CONFIG_SYS_SXCNFG_VAL   0x40044004
+
+/*
+ * PCMCIA and CF Interfaces
+ */
+#define CONFIG_SYS_MECR_VAL     0x00000003
+#define CONFIG_SYS_MCMEM0_VAL   0x0001c391
+#define CONFIG_SYS_MCMEM1_VAL   0x0001c391
+#define CONFIG_SYS_MCATT0_VAL   0x0001c391
+#define CONFIG_SYS_MCATT1_VAL   0x0001c391
+#define CONFIG_SYS_MCIO0_VAL    0x00014611
+#define CONFIG_SYS_MCIO1_VAL    0x0001c391
+
+/*
+ * USB
+ */
+#define CONFIG_USB_DEVICE
+#define CONFIG_USB_TTY
+#define CONFIG_USB_DEV_PULLUP_GPIO 114
+
+/*
+ * SPL
+ */
+#define CONFIG_SPL
+#define CONFIG_SPL_TEXT_BASE    0xa1700000 /* IPL loads SPL here */
+#define CONFIG_SPL_STACK        0x5c040000 /* top of internal SRAM */
+#define CONFIG_SPL_LDSCRIPT     board/palmtreo680/palmtreo680_spl.lds
+#define CONFIG_SPL_NAND_SUPPORT /* build libnand for spl */
+#define CONFIG_SPL_NAND_DOCG4   /* use lean docg4 nand spl driver */
+
+/*
+ * NAND
+ */
+#define CONFIG_NAND_DOCG4
+#define CONFIG_SYS_NAND_SELF_INIT
+#define CONFIG_SYS_MAX_NAND_DEVICE 1 /* only one device */
+#define CONFIG_SYS_NAND_BASE 0x00000000 /* mapped to reset vector */
+#define CONFIG_SYS_NAND_PAGE_SIZE 0x200
+#define CONFIG_SYS_NAND_BLOCK_SIZE 0x40000
+#define CONFIG_BITREVERSE       /* needed by docg4 driver */
+#define CONFIG_BCH              /* needed by docg4 driver */
+
+/*
+ * IMPORTANT NOTE: this is the size of the concatenated spl + u-boot image.  It
+ * will be rounded up to the next 64k boundary (the spl flash block size), so it
+ * does not have to be exact, but you must ensure that it is not less than the
+ * actual image size, or it may fail to boot (bricked phone)!
+ * (Tip: reduces to three blocks with lcd and mmc support removed from u-boot.)
+*/
+#define CONFIG_SYS_NAND_U_BOOT_SIZE 0x40000 /* four 64k flash blocks */
+
+/*
+ * This is the byte offset into the flash at which the concatenated spl + u-boot
+ * image is placed.  It must be at the start of a block (256k boundary).  Blocks
+ * 0 - 5 are write-protected, so we start at block 6.
+ */
+#define CONFIG_SYS_NAND_U_BOOT_OFFS 0x180000  /* block 6 */
+
+/* DRAM address to which u-boot proper is loaded (before it relocates itself) */
+#define CONFIG_SYS_NAND_U_BOOT_DST  0xa0000000
+#define CONFIG_SYS_NAND_U_BOOT_START CONFIG_SYS_NAND_U_BOOT_DST
+
+/* passed to linker by Makefile as arg to -Ttext option */
+#define CONFIG_SYS_TEXT_BASE 0xa0000000
+
+#define CONFIG_SYS_INIT_SP_ADDR         0x5c040000 /* end of internal SRAM */
+
+/*
+ * environment
+ */
+#define CONFIG_ENV_IS_NOWHERE
+#define CONFIG_BUILD_ENVCRC
+#define CONFIG_ENV_SIZE 0x200
+#define CONFIG_SYS_CONSOLE_IS_IN_ENV
+#define CONFIG_EXTRA_ENV_SETTINGS  \
+	"stdin=usbtty\0"           \
+	"stdout=usbtty\0"          \
+	"stderr=usbtty"
+#define CONFIG_BOOTARGS "mtdparts=Msys_Diskonchip_G4:1536k(protected_part)ro,1024k(bootloader_part),-(filesys_part) \
+ip=192.168.11.102:::255.255.255.0:treo:usb0"
+#define CONFIG_BOOTDELAY   3
+
+#if 0 /* example: try 2nd mmc partition, then nand */
+#define CONFIG_BOOTCOMMAND                                              \
+	"mmc rescan; "                                                  \
+	"if mmcinfo && ext2load mmc 0:2 0xa1000000 uImage; then "       \
+	    "bootm 0xa1000000; "					\
+	"elif nand read 0xa1000000 0x280000 0x240000; then "            \
+	    "bootm 0xa1000000; "					\
+	"fi; "
+#endif
+
+/* u-boot lives at end of SDRAM, so use start of SDRAM for stand alone apps */
+#define CONFIG_STANDALONE_LOAD_ADDR 0xa0000000
+
+#define CONFIG_SYS_DCACHE_OFF
+#define CONFIG_SYS_ICACHE_OFF
+
+#endif  /* __CONFIG_H */
diff --git a/tools/palmtreo680/flash_u-boot.c b/tools/palmtreo680/flash_u-boot.c
new file mode 100644
index 0000000..cc0afec
--- /dev/null
+++ b/tools/palmtreo680/flash_u-boot.c
@@ -0,0 +1,177 @@
+/*
+ * Copyright (C) 2013 Mike Dunn <mikedunn@newsguy.com>
+ *
+ * This file is released under the terms of GPL v2 and any later version.
+ * See the file COPYING in the root directory of the source tree for details.
+ *
+ *
+ * This is a userspace Linux utility that, when run on the Treo 680, will
+ * program u-boot to flash.  The docg4 driver *must* be loaded with the
+ * reliable_mode and ignore_badblocks parameters enabled:
+ *
+ *        modprobe docg4 ignore_badblocks=1 reliable_mode=1
+ *
+ * This utility writes the concatenated spl + u-boot image to the start of the
+ * mtd device in the format expected by the IPL/SPL.  The image file and mtd
+ * device node are passed to the utility as arguments.  The blocks must have
+ * been erased beforehand.
+ *
+ * When you compile this, note that it links to libmtd from mtd-utils, so ensure
+ * that your include and lib paths include this.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <string.h>
+#include <sys/types.h>
+#include <unistd.h>
+#include <errno.h>
+#include <mtd/mtd-user.h>
+#include "libmtd.h"
+
+#define RELIABLE_BLOCKSIZE  0x10000 /* block capacity in reliable mode */
+#define STANDARD_BLOCKSIZE  0x40000 /* block capacity in normal mode */
+#define PAGESIZE 512
+#define PAGES_PER_BLOCK 512
+#define OOBSIZE 7		/* available to user (16 total) */
+
+uint8_t ff_oob[OOBSIZE] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
+
+/* this is the magic number the IPL looks for (ASCII "BIPO") */
+uint8_t page0_oob[OOBSIZE] = {'B', 'I', 'P', 'O', 0xff, 0xff, 0xff};
+
+int main(int argc, char * const argv[])
+{
+	int devfd, datafd, num_blocks, block;
+	off_t file_size;
+	libmtd_t mtd_desc;
+	struct mtd_dev_info devinfo;
+	uint8_t *blockbuf;
+	char response[8];
+
+	if (argc != 3) {
+		printf("usage: %s <image file> <mtd dev node>\n", argv[0]);
+		exit(-1);
+	}
+
+	mtd_desc = libmtd_open();
+	if (mtd_desc == NULL) {
+		fprintf(stderr, "can't initialize libmtd\n");
+		exit(-1);
+	}
+
+	/* open the spl image file and mtd device */
+	datafd = open(argv[1], O_RDONLY);
+	if (datafd == -1) {
+		perror(argv[1]);
+		exit(-1);
+	}
+	devfd = open(argv[2], O_WRONLY);
+	if (devfd == -1) {
+		perror(argv[2]);
+		exit(-1);
+	}
+	if (mtd_get_dev_info(mtd_desc, argv[2], &devinfo) < 0) {
+		fprintf(stderr, "mtd_get_dev_info failed\n");
+		exit(-1);
+	}
+
+	/* determine the number of blocks needed by the image */
+	file_size = lseek(datafd, 0, SEEK_END);
+	if (file_size == (off_t)-1) {
+		perror("lseek");
+		exit(-1);
+	}
+	num_blocks = (file_size + RELIABLE_BLOCKSIZE - 1) / RELIABLE_BLOCKSIZE;
+	file_size = lseek(datafd, 0, SEEK_SET);
+	if (file_size == (off_t)-1) {
+		perror("lseek");
+		exit(-1);
+	}
+	printf("The mtd partition contains %d blocks\n", devinfo.eb_cnt);
+	printf("U-boot will occupy %d blocks\n", num_blocks);
+	if (num_blocks > devinfo.eb_cnt) {
+		fprintf(stderr, "Insufficient blocks on partition\n");
+		exit(-1);
+	}
+
+	printf("Do you want to proceed?\n");
+	scanf("%s", response);
+	if ((response[0] != 'y') && (response[0] != 'Y')) {
+		printf("Exiting\n");
+		close(devfd);
+		close(datafd);
+		exit(-1);
+	}
+
+	blockbuf = malloc(RELIABLE_BLOCKSIZE);
+	if (blockbuf == NULL) {
+		perror("malloc");
+		exit(-1);
+	}
+
+	for (block = 0; block < num_blocks; block++) {
+		int ofs, page;
+		ssize_t read_ret;
+		uint8_t *pagebuf = blockbuf, *buf = blockbuf;
+		uint8_t *oobbuf = page0_oob; /* magic num in oob of 1st page */
+		size_t len = RELIABLE_BLOCKSIZE;
+		int ret;
+
+#if 0 /* to minimize risk, require the user to erase the partition beforehand */
+		printf("Block %d: erasing\r", block + 1);
+		ret = mtd_erase(mtd_desc, &devinfo, devfd, block);
+		if (ret) {
+			fprintf(stderr,
+				"\nmtd_erase on block %d returned %d\n",
+				block + 1, ret);
+			exit(-1);
+		}
+#endif
+
+		/* read data for one block from file */
+		while (len != 0 && (read_ret = read(datafd, buf, len)) != 0) {
+			if (read_ret == -1) {
+				if (errno == EINTR)
+					continue;
+				perror("read");
+				exit(-1);
+			}
+			len -= read_ret;
+			buf += read_ret;
+		}
+
+		printf("Block %d: writing\r", block + 1);
+		fflush(stdout);
+
+		for (page = 0, ofs = 0;
+		     page < PAGES_PER_BLOCK;
+		     page++, ofs += PAGESIZE) {
+			if (page & 0x04)  /* Odd-numbered 2k page */
+				continue; /* skipped in reliable mode */
+
+			ret = mtd_write(mtd_desc, &devinfo, devfd, block, ofs,
+					pagebuf, PAGESIZE, oobbuf, OOBSIZE,
+					MTD_OPS_PLACE_OOB);
+			if (ret) {
+				fprintf(stderr,
+					"\nmtd_write returned %d on block %d, ofs %x\n",
+					ret, block + 1, ofs);
+				exit(-1);
+			}
+			oobbuf = ff_oob;  /* oob for subsequent pages */
+
+			if (page & 0x01)  /* odd-numbered subpage */
+				pagebuf += PAGESIZE;
+		}
+	}
+
+	printf("\nDone\n");
+
+	close(devfd);
+	close(datafd);
+	free(blockbuf);
+	return 0;
+}
-- 
1.7.8.6

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device Mike Dunn
@ 2013-04-11 19:14   ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:14 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> This adds the definitions required to support the LCD device on the Palm
> Treo 680.
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>

Reviewed-by: Marek Vasut <marex@denx.de>

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer Mike Dunn
@ 2013-04-11 19:15   ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:15 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> Make lcd_init() a weak pointer so that boards can overload it if necessary.
>  The palmtreo680 board needs to wiggle some gpios and configure the pwm
> controller in order to get the lcd and its backlight working.
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>

Reviewed-by: Marek Vasut <marex@denx.de>

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode()
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode() Mike Dunn
@ 2013-04-11 19:16   ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:16 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> If CONFIG_USB_DEV_PULLUP_GPIO is defined, a link error occurs because the
> set_GPIO_mode() helper function is not implemented.  This function doesn't
> do much except make the code a little more readable, so I just manually
> coded its equivalent and removed the prototype from the header file.  It
> is invoked no where else in the code.
> 
> While I was at it, I noticed that two other function prototypes in the same
> header file are also neither implemented nor invoked anywhere, so I removed
> them as well.
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>

Reviewed-by: Marek Vasut <marex@denx.de>

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux Mike Dunn
@ 2013-04-11 19:18   ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:18 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> On the pxa270, if the udc device is not disabled before jumping to linux,
> the device fails to initialize in linux because it was left in a running
> state, and the linux driver assumes that it is in a disabled state.
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>

I hope this won't break other platforms. Tom, can you test?

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel Mike Dunn
@ 2013-04-11 19:19   ` Marek Vasut
  2013-04-12 12:01     ` Mike Dunn
  0 siblings, 1 reply; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:19 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> This patch adds the bitrev library from the linux kernel.  This is a simple
> algorithm that uses an 8 bit look-up table to reverse the bits in data
> types of 8, 16, or 32 bit widths.  The docg4 nand flash driver uses it.
> 
> [port from linux kernel 2.6.20 commit
> a5cfc1ec58a07074dacb6aa8c79eff864c966d12]

Why did you port it from such an ancient kernel? Newer version is not an option?

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash Mike Dunn
@ 2013-04-11 19:19   ` Marek Vasut
  2013-04-12 16:29     ` Scott Wood
  2013-04-11 21:00   ` Scott Wood
  1 sibling, 1 reply; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:19 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> This patch adds a driver for the diskonchip G4 nand flash device.  It is
> based on the driver from the linux kernel.
> 
> This also includes a separate SPL driver.  A separate SPL driver is used
> because the device operates in a different mode (reliable mode) when
> loading a boot image, and also because the storage format of the boot
> image is different from normal data (pages are stored redundantly).  The
> SPL driver basically mimics how a typical IPL reads data from the device. 
> The special operating mode and storage format are used to compensate for
> the fact that the IPL does not contain the BCH ecc decoding algorithm (due
> to size constraints).  Although the u-boot SPL *could* use ecc, it
> operates like an IPL for the sake of simplicity and uniformity, since the
> IPL and SPL share the task of loading the u-boot image. As a side benefit,
> the SPL driver is very small.
> 
> [port from linux kernel 3.4 commit
> 570469f3bde7f71cc1ece07a18d54a05b6a8775d]

Scott, this really is your turf.

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board Mike Dunn
@ 2013-04-11 19:20   ` Marek Vasut
  2013-04-12 12:51     ` Mike Dunn
  0 siblings, 1 reply; 28+ messages in thread
From: Marek Vasut @ 2013-04-11 19:20 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> A quick overview of u-boot implementation on the treo 680...
> 
> The treo 680 has a Diskonchip G4 nand flash chip.  This device has a 2k
> region that maps to the system bus at the reset vector in a NOR-like
> fashion so that it can be used as the boot device.  The phone is shipped
> with this 2k region configured as write-protected (can't be modified) and
> programmed with an initial program loader (IPL).  At power-up, this IPL
> loads the contents of two flash blocks to SDRAM and jumps to it.  The
> capacity of the two blocks is not large enough to hold all of u-boot, so a
> u-boot SPL is used.  To conserve flash space, these two blocks and the
> necessary number of subsequent blocks are programmed with a concatenated
> spl + u-boot image.  That way, the IPL will also load a portion of u-boot
> proper, and when the spl runs, it relocates the portion of u-boot that the
> IPL has already loaded, and then resumes loading the remaining part of
> u-boot before jumping to it.
> 
> The default_environment is used (CONFIG_ENV_IS_NOWHERE) because I didn't
> think that having a writable environment was worth the cost of a flash
> block, although adding it would be straightforward.  I abuse the
> CONFIG_EXTRA_ENV_SETTINGS option to specify the usbtty for the console
> (CONFIG_SYS_CONSOLE_IS_IN_ENV).
> 
> Support for the LCD is included, but currently it is only useful for
> displaying the u-boot splash screen.  But if u-boot is built without the
> usbtty console, it does display the auto-boot progress nicely.
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>

I think the tool shall really go as a separate patch. Besides, can the tool not 
be implemented as a part of u-boot's mkimage infrastructure?

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash Mike Dunn
  2013-04-11 19:19   ` Marek Vasut
@ 2013-04-11 21:00   ` Scott Wood
  2013-04-12 13:36     ` Mike Dunn
  2013-04-12 17:27     ` Marek Vasut
  1 sibling, 2 replies; 28+ messages in thread
From: Scott Wood @ 2013-04-11 21:00 UTC (permalink / raw)
  To: u-boot

On 04/10/2013 07:45:27 PM, Mike Dunn wrote:
> This patch adds a driver for the diskonchip G4 nand flash device.  It  
> is based
> on the driver from the linux kernel.
> 
> This also includes a separate SPL driver.  A separate SPL driver is  
> used because
> the device operates in a different mode (reliable mode) when loading  
> a boot
> image, and also because the storage format of the boot image is  
> different from
> normal data (pages are stored redundantly).  The SPL driver basically  
> mimics how
> a typical IPL reads data from the device.  The special operating mode  
> and
> storage format are used to compensate for the fact that the IPL does  
> not contain
> the BCH ecc decoding algorithm (due to size constraints).  Although  
> the u-boot
> SPL *could* use ecc, it operates like an IPL for the sake of  
> simplicity and
> uniformity, since the IPL and SPL share the task of loading the  
> u-boot image.
> As a side benefit, the SPL driver is very small.
> 
> [port from linux kernel 3.4 commit  
> 570469f3bde7f71cc1ece07a18d54a05b6a8775d]
> 
> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
> ---
>  drivers/mtd/nand/Makefile    |    2 +
>  drivers/mtd/nand/docg4.c     | 1035  
> ++++++++++++++++++++++++++++++++++++++++++
>  drivers/mtd/nand/docg4_spl.c |  222 +++++++++
>  include/linux/mtd/docg4.h    |  134 ++++++
>  4 files changed, 1393 insertions(+), 0 deletions(-)
>  create mode 100644 drivers/mtd/nand/docg4.c
>  create mode 100644 drivers/mtd/nand/docg4_spl.c
>  create mode 100644 include/linux/mtd/docg4.h
[snip]
> +#ifdef DEBUG_DOCG4
> +#define dbg(format, arg...) printf("DEBUG: " format, ##arg)
> +#else
> +#define dbg(format, arg...) do {} while (0)
> +#endif

Maybe use MTDDEBUG?

Otherwise:
Acked-by: Scott Wood <scottwood@freescale.com>

-Scott

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel
  2013-04-11 19:19   ` Marek Vasut
@ 2013-04-12 12:01     ` Mike Dunn
  2013-04-12 17:28       ` Marek Vasut
  2013-04-13 19:27       ` Wolfgang Denk
  0 siblings, 2 replies; 28+ messages in thread
From: Mike Dunn @ 2013-04-12 12:01 UTC (permalink / raw)
  To: u-boot

On 04/11/2013 12:19 PM, Marek Vasut wrote:
> Dear Mike Dunn,
> 
>> This patch adds the bitrev library from the linux kernel.  This is a simple
>> algorithm that uses an 8 bit look-up table to reverse the bits in data
>> types of 8, 16, or 32 bit widths.  The docg4 nand flash driver uses it.
>>
>> [port from linux kernel 2.6.20 commit
>> a5cfc1ec58a07074dacb6aa8c79eff864c966d12]
> 
> Why did you port it from such an ancient kernel? Newer version is not an option?


Maybe I misunderstood and gave the wrong information (probably, now that I think
about it).  I took it fom the latest kernel, but reported the commit that added
it to the kernel.

In this case, it's a simple algorithm and only a couple trivial changes were
made since it was first added to the kernel, so the error is probably
inconsequential, but I'll resubmit, reporting the HEAD of the kernel I took it
from if you like.

BTW, I did the same for the docg4 driver, but I did the u-boot port a while ago,
so in that case it's correct, at least practically.  Since I did the port, the
kernel docg4 driver had some enhancements (reliable mode) that still need to be
brought into u-boot.

Thanks Marek,
Mike

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board
  2013-04-11 19:20   ` Marek Vasut
@ 2013-04-12 12:51     ` Mike Dunn
  2013-04-12 17:26       ` Marek Vasut
  0 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-12 12:51 UTC (permalink / raw)
  To: u-boot

On 04/11/2013 12:20 PM, Marek Vasut wrote:
> Dear Mike Dunn,
> 
>> A quick overview of u-boot implementation on the treo 680...
>>
>> The treo 680 has a Diskonchip G4 nand flash chip.  This device has a 2k
>> region that maps to the system bus at the reset vector in a NOR-like
>> fashion so that it can be used as the boot device.  The phone is shipped
>> with this 2k region configured as write-protected (can't be modified) and
>> programmed with an initial program loader (IPL).  At power-up, this IPL
>> loads the contents of two flash blocks to SDRAM and jumps to it.  The
>> capacity of the two blocks is not large enough to hold all of u-boot, so a
>> u-boot SPL is used.  To conserve flash space, these two blocks and the
>> necessary number of subsequent blocks are programmed with a concatenated
>> spl + u-boot image.  That way, the IPL will also load a portion of u-boot
>> proper, and when the spl runs, it relocates the portion of u-boot that the
>> IPL has already loaded, and then resumes loading the remaining part of
>> u-boot before jumping to it.
>>
>> The default_environment is used (CONFIG_ENV_IS_NOWHERE) because I didn't
>> think that having a writable environment was worth the cost of a flash
>> block, although adding it would be straightforward.  I abuse the
>> CONFIG_EXTRA_ENV_SETTINGS option to specify the usbtty for the console
>> (CONFIG_SYS_CONSOLE_IS_IN_ENV).
>>
>> Support for the LCD is included, but currently it is only useful for
>> displaying the u-boot splash screen.  But if u-boot is built without the
>> usbtty console, it does display the auto-boot progress nicely.
>>
>> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
> 
> I think the tool shall really go as a separate patch. Besides, can the tool not 
> be implemented as a part of u-boot's mkimage infrastructure?


OK, I can make the flash_u-boot utility (which writes u-boot to the flash boot
blocks) a separate patch.

As for making it part of mkimage...  I didn't really consider that because based
on my (limited) knowledge, I figured they are unrelated.  As I understand it,
mkimage creates an OS image file that u-boot can parse and load.  flash_u-boot
is a utility that performs the task of writing u-boot itself to flash.

I figured that mine was a special case, since u-boot must be written in a
special format (redundant pages) and in a special manner (alternate 4k regions
skipped), with the flash device in a special mode, and so it can not be done in
the normal manner; e.g., 'nandwrite' from mtd-utils, or its u-boot 'nand write'
equivalent, even if you first ran the u-boot image through a separate utility
that simply converted the format of the image.

Hope that makes sense.  Any insight appreciated.  I'll take a look at what's in
the tools directory.

Thanks Marek,
Mike

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11 21:00   ` Scott Wood
@ 2013-04-12 13:36     ` Mike Dunn
  2013-04-12 17:27     ` Marek Vasut
  1 sibling, 0 replies; 28+ messages in thread
From: Mike Dunn @ 2013-04-12 13:36 UTC (permalink / raw)
  To: u-boot

On 04/11/2013 02:00 PM, Scott Wood wrote:
> On 04/10/2013 07:45:27 PM, Mike Dunn wrote:
>> This patch adds a driver for the diskonchip G4 nand flash device.  It is based
>> on the driver from the linux kernel.
>>
>> This also includes a separate SPL driver.  A separate SPL driver is used because
>> the device operates in a different mode (reliable mode) when loading a boot
>> image, and also because the storage format of the boot image is different from
>> normal data (pages are stored redundantly).  The SPL driver basically mimics how
>> a typical IPL reads data from the device.  The special operating mode and
>> storage format are used to compensate for the fact that the IPL does not contain
>> the BCH ecc decoding algorithm (due to size constraints).  Although the u-boot
>> SPL *could* use ecc, it operates like an IPL for the sake of simplicity and
>> uniformity, since the IPL and SPL share the task of loading the u-boot image.
>> As a side benefit, the SPL driver is very small.
>>
>> [port from linux kernel 3.4 commit 570469f3bde7f71cc1ece07a18d54a05b6a8775d]
>>
>> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
>> ---
>>  drivers/mtd/nand/Makefile    |    2 +
>>  drivers/mtd/nand/docg4.c     | 1035 ++++++++++++++++++++++++++++++++++++++++++
>>  drivers/mtd/nand/docg4_spl.c |  222 +++++++++
>>  include/linux/mtd/docg4.h    |  134 ++++++
>>  4 files changed, 1393 insertions(+), 0 deletions(-)
>>  create mode 100644 drivers/mtd/nand/docg4.c
>>  create mode 100644 drivers/mtd/nand/docg4_spl.c
>>  create mode 100644 include/linux/mtd/docg4.h
> [snip]
>> +#ifdef DEBUG_DOCG4
>> +#define dbg(format, arg...) printf("DEBUG: " format, ##arg)
>> +#else
>> +#define dbg(format, arg...) do {} while (0)
>> +#endif
> 
> Maybe use MTDDEBUG?


Ok.  Alternatively, I wouldn't mind pulling them out entirely.  It's been
behaving quite nicely, and amyway, in the past I used a JTAG emultor rather than
the printfs.


> 
> Otherwise:
> Acked-by: Scott Wood <scottwood@freescale.com>


Many thanks Scott,
Mike

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11 19:19   ` Marek Vasut
@ 2013-04-12 16:29     ` Scott Wood
  0 siblings, 0 replies; 28+ messages in thread
From: Scott Wood @ 2013-04-12 16:29 UTC (permalink / raw)
  To: u-boot

On 04/11/2013 02:19:37 PM, Marek Vasut wrote:
> Dear Mike Dunn,
> 
> > This patch adds a driver for the diskonchip G4 nand flash device.   
> It is
> > based on the driver from the linux kernel.
> >
> > This also includes a separate SPL driver.  A separate SPL driver is  
> used
> > because the device operates in a different mode (reliable mode) when
> > loading a boot image, and also because the storage format of the  
> boot
> > image is different from normal data (pages are stored  
> redundantly).  The
> > SPL driver basically mimics how a typical IPL reads data from the  
> device.
> > The special operating mode and storage format are used to  
> compensate for
> > the fact that the IPL does not contain the BCH ecc decoding  
> algorithm (due
> > to size constraints).  Although the u-boot SPL *could* use ecc, it
> > operates like an IPL for the sake of simplicity and uniformity,  
> since the
> > IPL and SPL share the task of loading the u-boot image. As a side  
> benefit,
> > the SPL driver is very small.
> >
> > [port from linux kernel 3.4 commit
> > 570469f3bde7f71cc1ece07a18d54a05b6a8775d]
> 
> Scott, this really is your turf.

I already acked it (it's up to Mike what he wants to do with dbg).   
Feel free to pick it up as part of the larger patchset -- it's a  
dependency for patch 7/7 that adds the board support.

-Scott

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board
  2013-04-12 12:51     ` Mike Dunn
@ 2013-04-12 17:26       ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-12 17:26 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> On 04/11/2013 12:20 PM, Marek Vasut wrote:
> > Dear Mike Dunn,
> > 
> >> A quick overview of u-boot implementation on the treo 680...
> >> 
> >> The treo 680 has a Diskonchip G4 nand flash chip.  This device has a 2k
> >> region that maps to the system bus at the reset vector in a NOR-like
> >> fashion so that it can be used as the boot device.  The phone is shipped
> >> with this 2k region configured as write-protected (can't be modified)
> >> and programmed with an initial program loader (IPL).  At power-up, this
> >> IPL loads the contents of two flash blocks to SDRAM and jumps to it. 
> >> The capacity of the two blocks is not large enough to hold all of
> >> u-boot, so a u-boot SPL is used.  To conserve flash space, these two
> >> blocks and the necessary number of subsequent blocks are programmed
> >> with a concatenated spl + u-boot image.  That way, the IPL will also
> >> load a portion of u-boot proper, and when the spl runs, it relocates
> >> the portion of u-boot that the IPL has already loaded, and then resumes
> >> loading the remaining part of u-boot before jumping to it.
> >> 
> >> The default_environment is used (CONFIG_ENV_IS_NOWHERE) because I didn't
> >> think that having a writable environment was worth the cost of a flash
> >> block, although adding it would be straightforward.  I abuse the
> >> CONFIG_EXTRA_ENV_SETTINGS option to specify the usbtty for the console
> >> (CONFIG_SYS_CONSOLE_IS_IN_ENV).
> >> 
> >> Support for the LCD is included, but currently it is only useful for
> >> displaying the u-boot splash screen.  But if u-boot is built without the
> >> usbtty console, it does display the auto-boot progress nicely.
> >> 
> >> Signed-off-by: Mike Dunn <mikedunn@newsguy.com>
> > 
> > I think the tool shall really go as a separate patch. Besides, can the
> > tool not be implemented as a part of u-boot's mkimage infrastructure?
> 
> OK, I can make the flash_u-boot utility (which writes u-boot to the flash
> boot blocks) a separate patch.
> 
> As for making it part of mkimage...  I didn't really consider that because
> based on my (limited) knowledge, I figured they are unrelated.  As I
> understand it, mkimage creates an OS image file that u-boot can parse and
> load.  flash_u-boot is a utility that performs the task of writing u-boot
> itself to flash.

It can create an bootloader image that can be written to flash using standard 
mtd utilities. Does this not cut it for you? Why do you need a separate flasher, 
because the G4 is special ?

> I figured that mine was a special case, since u-boot must be written in a
> special format (redundant pages) and in a special manner (alternate 4k
> regions skipped), with the flash device in a special mode, and so it can
> not be done in the normal manner; e.g., 'nandwrite' from mtd-utils, or its
> u-boot 'nand write' equivalent, even if you first ran the u-boot image
> through a separate utility that simply converted the format of the image.
> 
> Hope that makes sense.  Any insight appreciated.  I'll take a look at
> what's in the tools directory.

I see ... so the G4 is such a horrible beast :( OK

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-11 21:00   ` Scott Wood
  2013-04-12 13:36     ` Mike Dunn
@ 2013-04-12 17:27     ` Marek Vasut
  2013-04-12 17:34       ` Scott Wood
  1 sibling, 1 reply; 28+ messages in thread
From: Marek Vasut @ 2013-04-12 17:27 UTC (permalink / raw)
  To: u-boot

Dear Scott Wood,

[...]
> 
> [snip]
> 
> > +#ifdef DEBUG_DOCG4
> > +#define dbg(format, arg...) printf("DEBUG: " format, ##arg)
> > +#else
> > +#define dbg(format, arg...) do {} while (0)
> > +#endif

There already is a debugging facility in include/common.h too. And it does the 
same thing too. MTDDEBUG might work as well.

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel
  2013-04-12 12:01     ` Mike Dunn
@ 2013-04-12 17:28       ` Marek Vasut
  2013-04-13 19:27       ` Wolfgang Denk
  1 sibling, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-12 17:28 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> On 04/11/2013 12:19 PM, Marek Vasut wrote:
> > Dear Mike Dunn,
> > 
> >> This patch adds the bitrev library from the linux kernel.  This is a
> >> simple algorithm that uses an 8 bit look-up table to reverse the bits
> >> in data types of 8, 16, or 32 bit widths.  The docg4 nand flash driver
> >> uses it.
> >> 
> >> [port from linux kernel 2.6.20 commit
> >> a5cfc1ec58a07074dacb6aa8c79eff864c966d12]
> > 
> > Why did you port it from such an ancient kernel? Newer version is not an
> > option?
> 
> Maybe I misunderstood and gave the wrong information (probably, now that I
> think about it).  I took it fom the latest kernel, but reported the commit
> that added it to the kernel.
> 
> In this case, it's a simple algorithm and only a couple trivial changes
> were made since it was first added to the kernel, so the error is probably
> inconsequential, but I'll resubmit, reporting the HEAD of the kernel I
> took it from if you like.
> 
> BTW, I did the same for the docg4 driver, but I did the u-boot port a while
> ago, so in that case it's correct, at least practically.  Since I did the
> port, the kernel docg4 driver had some enhancements (reliable mode) that

Knowing which tag in linux-stable you pulled it from is a good information too, 
yes.

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash
  2013-04-12 17:27     ` Marek Vasut
@ 2013-04-12 17:34       ` Scott Wood
  0 siblings, 0 replies; 28+ messages in thread
From: Scott Wood @ 2013-04-12 17:34 UTC (permalink / raw)
  To: u-boot

On 04/12/2013 12:27:09 PM, Marek Vasut wrote:
> Dear Scott Wood,
> 
> [...]
> >
> > [snip]
> >
> > > +#ifdef DEBUG_DOCG4
> > > +#define dbg(format, arg...) printf("DEBUG: " format, ##arg)
> > > +#else
> > > +#define dbg(format, arg...) do {} while (0)
> > > +#endif
> 
> There already is a debugging facility in include/common.h too. And it  
> does the
> same thing too. MTDDEBUG might work as well.

I already pointed out MTDDEBUG, though debug() may be a better fit as  
it doesn't require adding debug levels, and since this driver's usage  
doesn't correspond to CONFIG_MTD_DEBUG in Linux (which appears to have  
been removed from Linux -- removal from U-Boot should likely follow).

Mike said he may just remove the debug messages entirely (maybe also  
from the Linux driver?), making it moot.

-Scott

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel
  2013-04-12 12:01     ` Mike Dunn
  2013-04-12 17:28       ` Marek Vasut
@ 2013-04-13 19:27       ` Wolfgang Denk
  1 sibling, 0 replies; 28+ messages in thread
From: Wolfgang Denk @ 2013-04-13 19:27 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

In message <5167F7B4.3070007@newsguy.com> you wrote:
>
> In this case, it's a simple algorithm and only a couple trivial changes were
> made since it was first added to the kernel, so the error is probably
> inconsequential, but I'll resubmit, reporting the HEAD of the kernel I took it
> from if you like.

Please use the git commit ID of the exact kernel version which you
used to copy the code from, not any older nor any more recent version.

Thanks.

Best regards,

Wolfgang Denk

-- 
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de
A good marriage would be between a blind wife and deaf husband.
                                               -- Michel de Montaigne

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support
  2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
                   ` (6 preceding siblings ...)
  2013-04-11  0:45 ` [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board Mike Dunn
@ 2013-04-14 17:44 ` Marek Vasut
  2013-04-14 20:10   ` Mike Dunn
  7 siblings, 1 reply; 28+ messages in thread
From: Marek Vasut @ 2013-04-14 17:44 UTC (permalink / raw)
  To: u-boot

Hi Mike,

> Hi,
> 
> This patchset adds support for the Palm Treo 680 smartphone.  I had to make
> some minor tweaks to u-boot to get things working.  Most of these changes
> are small, and most only touch the pxa arch.
> 
> Thanks for looking.

I pushed what I considered ok to u-boot-pxa/master, please start your reworks on 
top of that.

Thanks!

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support
  2013-04-14 17:44 ` [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Marek Vasut
@ 2013-04-14 20:10   ` Mike Dunn
  2013-04-14 20:13     ` Marek Vasut
  0 siblings, 1 reply; 28+ messages in thread
From: Mike Dunn @ 2013-04-14 20:10 UTC (permalink / raw)
  To: u-boot

On 04/14/2013 10:44 AM, Marek Vasut wrote:
> Hi Mike,
> 
>> Hi,
>>
>> This patchset adds support for the Palm Treo 680 smartphone.  I had to make
>> some minor tweaks to u-boot to get things working.  Most of these changes
>> are small, and most only touch the pxa arch.
>>
>> Thanks for looking.
> 
> I pushed what I considered ok to u-boot-pxa/master, please start your reworks on 
> top of that.


Will do.  Thanks a lot for your time and effort in reviewing!

I forgot to add 'v3' to the subject line of patch 5/8 in the last set I sent:

[PATCH 5/8] lib: import bitrev library from the linux kernel

Don't know if that will cause problems or not.  The contents of the patch are
unchanged from v2, but the description added the HEAD commit from the kernel I
took the code from, as we discussed.

Thanks again,
Mike

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support
  2013-04-14 20:10   ` Mike Dunn
@ 2013-04-14 20:13     ` Marek Vasut
  0 siblings, 0 replies; 28+ messages in thread
From: Marek Vasut @ 2013-04-14 20:13 UTC (permalink / raw)
  To: u-boot

Dear Mike Dunn,

> On 04/14/2013 10:44 AM, Marek Vasut wrote:
> > Hi Mike,
> > 
> >> Hi,
> >> 
> >> This patchset adds support for the Palm Treo 680 smartphone.  I had to
> >> make some minor tweaks to u-boot to get things working.  Most of these
> >> changes are small, and most only touch the pxa arch.
> >> 
> >> Thanks for looking.
> > 
> > I pushed what I considered ok to u-boot-pxa/master, please start your
> > reworks on top of that.
> 
> Will do.  Thanks a lot for your time and effort in reviewing!
> 
> I forgot to add 'v3' to the subject line of patch 5/8 in the last set I
> sent:
> 
> [PATCH 5/8] lib: import bitrev library from the linux kernel
> 
> Don't know if that will cause problems or not.  The contents of the patch
> are unchanged from v2, but the description added the HEAD commit from the
> kernel I took the code from, as we discussed.

Don't worry, I picked most of them already.

Best regards,
Marek Vasut

^ permalink raw reply	[flat|nested] 28+ messages in thread

end of thread, other threads:[~2013-04-14 20:13 UTC | newest]

Thread overview: 28+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-04-11  0:45 [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Mike Dunn
2013-04-11  0:45 ` [U-Boot] [PATCH v2 1/7] pxa_lcd: add the ACX544AKN lcd device Mike Dunn
2013-04-11 19:14   ` Marek Vasut
2013-04-11  0:45 ` [U-Boot] [PATCH v2 2/7] pxa_lcd: make lcd_enable() a weak pointer Mike Dunn
2013-04-11 19:15   ` Marek Vasut
2013-04-11  0:45 ` [U-Boot] [PATCH v2 3/7] pxa27x_udc: remove call to unimplemented set_GPIO_mode() Mike Dunn
2013-04-11 19:16   ` Marek Vasut
2013-04-11  0:45 ` [U-Boot] [PATCH v2 4/7] arm: bootm: call udc_disable()before booting linux Mike Dunn
2013-04-11 19:18   ` Marek Vasut
2013-04-11  0:45 ` [U-Boot] [PATCH v2 5/7] lib: import bitrev library from the linux kernel Mike Dunn
2013-04-11 19:19   ` Marek Vasut
2013-04-12 12:01     ` Mike Dunn
2013-04-12 17:28       ` Marek Vasut
2013-04-13 19:27       ` Wolfgang Denk
2013-04-11  0:45 ` [U-Boot] [PATCH v2 6/7] mtd: nand: add driver for diskonchip g4 nand flash Mike Dunn
2013-04-11 19:19   ` Marek Vasut
2013-04-12 16:29     ` Scott Wood
2013-04-11 21:00   ` Scott Wood
2013-04-12 13:36     ` Mike Dunn
2013-04-12 17:27     ` Marek Vasut
2013-04-12 17:34       ` Scott Wood
2013-04-11  0:45 ` [U-Boot] [PATCH v2 7/7] add support for palm treo 680 board Mike Dunn
2013-04-11 19:20   ` Marek Vasut
2013-04-12 12:51     ` Mike Dunn
2013-04-12 17:26       ` Marek Vasut
2013-04-14 17:44 ` [U-Boot] [PATCH v2 0/7] palm treo 680 smartphone board support Marek Vasut
2013-04-14 20:10   ` Mike Dunn
2013-04-14 20:13     ` Marek Vasut

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.