[U-Boot] [PATCH 6/8] zmx25: Extended support for cpu and base boards

dietho at gmx.de dietho at gmx.de
Thu May 15 16:34:48 CEST 2014


From: Thomas Diener <dietho at gmx.de>

Added support for additional hardware variants.

Signed-off-by: Thomas Diener <dietho at gmx.de>
---

We don't use a linux kernel and have to do the complete
hardware setup in the boot loader.

 board/syteco/zmx25/lowlevel_init.S |   21 +
 board/syteco/zmx25/zmx25.c         | 1052 +++++++++++++++++++++++++++++++++---
 include/configs/zmx25.h            |   66 ++-
 3 files changed, 1064 insertions(+), 75 deletions(-)

diff --git a/board/syteco/zmx25/lowlevel_init.S b/board/syteco/zmx25/lowlevel_init.S
index 5eccf09..aa38459 100644
--- a/board/syteco/zmx25/lowlevel_init.S
+++ b/board/syteco/zmx25/lowlevel_init.S
@@ -92,6 +92,27 @@
 lowlevel_init:
 	init_aips
 	init_max
+
+	/* Setup of NOR flash CS */
+	write32 IMX_WEIM_CTRL_BASE + WEIM_CSCR0U, \
+		(WEIM_CSCR_U_WSC(14) | WEIM_CSCR_U_EDC(2))
+	write32 IMX_WEIM_CTRL_BASE + WEIM_CSCR0L, \
+		(WEIM_CSCR_L_OAE(1) | WEIM_CSCR_L_OEN(1) | \
+		WEIM_CSCR_L_DSZ(5)| WEIM_CSCR_L_CS_EN)
+	write32 IMX_WEIM_CTRL_BASE + WEIM_CSCR0A, \
+		(WEIM_CSCR_A_RWA(1) | WEIM_CSCR_A_RWN(1))
+
+	/* Set some memory access priorities */
+	write32 IMX_M3IF_CTRL_BASE + M3IF_CTL, M3IF_CTL_MRRP(1)
+	write32	IMX_MAX_BASE + MAX_MGPCR0, MAX_MGPCR_AULB(0x4)
+	write32	IMX_MAX_BASE + MAX_MGPCR1, MAX_MGPCR_AULB(0x4)
+	write32	IMX_MAX_BASE + MAX_MGPCR2, MAX_MGPCR_AULB(0x4)
+	write32	IMX_MAX_BASE + MAX_MGPCR3, MAX_MGPCR_AULB(0x4)
+	write32	IMX_MAX_BASE + MAX_MGPCR4, MAX_MGPCR_AULB(0x4)
+
+	/* Need this early for voltage sequence on G305 */
+	write32 IMX_IOPADMUX_BASE + 0x38c, 5 //Offset 0x38C IOPADMUX_SD1_CLK
+
 	init_clocks
 	init_lpddr
 	mov	pc, lr
diff --git a/board/syteco/zmx25/zmx25.c b/board/syteco/zmx25/zmx25.c
index bdbf02a..f6c018d 100644
--- a/board/syteco/zmx25/zmx25.c
+++ b/board/syteco/zmx25/zmx25.c
@@ -1,4 +1,7 @@
 /*
+ * (c) 2014 Graf-Syteco, Thomas Diener
+ * <dietho at gmx.de>
+ *
  * (c) 2011 Graf-Syteco, Matthias Weisser
  * <weisserm at arcor.de>
  *
@@ -14,63 +17,705 @@
  *
  * SPDX-License-Identifier:	GPL-2.0+
  */
+
 #include <common.h>
-#include <asm/gpio.h>
+#include <i2c.h>
+#include <spi.h>
+#include <video.h>
+#include <netdev.h>
+#include <mpr121.h>
+#include <fma1125.h>
+#include <polytouch.h>
+
 #include <asm/io.h>
+#include <asm/gpio.h>
 #include <asm/arch/imx-regs.h>
 #include <asm/arch/iomux-mx25.h>
+#include <asm/imx-common/mxc_i2c.h>
+
+
+#define ZMX25_CPU_BOARD_TYPE_UNKNOWN	0
+#define ZMX25_CPU_BOARD_TYPE_G282A0	1
+#define ZMX25_CPU_BOARD_TYPE_G282A1	2
+#define ZMX25_CPU_BOARD_TYPE_G292	3
+#define ZMX25_CPU_BOARD_TYPE_G305	4
+
+#define ZMX25_IO_BOARD_TYPE_NONE	0
+#define ZMX25_IO_BOARD_TYPE_UNKNOWN	1
+#define ZMX25_IO_BOARD_TYPE_G283	2
+#define ZMX25_IO_BOARD_TYPE_G297	3
+
+#define ZMX25_FIXED_EEPROM_ADDR_APP	0x80
+#define ZMX25_FIXED_EEPROM_ADDR_BI1	0xA0
+#define ZMX25_FIXED_EEPROM_ADDR_BI2	0xC0
+
+#define ZMX25_BOOT_MODE_SLOW		0x55AAAA55
+#define ZMX25_BOOT_MODE_FAST		0xAA5555AA
 
 DECLARE_GLOBAL_DATA_PTR;
 
-int board_init()
+static inline u32 hw_setup_common(void);
+
+static inline void hw_setup_cpu_g282g292(void);
+static inline void hw_setup_cpu_g282(void);
+static inline void hw_setup_cpu_g282a1(void);
+static inline void hw_setup_cpu_g292(void);
+static inline void hw_setup_cpu_g305(void);
+
+static inline void hw_setup_io_g283(void);
+static inline void hw_setup_io_g297(void);
+
+static const iomux_v3_cfg_t can_pads[] = {
+	CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_GPIO_A__CAN1_TX, 0)),
+	CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_GPIO_B__CAN1_RX,
+				PAD_CTL_PUS_100K_DOWN)),
+	CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_GPIO_C__CAN2_TX, 0)),
+	CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_GPIO_D__CAN2_RX, 0)),
+};
+
+static const struct fma1125_register_tbl fma1125_config[] = {
+	{ FMA1125_COLD_RESET,	0x00 },	/* cold reset */
+	{ FMA1125_REGISTER_CHECK,	0xFF },	/* register check */
+	{ FMA1125_GINT_INTERRUPT_MASK,	0xFE },	/* Mask all interrupts */
+	{ FMA1125_GINT_INTERRUPT_CLEAR,	0xFF },	/* Mask all interrupts */
+	{ FMA1125_GPIO_DIRECTION,	0x00 },	/* All GPIOs are output */
+	{ FMA1125_GPIO_CONFIGURATION,	0x0f },	/* All GPIOs are GPIOs */
+	{ FMA1125_GPIO_DATA_OUT,	0x03 },	/* Switch the LEDs off */
+
+	/* P0A - PA7 Alpha; sensitivity of each sensor input*/
+	{ FMA1125_PA0_ALPHA,	0x0A },
+	{ FMA1125_PA1_ALPHA,	0x0A },
+	{ FMA1125_PA2_ALPHA,	0x0A },
+	{ FMA1125_PA3_ALPHA,	0x0A },
+	{ FMA1125_PA4_ALPHA,	0x0A },
+	{ FMA1125_PA5_ALPHA,	0x0A },
+	{ FMA1125_PA6_ALPHA,	0x0A },
+	{ FMA1125_PA7_ALPHA,	0x0A },
+
+	{ FMA1125_REFERENCE_DELAY, 0x50 },	/* Reference delay */
+	{ FMA1125_BETA,	4 },	/* Beta */
+	{ FMA1125_AIC_WAIT_TIME,	0x27 },	/* AIC wait time */
+
+	/* PA0 - PA7 Strength threshold to 2/10 of integration time */
+	{ FMA1125_PA0_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA1_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA2_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA3_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA4_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA5_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA6_STRENGTH_THRESHOLD,	0x28 },
+	{ FMA1125_PA7_STRENGTH_THRESHOLD,	0x28 },
+
+	{ FMA1125_INTEGRATION_TIME, 0xC8 },	/* Integration time 200 */
+	{ FMA1125_FEATURE_SELECT, 0x04 },	/* Enable APIS mode 2 */
+	{ FMA1125_CONTROL_1,	0xA0 }, /* Enable ACTIVE mode, LED dimming) */
+	{ FMA1125_CONTROL_2,	0x02 }, /* Interrupt Polarity falling edge */
+	{ FMA1125_PA_CONFIGURATION,	0x00 },	/* PA0-PA7 sensor input pins */
+	{ FMA1125_PA03_RESISTOR_SELECT, FMA1125_PA3_R_SEL(3) |
+					FMA1125_PA2_R_SEL(1) |
+					FMA1125_PA1_R_SEL(1) |
+					FMA1125_PA0_R_SEL(1) },
+	{ FMA1125_PA47_RESISTOR_SELECT, FMA1125_PA7_R_SEL(3) |
+					FMA1125_PA6_R_SEL(1) |
+					FMA1125_PA5_R_SEL(1) |
+					FMA1125_PA4_R_SEL(1) },
+	{ FMA1125_WARM_RESET,	0x00 }, /* Perform a warm reset */
+};
+
+static const struct mpr121_register_tbl mpr121_config[] = {
+	/* Soft reset */
+	{ MPR121_ECR,	0x00 },
+	{ MPR121_SRST,	0x63 },
+
+	/* Settings according to AN3944 */
+	{ MPR121_MHD_RIS,	0x01 },
+	{ MPR121_NHD_RIS,	0x01 },
+	{ MPR121_NCL_RIS,	0x00 },
+	{ MPR121_FDL_RIS,	0x00 },
+
+	{ MPR121_MHD_FALL,	0x01 },
+	{ MPR121_NHD_FALL,	0x01 },
+	{ MPR121_NCL_FALL,	0xff },
+	{ MPR121_FDL_FALL,	0x02 },
+
+	{ MPR121_ELE0_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE0_THRESH_REL,	0x02 },
+	{ MPR121_ELE1_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE1_THRESH_REL,	0x02 },
+	{ MPR121_ELE2_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE2_THRESH_REL,	0x02 },
+	{ MPR121_ELE3_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE3_THRESH_REL,	0x02 },
+	{ MPR121_ELE4_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE4_THRESH_REL,	0x02 },
+	{ MPR121_ELE5_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE5_THRESH_REL,	0x02 },
+	{ MPR121_ELE6_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE6_THRESH_REL,	0x02 },
+	{ MPR121_ELE7_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE7_THRESH_REL,	0x02 },
+	{ MPR121_ELE8_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE8_THRESH_REL,	0x02 },
+	{ MPR121_ELE9_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE9_THRESH_REL,	0x02 },
+	{ MPR121_ELE10_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE10_THRESH_REL,	0x02 },
+	{ MPR121_ELE11_THRESH_TOUCH,	0x04 },
+	{ MPR121_ELE11_THRESH_REL,	0x02 },
+
+	{ MPR121_FILT_CDT,	0x04 },
+
+	{ MPR121_ELE0_CURRENT,	0x12 },
+	{ MPR121_ELE1_CURRENT,	0x12 },
+	{ MPR121_ELE2_CURRENT,	0x22 },
+	{ MPR121_ELE3_CURRENT,	0x20 },
+	{ MPR121_ELE4_CURRENT,	0x1e },
+	{ MPR121_ELE5_CURRENT,	0x1b },
+	{ MPR121_ELE6_CURRENT,	0x19 },
+	{ MPR121_ELE7_CURRENT,	0x18 },
+	{ MPR121_ELE8_CURRENT,	0x1a },
+	{ MPR121_ELE9_CURRENT,	0x1e },
+	{ MPR121_ELE10_CURRENT,	0x22 },
+	{ MPR121_ELE11_CURRENT,	0x23 },
+
+	{ MPR121_ELE0_1_CHARGE,	0x22 },
+	{ MPR121_ELE2_3_CHARGE,	0x22 },
+	{ MPR121_ELE4_5_CHARGE,	0x22 },
+	{ MPR121_ELE6_7_CHARGE,	0x22 },
+	{ MPR121_ELE8_9_CHARGE,	0x22 },
+	{ MPR121_ELE10_11_CHARGE,	0x22 },
+
+	{ MPR121_ECR,	0xCC },
+};
+
+static u32 cpu_board_type;
+static u32 io_board_type;
+static u32 have_touch_display;
+
+static inline u16 hw_g297_xfer_srio(u16 value)
 {
+	/* Set LCD PWR CTRL and release RESET */
+
+	struct spi_slave *spi;
+	u8 spi_in[2];
+	u8 spi_out[2];
+
+	writeb((WEIM_CSCR_U_EDC(5) | WEIM_CSCR_U_WWS(4)), IMX_WEIM_CS4);
+
+	spi_out[0] = value >> 8;
+	spi_out[1] = value;
+
+	spi = spi_setup_slave(2, 0, 1000000, 0);
+	spi_claim_bus(spi);
+	spi_xfer(spi, 16, spi_out, spi_in, SPI_XFER_BEGIN | SPI_XFER_END);
+	spi_release_bus(spi);
+	spi_free_slave(spi);
+
+	writeb((WEIM_CSCR_U_EDC(3) | WEIM_CSCR_U_WWS(4)), IMX_WEIM_CS4);
+	udelay(1000);
+	writeb((WEIM_CSCR_U_EDC(5) | WEIM_CSCR_U_WWS(4)), IMX_WEIM_CS4);
+
+	return	spi_in[0] | (spi_in[1] << 8);
+}
+
+static inline u32 hw_setup_common(void)
+{
+	struct ccm_regs *ccm;
+	u32 bt_uart_src;
+	u32 res;
+
+	ccm = (struct ccm_regs *)IMX_CCM_BASE;
+
+	have_touch_display = 0;
+
+	/* Setup of CAN1 signals */
+	imx_iomux_v3_setup_multiple_pads(can_pads, ARRAY_SIZE(can_pads));
+
+	/* Set CPU clock to 399MHz */
+	writel(((CCM_CCTL_AHB_DIV(2)) |
+		(CCM_CCTL_USB_DIV(3)) |
+		(CCM_CCTL_ARM_SRC)), &ccm->cctl);
+
+	/*
+	 * We decide on which board we are running according to BT_UART_SRC
+	 * bits in CRDR register of CCM. 0 -> G292, 1 -> G282
+	 */
+	bt_uart_src = (readl(&ccm->crdr) >> CCM_CRDR_BT_UART_SRC_SHIFT) &
+		CCM_CRDR_BT_UART_SRC_MASK;
+
+	/* Setup of cpu board */
+	if (bt_uart_src == 0) {
+		res = ZMX25_CPU_BOARD_TYPE_G292;
+		hw_setup_cpu_g282g292();
+		hw_setup_cpu_g292();
+		puts("zmx25: G292\n");
+	} else if (bt_uart_src == 1) {
+		res = ZMX25_CPU_BOARD_TYPE_G282A0;
+		hw_setup_cpu_g282g292();
+		hw_setup_cpu_g282();
+		puts("zmx25: G282A0\n");
+	} else if (bt_uart_src == 2) {
+		res = ZMX25_CPU_BOARD_TYPE_G282A1;
+		hw_setup_cpu_g282g292();
+		hw_setup_cpu_g282();
+		hw_setup_cpu_g282a1();
+		puts("zmx25: G282A1\n");
+	} else if (bt_uart_src == 4) {
+		res = ZMX25_CPU_BOARD_TYPE_G305;
+		hw_setup_cpu_g305();
+		puts("zmx25: G305\n");
+	} else {
+		res = ZMX25_CPU_BOARD_TYPE_UNKNOWN;
+		puts("zmx25: UNKNOWN\n");
+	}
+
+	/* Setup of io board */
+	if (io_board_type == ZMX25_IO_BOARD_TYPE_G283) {
+		hw_setup_io_g283();
+		puts("zmx25: IO->G283\n");
+	} else if (io_board_type == ZMX25_IO_BOARD_TYPE_G297) {
+		hw_setup_io_g297();
+		puts("zmx25: IO->G297\n");
+	} else if (io_board_type == ZMX25_IO_BOARD_TYPE_UNKNOWN) {
+		puts("zmx25: IO->UNKNOWN\n");
+	}
+
+	return res;
+}
+
+static inline void hw_setup_cpu_g282g292(void)
+{
+	static const iomux_v3_cfg_t i2c3_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_SS1__I2C3_DAT),
+		CLEAR_MODE_SION(MX25_PAD_GPIO_E__I2C3_CLK),
+	};
+
 	static const iomux_v3_cfg_t sdhc1_pads[] = {
 		NEW_PAD_CTRL(MX25_PAD_SD1_CMD__SD1_CMD, NO_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_SD1_CLK__SD1_CLK, NO_PAD_CTRL),
+		NEW_PAD_CTRL(MX25_PAD_SD1_CLK__SD1_CLK,
+			PAD_CTL_PUS_47K_UP | PAD_CTL_SRE_FAST),
 		NEW_PAD_CTRL(MX25_PAD_SD1_DATA0__SD1_DATA0, NO_PAD_CTRL),
 		NEW_PAD_CTRL(MX25_PAD_SD1_DATA1__SD1_DATA1, NO_PAD_CTRL),
 		NEW_PAD_CTRL(MX25_PAD_SD1_DATA2__SD1_DATA2, NO_PAD_CTRL),
 		NEW_PAD_CTRL(MX25_PAD_SD1_DATA3__SD1_DATA3, NO_PAD_CTRL),
 	};
 
-	static const iomux_v3_cfg_t dig_out_pads[] = {
-		MX25_PAD_CSI_D8__GPIO_1_7, /* Ouput 1 Ctrl */
-		MX25_PAD_CSI_D7__GPIO_1_6, /* Ouput 2 Ctrl */
-		NEW_PAD_CTRL(MX25_PAD_CSI_D6__GPIO_1_31, 0), /* Ouput 1 Stat */
-		NEW_PAD_CTRL(MX25_PAD_CSI_D5__GPIO_1_30, 0), /* Ouput 2 Stat */
+	/* Setup of core voltage selection pin to run at 1.4V */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_EXT_ARMCLK__GPIO_3_15));
+	gpio_direction_output(IMX_GPIO_NR(3, 15), 1);
+
+	/* Setup of input daisy chains for SD card pins */
+	imx_iomux_v3_setup_multiple_pads(sdhc1_pads, ARRAY_SIZE(sdhc1_pads));
+
+	/* Setup of I2C3 signals */
+	imx_iomux_v3_setup_multiple_pads(i2c3_pads, ARRAY_SIZE(i2c3_pads));
+}
+
+static inline void hw_setup_cpu_g282(void)
+{
+	/* GPIO1[26] -> LCD_PWR */
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(
+			CLEAR_MODE_SION(MX25_PAD_PWM__GPIO_1_26),
+				PAD_CTL_PUS_100K_UP));
+	udelay(1000);
+
+	/* GPIO3[19] -> Used as power fail interrupt */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_POWER_FAIL__GPIO_3_19));
+	gpio_direction_input(IMX_GPIO_NR(3, 19));
+
+	if (!gpio_get_value(IMX_GPIO_NR(1, 26)))
+		io_board_type = ZMX25_IO_BOARD_TYPE_G297;
+	else
+		io_board_type = ZMX25_IO_BOARD_TYPE_G283;
+}
+
+static inline void hw_setup_cpu_g282a1(void)
+{
+	struct ccm_regs *ccm;
+	struct weim_regs *weim;
+
+	static const iomux_v3_cfg_t fpga_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSI_MCLK__GPIO_1_8),	/* TMS */
+		CLEAR_MODE_SION(MX25_PAD_CSI_VSYNC__GPIO_1_9),	/* TCK */
+		CLEAR_MODE_SION(MX25_PAD_CSI_HSYNC__GPIO_1_10),/* TDI */
+		CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_CSI_PIXCLK__GPIO_1_11,
+			PAD_CTL_PUS_100K_UP | PAD_CTL_HYS)), /* TDO */
+		CLEAR_MODE_SION(MX25_PAD_KPP_COL2__GPIO_3_3),	/* Program */
+		CLEAR_MODE_SION(MX25_PAD_KPP_COL3__GPIO_3_4),	/* JTAGENB */
+	};
+
+	ccm = (struct ccm_regs *)IMX_CCM_BASE;
+	weim = (struct weim_regs *)IMX_WEIM_CTRL_BASE;
+
+	/* --- Setup of FPGA program pins --- */
+	imx_iomux_v3_setup_multiple_pads(fpga_pads, ARRAY_SIZE(fpga_pads));
+
+	gpio_direction_output(IMX_GPIO_NR(1, 8), 0);
+	gpio_direction_output(IMX_GPIO_NR(1, 9), 0);
+	gpio_direction_output(IMX_GPIO_NR(1, 10), 0);
+
+	gpio_direction_input(IMX_GPIO_NR(1, 11));
+	gpio_direction_input(IMX_GPIO_NR(3, 3));
+	gpio_direction_input(IMX_GPIO_NR(3, 4));
+
+	/* --- Clock output (33,25MHz) --- */
+	writel((1<<CCM_CCTL_ARM_DIV_SHIFT) |
+		(1<<CCM_CCTL_LP_CTL_SHIFT) |
+		(1<<CCM_CCTL_MPLL_BYP_SHIFT), &ccm->mcr);
+
+	/* --- Setup of FPGA CS --- */
+	writel(WEIM_CSCR_U_CNC(3) | WEIM_CSCR_U_WSC(20),
+		&weim->cscr5u);
+	writel((WEIM_CSCR_L_OAE(6) | WEIM_CSCR_L_OEN(12) | WEIM_CSCR_L_EBWA(4) |
+		WEIM_CSCR_L_EBWN(10) | WEIM_CSCR_L_EBC | WEIM_CSCR_L_DSZ(3) |
+		WEIM_CSCR_L_CSN(8) | WEIM_CSCR_L_CS_EN), &weim->cscr5l);
+	writel((WEIM_CSCR_A_RWA(6) | WEIM_CSCR_A_RWN(12) | WEIM_CSCR_A_LBN(4)),
+		&weim->cscr5a);
+}
+
+static inline void hw_setup_cpu_g292(void)
+{
+	struct ccm_regs *ccm;
+	struct weim_regs *weim;
+
+	static const iomux_v3_cfg_t uart3_pads[] = {
+		MX25_PAD_KPP_ROW0__UART3_RXD,
+		MX25_PAD_KPP_ROW1__UART3_TXD,
+		MX25_PAD_KPP_ROW2__UART3_RTS,
+		MX25_PAD_KPP_ROW3__UART3_CTS,
+	};
+
+	static const iomux_v3_cfg_t lcd_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_SS0__LD16),
+		NEW_PAD_CTRL(MX25_PAD_GPIO_F__LD17, 0),
+		/* reset active */
+		CLEAR_MODE_SION(MX25_PAD_CSI_MCLK__GPIO_1_8),
+		CLEAR_MODE_SION(MX25_PAD_UART2_RTS__GPIO_4_28),/* low power */
+		CLEAR_MODE_SION(MX25_PAD_CSI_VSYNC__GPIO_1_9),	/* on */
+	};
+
+	static const iomux_v3_cfg_t detect_touchscreen_pads[] = {
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D8__GPIO_1_7),
+				PAD_CTL_PUS_22K_UP),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSPI1_SCLK__GPIO_1_18),
+				PAD_CTL_PUS_22K_UP),
+	};
+
+	static const iomux_v3_cfg_t touchscreen_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSI_HSYNC__GPIO_1_10),/* Touch Int */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_MISO__GPIO_1_15),/* Touch SCK */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_RDY__GPIO_2_22),/* Touch MISO */
+	};
+
+	static const iomux_v3_cfg_t touch_keys_pads[] = {
+		/* Motor */
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL1__GPIO_3_2), 0),
+		/* Reset */
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL2__GPIO_3_3), 0),
+		/* GINT */
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL3__GPIO_3_4), 0),
+	};
+
+	static const iomux_v3_cfg_t fpga_pads[] = {
+		/* TMS */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D5__GPIO_1_30),
+		/* TCK */
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL0__GPIO_3_1), 0),
+		/* TDI */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D7__GPIO_1_6),
+		/* TDO */
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_PIXCLK__GPIO_1_11),
+				PAD_CTL_PUS_100K_UP | PAD_CTL_HYS),
 	};
 
+	static const iomux_v3_cfg_t acc_sensor_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSI_D7__GPIO_1_6),	/* INT1 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D4__GPIO_1_29),	/* INT2 */
+	};
+
+	ccm = (struct ccm_regs *)IMX_CCM_BASE;
+	weim = (struct weim_regs *)IMX_WEIM_CTRL_BASE;
+
+	/* Setup of CAN2 signals */
+	imx_iomux_v3_setup_multiple_pads(can_pads, ARRAY_SIZE(can_pads));
+
+	/* Setup of UART3 signals */
+	imx_iomux_v3_setup_multiple_pads(uart3_pads, ARRAY_SIZE(uart3_pads));
+
+	/* Setup of LCD signals */
+	imx_iomux_v3_setup_multiple_pads(lcd_pads, ARRAY_SIZE(lcd_pads));
+	gpio_direction_output(IMX_GPIO_NR(1,  8), 0);
+	gpio_direction_output(IMX_GPIO_NR(4, 28), 0);
+	gpio_direction_output(IMX_GPIO_NR(1,  9), 1);
+
+	/* --- Setup of touch display related pins --- */
+	imx_iomux_v3_setup_multiple_pads(detect_touchscreen_pads,
+			ARRAY_SIZE(detect_touchscreen_pads));
+	gpio_direction_input(IMX_GPIO_NR(1,  7));
+	gpio_direction_input(IMX_GPIO_NR(1, 18));
+
+	udelay(5000);
+
+	/* If GPIO1[7] and GPIO1[18] are high -> touch display */
+	if ((gpio_get_value(IMX_GPIO_NR(1,  7))) &&
+	    (gpio_get_value(IMX_GPIO_NR(1, 18)))) {
+		have_touch_display = 1;
+
+		/* Set reset to output and assert reset */
+		imx_iomux_v3_setup_multiple_pads(touchscreen_pads,
+					ARRAY_SIZE(touchscreen_pads));
+		gpio_direction_output(IMX_GPIO_NR(1, 7), 0);
+		gpio_direction_input(IMX_GPIO_NR(1, 10));
+		gpio_direction_output(IMX_GPIO_NR(1, 15), 1);
+		gpio_direction_input(IMX_GPIO_NR(2, 22));
+
+	} else {
+		/* Without touch we disable the pullups */
+		imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D8__GPIO_1_7), 0));
+		imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSPI1_SCLK__GPIO_1_18), 0));
+	}
+
+	/* --- Setup of touch keys related pins --- */
+	imx_iomux_v3_setup_multiple_pads(touch_keys_pads,
+					ARRAY_SIZE(touch_keys_pads));
+	gpio_direction_output(IMX_GPIO_NR(3, 2), 0);
+	gpio_direction_output(IMX_GPIO_NR(3, 3), 0);
+	gpio_direction_input(IMX_GPIO_NR(3, 4));
+
+	/* --- Setup of FPGA program pins --- */
+	imx_iomux_v3_setup_multiple_pads(fpga_pads, ARRAY_SIZE(fpga_pads));
+
+	/* --- Setup of FPGA CS --- */
+	writel(WEIM_CSCR_U_CNC(3) | WEIM_CSCR_U_WSC(20), &weim->cscr5u);
+	writel((WEIM_CSCR_L_OAE(6) | WEIM_CSCR_L_OEN(12) | WEIM_CSCR_L_EBWA(4) |
+		WEIM_CSCR_L_EBWN(10) | WEIM_CSCR_L_EBC | WEIM_CSCR_L_DSZ(3) |
+		WEIM_CSCR_L_CSN(8) | WEIM_CSCR_L_CS_EN), &weim->cscr5l);
+	writel((WEIM_CSCR_A_RWA(6) | WEIM_CSCR_A_RWN(12) | WEIM_CSCR_A_LBN(4)),
+		&weim->cscr5a);
+
+	/* --- Clock output (33,25MHz) --- */
+	writel((1<<CCM_CCTL_ARM_DIV_SHIFT) |
+		(1<<CCM_CCTL_LP_CTL_SHIFT) |
+		(1<<CCM_CCTL_MPLL_BYP_SHIFT), &ccm->mcr);
+
+	/* --- Setup of SD card detection pin --- */
+	/* GPIO1[14] -> SD_DET */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSPI1_MOSI__GPIO_1_14));
+	gpio_direction_input(IMX_GPIO_NR(1, 14));
+
+	/* --- Setup of INT pins of acceleration sensor --- */
+	imx_iomux_v3_setup_multiple_pads(acc_sensor_pads,
+					ARRAY_SIZE(acc_sensor_pads));
+	gpio_direction_input(IMX_GPIO_NR(1, 6));
+	gpio_direction_input(IMX_GPIO_NR(1, 29));
+
+	/* GPIO3[19] -> Used as power fail interrupt */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_POWER_FAIL__GPIO_3_19));
+	gpio_direction_input(IMX_GPIO_NR(3, 19));
+
+	io_board_type = ZMX25_IO_BOARD_TYPE_NONE;
+}
+
+static inline void hw_setup_cpu_g305(void)
+{
+	struct pwm_regs *pwm1;
+	struct pwm_regs *pwm2;
+	struct epit_regs *epit1;
+
 	static const iomux_v3_cfg_t led_pads[] = {
-		MX25_PAD_CSI_D9__GPIO_4_21,
-		MX25_PAD_CSI_D4__GPIO_1_29,
+		MX25_PAD_NFCLE__GPIO_3_29,	/* LED CAN0 */
+		MX25_PAD_NFALE__GPIO_3_28,	/* LED CAN1 */
+		MX25_PAD_NFWE_B__GPIO_3_26,	/* LED STOP */
+		MX25_PAD_NFWP_B__GPIO_3_30,	/* LED STATUS */
 	};
 
-	static const iomux_v3_cfg_t can_pads[] = {
-		NEW_PAD_CTRL(MX25_PAD_GPIO_A__CAN1_TX, NO_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_GPIO_B__CAN1_RX, NO_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_GPIO_C__CAN2_TX, NO_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_GPIO_D__CAN2_RX, NO_PAD_CTRL),
+	static const iomux_v3_cfg_t digital_outputs_pads[] = {
+		MX25_PAD_KPP_ROW1__GPIO_2_30,	/* OUT9 */
+		MX25_PAD_KPP_ROW0__GPIO_2_29,	/* OUT8 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D2__GPIO_1_27),	/* OUT7 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D3__GPIO_1_28),	/* OUT6 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D4__GPIO_1_29),	/* OUT5 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D5__GPIO_1_30),	/* OUT4 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D6__GPIO_1_31),	/* OUT3 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D7__GPIO_1_6),	/* OUT2 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D8__GPIO_1_7),	/* OUT1 */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D9__GPIO_4_21),	/* OUT0 */
 	};
 
-	static const iomux_v3_cfg_t i2c3_pads[] = {
-		MX25_PAD_CSPI1_SS1__I2C3_DAT,
-		MX25_PAD_GPIO_E__I2C3_CLK,
+	static const iomux_v3_cfg_t digital_inputs_pads[] = {
+		MX25_PAD_UART1_RTS__GPT3_CAPIN1,/* 0 */
+		MX25_PAD_UART2_RTS__GPT1_CAPIN1,/* 1 */
+		MX25_PAD_UART1_CTS__GPIO_4_25,	/* 2 */
+		MX25_PAD_UART1_TXD__GPIO_4_23,	/* 3 */
+		MX25_PAD_UART1_RXD__GPIO_4_22,	/* 4 */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_RDY__GPIO_2_22),	/* 5 */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_SCLK__GPIO_1_18),/* 6 */
+		MX25_PAD_CSPI1_SS1__GPIO_1_17,	/* 7 */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_MISO__GPIO_1_15),/* 8 */
+		CLEAR_MODE_SION(MX25_PAD_CSPI1_MOSI__GPIO_1_14),/* 9 */
+		MX25_PAD_SD1_DATA2__GPIO_2_27,	/* 10 */
+		MX25_PAD_SD1_DATA1__GPIO_2_26,	/* 11 */
+		MX25_PAD_SD1_DATA0__GPIO_2_25,	/* 14 */
+		MX25_PAD_SD1_CMD__GPIO_2_23,	/* 15 */
 	};
 
-	icache_enable();
+	pwm1 = (struct pwm_regs *)IMX_PWM1_BASE;
+	pwm2 = (struct pwm_regs *)IMX_PWM2_BASE;
+	epit1 = (struct epit_regs *)IMX_EPIT1_BASE;
 
-	/* Setup of core voltage selection pin to run at 1.4V */
-	imx_iomux_v3_setup_pad(MX25_PAD_EXT_ARMCLK__GPIO_3_15); /* VCORE */
-	gpio_direction_output(IMX_GPIO_NR(3, 15), 1);
+	/* Setup of CAN1 and CAN2 signals */
+	imx_iomux_v3_setup_multiple_pads(can_pads, ARRAY_SIZE(can_pads));
 
-	/* Setup of SD card pins*/
-	imx_iomux_v3_setup_multiple_pads(sdhc1_pads, ARRAY_SIZE(sdhc1_pads));
+	/* EPIT1O -> Buzzer */
+	imx_iomux_v3_setup_pad(MX25_PAD_VSTBY_ACK__EPIT1_EPITO);
+
+	/* Switch the buzzer on */
+	writel((EPIT_CR_EN | EPIT_CR_RLD | EPIT_CR_IOVW | EPIT_CR_OM(1) |
+		EPIT_CR_CLKSRC(1)), &epit1->cr);
+	writel(EPIT_LR(10000), &epit1->lr);
+	writel(EPIT_CMPR(5000), &epit1->cmpr);
+
+	/* --- Display --- */
+	/* LCD_PWRCTRL GPIO3[15] -> low power */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_EXT_ARMCLK__GPIO_3_15));
+	gpio_direction_output(IMX_GPIO_NR(3, 15), 0);
+
+	/* GPIO3[16] */
+	/* LCD_RESET GPIO3[0] -> reset active */
+	imx_iomux_v3_setup_pad(MX25_PAD_KPP_ROW3__GPIO_3_0);
+	gpio_direction_input(IMX_GPIO_NR(3, 0));
+	udelay(1000);
+	if (gpio_get_value(IMX_GPIO_NR(3, 0)))	{
+		have_touch_display = 1;
+
+		/* --- Touch --- */
+		/* TOUCH_WAKE GPIO3[16] */
+		imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_UPLL_BYPCLK__GPIO_3_16));
+		gpio_direction_output(IMX_GPIO_NR(3, 16), 1);
+
+		/* TOUCH_INT GPIO3[27] */
+		imx_iomux_v3_setup_pad(MX25_PAD_NFRE_B__GPIO_3_27);
+		gpio_direction_input(IMX_GPIO_NR(3, 27));
+	}
+	gpio_direction_output(IMX_GPIO_NR(3, 0), 0);
+
+	/* LCD_BL_EN GPIO3[31] -> off */
+	imx_iomux_v3_setup_pad(MX25_PAD_NFRB__GPIO_3_31);
+	gpio_direction_output(IMX_GPIO_NR(3, 31), 0);
+
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(MX25_PAD_GPIO_E__LD16, 0));
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(MX25_PAD_GPIO_F__LD17, 0));
+
+	/* --- Misc --- */
+	imx_iomux_v3_setup_multiple_pads(led_pads, ARRAY_SIZE(led_pads));
+	gpio_direction_output(IMX_GPIO_NR(3, 29), 0);
+	gpio_direction_output(IMX_GPIO_NR(3, 28), 0);
+	gpio_direction_output(IMX_GPIO_NR(3, 26), 0);
+	gpio_direction_output(IMX_GPIO_NR(3, 30), 0);
+
+	/* GPIO3[19] -> POWER FAIL */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_POWER_FAIL__GPIO_3_19));
+	gpio_direction_input(IMX_GPIO_NR(3, 19));
+
+	/* --- Incremental encoder inputs --- */
+	/* GPIO1[9] -> A */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSI_VSYNC__GPIO_1_9));
+	gpio_direction_input(IMX_GPIO_NR(1, 9));
+
+	/* GPIO1[10] -> B */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSI_HSYNC__GPIO_1_10));
+	gpio_direction_input(IMX_GPIO_NR(1, 10));
+
+	/* GPIO1[11] -> T */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSI_PIXCLK__GPIO_1_11));
+	gpio_direction_input(IMX_GPIO_NR(1, 11));
 
-	/* Setup of digital output for USB power and OC */
-	imx_iomux_v3_setup_pad(MX25_PAD_CSI_D3__GPIO_1_28); /* USB Power */
+	/* --- Digital outputs --- */
+	imx_iomux_v3_setup_multiple_pads(digital_outputs_pads,
+					ARRAY_SIZE(digital_outputs_pads));
+	gpio_direction_output(IMX_GPIO_NR(2, 30), 0);
+	gpio_direction_output(IMX_GPIO_NR(2, 29), 0);
+	gpio_direction_output(IMX_GPIO_NR(1, 27), 1);
 	gpio_direction_output(IMX_GPIO_NR(1, 28), 1);
+	gpio_direction_output(IMX_GPIO_NR(1, 29), 1);
+	gpio_direction_output(IMX_GPIO_NR(1, 30), 1);
+	gpio_direction_output(IMX_GPIO_NR(1, 31), 1);
+	gpio_direction_output(IMX_GPIO_NR(1, 6), 1);
+	gpio_direction_output(IMX_GPIO_NR(1, 7), 1);
+	gpio_direction_output(IMX_GPIO_NR(4, 21), 1);
 
-	imx_iomux_v3_setup_pad(MX25_PAD_CSI_D2__GPIO_1_27); /* USB OC */
+	/* Status input */
+	imx_iomux_v3_setup_pad(MX25_PAD_SD1_DATA3__GPIO_2_28);
+	gpio_direction_input(IMX_GPIO_NR(2, 28));
+
+	/* --- PWM outputs --- */
+	imx_iomux_v3_setup_pad(MX25_PAD_PWM__PWM);		/* PWM0 */
+	imx_iomux_v3_setup_pad(MX25_PAD_CSPI1_SS0__PWM2_PWMO);	/* PWM1 */
+	writel((PWM_CR_EN | PWM_CR_CLKSRC(1) | PWM_CR_POUTC(1)), &pwm1->cr);
+	writel((PWM_CR_EN | PWM_CR_CLKSRC(1) | PWM_CR_POUTC(1)), &pwm2->cr);
+
+	/* --- Digital inputs --- */
+	imx_iomux_v3_setup_multiple_pads(digital_inputs_pads,
+					ARRAY_SIZE(digital_inputs_pads));
+	gpio_direction_input(IMX_GPIO_NR(4, 25));
+	gpio_direction_input(IMX_GPIO_NR(4, 23));
+	gpio_direction_input(IMX_GPIO_NR(4, 22));
+	gpio_direction_input(IMX_GPIO_NR(2, 22));
+	gpio_direction_input(IMX_GPIO_NR(1, 18));
+	gpio_direction_input(IMX_GPIO_NR(1, 17));
+	gpio_direction_input(IMX_GPIO_NR(1, 15));
+	gpio_direction_input(IMX_GPIO_NR(1, 14));
+	gpio_direction_input(IMX_GPIO_NR(2, 27));
+	gpio_direction_input(IMX_GPIO_NR(2, 26));
+	gpio_direction_input(IMX_GPIO_NR(2, 25));
+	gpio_direction_input(IMX_GPIO_NR(2, 23));
+
+	/* --- Analog/digital input selection --- */
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL0__GPIO_3_1), 0));
+	gpio_direction_output(IMX_GPIO_NR(3, 1), 0);
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL1__GPIO_3_2), 0));
+	gpio_direction_output(IMX_GPIO_NR(3, 2), 0);
+
+	/* --- Analog type selection --- */
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL2__GPIO_3_3), 0));
+	gpio_direction_output(IMX_GPIO_NR(3, 3), 0);
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_KPP_COL3__GPIO_3_4), 0));
+	gpio_direction_output(IMX_GPIO_NR(3, 4), 0);
+
+	/* GPIO2[24] -> 5V EN */
+	imx_iomux_v3_setup_pad(MX25_PAD_SD1_CLK__GPIO_2_24);
+	gpio_direction_output(IMX_GPIO_NR(2, 24), 0);
+
+	io_board_type = ZMX25_IO_BOARD_TYPE_NONE;
+}
+
+static inline void hw_setup_io_g283(void)
+{
+	static const iomux_v3_cfg_t dig_out_pads[] = {
+		/* Output 1 Ctrl */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D8__GPIO_1_7),
+		/* Output 2 Ctrl */
+		CLEAR_MODE_SION(MX25_PAD_CSI_D7__GPIO_1_6),
+		/* Output 1 Stat */
+		CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_CSI_D6__GPIO_1_31, 0)),
+		/* Output 2 Stat */
+		CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_CSI_D5__GPIO_1_30, 0)),
+	};
+
+	static const iomux_v3_cfg_t led_pads[] = {
+		CLEAR_MODE_SION(MX25_PAD_CSI_D9__GPIO_4_21),
+		CLEAR_MODE_SION(MX25_PAD_CSI_D4__GPIO_1_29),
+	};
+
+	/* Setup of CAN1 and CAN2 signals */
+	imx_iomux_v3_setup_multiple_pads(can_pads, ARRAY_SIZE(can_pads));
+
+	/* Setup of digital output for USB power */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSI_D3__GPIO_1_28));
+	gpio_direction_output(IMX_GPIO_NR(1, 28), 1);
+
+	/* Setup of digital output for OC */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSI_D2__GPIO_1_27));
 	gpio_direction_input(IMX_GPIO_NR(1, 18));
 
 	/* Setup of digital output control pins */
@@ -91,77 +736,346 @@ int board_init()
 	/* Switch both LEDs off */
 	gpio_direction_output(IMX_GPIO_NR(4, 21), 0);
 	gpio_direction_output(IMX_GPIO_NR(1, 29), 0);
+}
 
-	/* Setup of CAN1 and CAN2 signals */
-	imx_iomux_v3_setup_multiple_pads(can_pads, ARRAY_SIZE(can_pads));
+static inline void hw_setup_io_g297(void)
+{
+	struct weim_regs *weim;
 
-	/* Setup of I2C3 signals */
-	imx_iomux_v3_setup_multiple_pads(i2c3_pads, ARRAY_SIZE(i2c3_pads));
+	static const iomux_v3_cfg_t cspi3_pads[] = {
+		NEW_SEL_INPUT(CLEAR_MODE_SION(MX25_PAD_CSI_D2__CSPI3_MOSI), 1),
+		CLEAR_MODE_SION(MX25_PAD_CSI_D3__CSPI3_MISO),
+		NEW_SEL_INPUT(CLEAR_MODE_SION(MX25_PAD_CSI_D4__CSPI3_SCLK), 1),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D6__CSPI3_SS0),
+				PAD_CTL_PUS_22K_UP),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D7__CSPI3_SS1),
+				PAD_CTL_PUS_22K_UP),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D8__CSPI3_SS2),
+				PAD_CTL_PUS_22K_UP),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_CSI_D9__CSPI3_SS3),
+				PAD_CTL_PUS_22K_UP),
+	};
 
-	gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
+	weim = (struct weim_regs *)IMX_WEIM_CTRL_BASE;
 
-	return 0;
+	/* --- Setup of IO CS --- */
+	writel(WEIM_CSCR_U_CNC(3) | WEIM_CSCR_U_WSC(20),
+	       &weim->cscr4u);
+	writel((WEIM_CSCR_L_OAE(6) | WEIM_CSCR_L_OEN(12) | WEIM_CSCR_L_EBWA(4) |
+		WEIM_CSCR_L_EBWN(10) | WEIM_CSCR_L_EBC | WEIM_CSCR_L_DSZ(3) |
+		WEIM_CSCR_L_CSN(8) | WEIM_CSCR_L_CS_EN), &weim->cscr4l);
+	writel((WEIM_CSCR_A_RWA(6) | WEIM_CSCR_A_RWN(12) | WEIM_CSCR_A_LBN(4)),
+	       &weim->cscr4a);
+
+	/* GPIO1[26] -> LCD_PWR -> off */
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_PWM__GPIO_1_26));
+	gpio_direction_output(IMX_GPIO_NR(1, 26), 0);
+
+	/* Setup of CSPI3 pins */
+	imx_iomux_v3_setup_multiple_pads(cspi3_pads, ARRAY_SIZE(cspi3_pads));
+
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_CSPI1_SS0__LD16));
+	imx_iomux_v3_setup_pad(NEW_PAD_CTRL(MX25_PAD_GPIO_F__LD17, 0));
 }
 
-int board_late_init(void)
+#ifdef CONFIG_FEC_MXC
+int board_eth_init(bd_t *bis)
 {
-	const char *e;
+	struct ccm_regs *ccm;
 
-#ifdef CONFIG_FEC_MXC
-/*
- * FIXME: need to revisit this
- * The original code enabled PUE and 100-k pull-down without PKE, so the right
- * value here is likely:
- *	0 for no pull
- * or:
- *	PAD_CTL_PUS_100K_DOWN for 100-k pull-down
- */
-#define FEC_OUT_PAD_CTRL	0
+	#define FEC_OUT_PAD_CTRL	0
 
 	static const iomux_v3_cfg_t fec_pads[] = {
-		MX25_PAD_FEC_TX_CLK__FEC_TX_CLK,
-		MX25_PAD_FEC_RX_DV__FEC_RX_DV,
-		MX25_PAD_FEC_RDATA0__FEC_RDATA0,
-		NEW_PAD_CTRL(MX25_PAD_FEC_TDATA0__FEC_TDATA0, FEC_OUT_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_FEC_TX_EN__FEC_TX_EN, FEC_OUT_PAD_CTRL),
-		NEW_PAD_CTRL(MX25_PAD_FEC_MDC__FEC_MDC, FEC_OUT_PAD_CTRL),
-		MX25_PAD_FEC_MDIO__FEC_MDIO,
-		MX25_PAD_FEC_RDATA1__FEC_RDATA1,
-		NEW_PAD_CTRL(MX25_PAD_FEC_TDATA1__FEC_TDATA1, FEC_OUT_PAD_CTRL),
+		CLEAR_MODE_SION(MX25_PAD_FEC_TX_CLK__FEC_TX_CLK),
+		CLEAR_MODE_SION(MX25_PAD_FEC_RX_DV__FEC_RX_DV),
+		CLEAR_MODE_SION(MX25_PAD_FEC_RDATA0__FEC_RDATA0),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_FEC_TDATA0__FEC_TDATA0),
+				FEC_OUT_PAD_CTRL),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_FEC_TX_EN__FEC_TX_EN),
+				FEC_OUT_PAD_CTRL),
+		NEW_PAD_CTRL(CLEAR_MODE_SION(MX25_PAD_FEC_MDC__FEC_MDC),
+				FEC_OUT_PAD_CTRL),
+		CLEAR_MODE_SION(MX25_PAD_FEC_MDIO__FEC_MDIO),
+		CLEAR_MODE_SION(MX25_PAD_FEC_RDATA1__FEC_RDATA1),
+		CLEAR_MODE_SION(NEW_PAD_CTRL(MX25_PAD_FEC_TDATA1__FEC_TDATA1,
+				FEC_OUT_PAD_CTRL)),
 
-		MX25_PAD_UPLL_BYPCLK__GPIO_3_16, /* LAN-RESET */
-		MX25_PAD_UART2_CTS__FEC_RX_ER, /* FEC_RX_ERR */
+		CLEAR_MODE_SION(MX25_PAD_UPLL_BYPCLK__GPIO_3_16),/* LAN-RESET */
+		CLEAR_MODE_SION(MX25_PAD_UART2_CTS__FEC_RX_ER),	/* FEC_RX_ERR */
 	};
 
+	/*
+	 * Set up LAN-RESET and FEC_RX_ERR
+	 *
+	 * LAN-RESET:  GPIO3[16] is ALT 5 mode of pin U20
+	 * FEC_RX_ERR: FEC_RX_ERR is ALT 2 mode of pin R2
+	 */
+	ccm = (struct ccm_regs *)IMX_CCM_BASE;
+
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305) {
+		/* --- Clock output (25MHz) --- */
+		/* UPLL output to 250MHz */
+		writel((CCM_UPCTL_PD(1) | CCM_UPCTL_MFD(11) |
+			CCM_UPCTL_MFI(10) | CCM_UPCTL_MFN(5)), &ccm->upctl);
+
+		/* Reset UPLL */
+		writel(readl(&ccm->cctl) | CCM_UPCTL_PD(1), &ccm->cctl);
+
+		/* Wait until PLL locked */
+		while ((readl(&ccm->upctl) & CCM_PLL_LOCK) == 0)
+			udelay(1000);
+
+		/* Enable clock output for UPLL at DIV = 10 */
+		writel((CCM_MCR_CLKO_EN | CCM_MCR_CLKO_DIV(9) |
+			CCM_MCR_CLKO_SEL(6)), &ccm->mcr);
+	}
+
 	imx_iomux_v3_setup_multiple_pads(fec_pads, ARRAY_SIZE(fec_pads));
 
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305)
+		imx_iomux_v3_setup_pad(MX25_PAD_KPP_ROW2__GPIO_2_31);
+	else
+		imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_UPLL_BYPCLK__GPIO_3_16));
+
+	imx_iomux_v3_setup_pad(CLEAR_MODE_SION(MX25_PAD_UART2_CTS__FEC_RX_ER));
+
 	/* assert PHY reset (low) */
-	gpio_direction_output(IMX_GPIO_NR(3, 16), 0);
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305)
+		gpio_direction_output(IMX_GPIO_NR(2, 31), 0);
+	else
+		gpio_direction_output(IMX_GPIO_NR(3, 16), 0);
 
 	udelay(5000);
 
 	/* deassert PHY reset */
-	gpio_set_value(IMX_GPIO_NR(3, 16), 1);
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305)
+		gpio_set_value(IMX_GPIO_NR(2, 31), 1);
+	else
+		gpio_set_value(IMX_GPIO_NR(3, 16), 1);
 
 	udelay(5000);
+
+	return cpu_eth_init(bis);
+}
 #endif
 
-	e = getenv("gs_base_board");
-	if (e != NULL) {
-		if (strcmp(e, "G283") == 0) {
-			int key = gpio_get_value(IMX_GPIO_NR(2, 29));
+#ifdef CONFIG_VIDEO
+int board_video_init(void)
+{
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305) {
+		/* LCD power on */
+		gpio_direction_output(IMX_GPIO_NR(3, 31), 1);
+		udelay(1000);
+
+		/* LCD reset off */
+		gpio_direction_output(IMX_GPIO_NR(3, 0), 1);
+		udelay(100000);
+
+		/* LCD pwr ctrl off */
+		gpio_direction_output(IMX_GPIO_NR(3, 15), 1);
+
+		return 1;
+	} else if ((cpu_board_type == ZMX25_CPU_BOARD_TYPE_G282A1) &&
+		   (io_board_type == ZMX25_IO_BOARD_TYPE_G297)) {
+		/* LCD power on */
+		gpio_set_value(IMX_GPIO_NR(1, 26), 1);
+
+		/* Set LCD PWR CTRL and release RESET */
+		hw_g297_xfer_srio(0x0011);
+
+		return 1;
+	} else {
+		/* LCD reset off */
+		gpio_direction_output(IMX_GPIO_NR(1, 8), 1);
+		udelay(20000);
+
+		/* LCD pwr ctrl off */
+		gpio_direction_output(IMX_GPIO_NR(4, 28), 1);
+
+		return 1;
+	}
+
+	return 0;
+}
+#endif
+
+
+int board_init(void)
+{
+	cpu_board_type = hw_setup_common();
+
+	gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
+
+	return 0;
+}
+
+int board_late_init(void)
+{
+	int have_fma1125;
+	int have_mpr121;
+	int slow_boot = 0;
+	const char *e;
+	struct epit_regs *epit1;
+
+	epit1 = (struct epit_regs *)IMX_EPIT1_BASE;
+	have_fma1125 = 0;
+	have_mpr121 = 0;
+
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G292) {
+		int delay = 0;
 
-			if (key) {
-				/* Switch on both LEDs to inidcate boot mode */
-				gpio_set_value(IMX_GPIO_NR(1, 29), 0);
-				gpio_set_value(IMX_GPIO_NR(4, 21), 0);
+		/* Release touch display reset */
+		if (have_touch_display)
+			gpio_set_value(IMX_GPIO_NR(1, 7), 1);
 
-				setenv("preboot", "run gs_slow_boot");
-			} else
-				setenv("preboot", "run gs_fast_boot");
+		/* Release touch key reset */
+		gpio_set_value(IMX_GPIO_NR(3, 3), 1);
+		udelay(10000);
+
+		i2c_set_bus_num(2);
+		i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
+		udelay(10000);
+
+		have_mpr121 = mpr121_init(mpr121_config,
+						ARRAY_SIZE(mpr121_config));
+		if (have_mpr121) {
+			delay = 100000;
+		} else {
+			have_fma1125 = fma1125_init(FMA1125_SA, fma1125_config,
+						ARRAY_SIZE(fma1125_config));
+			if (have_fma1125)
+				delay = 25000;
+		}
+
+		if (have_touch_display && polytouch_init())
+			delay = 300000;
+
+		udelay(delay);
+	}
+
+	/* Disable buzzer */
+	if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305)
+		writel(0, &epit1->cr);
+
+	if (io_board_type == ZMX25_IO_BOARD_TYPE_G283) {
+		int key = gpio_get_value(IMX_GPIO_NR(2, 29));
+
+		if (key) {
+			/* Switch on both LEDs to indicate boot mode */
+			gpio_set_value(IMX_GPIO_NR(1, 29), 0);
+			gpio_set_value(IMX_GPIO_NR(4, 21), 0);
+
+			setenv("preboot", "run gs_slow_boot");
+		} else {
+			setenv("preboot", "run gs_fast_boot");
+		}
+	} else if (cpu_board_type == ZMX25_CPU_BOARD_TYPE_G292) {
+		int key = 0;
+
+		if (have_mpr121)
+			key = mpr121_get_touch_bits(have_mpr121) & 0xFFC;
+		if (have_fma1125)
+			key = fma1125_get_touch_bits() & 0x3C;
+		if (have_touch_display)
+			if (!gpio_get_value(IMX_GPIO_NR(1, 10))) {
+				struct polytouch_resolution res;
+				struct polytouch_area area;
+
+				polytouch_get_resolution(&res);
+
+				/* check the lower left area */
+				area.x1 = 0;
+				area.x2 = res.x / 4;
+				area.y1 = res.y - res.y / 4;
+				area.y2 = res.y;
+
+				key = polytouch_is_touched(&area);
+			}
+
+		if (key) {
+			/* Switch on key LEDs to indicate boot mode */
+			if (have_mpr121)
+				mpr121_set_leds_on();
+			if (have_fma1125)
+				fma1125_set_gpio_out(0x09);
+			slow_boot = 1;
+			setenv("stdout", "vga");
+		}
+	} else if (io_board_type == ZMX25_IO_BOARD_TYPE_G297) {
+		u16 srdata;
+
+		/* Key is connected to SRIO
+		 * -> check for press
+		 */
+		srdata = hw_g297_xfer_srio(0x0011);
+		if (srdata & (1<<3)) {
+			slow_boot = 1;
+			setenv("stdout", "vga");
 		}
+	} else {
+		slow_boot = 1;
 	}
 
+	if ((cpu_board_type == ZMX25_CPU_BOARD_TYPE_G305) &&
+	    (getenv("gs_print_infos"))) {
+		const char *fw = "UNKNOWN";
+		const char *sn = "";
+		char stdout_old[32];
+		u8 buffer[256];
+		char app[33];
+		char bi1[33];
+		char bi2[33];
+
+		e = getenv("gs_firmware_info");
+		if (NULL != e)
+			fw = e;
+
+		e = getenv("gs_dev_serialno");
+		if (NULL != e)
+			sn = e;
+
+		memset(app, 0, sizeof(app));
+		memset(bi1, 0, sizeof(bi1));
+		memset(bi2, 0, sizeof(bi2));
+
+		i2c_set_bus_num(1);
+
+		/* Read device information from fixed eeprom locations */
+		if ((i2c_read(0x50, 8192 - 256, 2, buffer, 256) == 0) ||
+			(i2c_read(0x50, 8192 - 256, 2, buffer, 256) == 0)) {
+			memcpy(app, buffer + ZMX25_FIXED_EEPROM_ADDR_APP, 32);
+			memcpy(bi1, buffer + ZMX25_FIXED_EEPROM_ADDR_BI1, 32);
+			memcpy(bi2, buffer + ZMX25_FIXED_EEPROM_ADDR_BI2, 32);
+		}
+
+		strcpy(stdout_old, getenv("stdout"));
+		setenv("stdout", "vga");
+
+		/*
+		 * move the courser to the bottom according to
+		 * the display resolution
+		 */
+		if (video_get_pixel_height() == 480)
+			printf("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");
+		else
+			printf("\n\n\n\n\n\n\n\n\n");
+		printf(" FW  : %s\n", fw);
+		printf(" SN  : %s\n", sn);
+		printf(" APP : %s\n", app);
+		printf(" BI1 : %s\n", bi1);
+		printf(" BI2 : %s\n", bi2);
+
+		setenv("stdout", stdout_old);
+	}
+
+	/* setup magic for boot mode used by the os */
+	if (slow_boot) {
+		writel(ZMX25_BOOT_MODE_SLOW, (void *)IMX_RAM_BASE);
+		setenv("preboot", "run gs_slow_boot");
+	} else {
+		writel(ZMX25_BOOT_MODE_FAST, (void *)IMX_RAM_BASE);
+		setenv("preboot", "run gs_fast_boot");
+	}
 	return 0;
 }
 
diff --git a/include/configs/zmx25.h b/include/configs/zmx25.h
index 8ffe6f1..3c04df8 100644
--- a/include/configs/zmx25.h
+++ b/include/configs/zmx25.h
@@ -12,9 +12,10 @@
 
 #include <asm/arch/imx-regs.h>
 
-#define CONFIG_ARM926EJS			/* arm926ejs CPU core */
+#define CONFIG_ARM926EJS		/* arm926ejs CPU core */
 #define CONFIG_MX25
 #define CONFIG_SYS_TEXT_BASE		0xA0000000
+#define CONFIG_USE_PRIVATE_LIBGCC
 
 #define CONFIG_SYS_TIMER_RATE		32768
 #define CONFIG_SYS_TIMER_COUNTER	\
@@ -24,17 +25,19 @@
 /*
  * Environment settings
  */
+#define CONFIG_SYS_GENERIC_BOARD
 #define CONFIG_EXTRA_ENV_SETTINGS \
 	"gs_fast_boot=setenv bootdelay 5\0" \
 	"gs_slow_boot=setenv bootdelay 10\0" \
 	"bootcmd=dcache off; mw.l 0x81000000 0 1024; usb start;" \
-		"fatls usb 0; fatload usb 0 0x81000000 zmx25-init.bin;" \
-		"bootm 0x81000000; bootelf 0x81000000\0"
+	"fatls usb 0; fatload usb 0 0x81000000 zmx25-init.bin;" \
+	"bootm 0x81000000; bootelf 0x81000000\0"
 
 #define CONFIG_CMDLINE_TAG		/* enable passing of ATAGs	*/
 #define CONFIG_SETUP_MEMORY_TAGS
 #define CONFIG_INITRD_TAG
 #define CONFIG_BOARD_LATE_INIT
+#define CONFIG_SYS_GENERIC_BOARD
 
 /*
  * Compressions
@@ -51,6 +54,11 @@
 #define CONFIG_MXC_GPIO
 
 /*
+ * SPI
+ */
+#define CONFIG_MXC_SPI
+
+/*
  * Serial
  */
 #define CONFIG_MXC_UART
@@ -59,6 +67,18 @@
 #define CONFIG_BAUDRATE		115200	/* Default baud rate */
 
 /*
+ * I2C
+ */
+#define MXC_IPG_PERCLK MXC_I2C_CLK
+#define CONFIG_HARD_I2C
+#define CONFIG_SYS_I2C_MXC
+#define CONFIG_I2C_MULTI_BUS
+#define CONFIG_SYS_I2C
+#define CONFIG_SYS_I2C_BASE	IMX_I2C3_BASE
+#define CONFIG_SYS_I2C_SPEED	400000
+#define CONFIG_SYS_I2C_SLAVE	0xfe
+
+/*
  * Ethernet
  */
 #define CONFIG_FEC_MXC
@@ -66,7 +86,28 @@
 #define CONFIG_MII
 
 /*
- * BOOTP options
+  * Video
+ */
+#define CONFIG_VIDEO
+#define CONFIG_VIDEO_IMX25LCDC
+#define CONFIG_SYS_WHITE_ON_BLACK
+#define CONFIG_CFB_CONSOLE
+#define CONFIG_SYS_CONSOLE_IS_IN_ENV
+#define CONFIG_SYS_CONSOLE_ENV_OVERWRITE
+#define CONFIG_SYS_CONSOLE_BG_COL	0xff
+#define CONFIG_SYS_CONSOLE_FG_COL	0x00
+#define CONFIG_VIDEO_LOGO
+#define CONFIG_SPLASH_SCREEN
+#define CONFIG_SPLASH_SCREEN_ALIGN
+#define CONFIG_VIDEO_BMP_LOGO
+#define CONFIG_VIDEO_BMP_GZIP
+#define CONFIG_VIDEO_BMP_RLE8
+#define CONFIG_SYS_VIDEO_LOGO_MAX_SIZE	(800*480 + 256*4 + 10*1024)
+#define CONFIG_VGA_AS_SINGLE_DEVICE
+#define VIDEO_FB_16BPP_WORD_SWAP
+
+/*
+* BOOTP options
  */
 #define CONFIG_BOOTP_BOOTFILESIZE
 #define CONFIG_BOOTP_BOOTPATH
@@ -88,6 +129,11 @@
 #define CONFIG_CMD_ELF
 #define CONFIG_CMD_FAT
 #define CONFIG_CMD_USB
+#define CONFIG_CMD_I2C
+#define CONFIG_CMD_BMP
+#define CONFIG_CMD_GPIO
+#define CONFIG_CMD_SPI
+#define CONFIG_CMD_BOOTZ
 
 #define CONFIG_SYS_HUSH_PARSER
 
@@ -114,6 +160,7 @@
 
 #define CONFIG_SYS_SDRAM_BASE	PHYS_SDRAM
 #define CONFIG_SYS_INIT_SP_ADDR	0x78020000	/* end of internal SRAM */
+#define CONFIG_SYS_MEM_TOP_HIDE	(4 << 20)
 
 /*
  * FLASH and environment organization
@@ -147,7 +194,7 @@
 #define CONFIG_SYS_LONGHELP
 #define CONFIG_CMDLINE_EDITING
 
-#define CONFIG_PREBOOT  ""
+#define CONFIG_PREBOOT	""
 
 #define CONFIG_BOOTDELAY	5
 #define CONFIG_AUTOBOOT_KEYED
@@ -158,6 +205,13 @@
 /*
  * Size of malloc() pool
  */
-#define CONFIG_SYS_MALLOC_LEN		(0x400000 - 0x8000)
+#define CONFIG_SYS_MALLOC_LEN	(0x400000 - 0x8000)
+
+/*
+ * Touch screen drivers
+ */
+#define CONFIG_FMA1125
+#define CONFIG_MPR121
+#define CONFIG_POLYTOUCH
 
 #endif	/* __CONFIG_H */
-- 
1.7.9.5



More information about the U-Boot mailing list