[U-Boot] [PATCH 0/27] Amazon Kindle Fire (first generation) codename kc1 support series

This series adds support for the Amazon Kindle Fire (first generation) codename kc1, as described in the commit introducing board and config support.
Support for this device requires a series of changes to both the omap4 and twl6030 code. It introduces some cleanups and new features for both. Thus, it would be nice if this series could be tested with other OMAP4 devices.
More drastic cleanups of the omap and twl code will probably follow eventually.
At this point, support is rather minimalistic as various bits and pieces are missing, especially the display and battery charging. However, booting from the internal eMMC works, as well as USB peripheral mode and fastboot.

This makes the twl6030 mmc and usb-related power registers and values definitions more explicit and clear and adds prefixes to them.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 26 +++++++++++++++----------- include/twl6030.h | 14 ++++++++++---- 2 files changed, 25 insertions(+), 15 deletions(-)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index a1c6663..8924f7f 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -214,22 +214,26 @@ void twl6030_init_battery_charging(void)
void twl6030_power_mmc_init() { - /* set voltage to 3.0 and turnon for APP */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, VMMC_CFG_VOLTATE, 0x15); - twl6030_i2c_write_u8(TWL6030_CHIP_PM, VMMC_CFG_STATE, 0x21); + /* 3.0V voltage output for VMMC */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_30); + + /* Enable P1 output for VMMC */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_STATE, + TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); }
void twl6030_usb_device_settings() { - u8 data = 0; - - /* Select APP Group and set state to ON */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, VUSB_CFG_STATE, 0x21); + u8 value = 0;
- twl6030_i2c_read_u8(TWL6030_CHIP_PM, MISC2, &data); - data |= 0x10; + /* Enable P1 output for VUSB */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VUSB_CFG_STATE, + TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON);
- /* Select the input supply for VBUS regulator */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, MISC2, data); + /* Select the input supply for VUSB regulator */ + twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_MISC2, &value); + value |= TWL6030_MISC2_VUSB_IN_VSYS; + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_MISC2, value); } #endif diff --git a/include/twl6030.h b/include/twl6030.h index 7898699..bb02d6f 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -20,16 +20,22 @@ #define TWL6030_CHIP_PWM 0x49
/* Slave Address 0x48 */ -#define VMMC_CFG_STATE 0x9A -#define VMMC_CFG_VOLTATE 0x9B -#define VUSB_CFG_STATE 0xA2 +#define TWL6030_VMMC_CFG_STATE 0x9A +#define TWL6030_VMMC_CFG_VOLTAGE 0x9B +#define TWL6030_VUSB_CFG_STATE 0xA2 + +#define TWL6030_CFG_GRP_P1 (1 << 0) +#define TWL6030_CFG_STATE_ON (1 << 0) +#define TWL6030_CFG_STATE_P1 (TWL6030_CFG_GRP_P1 << 5) +#define TWL6030_CFG_VOLTAGE_30 0x15
#define MISC1 0xE4 #define VAC_MEAS (1 << 2) #define VBAT_MEAS (1 << 1) #define BB_MEAS (1 << 0)
-#define MISC2 0xE5 +#define TWL6030_MISC2 0xE5 +#define TWL6030_MISC2_VUSB_IN_VSYS (1 << 4)
/* Slave Address 0x49 */

On Sat, Feb 27, 2016 at 07:18:49PM +0100, Paul Kocialkowski wrote:
This makes the twl6030 mmc and usb-related power registers and values definitions more explicit and clear and adds prefixes to them.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This enables the VAUX1 supply, used for eMMC power in standard configurations. Its voltage is determined by the value of the BOOT2 pin of the TWL6030.
Note that the TWL6030 might already have enabled this regulator at startup (depending on the value of the BOOT3 pin of the TWL6030), according to the TWL6030 datasheet.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 19 +++++++++++++++++++ include/twl6030.h | 11 +++++++++++ 2 files changed, 30 insertions(+)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index 8924f7f..2fb3967 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -214,6 +214,8 @@ void twl6030_init_battery_charging(void)
void twl6030_power_mmc_init() { + u8 value = 0; + /* 3.0V voltage output for VMMC */ twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_VOLTAGE, TWL6030_CFG_VOLTAGE_30); @@ -221,6 +223,23 @@ void twl6030_power_mmc_init() /* Enable P1 output for VMMC */ twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_STATE, TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); + + twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_PH_STS_BOOT, &value); + + /* BOOT2 indicates 1.8V/2.8V VAUX1 for eMMC */ + if (value & TWL6030_PH_STS_BOOT2) { + /* 1.8V voltage output for VAUX1 */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_18); + } else { + /* 2.8V voltage output for VAUX1 */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_28); + } + + /* Enable P1 output for VAUX */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_STATE, + TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); }
void twl6030_usb_device_settings() diff --git a/include/twl6030.h b/include/twl6030.h index bb02d6f..a17a9b5 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -20,6 +20,15 @@ #define TWL6030_CHIP_PWM 0x49
/* Slave Address 0x48 */ +#define TWL6030_PH_STS_BOOT 0x29 + +#define TWL6030_PH_STS_BOOT0 (1 << 0) +#define TWL6030_PH_STS_BOOT1 (1 << 1) +#define TWL6030_PH_STS_BOOT2 (1 << 2) +#define TWL6030_PH_STS_BOOT3 (1 << 3) + +#define TWL6030_VAUX1_CFG_STATE 0x86 +#define TWL6030_VAUX1_CFG_VOLTAGE 0x87 #define TWL6030_VMMC_CFG_STATE 0x9A #define TWL6030_VMMC_CFG_VOLTAGE 0x9B #define TWL6030_VUSB_CFG_STATE 0xA2 @@ -27,6 +36,8 @@ #define TWL6030_CFG_GRP_P1 (1 << 0) #define TWL6030_CFG_STATE_ON (1 << 0) #define TWL6030_CFG_STATE_P1 (TWL6030_CFG_GRP_P1 << 5) +#define TWL6030_CFG_VOLTAGE_18 0x09 +#define TWL6030_CFG_VOLTAGE_28 0x13 #define TWL6030_CFG_VOLTAGE_30 0x15
#define MISC1 0xE4

On Sat, Feb 27, 2016 at 07:18:50PM +0100, Paul Kocialkowski wrote:
This enables the VAUX1 supply, used for eMMC power in standard configurations. Its voltage is determined by the value of the BOOT2 pin of the TWL6030.
Note that the TWL6030 might already have enabled this regulator at startup (depending on the value of the BOOT3 pin of the TWL6030), according to the TWL6030 datasheet.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Not every device has multiple MMC slots available, so it makes sense to enable only the required LDOs for the available slots. Generic code in omap_hsmmc will enable both VMMC and VAUX1, in doubt.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/mmc/omap_hsmmc.c | 4 ++-- drivers/power/twl6030.c | 50 +++++++++++++++++++++++++----------------------- include/twl6030.h | 2 +- 3 files changed, 29 insertions(+), 27 deletions(-)
diff --git a/drivers/mmc/omap_hsmmc.c b/drivers/mmc/omap_hsmmc.c index 5038a9f..0ea3101 100644 --- a/drivers/mmc/omap_hsmmc.c +++ b/drivers/mmc/omap_hsmmc.c @@ -104,8 +104,8 @@ static void omap4_vmmc_pbias_config(struct mmc *mmc) value = readl((*ctrl)->control_pbiaslite); value &= ~(MMC1_PBIASLITE_PWRDNZ | MMC1_PWRDNZ); writel(value, (*ctrl)->control_pbiaslite); - /* set VMMC to 3V */ - twl6030_power_mmc_init(); + twl6030_power_mmc_init(0); + twl6030_power_mmc_init(1); value = readl((*ctrl)->control_pbiaslite); value |= MMC1_PBIASLITE_VMODE | MMC1_PBIASLITE_PWRDNZ | MMC1_PWRDNZ; writel(value, (*ctrl)->control_pbiaslite); diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index 2fb3967..7ed9129 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -212,34 +212,36 @@ void twl6030_init_battery_charging(void) return; }
-void twl6030_power_mmc_init() +void twl6030_power_mmc_init(int dev_index) { u8 value = 0;
- /* 3.0V voltage output for VMMC */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_VOLTAGE, - TWL6030_CFG_VOLTAGE_30); - - /* Enable P1 output for VMMC */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_STATE, - TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); - - twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_PH_STS_BOOT, &value); - - /* BOOT2 indicates 1.8V/2.8V VAUX1 for eMMC */ - if (value & TWL6030_PH_STS_BOOT2) { - /* 1.8V voltage output for VAUX1 */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, - TWL6030_CFG_VOLTAGE_18); - } else { - /* 2.8V voltage output for VAUX1 */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, - TWL6030_CFG_VOLTAGE_28); + if (dev_index == 0) { + /* 3.0V voltage output for VMMC */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_30); + + /* Enable P1 output for VMMC */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VMMC_CFG_STATE, + TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); + + twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_PH_STS_BOOT, &value); + } else if (dev_index == 1) { + /* BOOT2 indicates 1.8V/2.8V VAUX1 for eMMC */ + if (value & TWL6030_PH_STS_BOOT2) { + /* 1.8V voltage output for VAUX1 */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_18); + } else { + /* 2.8V voltage output for VAUX1 */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_28); + } + + /* Enable P1 output for VAUX */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_STATE, + TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); } - - /* Enable P1 output for VAUX */ - twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VAUX1_CFG_STATE, - TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); }
void twl6030_usb_device_settings() diff --git a/include/twl6030.h b/include/twl6030.h index a17a9b5..04295c9 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -185,6 +185,6 @@ void twl6030_start_usb_charging(void); void twl6030_stop_usb_charging(void); int twl6030_get_battery_voltage(void); int twl6030_get_battery_current(void); -void twl6030_power_mmc_init(void); +void twl6030_power_mmc_init(int dev_index);
#endif /* TWL6030_H */

On Sat, Feb 27, 2016 at 07:18:51PM +0100, Paul Kocialkowski wrote:
Not every device has multiple MMC slots available, so it makes sense to enable only the required LDOs for the available slots. Generic code in omap_hsmmc will enable both VMMC and VAUX1, in doubt.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Boards using the TWL6030 regulator may not all use the LDOs the same way. Some might also not use MMC1 at all, so VMMC would't have to be enabled.
This delegates TWL6030 MMC power initializations to board-specific functions, that may still call twl6030_power_mmc_init for the default behavior.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/gumstix/duovero/duovero.c | 6 +++++- board/ti/panda/panda.c | 6 ++++++ board/ti/sdp4430/sdp.c | 6 ++++++ drivers/mmc/omap_hsmmc.c | 6 ++---- 4 files changed, 19 insertions(+), 5 deletions(-)
diff --git a/board/gumstix/duovero/duovero.c b/board/gumstix/duovero/duovero.c index 81d6c82..1fb6b5d 100644 --- a/board/gumstix/duovero/duovero.c +++ b/board/gumstix/duovero/duovero.c @@ -115,8 +115,12 @@ int board_mmc_init(bd_t *bis) { return omap_mmc_init(0, 0, 0, -1, -1); } -#endif
+void board_mmc_power_init(void) +{ + twl6030_power_mmc_init(0); +} +#endif
#if defined(CONFIG_CMD_NET)
diff --git a/board/ti/panda/panda.c b/board/ti/panda/panda.c index eb9ce63..959a23f 100644 --- a/board/ti/panda/panda.c +++ b/board/ti/panda/panda.c @@ -11,6 +11,7 @@ #include <asm/arch/clock.h> #include <asm/arch/gpio.h> #include <asm/gpio.h> +#include <twl6030.h>
#include "panda_mux_data.h"
@@ -291,6 +292,11 @@ int board_mmc_init(bd_t *bis) { return omap_mmc_init(0, 0, 0, -1, -1); } + +void board_mmc_power_init(void) +{ + twl6030_power_mmc_init(0); +} #endif
#ifdef CONFIG_USB_EHCI diff --git a/board/ti/sdp4430/sdp.c b/board/ti/sdp4430/sdp.c index 1e9ef9e..c456745 100644 --- a/board/ti/sdp4430/sdp.c +++ b/board/ti/sdp4430/sdp.c @@ -80,6 +80,12 @@ int board_mmc_init(bd_t *bis) omap_mmc_init(1, 0, 0, -1, -1); return 0; } + +void board_mmc_power_init(void) +{ + twl6030_power_mmc_init(0); + twl6030_power_mmc_init(1); +} #endif
/* diff --git a/drivers/mmc/omap_hsmmc.c b/drivers/mmc/omap_hsmmc.c index 0ea3101..29773d0 100644 --- a/drivers/mmc/omap_hsmmc.c +++ b/drivers/mmc/omap_hsmmc.c @@ -96,7 +96,7 @@ static int omap_mmc_setup_gpio_in(int gpio, const char *label) } #endif
-#if defined(CONFIG_OMAP44XX) && defined(CONFIG_TWL6030_POWER) +#if defined(CONFIG_OMAP44XX) static void omap4_vmmc_pbias_config(struct mmc *mmc) { u32 value = 0; @@ -104,8 +104,6 @@ static void omap4_vmmc_pbias_config(struct mmc *mmc) value = readl((*ctrl)->control_pbiaslite); value &= ~(MMC1_PBIASLITE_PWRDNZ | MMC1_PWRDNZ); writel(value, (*ctrl)->control_pbiaslite); - twl6030_power_mmc_init(0); - twl6030_power_mmc_init(1); value = readl((*ctrl)->control_pbiaslite); value |= MMC1_PBIASLITE_VMODE | MMC1_PBIASLITE_PWRDNZ | MMC1_PWRDNZ; writel(value, (*ctrl)->control_pbiaslite); @@ -175,7 +173,7 @@ static unsigned char mmc_board_init(struct mmc *mmc) &prcm_base->iclken1_core); #endif
-#if defined(CONFIG_OMAP44XX) && defined(CONFIG_TWL6030_POWER) +#if defined(CONFIG_OMAP44XX) /* PBIAS config needed for MMC1 only */ if (mmc->block_dev.dev == 0) omap4_vmmc_pbias_config(mmc);

On Sat, Feb 27, 2016 at 07:18:52PM +0100, Paul Kocialkowski wrote:
Boards using the TWL6030 regulator may not all use the LDOs the same way. Some might also not use MMC1 at all, so VMMC would't have to be enabled.
This delegates TWL6030 MMC power initializations to board-specific functions, that may still call twl6030_power_mmc_init for the default behavior.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Individual boards might provide their own emif_get_device_details function and use elpidia device details in their own way, hence those have to be exported.
This also wraps existing definitions with the proper ifdef logic.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/sdram_elpida.c | 4 ++-- arch/arm/include/asm/arch-omap4/sys_proto.h | 5 +++++ 2 files changed, 7 insertions(+), 2 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap4/sdram_elpida.c b/arch/arm/cpu/armv7/omap4/sdram_elpida.c index 4462c72..ad18c6c 100644 --- a/arch/arm/cpu/armv7/omap4/sdram_elpida.c +++ b/arch/arm/cpu/armv7/omap4/sdram_elpida.c @@ -147,14 +147,14 @@ void emif_get_dmm_regs(const struct dmm_lisa_map_regs **dmm_lisa_regs)
#else
-static const struct lpddr2_device_details elpida_2G_S4_details = { +const struct lpddr2_device_details elpida_2G_S4_details = { .type = LPDDR2_TYPE_S4, .density = LPDDR2_DENSITY_2Gb, .io_width = LPDDR2_IO_WIDTH_32, .manufacturer = LPDDR2_MANUFACTURER_ELPIDA };
-static const struct lpddr2_device_details elpida_4G_S4_details = { +const struct lpddr2_device_details elpida_4G_S4_details = { .type = LPDDR2_TYPE_S4, .density = LPDDR2_DENSITY_4Gb, .io_width = LPDDR2_IO_WIDTH_32, diff --git a/arch/arm/include/asm/arch-omap4/sys_proto.h b/arch/arm/include/asm/arch-omap4/sys_proto.h index f30f865..f9bcbb6 100644 --- a/arch/arm/include/asm/arch-omap4/sys_proto.h +++ b/arch/arm/include/asm/arch-omap4/sys_proto.h @@ -18,6 +18,7 @@
DECLARE_GLOBAL_DATA_PTR;
+#ifdef CONFIG_SYS_EMIF_PRECALCULATED_TIMING_REGS extern const struct emif_regs emif_regs_elpida_200_mhz_2cs; extern const struct emif_regs emif_regs_elpida_380_mhz_1cs; extern const struct emif_regs emif_regs_elpida_400_mhz_1cs; @@ -25,6 +26,10 @@ extern const struct emif_regs emif_regs_elpida_400_mhz_2cs; extern const struct dmm_lisa_map_regs lisa_map_2G_x_1_x_2; extern const struct dmm_lisa_map_regs lisa_map_2G_x_2_x_2; extern const struct dmm_lisa_map_regs ma_lisa_map_2G_x_2_x_2; +#else +extern const struct lpddr2_device_details elpida_2G_S4_details; +extern const struct lpddr2_device_details elpida_4G_S4_details; +#endif struct omap_sysinfo { char *board_string; };

On Sat, Feb 27, 2016 at 07:18:53PM +0100, Paul Kocialkowski wrote:
Individual boards might provide their own emif_get_device_details function and use elpidia device details in their own way, hence those have to be exported.
This also wraps existing definitions with the proper ifdef logic.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Individual boards might provide their own emif_get_device_timings function and use the elpidia timings in their own way, hence those have to be exported.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/sdram_elpida.c | 2 +- arch/arm/include/asm/arch-omap4/sys_proto.h | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-)
diff --git a/arch/arm/cpu/armv7/omap4/sdram_elpida.c b/arch/arm/cpu/armv7/omap4/sdram_elpida.c index ad18c6c..78b4f09 100644 --- a/arch/arm/cpu/armv7/omap4/sdram_elpida.c +++ b/arch/arm/cpu/armv7/omap4/sdram_elpida.c @@ -278,7 +278,7 @@ static const struct lpddr2_ac_timings *elpida_ac_timings[MAX_NUM_SPEEDBINS] = { &timings_elpida_400_mhz };
-static const struct lpddr2_device_timings elpida_2G_S4_timings = { +const struct lpddr2_device_timings elpida_2G_S4_timings = { .ac_timings = elpida_ac_timings, .min_tck = &min_tck_elpida, }; diff --git a/arch/arm/include/asm/arch-omap4/sys_proto.h b/arch/arm/include/asm/arch-omap4/sys_proto.h index f9bcbb6..27900dd 100644 --- a/arch/arm/include/asm/arch-omap4/sys_proto.h +++ b/arch/arm/include/asm/arch-omap4/sys_proto.h @@ -30,6 +30,11 @@ extern const struct dmm_lisa_map_regs ma_lisa_map_2G_x_2_x_2; extern const struct lpddr2_device_details elpida_2G_S4_details; extern const struct lpddr2_device_details elpida_4G_S4_details; #endif + +#ifndef CONFIG_SYS_DEFAULT_LPDDR2_TIMINGS +extern const struct lpddr2_device_timings elpida_2G_S4_timings; +#endif + struct omap_sysinfo { char *board_string; };

On Sat, Feb 27, 2016 at 07:18:54PM +0100, Paul Kocialkowski wrote:
Individual boards might provide their own emif_get_device_timings function and use the elpidia timings in their own way, hence those have to be exported.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Individual boards might provide their own emif_get_device_timings function and use the jedec timings in their own way, hence those have to be exported.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/emif.c | 2 +- arch/arm/include/asm/arch-omap4/sys_proto.h | 4 +++- 2 files changed, 4 insertions(+), 2 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap4/emif.c b/arch/arm/cpu/armv7/omap4/emif.c index e89032b..403c3c6 100644 --- a/arch/arm/cpu/armv7/omap4/emif.c +++ b/arch/arm/cpu/armv7/omap4/emif.c @@ -96,7 +96,7 @@ static const struct lpddr2_ac_timings const* &timings_jedec_400_mhz };
-static const struct lpddr2_device_timings jedec_default_timings = { +const struct lpddr2_device_timings jedec_default_timings = { .ac_timings = jedec_ac_timings, .min_tck = &min_tck_jedec }; diff --git a/arch/arm/include/asm/arch-omap4/sys_proto.h b/arch/arm/include/asm/arch-omap4/sys_proto.h index 27900dd..0e4e129 100644 --- a/arch/arm/include/asm/arch-omap4/sys_proto.h +++ b/arch/arm/include/asm/arch-omap4/sys_proto.h @@ -31,7 +31,9 @@ extern const struct lpddr2_device_details elpida_2G_S4_details; extern const struct lpddr2_device_details elpida_4G_S4_details; #endif
-#ifndef CONFIG_SYS_DEFAULT_LPDDR2_TIMINGS +#ifdef CONFIG_SYS_DEFAULT_LPDDR2_TIMINGS +extern const struct lpddr2_device_timings jedec_default_timings; +#else extern const struct lpddr2_device_timings elpida_2G_S4_timings; #endif

On Sat, Feb 27, 2016 at 07:18:55PM +0100, Paul Kocialkowski wrote:
Individual boards might provide their own emif_get_device_timings function and use the jedec timings in their own way, hence those have to be exported.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

There is no distinction between essential and non-essential mux configuration, so it doesn't make sense to have an "essential" prefix.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap-common/hwinit-common.c | 4 ++-- arch/arm/include/asm/arch-omap4/sys_proto.h | 2 +- arch/arm/include/asm/arch-omap5/sys_proto.h | 2 +- board/compulab/cm_t54/cm_t54.c | 2 +- board/compulab/cm_t54/mux.c | 4 ++-- board/gumstix/duovero/duovero.c | 2 +- board/ti/am57xx/board.c | 2 +- board/ti/dra7xx/evm.c | 2 +- board/ti/omap5_uevm/evm.c | 2 +- board/ti/panda/panda.c | 2 +- board/ti/sdp4430/sdp.c | 2 +- 11 files changed, 13 insertions(+), 13 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap-common/hwinit-common.c b/arch/arm/cpu/armv7/omap-common/hwinit-common.c index 80794f9..a057ef4 100644 --- a/arch/arm/cpu/armv7/omap-common/hwinit-common.c +++ b/arch/arm/cpu/armv7/omap-common/hwinit-common.c @@ -35,13 +35,13 @@ static void set_mux_conf_regs(void) { switch (omap_hw_init_context()) { case OMAP_INIT_CONTEXT_SPL: - set_muxconf_regs_essential(); + set_muxconf_regs(); break; case OMAP_INIT_CONTEXT_UBOOT_AFTER_SPL: break; case OMAP_INIT_CONTEXT_UBOOT_FROM_NOR: case OMAP_INIT_CONTEXT_UBOOT_AFTER_CH: - set_muxconf_regs_essential(); + set_muxconf_regs(); break; } } diff --git a/arch/arm/include/asm/arch-omap4/sys_proto.h b/arch/arm/include/asm/arch-omap4/sys_proto.h index 0e4e129..d1ee5b2 100644 --- a/arch/arm/include/asm/arch-omap4/sys_proto.h +++ b/arch/arm/include/asm/arch-omap4/sys_proto.h @@ -46,7 +46,7 @@ void gpmc_init(void); void watchdog_init(void); u32 get_device_type(void); void do_set_mux(u32 base, struct pad_conf_entry const *array, int size); -void set_muxconf_regs_essential(void); +void set_muxconf_regs(void); u32 wait_on_value(u32, u32, void *, u32); void sdelay(unsigned long); void setup_clocks_for_console(void); diff --git a/arch/arm/include/asm/arch-omap5/sys_proto.h b/arch/arm/include/asm/arch-omap5/sys_proto.h index 7fcb783..a70f0e2 100644 --- a/arch/arm/include/asm/arch-omap5/sys_proto.h +++ b/arch/arm/include/asm/arch-omap5/sys_proto.h @@ -45,7 +45,7 @@ void watchdog_init(void); u32 get_device_type(void); void do_set_mux(u32 base, struct pad_conf_entry const *array, int size); void do_set_mux32(u32 base, struct pad_conf_entry const *array, int size); -void set_muxconf_regs_essential(void); +void set_muxconf_regs(void); u32 wait_on_value(u32, u32, void *, u32); void sdelay(unsigned long); void setup_clocks_for_console(void); diff --git a/board/compulab/cm_t54/cm_t54.c b/board/compulab/cm_t54/cm_t54.c index 6d3b18a..b4f5d40 100644 --- a/board/compulab/cm_t54/cm_t54.c +++ b/board/compulab/cm_t54/cm_t54.c @@ -30,7 +30,7 @@ DECLARE_GLOBAL_DATA_PTR;
#if !defined(CONFIG_SPL_BUILD) -inline void set_muxconf_regs_essential(void){}; +inline void set_muxconf_regs(void){}; #endif
const struct omap_sysinfo sysinfo = { diff --git a/board/compulab/cm_t54/mux.c b/board/compulab/cm_t54/mux.c index da35383..45d868f 100644 --- a/board/compulab/cm_t54/mux.c +++ b/board/compulab/cm_t54/mux.c @@ -75,10 +75,10 @@ const struct pad_conf_entry wkup_padconf_array_essential[] = { };
/* - * Routine: set_muxconf_regs_essential + * Routine: set_muxconf_regs * Description: setup board pinmux configuration. */ -void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array_essential, diff --git a/board/gumstix/duovero/duovero.c b/board/gumstix/duovero/duovero.c index 1fb6b5d..9671c5a 100644 --- a/board/gumstix/duovero/duovero.c +++ b/board/gumstix/duovero/duovero.c @@ -87,7 +87,7 @@ int misc_init_r(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array_essential, diff --git a/board/ti/am57xx/board.c b/board/ti/am57xx/board.c index 042f9ab..5ee480f 100644 --- a/board/ti/am57xx/board.c +++ b/board/ti/am57xx/board.c @@ -273,7 +273,7 @@ int board_late_init(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux32((*ctrl)->control_padconf_core_base, early_padconf, ARRAY_SIZE(early_padconf)); diff --git a/board/ti/dra7xx/evm.c b/board/ti/dra7xx/evm.c index eebec88..c3460cf 100644 --- a/board/ti/dra7xx/evm.c +++ b/board/ti/dra7xx/evm.c @@ -67,7 +67,7 @@ int board_late_init(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux32((*ctrl)->control_padconf_core_base, early_padconf, ARRAY_SIZE(early_padconf)); diff --git a/board/ti/omap5_uevm/evm.c b/board/ti/omap5_uevm/evm.c index 853f196..50da410 100644 --- a/board/ti/omap5_uevm/evm.c +++ b/board/ti/omap5_uevm/evm.c @@ -198,7 +198,7 @@ int misc_init_r(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array_essential, diff --git a/board/ti/panda/panda.c b/board/ti/panda/panda.c index 959a23f..13b5daf 100644 --- a/board/ti/panda/panda.c +++ b/board/ti/panda/panda.c @@ -268,7 +268,7 @@ int misc_init_r(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array_essential, diff --git a/board/ti/sdp4430/sdp.c b/board/ti/sdp4430/sdp.c index c456745..6037cdd 100644 --- a/board/ti/sdp4430/sdp.c +++ b/board/ti/sdp4430/sdp.c @@ -53,7 +53,7 @@ int misc_init_r(void) return 0; }
-void set_muxconf_regs_essential(void) +void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array_essential,

On Sat, Feb 27, 2016 at 07:18:56PM +0100, Paul Kocialkowski wrote:
There is no distinction between essential and non-essential mux configuration, so it doesn't make sense to have an "essential" prefix.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

save_omap_boot_params is called from spl_board_init in the SPL context. Thus, there is no reason to duplicate that call on arch_cpu_init.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap-common/hwinit-common.c | 13 ------------- include/configs/ti_omap4_common.h | 1 - include/configs/ti_omap5_common.h | 1 - 3 files changed, 15 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap-common/hwinit-common.c b/arch/arm/cpu/armv7/omap-common/hwinit-common.c index a057ef4..2c0b82f 100644 --- a/arch/arm/cpu/armv7/omap-common/hwinit-common.c +++ b/arch/arm/cpu/armv7/omap-common/hwinit-common.c @@ -84,19 +84,6 @@ void __weak srcomp_enable(void) { }
-#ifdef CONFIG_ARCH_CPU_INIT -/* - * SOC specific cpu init - */ -int arch_cpu_init(void) -{ -#ifdef CONFIG_SPL - save_omap_boot_params(); -#endif - return 0; -} -#endif /* CONFIG_ARCH_CPU_INIT */ - /* * Routine: s_init * Description: Does early system init of watchdog, muxing, andclocks diff --git a/include/configs/ti_omap4_common.h b/include/configs/ti_omap4_common.h index 8b6c065..72ed0b9 100644 --- a/include/configs/ti_omap4_common.h +++ b/include/configs/ti_omap4_common.h @@ -17,7 +17,6 @@ */ #define CONFIG_OMAP4430 1 /* which is in a 4430 */ #define CONFIG_MISC_INIT_R -#define CONFIG_ARCH_CPU_INIT #define CONFIG_DISPLAY_CPUINFO 1 #define CONFIG_DISPLAY_BOARDINFO 1
diff --git a/include/configs/ti_omap5_common.h b/include/configs/ti_omap5_common.h index d164e6a..0bb1d00 100644 --- a/include/configs/ti_omap5_common.h +++ b/include/configs/ti_omap5_common.h @@ -19,7 +19,6 @@
#define CONFIG_DISPLAY_CPUINFO #define CONFIG_DISPLAY_BOARDINFO -#define CONFIG_ARCH_CPU_INIT
/* Common ARM Erratas */ #define CONFIG_ARM_ERRATA_798870

On Sat, Feb 27, 2016 at 07:18:57PM +0100, Paul Kocialkowski wrote:
save_omap_boot_params is called from spl_board_init in the SPL context. Thus, there is no reason to duplicate that call on arch_cpu_init.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This removes a duplicate reference to CM_L3INIT_USBPHY_CLKCTRLin enable_basic_uboot_clocks. Also, a doubled whitespace is removed.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/hw_data.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap4/hw_data.c b/arch/arm/cpu/armv7/omap4/hw_data.c index 029533c..1359b44 100644 --- a/arch/arm/cpu/armv7/omap4/hw_data.c +++ b/arch/arm/cpu/armv7/omap4/hw_data.c @@ -372,7 +372,7 @@ void enable_basic_clocks(void) setbits_le32((*prcm)->cm_wkup_gptimer1_clkctrl, GPTIMER1_CLKCTRL_CLKSEL_MASK);
- /* Enable optional 48M functional clock for USB PHY */ + /* Enable optional 48M functional clock for USB PHY */ setbits_le32((*prcm)->cm_l3init_usbphy_clkctrl, USBPHY_CLKCTRL_OPTFCLKEN_PHY_48M_MASK);
@@ -391,7 +391,6 @@ void enable_basic_uboot_clocks(void) u32 const clk_modules_hw_auto_essential[] = { (*prcm)->cm_l3init_hsusbotg_clkctrl, (*prcm)->cm_l3init_usbphy_clkctrl, - (*prcm)->cm_l3init_usbphy_clkctrl, (*prcm)->cm_clksel_usb_60mhz, (*prcm)->cm_l3init_hsusbtll_clkctrl, 0

On Sat, Feb 27, 2016 at 07:18:58PM +0100, Paul Kocialkowski wrote:
This removes a duplicate reference to CM_L3INIT_USBPHY_CLKCTRLin enable_basic_uboot_clocks. Also, a doubled whitespace is removed.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

I2C is often enabled withing the U-Boot SPL, thus those clocks are required to be enabled early (especially when the bootrom doesn't enable them for us).
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/hw_data.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap4/hw_data.c b/arch/arm/cpu/armv7/omap4/hw_data.c index 1359b44..1cc2072 100644 --- a/arch/arm/cpu/armv7/omap4/hw_data.c +++ b/arch/arm/cpu/armv7/omap4/hw_data.c @@ -355,6 +355,10 @@ void enable_basic_clocks(void) (*prcm)->cm_l4per_gptimer2_clkctrl, (*prcm)->cm_wkup_wdtimer2_clkctrl, (*prcm)->cm_l4per_uart3_clkctrl, + (*prcm)->cm_l4per_i2c1_clkctrl, + (*prcm)->cm_l4per_i2c2_clkctrl, + (*prcm)->cm_l4per_i2c3_clkctrl, + (*prcm)->cm_l4per_i2c4_clkctrl, 0 };
@@ -398,10 +402,6 @@ void enable_basic_uboot_clocks(void)
u32 const clk_modules_explicit_en_essential[] = { (*prcm)->cm_l4per_mcspi1_clkctrl, - (*prcm)->cm_l4per_i2c1_clkctrl, - (*prcm)->cm_l4per_i2c2_clkctrl, - (*prcm)->cm_l4per_i2c3_clkctrl, - (*prcm)->cm_l4per_i2c4_clkctrl, (*prcm)->cm_l3init_hsusbhost_clkctrl, 0 };

On Sat, Feb 27, 2016 at 07:18:59PM +0100, Paul Kocialkowski wrote:
I2C is often enabled withing the U-Boot SPL, thus those clocks are required to be enabled early (especially when the bootrom doesn't enable them for us).
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

The Amazon Kindle Fire (first generation) codename kc1 is a tablet that was released by Amazon back in 2011.
It is using an OMAP4430 SoC GP version, which allows running U-Boot and the U-Boot SPL from the ground up.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/Kconfig | 4 + board/amazon/kc1/Kconfig | 12 ++ board/amazon/kc1/MAINTAINERS | 6 + board/amazon/kc1/Makefile | 9 ++ board/amazon/kc1/kc1.c | 109 +++++++++++++++++++ board/amazon/kc1/kc1.h | 92 ++++++++++++++++ configs/kc1_defconfig | 12 ++ include/configs/kc1.h | 230 +++++++++++++++++++++++++++++++++++++++ 8 files changed, 474 insertions(+) create mode 100644 board/amazon/kc1/Kconfig create mode 100644 board/amazon/kc1/MAINTAINERS create mode 100644 board/amazon/kc1/Makefile create mode 100644 board/amazon/kc1/kc1.c create mode 100644 board/amazon/kc1/kc1.h create mode 100644 configs/kc1_defconfig create mode 100644 include/configs/kc1.h
diff --git a/arch/arm/cpu/armv7/omap4/Kconfig b/arch/arm/cpu/armv7/omap4/Kconfig index df27ea1..49adb8e 100644 --- a/arch/arm/cpu/armv7/omap4/Kconfig +++ b/arch/arm/cpu/armv7/omap4/Kconfig @@ -13,6 +13,9 @@ config TARGET_OMAP4_PANDA config TARGET_OMAP4_SDP4430 bool "TI OMAP4 SDP4430"
+config TARGET_KC1 + bool "Amazon Kindle Fire (first generation)" + endchoice
config SYS_SOC @@ -21,5 +24,6 @@ config SYS_SOC source "board/gumstix/duovero/Kconfig" source "board/ti/panda/Kconfig" source "board/ti/sdp4430/Kconfig" +source "board/amazon/kc1/Kconfig"
endif diff --git a/board/amazon/kc1/Kconfig b/board/amazon/kc1/Kconfig new file mode 100644 index 0000000..1b46a8f --- /dev/null +++ b/board/amazon/kc1/Kconfig @@ -0,0 +1,12 @@ +if TARGET_KC1 + +config SYS_BOARD + default "kc1" + +config SYS_VENDOR + default "amazon" + +config SYS_CONFIG_NAME + default "kc1" + +endif diff --git a/board/amazon/kc1/MAINTAINERS b/board/amazon/kc1/MAINTAINERS new file mode 100644 index 0000000..7e596d9 --- /dev/null +++ b/board/amazon/kc1/MAINTAINERS @@ -0,0 +1,6 @@ +KC1 BOARD +M: Paul Kocialkowski contact@paulk.fr +S: Maintained +F: board/amazon/kc1/ +F: include/configs/kc1.h +F: configs/kc1_defconfig diff --git a/board/amazon/kc1/Makefile b/board/amazon/kc1/Makefile new file mode 100644 index 0000000..59c8347 --- /dev/null +++ b/board/amazon/kc1/Makefile @@ -0,0 +1,9 @@ +# +# Amazon Kindle Fire (first generation) codename kc1 config +# +# Copyright (C) 2016 Paul Kocialkowski contact@paulk.fr +# +# SPDX-License-Identifier: GPL-2.0+ +# + +obj-y := kc1.o diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c new file mode 100644 index 0000000..a189bb2 --- /dev/null +++ b/board/amazon/kc1/kc1.c @@ -0,0 +1,109 @@ +/* + * Amazon Kindle Fire (first generation) codename kc1 config + * + * Copyright (C) 2016 Paul Kocialkowski contact@paulk.fr + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <config.h> +#include <common.h> +#include <asm/arch/sys_proto.h> +#include <asm/arch/mmc_host_def.h> +#include <asm/gpio.h> +#include <asm/emif.h> +#include <twl6030.h> +#include "kc1.h" + +DECLARE_GLOBAL_DATA_PTR; + +const struct omap_sysinfo sysinfo = { + .board_string = "kc1" +}; + +void set_muxconf_regs(void) +{ + do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array, + sizeof(core_padconf_array) / sizeof(struct pad_conf_entry)); +} + +struct lpddr2_device_details *emif_get_device_details(u32 emif_nr, u8 cs, + struct lpddr2_device_details *lpddr2_dev_details) +{ + if (cs == CS1) + return NULL; + + *lpddr2_dev_details = elpida_2G_S4_details; + + return lpddr2_dev_details; +} + +void emif_get_device_timings(u32 emif_nr, + const struct lpddr2_device_timings **cs0_device_timings, + const struct lpddr2_device_timings **cs1_device_timings) +{ + *cs0_device_timings = &elpida_2G_S4_timings; + *cs1_device_timings = NULL; +} + +int board_init(void) +{ + /* GPMC init */ + gpmc_init(); + + /* MACH number */ + gd->bd->bi_arch_number = MACH_TYPE_OMAP_4430SDP; + + /* ATAGs location */ + gd->bd->bi_boot_params = OMAP44XX_DRAM_ADDR_SPACE_START + 0x100; + + return 0; +} + +int misc_init_r(void) +{ + /* Serial number */ + + omap_die_id_serial(); + + return 0; +} + +u32 get_board_rev(void) +{ + u32 value = 0; + + gpio_request(KC1_GPIO_MBID0, "MBID0"); + gpio_request(KC1_GPIO_MBID1, "MBID1"); + gpio_request(KC1_GPIO_MBID2, "MBID2"); + gpio_request(KC1_GPIO_MBID3, "MBID3"); + + gpio_direction_input(KC1_GPIO_MBID0); + gpio_direction_input(KC1_GPIO_MBID1); + gpio_direction_input(KC1_GPIO_MBID2); + gpio_direction_input(KC1_GPIO_MBID3); + + value |= (gpio_get_value(KC1_GPIO_MBID0) << 0); + value |= (gpio_get_value(KC1_GPIO_MBID1) << 1); + value |= (gpio_get_value(KC1_GPIO_MBID2) << 2); + value |= (gpio_get_value(KC1_GPIO_MBID3) << 3); + + return value; +} + +void get_board_serial(struct tag_serialnr *serialnr) +{ + omap_die_id_get_board_serial(serialnr); +} + +#ifndef CONFIG_SPL_BUILD +int board_mmc_init(bd_t *bis) +{ + return omap_mmc_init(1, 0, 0, -1, -1); +} +#endif + +void board_mmc_power_init(void) +{ + twl6030_power_mmc_init(1); +} diff --git a/board/amazon/kc1/kc1.h b/board/amazon/kc1/kc1.h new file mode 100644 index 0000000..886bd38 --- /dev/null +++ b/board/amazon/kc1/kc1.h @@ -0,0 +1,92 @@ +/* + * Amazon Kindle Fire (first generation) codename kc1 config + * + * Copyright (C) 2016 Paul Kocialkowski contact@paulk.fr + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#ifndef _KC1_H_ +#define _KC1_H_ + +#include <asm/arch/mux_omap4.h> + +#define KC1_GPIO_MBID1 173 +#define KC1_GPIO_MBID0 174 +#define KC1_GPIO_MBID3 177 +#define KC1_GPIO_MBID2 178 + +const struct pad_conf_entry core_padconf_array[] = { + /* GPMC */ + { GPMC_AD0, (IEN | PTU | M1) }, /* sdmmc2_dat0 */ + { GPMC_AD1, (IEN | PTU | M1) }, /* sdmmc2_dat1 */ + { GPMC_AD2, (IEN | PTU | M1) }, /* sdmmc2_dat2 */ + { GPMC_AD3, (IEN | PTU | M1) }, /* sdmmc2_dat3 */ + { GPMC_AD4, (IEN | PTU | M1) }, /* sdmmc2_dat4 */ + { GPMC_AD5, (IEN | PTU | M1) }, /* sdmmc2_dat5 */ + { GPMC_AD6, (IEN | PTU | M1) }, /* sdmmc2_dat6 */ + { GPMC_AD7, (IEN | PTU | M1) }, /* sdmmc2_dat7 */ + { GPMC_NOE, (IEN | PTU | M1) }, /* sdmmc2_clk */ + { GPMC_NWE, (IEN | PTU | M1) }, /* sdmmc2_cmd */ + /* CAM */ + { CAM_SHUTTER, (IDIS | DIS | M7) }, /* safe_mode */ + { CAM_STROBE, (IDIS | DIS | M7) }, /* safe_mode */ + { CAM_GLOBALRESET, (IDIS | DIS | M7) }, /* safe_mode */ + /* HDQ */ + { HDQ_SIO, (IDIS | DIS | M7) }, /* safe_mode */ + /* I2C1 */ + { I2C1_SCL, (IEN | PTU | M0) }, /* i2c1_scl */ + { I2C1_SDA, (IEN | PTU | M0) }, /* i2c1_sda */ + /* I2C2 */ + { I2C2_SCL, (IEN | PTU | M0) }, /* i2c2_scl */ + { I2C2_SDA, (IEN | PTU | M0) }, /* i2c2_sda */ + /* I2C3 */ + { I2C3_SCL, (IEN | PTU | M0) }, /* i2c3_scl */ + { I2C3_SDA, (IEN | PTU | M0) }, /* i2c3_sda */ + /* I2C4 */ + { I2C4_SCL, (IEN | PTU | M0) }, /* i2c4_scl */ + { I2C4_SDA, (IEN | PTU | M0) }, /* i2c4_sda */ + /* MCSPI1 */ + { MCSPI1_CLK, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_SOMI, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_SIMO, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_CS0, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_CS1, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_CS2, (IDIS | DIS | M7) }, /* safe_mode */ + { MCSPI1_CS3, (IDIS | DIS | M7) }, /* safe_mode */ + /* UART3 */ + { UART3_CTS_RCTX, (IDIS | DIS | M7) }, /* safe_mode */ + { UART3_RTS_SD, (IDIS | DIS | M7) }, /* safe_mode */ + { UART3_RX_IRRX, (IEN | DIS | M0) }, /* uart3_rx_irrx */ + { UART3_TX_IRTX, (IDIS | DIS | M0) }, /* uart3_tx_irtx */ + /* SDMMC5 */ + { SDMMC5_CLK, (IEN | PTU | M0) }, /* sdmmc5_clk */ + { SDMMC5_CMD, (IEN | PTU | M0) }, /* sdmmc5_cmd */ + { SDMMC5_DAT0, (IEN | PTU | M0) }, /* sdmmc5_dat0 */ + { SDMMC5_DAT1, (IEN | PTU | M0) }, /* sdmmc5_dat1 */ + { SDMMC5_DAT2, (IEN | PTU | M0) }, /* sdmmc5_dat2 */ + { SDMMC5_DAT3, (IEN | PTU | M0) }, /* sdmmc5_dat3 */ + /* MCSPI4 */ + { MCSPI4_CLK, (IEN | DIS | M0) }, /* mcspi4_clk */ + { MCSPI4_SIMO, (IEN | DIS | M0) }, /* mcspi4_simo */ + { MCSPI4_SOMI, (IEN | DIS | M0) }, /* mcspi4_somi */ + { MCSPI4_CS0, (IEN | PTD | M0) }, /* mcspi4_cs0 */ + /* UART4 */ + { UART4_RX, (IDIS | DIS | M4) }, /* gpio_155 */ + { UART4_TX, (IDIS | DIS | M7) }, /* safe_mode */ + /* UNIPRO */ + { UNIPRO_TX0, (IDIS | DIS | M7) }, /* safe_mode */ + { UNIPRO_TY0, (IDIS | DIS | M7) }, /* safe_mode */ + { UNIPRO_TX1, (IEN | DIS | M3) }, /* gpio_173 */ + { UNIPRO_TY1, (IEN | DIS | M3) }, /* gpio_174 */ + { UNIPRO_TX2, (IDIS | DIS | M7) }, /* safe_mode */ + { UNIPRO_TY2, (IDIS | DIS | M7) }, /* safe_mode */ + { UNIPRO_RX0, (IEN | DIS | M3) }, /* gpio_175 */ + { UNIPRO_RY0, (IEN | DIS | M3) }, /* gpio_176 */ + { UNIPRO_RX1, (IEN | DIS | M3) }, /* gpio_177 */ + { UNIPRO_RY1, (IEN | DIS | M3) }, /* gpio_178 */ + { UNIPRO_RX2, (IDIS | DIS | M7) }, /* safe_mode */ + { UNIPRO_RY2, (IDIS | DIS | M7) }, /* safe_mode */ +}; + +#endif diff --git a/configs/kc1_defconfig b/configs/kc1_defconfig new file mode 100644 index 0000000..c9cadd9 --- /dev/null +++ b/configs/kc1_defconfig @@ -0,0 +1,12 @@ +CONFIG_ARM=y +CONFIG_OMAP44XX=y +CONFIG_TARGET_KC1=y +CONFIG_SPL=y +CONFIG_SYS_PROMPT="kc1 # " +# CONFIG_CMD_IMLS is not set +# CONFIG_CMD_FLASH is not set +# CONFIG_CMD_FPGA is not set +CONFIG_CMD_GPIO=y +# CONFIG_CMD_SETEXPR is not set +# CONFIG_CMD_NFS is not set +CONFIG_SYS_NS16550=y diff --git a/include/configs/kc1.h b/include/configs/kc1.h new file mode 100644 index 0000000..281041d --- /dev/null +++ b/include/configs/kc1.h @@ -0,0 +1,230 @@ +/* + * Amazon Kindle Fire (first generation) codename kc1 config + * + * Copyright (C) 2016 Paul Kocialkowski contact@paulk.fr + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#ifndef __CONFIG_H +#define __CONFIG_H + +#include <asm/arch/cpu.h> +#include <asm/arch/omap.h> + +/* + * Build + */ + +#define CONFIG_SYS_THUMB_BUILD + +/* + * CPU + */ + +#define CONFIG_SYS_L2_PL310 1 +#define CONFIG_SYS_PL310_BASE 0x48242000 +#define CONFIG_SYS_CACHELINE_SIZE 32 + +/* + * Platform + */ + +#define CONFIG_OMAP +#define CONFIG_OMAP4430 +#define CONFIG_OMAP_COMMON + +/* + * Board + */ + +#define CONFIG_MISC_INIT_R + +/* + * Clocks + */ + +#define CONFIG_SYS_TIMERBASE GPT2_BASE +#define CONFIG_SYS_PTV 2 + +/* + * DRAM + */ + +#define CONFIG_NR_DRAM_BANKS 1 + +/* + * Memory + */ + +#define CONFIG_SYS_TEXT_BASE 0x80100000 +#define CONFIG_SYS_SDRAM_BASE 0x80000000 +#define CONFIG_SYS_INIT_SP_ADDR (NON_SECURE_SRAM_END - \ + GENERATED_GBL_DATA_SIZE) + +#define CONFIG_SYS_MALLOC_LEN (1024 * 1024 + CONFIG_ENV_SIZE) + +/* + * GPIO + */ + +#define CONFIG_OMAP_GPIO + +/* + * I2C + */ + +#define CONFIG_SYS_I2C +#define CONFIG_SYS_OMAP24_I2C_SPEED 400000 +#define CONFIG_SYS_OMAP24_I2C_SLAVE 1 +#define CONFIG_SYS_I2C_OMAP24XX +#define CONFIG_I2C_MULTI_BUS + +#define CONFIG_CMD_I2C + +/* + * Flash + */ + +#define CONFIG_SYS_NO_FLASH + +/* + * MMC + */ + +#define CONFIG_MMC +#define CONFIG_GENERIC_MMC +#define CONFIG_OMAP_HSMMC + +#define CONFIG_CMD_MMC + +/* + * Power + */ + +#define CONFIG_TWL6030_POWER + +/* + * Partitions + */ + +#define CONFIG_PARTITION_UUIDS +#define CONFIG_CMD_PART + +/* + * SPL + */ + +#define CONFIG_SPL_FRAMEWORK + +#define CONFIG_SPL_TEXT_BASE 0x40300000 +#define CONFIG_SPL_MAX_SIZE (48 * 1024) +#define CONFIG_SPL_BSS_START_ADDR 0x80000000 +#define CONFIG_SPL_BSS_MAX_SIZE (512 * 1024) +#define CONFIG_SYS_SPL_MALLOC_START 0x80208000 +#define CONFIG_SYS_SPL_MALLOC_SIZE (1024 * 1024) + +#define CONFIG_SPL_LDSCRIPT "$(CPUDIR)/omap-common/u-boot-spl.lds" +#define CONFIG_SPL_BOARD_INIT + +#define CONFIG_SPL_LIBGENERIC_SUPPORT +#define CONFIG_SPL_LIBCOMMON_SUPPORT +#define CONFIG_SPL_LIBDISK_SUPPORT +#define CONFIG_SPL_SERIAL_SUPPORT +#define CONFIG_SPL_POWER_SUPPORT +#define CONFIG_SPL_GPIO_SUPPORT +#define CONFIG_SPL_I2C_SUPPORT +#define CONFIG_SPL_MMC_SUPPORT + +#define CONFIG_SYS_MMCSD_RAW_MODE_U_BOOT_PARTITION 2 + +/* + * Console + */ + +#define CONFIG_SYS_CONSOLE_IS_IN_ENV + +#define CONFIG_DISPLAY_CPUINFO +#define CONFIG_DISPLAY_BOARDINFO + +#define CONFIG_AUTO_COMPLETE + +#define CONFIG_SYS_LONGHELP +#define CONFIG_SYS_HUSH_PARSER + +#define CONFIG_SYS_MAXARGS 16 +#define CONFIG_SYS_CBSIZE 512 +#define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + sizeof(CONFIG_SYS_PROMPT) \ + + 16) + +/* + * Serial + */ + +#define CONFIG_SYS_NS16550_SERIAL +#define CONFIG_SYS_NS16550_REG_SIZE (-4) +#define CONFIG_SYS_NS16550_CLK 48000000 +#define CONFIG_SYS_NS16550_COM3 UART3_BASE +#define CONFIG_CONS_INDEX 3 + +#define CONFIG_BAUDRATE 115200 +#define CONFIG_SYS_BAUDRATE_TABLE { 4800, 9600, 19200, 38400, 57600, \ + 115200 } + +/* + * Environment + */ + +#define CONFIG_ENV_SIZE (128 * 1024) +#define CONFIG_ENV_IS_NOWHERE + +#define CONFIG_ENV_OVERWRITE + +#define CONFIG_EXTRA_ENV_SETTINGS \ + "kernel_addr_r=0x82000000\0" \ + "loadaddr=0x82000000\0" \ + "fdt_addr_r=0x88000000\0" \ + "fdtaddr=0x88000000\0" \ + "ramdisk_addr_r=0x88080000\0" \ + "pxefile_addr_r=0x80100000\0" \ + "scriptaddr=0x80000000\0" \ + "bootm_size=0x10000000\0" \ + "boot_mmc_dev=0\0" \ + "kernel_mmc_part=7\0" \ + "recovery_mmc_part=5\0" \ + "bootargs=mem=512M console=ttyO2\0" + +/* + * ATAGs + */ + +#define CONFIG_SETUP_MEMORY_TAGS +#define CONFIG_CMDLINE_TAG +#define CONFIG_INITRD_TAG +#define CONFIG_REVISION_TAG +#define CONFIG_SERIAL_TAG + +/* + * Boot + */ + +#define CONFIG_SYS_LOAD_ADDR 0x82000000 + +#define CONFIG_ANDROID_BOOT_IMAGE + +#define CONFIG_BOOTCOMMAND \ + "setenv boot_mmc_part ${kernel_mmc_part}; " \ + "part start mmc ${boot_mmc_dev} ${boot_mmc_part} boot_mmc_start; " \ + "part size mmc ${boot_mmc_dev} ${boot_mmc_part} boot_mmc_size; " \ + "mmc dev ${boot_mmc_dev}; " \ + "mmc read ${kernel_addr_r} ${boot_mmc_start} ${boot_mmc_size} && " \ + "bootm ${kernel_addr_r};" + +/* + * Defaults + */ + +#include <config_defaults.h> +#include <config_distro_defaults.h> + +#endif

On Sat, Feb 27, 2016 at 07:19:00PM +0100, Paul Kocialkowski wrote:
The Amazon Kindle Fire (first generation) codename kc1 is a tablet that was released by Amazon back in 2011.
It is using an OMAP4430 SoC GP version, which allows running U-Boot and the U-Boot SPL from the ground up.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

On (at least) OMAP4, the USB DPLL is required to be setup for the internal PHY to work properly. The internal PHY is used by default with the MUSB USB OTG controller.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap-common/clocks-common.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/arch/arm/cpu/armv7/omap-common/clocks-common.c b/arch/arm/cpu/armv7/omap-common/clocks-common.c index e28b795..1ba9995 100644 --- a/arch/arm/cpu/armv7/omap-common/clocks-common.c +++ b/arch/arm/cpu/armv7/omap-common/clocks-common.c @@ -339,7 +339,8 @@ void configure_mpu_dpll(void) debug("MPU DPLL locked\n"); }
-#if defined(CONFIG_USB_EHCI_OMAP) || defined(CONFIG_USB_XHCI_OMAP) +#if defined(CONFIG_USB_EHCI_OMAP) || defined(CONFIG_USB_XHCI_OMAP) || \ + defined(CONFIG_USB_MUSB_OMAP2PLUS) static void setup_usb_dpll(void) { const struct dpll_params *params; @@ -406,7 +407,8 @@ static void setup_dplls(void) /* MPU dpll */ configure_mpu_dpll();
-#if defined(CONFIG_USB_EHCI_OMAP) || defined(CONFIG_USB_XHCI_OMAP) +#if defined(CONFIG_USB_EHCI_OMAP) || defined(CONFIG_USB_XHCI_OMAP) || \ + defined(CONFIG_USB_MUSB_OMAP2PLUS) setup_usb_dpll(); #endif params = get_ddr_dpll_params(*dplls_data);

On Sat, Feb 27, 2016 at 07:19:01PM +0100, Paul Kocialkowski wrote:
On (at least) OMAP4, the USB DPLL is required to be setup for the internal PHY to work properly. The internal PHY is used by default with the MUSB USB OTG controller.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This correctly enables the USB PHY clocks, by enabling CM_ALWON_USBPHY_CLKCTRL and correctly setting CM_L3INIT_USBPHY_CLKCTRL's value.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/hw_data.c | 4 ++++ arch/arm/cpu/armv7/omap4/prcm-regs.c | 1 + arch/arm/include/asm/arch-omap4/clock.h | 5 ++++- 3 files changed, 9 insertions(+), 1 deletion(-)
diff --git a/arch/arm/cpu/armv7/omap4/hw_data.c b/arch/arm/cpu/armv7/omap4/hw_data.c index 1cc2072..02c06c1 100644 --- a/arch/arm/cpu/armv7/omap4/hw_data.c +++ b/arch/arm/cpu/armv7/omap4/hw_data.c @@ -380,6 +380,10 @@ void enable_basic_clocks(void) setbits_le32((*prcm)->cm_l3init_usbphy_clkctrl, USBPHY_CLKCTRL_OPTFCLKEN_PHY_48M_MASK);
+ /* Enable 32 KHz clock for USB PHY */ + setbits_le32((*prcm)->cm_coreaon_usb_phy1_core_clkctrl, + USBPHY_CORE_CLKCTRL_OPTFCLKEN_CLK32K); + do_enable_clocks(clk_domains_essential, clk_modules_hw_auto_essential, clk_modules_explicit_en_essential, diff --git a/arch/arm/cpu/armv7/omap4/prcm-regs.c b/arch/arm/cpu/armv7/omap4/prcm-regs.c index a09581e..2f0e1e8 100644 --- a/arch/arm/cpu/armv7/omap4/prcm-regs.c +++ b/arch/arm/cpu/armv7/omap4/prcm-regs.c @@ -129,6 +129,7 @@ struct prcm_regs const omap4_prcm = { .cm_div_m2_dpll_unipro = 0x4a0081d0, .cm_ssc_deltamstep_dpll_unipro = 0x4a0081e8, .cm_ssc_modfreqdiv_dpll_unipro = 0x4a0081ec, + .cm_coreaon_usb_phy1_core_clkctrl = 0x4a008640,
/* cm2.core */ .cm_l3_1_clkstctrl = 0x4a008700, diff --git a/arch/arm/include/asm/arch-omap4/clock.h b/arch/arm/include/asm/arch-omap4/clock.h index f3a682a..a408c0c 100644 --- a/arch/arm/include/asm/arch-omap4/clock.h +++ b/arch/arm/include/asm/arch-omap4/clock.h @@ -134,8 +134,11 @@ /* CM_DSS_DSS_CLKCTRL */ #define DSS_CLKCTRL_OPTFCLKEN_MASK 0xF00
+/* CM_COREAON_USB_PHY_CORE_CLKCTRL */ +#define USBPHY_CORE_CLKCTRL_OPTFCLKEN_CLK32K (1 << 8) + /* CM_L3INIT_USBPHY_CLKCTRL */ -#define USBPHY_CLKCTRL_OPTFCLKEN_PHY_48M_MASK 8 +#define USBPHY_CLKCTRL_OPTFCLKEN_PHY_48M_MASK (1 << 8)
/* CM_MPU_MPU_CLKCTRL */ #define MPU_CLKCTRL_CLKSEL_EMIF_DIV_MODE_SHIFT 24

On Sat, Feb 27, 2016 at 07:19:02PM +0100, Paul Kocialkowski wrote:
This correctly enables the USB PHY clocks, by enabling CM_ALWON_USBPHY_CLKCTRL and correctly setting CM_L3INIT_USBPHY_CLKCTRL's value.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This explicitly sets VUSB voltage to 3.3V when enabling USB.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 4 ++++ include/twl6030.h | 2 ++ 2 files changed, 6 insertions(+)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index 7ed9129..df43cca 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -248,6 +248,10 @@ void twl6030_usb_device_settings() { u8 value = 0;
+ /* 3.3V voltage output for VUSB */ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VUSB_CFG_VOLTAGE, + TWL6030_CFG_VOLTAGE_33); + /* Enable P1 output for VUSB */ twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_VUSB_CFG_STATE, TWL6030_CFG_STATE_P1 | TWL6030_CFG_STATE_ON); diff --git a/include/twl6030.h b/include/twl6030.h index 04295c9..e68393c 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -32,6 +32,7 @@ #define TWL6030_VMMC_CFG_STATE 0x9A #define TWL6030_VMMC_CFG_VOLTAGE 0x9B #define TWL6030_VUSB_CFG_STATE 0xA2 +#define TWL6030_VUSB_CFG_VOLTAGE 0xA3
#define TWL6030_CFG_GRP_P1 (1 << 0) #define TWL6030_CFG_STATE_ON (1 << 0) @@ -39,6 +40,7 @@ #define TWL6030_CFG_VOLTAGE_18 0x09 #define TWL6030_CFG_VOLTAGE_28 0x13 #define TWL6030_CFG_VOLTAGE_30 0x15 +#define TWL6030_CFG_VOLTAGE_33 0x18
#define MISC1 0xE4 #define VAC_MEAS (1 << 2)

On Sat, Feb 27, 2016 at 07:19:03PM +0100, Paul Kocialkowski wrote:
This explicitly sets VUSB voltage to 3.3V when enabling USB.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

When booting from USB, the bootrom sets the VUSB_IN_PMID bit of the MISC2 register of the TWL6030. However, U-Boot sets the VUSB_IN_VSYS bit to enable VBUS input. As both bits are contradictory, enabling both disables the input, according to the TWL6030 TRM.
Thus, we need to clear the VUSB_IN_PMID bit in case of an USB boot (which could just as well be a memory boot after USB timed out).
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 1 + include/twl6030.h | 1 + 2 files changed, 2 insertions(+)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index df43cca..c6d06f1 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -259,6 +259,7 @@ void twl6030_usb_device_settings() /* Select the input supply for VUSB regulator */ twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_MISC2, &value); value |= TWL6030_MISC2_VUSB_IN_VSYS; + value &= ~TWL6030_MISC2_VUSB_IN_PMID; twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_MISC2, value); } #endif diff --git a/include/twl6030.h b/include/twl6030.h index e68393c..9a1c645 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -48,6 +48,7 @@ #define BB_MEAS (1 << 0)
#define TWL6030_MISC2 0xE5 +#define TWL6030_MISC2_VUSB_IN_PMID (1 << 3) #define TWL6030_MISC2_VUSB_IN_VSYS (1 << 4)
/* Slave Address 0x49 */

On Sat, Feb 27, 2016 at 07:19:04PM +0100, Paul Kocialkowski wrote:
When booting from USB, the bootrom sets the VUSB_IN_PMID bit of the MISC2 register of the TWL6030. However, U-Boot sets the VUSB_IN_VSYS bit to enable VBUS input. As both bits are contradictory, enabling both disables the input, according to the TWL6030 TRM.
Thus, we need to clear the VUSB_IN_PMID bit in case of an USB boot (which could just as well be a memory boot after USB timed out).
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This adds support for the OMAP4 MUSB USB controller, with a matching Linux compat definition, TWL6030 USB device setup and USBOTGHS register setup.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/usb/musb-new/linux-compat.h | 4 ++++ drivers/usb/musb-new/omap2430.c | 13 +++++++++++++ drivers/usb/musb-new/omap2430.h | 8 ++++++++ 3 files changed, 25 insertions(+)
diff --git a/drivers/usb/musb-new/linux-compat.h b/drivers/usb/musb-new/linux-compat.h index 46f83d9..1fc9391 100644 --- a/drivers/usb/musb-new/linux-compat.h +++ b/drivers/usb/musb-new/linux-compat.h @@ -37,4 +37,8 @@ #define CONFIG_SOC_OMAP3430 #endif
+#ifdef CONFIG_OMAP4430 +#define CONFIG_ARCH_OMAP4 +#endif + #endif /* __LINUX_COMPAT_H__ */ diff --git a/drivers/usb/musb-new/omap2430.c b/drivers/usb/musb-new/omap2430.c index 9f307e9..684ad95 100644 --- a/drivers/usb/musb-new/omap2430.c +++ b/drivers/usb/musb-new/omap2430.c @@ -23,8 +23,10 @@ #include <linux/usb/musb-omap.h> #else #include <common.h> +#include <asm/omap_common.h> #include <asm/omap_musb.h> #include <twl4030.h> +#include <twl6030.h> #include "linux-compat.h" #endif
@@ -434,6 +436,17 @@ static int omap2430_musb_enable(struct musb *musb) __PRETTY_FUNCTION__); } #endif + +#ifdef CONFIG_TWL6030_POWER + twl6030_usb_device_settings(); +#endif + +#ifdef CONFIG_OMAP4430 + u32 *usbotghs_control = (u32 *)((*ctrl)->control_usbotghs_ctrl); + *usbotghs_control = USBOTGHS_CONTROL_AVALID | + USBOTGHS_CONTROL_VBUSVALID | USBOTGHS_CONTROL_IDDIG; +#endif + return 0; #endif } diff --git a/drivers/usb/musb-new/omap2430.h b/drivers/usb/musb-new/omap2430.h index 56998c7..0c3dd8b 100644 --- a/drivers/usb/musb-new/omap2430.h +++ b/drivers/usb/musb-new/omap2430.h @@ -50,4 +50,12 @@ #define OTG_FORCESTDBY 0x414 # define ENABLEFORCE (1 << 0)
+/* + * OMAP4-specific definitions + */ + +#define USBOTGHS_CONTROL_AVALID (1 << 0) +#define USBOTGHS_CONTROL_VBUSVALID (1 << 2) +#define USBOTGHS_CONTROL_IDDIG (1 << 4) + #endif /* __MUSB_OMAP243X_H__ */

On Sat, Feb 27, 2016 at 07:19:05PM +0100, Paul Kocialkowski wrote:
This adds support for the OMAP4 MUSB USB controller, with a matching Linux compat definition, TWL6030 USB device setup and USBOTGHS register setup.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This adds support for the MUSB USB dual-role controller in peripheral mode, with configuration options for the fastboot USB gadget.
At this point, flashing the internal eMMC is support.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/amazon/kc1/kc1.c | 27 +++++++++++++++++++++++++++ board/amazon/kc1/kc1.h | 4 ++++ configs/kc1_defconfig | 2 ++ include/configs/kc1.h | 35 +++++++++++++++++++++++++++++++++++ 4 files changed, 68 insertions(+)
diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c index a189bb2..29d9c64 100644 --- a/board/amazon/kc1/kc1.c +++ b/board/amazon/kc1/kc1.c @@ -8,6 +8,9 @@
#include <config.h> #include <common.h> +#include <linux/ctype.h> +#include <linux/usb/musb.h> +#include <asm/omap_musb.h> #include <asm/arch/sys_proto.h> #include <asm/arch/mmc_host_def.h> #include <asm/gpio.h> @@ -21,6 +24,26 @@ const struct omap_sysinfo sysinfo = { .board_string = "kc1" };
+static struct musb_hdrc_config musb_config = { + .multipoint = 1, + .dyn_fifo = 1, + .num_eps = 16, + .ram_bits = 12 +}; + +static struct omap_musb_board_data musb_board_data = { + .interface_type = MUSB_INTERFACE_UTMI, +}; + +static struct musb_hdrc_platform_data musb_platform_data = { + .mode = MUSB_PERIPHERAL, + .config = &musb_config, + .power = 100, + .platform_ops = &omap2430_ops, + .board_data = &musb_board_data, +}; + + void set_muxconf_regs(void) { do_set_mux((*ctrl)->control_padconf_core_base, core_padconf_array, @@ -66,6 +89,10 @@ int misc_init_r(void)
omap_die_id_serial();
+ /* MUSB */ + + musb_register(&musb_platform_data, &musb_board_data, (void *)MUSB_BASE); + return 0; }
diff --git a/board/amazon/kc1/kc1.h b/board/amazon/kc1/kc1.h index 886bd38..67d008f 100644 --- a/board/amazon/kc1/kc1.h +++ b/board/amazon/kc1/kc1.h @@ -87,6 +87,10 @@ const struct pad_conf_entry core_padconf_array[] = { { UNIPRO_RY1, (IEN | DIS | M3) }, /* gpio_178 */ { UNIPRO_RX2, (IDIS | DIS | M7) }, /* safe_mode */ { UNIPRO_RY2, (IDIS | DIS | M7) }, /* safe_mode */ + /* USBA0_OTG */ + { USBA0_OTG_CE, (IDIS | PTD | M0) }, /* usba0_otg_ce */ + { USBA0_OTG_DP, (IEN | DIS | M0) }, /* usba0_otg_dp */ + { USBA0_OTG_DM, (IEN | DIS | M0) }, /* usba0_otg_dm */ };
#endif diff --git a/configs/kc1_defconfig b/configs/kc1_defconfig index c9cadd9..1e5c918 100644 --- a/configs/kc1_defconfig +++ b/configs/kc1_defconfig @@ -10,3 +10,5 @@ CONFIG_CMD_GPIO=y # CONFIG_CMD_SETEXPR is not set # CONFIG_CMD_NFS is not set CONFIG_SYS_NS16550=y +CONFIG_USB=y +CONFIG_USB_MUSB_GADGET=y diff --git a/include/configs/kc1.h b/include/configs/kc1.h index 281041d..185e8de 100644 --- a/include/configs/kc1.h +++ b/include/configs/kc1.h @@ -172,6 +172,41 @@ 115200 }
/* + * USB gadget + */ + +#define CONFIG_USB_MUSB_PIO_ONLY +#define CONFIG_USB_MUSB_OMAP2PLUS + +#define CONFIG_USB_GADGET +#define CONFIG_USB_GADGET_DUALSPEED +#define CONFIG_USB_GADGET_VBUS_DRAW 0 + +/* + * Download + */ + +#define CONFIG_USB_GADGET_DOWNLOAD + +#define CONFIG_G_DNL_VENDOR_NUM 0x0451 +#define CONFIG_G_DNL_PRODUCT_NUM 0xd022 +#define CONFIG_G_DNL_MANUFACTURER "Texas Instruments" + +/* + * Fastboot + */ + +#define CONFIG_USB_FUNCTION_FASTBOOT + +#define CONFIG_FASTBOOT_BUF_ADDR CONFIG_SYS_LOAD_ADDR +#define CONFIG_FASTBOOT_BUF_SIZE 0x2000000 + +#define CONFIG_FASTBOOT_FLASH +#define CONFIG_FASTBOOT_FLASH_MMC_DEV 0 + +#define CONFIG_CMD_FASTBOOT + +/* * Environment */

On Sat, Feb 27, 2016 at 07:19:06PM +0100, Paul Kocialkowski wrote:
This adds support for the MUSB USB dual-role controller in peripheral mode, with configuration options for the fastboot USB gadget.
At this point, flashing the internal eMMC is support.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Reboot mode is written to SAR memory before reboot in the form of a string.
This mechanism is supported on OMAP4 by various TI kernels.
It is up to each board to make use of this mechanism or not.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/boot.c | 41 ++++++++++++++++++++++++++++++++++ arch/arm/include/asm/arch-omap4/omap.h | 8 +++++++ 2 files changed, 49 insertions(+)
diff --git a/arch/arm/cpu/armv7/omap4/boot.c b/arch/arm/cpu/armv7/omap4/boot.c index 4b5aa77..bae49f4 100644 --- a/arch/arm/cpu/armv7/omap4/boot.c +++ b/arch/arm/cpu/armv7/omap4/boot.c @@ -58,3 +58,44 @@ u32 omap_sys_boot_device(void)
return boot_devices[sys_boot]; } + +int omap_reboot_mode(char *mode, unsigned int length) +{ + unsigned int limit; + unsigned int i; + + if (length < 2) + return -1; + + limit = (length < OMAP_REBOOT_REASON_SIZE) ? length : + OMAP_REBOOT_REASON_SIZE; + + for (i = 0; i < (limit - 1); i++) + mode[i] = readb((u8 *)(OMAP44XX_SAR_RAM_BASE + + OMAP_REBOOT_REASON_OFFSET + i)); + + mode[i] = '\0'; + + return 0; +} + +int omap_reboot_mode_clear(void) +{ + writeb(0, (u8 *)(OMAP44XX_SAR_RAM_BASE + OMAP_REBOOT_REASON_OFFSET)); + + return 0; +} + +int omap_reboot_mode_store(char *mode) +{ + unsigned int i; + + for (i = 0; i < (OMAP_REBOOT_REASON_SIZE - 1) && mode[i] != '\0'; i++) + writeb(mode[i], (u8 *)(OMAP44XX_SAR_RAM_BASE + + OMAP_REBOOT_REASON_OFFSET + i)); + + writeb('\0', (u8 *)(OMAP44XX_SAR_RAM_BASE + + OMAP_REBOOT_REASON_OFFSET + i)); + + return 0; +} diff --git a/arch/arm/include/asm/arch-omap4/omap.h b/arch/arm/include/asm/arch-omap4/omap.h index 4712722..5ccda6e 100644 --- a/arch/arm/include/asm/arch-omap4/omap.h +++ b/arch/arm/include/asm/arch-omap4/omap.h @@ -120,6 +120,10 @@ struct s32ktimer { /* ABB tranxdone mask */ #define OMAP_ABB_MPU_TXDONE_MASK (0x1 << 7)
+#define OMAP44XX_SAR_RAM_BASE 0x4a326000 +#define OMAP_REBOOT_REASON_OFFSET 0xA0C +#define OMAP_REBOOT_REASON_SIZE 0x0F + /* Boot parameters */ #ifndef __ASSEMBLY__ struct omap_boot_parameters { @@ -129,6 +133,10 @@ struct omap_boot_parameters { unsigned char reset_reason; unsigned char ch_flags; }; + +int omap_reboot_mode(char *mode, unsigned int length); +int omap_reboot_mode_clear(void); +int omap_reboot_mode_store(char *mode); #endif
#endif

On Sat, Feb 27, 2016 at 07:19:07PM +0100, Paul Kocialkowski wrote:
Reboot mode is written to SAR memory before reboot in the form of a string.
This mechanism is supported on OMAP4 by various TI kernels.
It is up to each board to make use of this mechanism or not.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Since the SAR registers are filled with garbage on cold reset, this checks for a warm reset to assert the validity of reboot mode.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- arch/arm/cpu/armv7/omap4/boot.c | 4 ++++ 1 file changed, 4 insertions(+)
diff --git a/arch/arm/cpu/armv7/omap4/boot.c b/arch/arm/cpu/armv7/omap4/boot.c index bae49f4..7f5791e 100644 --- a/arch/arm/cpu/armv7/omap4/boot.c +++ b/arch/arm/cpu/armv7/omap4/boot.c @@ -9,6 +9,7 @@ #include <common.h> #include <asm/io.h> #include <asm/omap_common.h> +#include <asm/arch/sys_proto.h> #include <spl.h>
static u32 boot_devices[] = { @@ -67,6 +68,9 @@ int omap_reboot_mode(char *mode, unsigned int length) if (length < 2) return -1;
+ if (!warm_reset()) + return -1; + limit = (length < OMAP_REBOOT_REASON_SIZE) ? length : OMAP_REBOOT_REASON_SIZE;

On Sat, Feb 27, 2016 at 07:19:08PM +0100, Paul Kocialkowski wrote:
Since the SAR registers are filled with garbage on cold reset, this checks for a warm reset to assert the validity of reboot mode.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This adds support for the omap4 reboot mode mechanism and exports the reboot mode via an environment variable, that is used in the boot command to make it possible to boot from the recovery partition or fastboot.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/amazon/kc1/kc1.c | 18 ++++++++++++++++++ board/amazon/kc1/kc1.h | 2 ++ include/configs/kc1.h | 4 ++++ 3 files changed, 24 insertions(+)
diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c index 29d9c64..d526695 100644 --- a/board/amazon/kc1/kc1.c +++ b/board/amazon/kc1/kc1.c @@ -85,6 +85,19 @@ int board_init(void)
int misc_init_r(void) { + char reboot_mode[2] = { 0 }; + + /* Reboot mode */ + + omap_reboot_mode(reboot_mode, sizeof(reboot_mode)); + + if (reboot_mode[0] > 0 && isascii(reboot_mode[0])) { + if (!getenv("reboot-mode")) + setenv("reboot-mode", (char *)reboot_mode); + + omap_reboot_mode_clear(); + } + /* Serial number */
omap_die_id_serial(); @@ -123,6 +136,11 @@ void get_board_serial(struct tag_serialnr *serialnr) omap_die_id_get_board_serial(serialnr); }
+int fb_set_reboot_flag(void) +{ + return omap_reboot_mode_store("b"); +} + #ifndef CONFIG_SPL_BUILD int board_mmc_init(bd_t *bis) { diff --git a/board/amazon/kc1/kc1.h b/board/amazon/kc1/kc1.h index 67d008f..14737d7 100644 --- a/board/amazon/kc1/kc1.h +++ b/board/amazon/kc1/kc1.h @@ -11,6 +11,7 @@
#include <asm/arch/mux_omap4.h>
+#define KC1_GPIO_USB_ID 52 #define KC1_GPIO_MBID1 173 #define KC1_GPIO_MBID0 174 #define KC1_GPIO_MBID3 177 @@ -28,6 +29,7 @@ const struct pad_conf_entry core_padconf_array[] = { { GPMC_AD7, (IEN | PTU | M1) }, /* sdmmc2_dat7 */ { GPMC_NOE, (IEN | PTU | M1) }, /* sdmmc2_clk */ { GPMC_NWE, (IEN | PTU | M1) }, /* sdmmc2_cmd */ + { GPMC_NCS2, (IEN | PTD | M3) }, /* gpio_52 */ /* CAM */ { CAM_SHUTTER, (IDIS | DIS | M7) }, /* safe_mode */ { CAM_STROBE, (IDIS | DIS | M7) }, /* safe_mode */ diff --git a/include/configs/kc1.h b/include/configs/kc1.h index 185e8de..04cb320 100644 --- a/include/configs/kc1.h +++ b/include/configs/kc1.h @@ -249,6 +249,10 @@
#define CONFIG_BOOTCOMMAND \ "setenv boot_mmc_part ${kernel_mmc_part}; " \ + "if test reboot-${reboot-mode} = reboot-r; then " \ + "echo recovery; setenv boot_mmc_part ${recovery_mmc_part}; fi; " \ + "if test reboot-${reboot-mode} = reboot-b; then " \ + "echo fastboot; fastboot 0; fi; " \ "part start mmc ${boot_mmc_dev} ${boot_mmc_part} boot_mmc_start; " \ "part size mmc ${boot_mmc_dev} ${boot_mmc_part} boot_mmc_size; " \ "mmc dev ${boot_mmc_dev}; " \

On Sat, Feb 27, 2016 at 07:19:09PM +0100, Paul Kocialkowski wrote:
This adds support for the omap4 reboot mode mechanism and exports the reboot mode via an environment variable, that is used in the boot command to make it possible to boot from the recovery partition or fastboot.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

USB ID pin pull-up indicates factory (fastboot) cable detection.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/amazon/kc1/kc1.c | 9 +++++++++ 1 file changed, 9 insertions(+)
diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c index d526695..9367b50 100644 --- a/board/amazon/kc1/kc1.c +++ b/board/amazon/kc1/kc1.c @@ -86,11 +86,20 @@ int board_init(void) int misc_init_r(void) { char reboot_mode[2] = { 0 }; + u32 value;
/* Reboot mode */
omap_reboot_mode(reboot_mode, sizeof(reboot_mode));
+ /* USB ID pin pull-up indicates factory (fastboot) cable detection. */ + gpio_request(KC1_GPIO_USB_ID, "USB_ID"); + gpio_direction_input(KC1_GPIO_USB_ID); + value = gpio_get_value(KC1_GPIO_USB_ID); + + if (value) + reboot_mode[0] = 'b'; + if (reboot_mode[0] > 0 && isascii(reboot_mode[0])) { if (!getenv("reboot-mode")) setenv("reboot-mode", (char *)reboot_mode);

On Sat, Feb 27, 2016 at 07:19:10PM +0100, Paul Kocialkowski wrote:
USB ID pin pull-up indicates factory (fastboot) cable detection.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

The TWL6030 power driver is only built when CONFIG_TWL6030_POWER is selected, thus there is no reason to wrap the code with ifdef.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 2 -- 1 file changed, 2 deletions(-)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index c6d06f1..bfeb34b 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -5,7 +5,6 @@ * SPDX-License-Identifier: GPL-2.0+ */ #include <config.h> -#ifdef CONFIG_TWL6030_POWER
#include <twl6030.h>
@@ -262,4 +261,3 @@ void twl6030_usb_device_settings() value &= ~TWL6030_MISC2_VUSB_IN_PMID; twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_MISC2, value); } -#endif

On Sat, Feb 27, 2016 at 07:19:11PM +0100, Paul Kocialkowski wrote:
The TWL6030 power driver is only built when CONFIG_TWL6030_POWER is selected, thus there is no reason to wrap the code with ifdef.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This adds support for powering off (the omap SoC) from the twl6030.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/power/twl6030.c | 8 ++++++++ include/twl6030.h | 7 +++++++ 2 files changed, 15 insertions(+)
diff --git a/drivers/power/twl6030.c b/drivers/power/twl6030.c index bfeb34b..05c79be 100644 --- a/drivers/power/twl6030.c +++ b/drivers/power/twl6030.c @@ -28,6 +28,7 @@ static struct twl6030_data twl6032_info = { .vbat_shift = TWL6032_VBAT_SHIFT, };
+ static int twl6030_gpadc_read_channel(u8 channel_no) { u8 lsb = 0; @@ -71,6 +72,13 @@ static int twl6030_gpadc_sw2_trigger(void) return 0; }
+void twl6030_power_off(void) +{ + twl6030_i2c_write_u8(TWL6030_CHIP_PM, TWL6030_PHOENIX_DEV_ON, + TWL6030_PHOENIX_APP_DEVOFF | TWL6030_PHOENIX_CON_DEVOFF | + TWL6030_PHOENIX_MOD_DEVOFF); +} + void twl6030_stop_usb_charging(void) { twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, CONTROLLER_CTRL1, 0); diff --git a/include/twl6030.h b/include/twl6030.h index 9a1c645..26c27a4 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -20,6 +20,12 @@ #define TWL6030_CHIP_PWM 0x49
/* Slave Address 0x48 */ +#define TWL6030_PHOENIX_DEV_ON 0x25 + +#define TWL6030_PHOENIX_APP_DEVOFF (1 << 0) +#define TWL6030_PHOENIX_CON_DEVOFF (1 << 1) +#define TWL6030_PHOENIX_MOD_DEVOFF (1 << 2) + #define TWL6030_PH_STS_BOOT 0x29
#define TWL6030_PH_STS_BOOT0 (1 << 0) @@ -182,6 +188,7 @@ static inline int twl6030_i2c_read_u8(u8 chip_no, u8 reg, u8 *val) return i2c_read(chip_no, reg, 1, val, 1); }
+void twl6030_power_off(void); void twl6030_init_battery_charging(void); void twl6030_usb_device_settings(void); void twl6030_start_usb_charging(void);

On Sat, Feb 27, 2016 at 07:19:12PM +0100, Paul Kocialkowski wrote:
This adds support for powering off (the omap SoC) from the twl6030.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

This adds support for detecting a few inputs exported by the TWL6030. Currently-supported inputs are the power button, USB and charger presence.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- drivers/input/Makefile | 1 + drivers/input/twl6030.c | 48 ++++++++++++++++++++++++++++++++++++++++++++++++ include/twl6030.h | 21 +++++++++++++++++++++ 3 files changed, 70 insertions(+) create mode 100644 drivers/input/twl6030.c
diff --git a/drivers/input/Makefile b/drivers/input/Makefile index 5f15265..9109ac6 100644 --- a/drivers/input/Makefile +++ b/drivers/input/Makefile @@ -10,6 +10,7 @@ obj-$(CONFIG_DM_KEYBOARD) += keyboard-uclass.o obj-$(CONFIG_I8042_KEYB) += i8042.o obj-$(CONFIG_TEGRA_KEYBOARD) += tegra-kbc.o obj-$(CONFIG_TWL4030_INPUT) += twl4030.o +obj-$(CONFIG_TWL6030_INPUT) += twl6030.o obj-$(CONFIG_CROS_EC_KEYB) += cros_ec_keyb.o ifdef CONFIG_PS2KBD obj-y += keyboard.o pc_keyb.o diff --git a/drivers/input/twl6030.c b/drivers/input/twl6030.c new file mode 100644 index 0000000..8de032a --- /dev/null +++ b/drivers/input/twl6030.c @@ -0,0 +1,48 @@ +/* + * TWL6030 input + * + * Copyright (C) 2016 Paul Kocialkowski contact@paulk.fr + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <twl6030.h> + +int twl6030_input_power_button(void) +{ + u8 value; + + twl6030_i2c_read_u8(TWL6030_CHIP_PM, TWL6030_STS_HW_CONDITIONS, &value); + + /* Power button is active low. */ + if (value & TWL6030_STS_HW_CONDITIONS_PWRON) + return 0; + + return 1; +} + +int twl6030_input_charger(void) +{ + u8 value; + + twl6030_i2c_read_u8(TWL6030_CHIP_CHARGER, TWL6030_CONTROLLER_STAT1, + &value); + + if (value & TWL6030_CONTROLLER_STAT1_VAC_DET) + return 1; + + return 0; +} + +int twl6030_input_usb(void) +{ + u8 value; + + twl6030_i2c_read_u8(TWL6030_CHIP_CHARGER, TWL6030_CONTROLLER_STAT1, + &value); + + if (value & TWL6030_CONTROLLER_STAT1_VBUS_DET) + return 1; + + return 0; +} diff --git a/include/twl6030.h b/include/twl6030.h index 26c27a4..40e2c11 100644 --- a/include/twl6030.h +++ b/include/twl6030.h @@ -20,6 +20,10 @@ #define TWL6030_CHIP_PWM 0x49
/* Slave Address 0x48 */ +#define TWL6030_STS_HW_CONDITIONS 0x21 + +#define TWL6030_STS_HW_CONDITIONS_PWRON (1 << 0) + #define TWL6030_PHOENIX_DEV_ON 0x25
#define TWL6030_PHOENIX_APP_DEVOFF (1 << 0) @@ -59,6 +63,11 @@
/* Slave Address 0x49 */
+#define TWL6030_CONTROLLER_STAT1 0xE3 + +#define TWL6030_CONTROLLER_STAT1_VAC_DET (1 << 3) +#define TWL6030_CONTROLLER_STAT1_VBUS_DET (1 << 2) + /* Battery CHARGER REGISTERS */ #define CONTROLLER_INT_MASK 0xE0 #define CONTROLLER_CTRL1 0xE1 @@ -188,6 +197,10 @@ static inline int twl6030_i2c_read_u8(u8 chip_no, u8 reg, u8 *val) return i2c_read(chip_no, reg, 1, val, 1); }
+/* + * Power + */ + void twl6030_power_off(void); void twl6030_init_battery_charging(void); void twl6030_usb_device_settings(void); @@ -197,4 +210,12 @@ int twl6030_get_battery_voltage(void); int twl6030_get_battery_current(void); void twl6030_power_mmc_init(int dev_index);
+/* + * Input + */ + +int twl6030_input_power_button(void); +int twl6030_input_charger(void); +int twl6030_input_usb(void); + #endif /* TWL6030_H */

On Sat, Feb 27, 2016 at 07:19:13PM +0100, Paul Kocialkowski wrote:
This adds support for detecting a few inputs exported by the TWL6030. Currently-supported inputs are the power button, USB and charger presence.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Some power on reasons are not desirable (e.g. too short press on the power button), battery plug. Thus, power off the device when one of those occurs.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/amazon/kc1/kc1.c | 16 ++++++++++++++++ include/configs/kc1.h | 6 ++++++ 2 files changed, 22 insertions(+)
diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c index 9367b50..54e3fa3 100644 --- a/board/amazon/kc1/kc1.c +++ b/board/amazon/kc1/kc1.c @@ -86,6 +86,7 @@ int board_init(void) int misc_init_r(void) { char reboot_mode[2] = { 0 }; + u32 data = 0; u32 value;
/* Reboot mode */ @@ -101,10 +102,25 @@ int misc_init_r(void) reboot_mode[0] = 'b';
if (reboot_mode[0] > 0 && isascii(reboot_mode[0])) { + if (reboot_mode[0] == 'o') + twl6030_power_off(); + if (!getenv("reboot-mode")) setenv("reboot-mode", (char *)reboot_mode);
omap_reboot_mode_clear(); + } else { + /* + * When not rebooting, valid power on reasons are either the + * power button, charger plug or USB plug. + */ + + data |= twl6030_input_power_button(); + data |= twl6030_input_charger(); + data |= twl6030_input_usb(); + + if (!data) + twl6030_power_off(); }
/* Serial number */ diff --git a/include/configs/kc1.h b/include/configs/kc1.h index 04cb320..c2ac148 100644 --- a/include/configs/kc1.h +++ b/include/configs/kc1.h @@ -105,6 +105,12 @@ #define CONFIG_TWL6030_POWER
/* + * Input + */ + +#define CONFIG_TWL6030_INPUT + +/* * Partitions */

On Sat, Feb 27, 2016 at 07:19:14PM +0100, Paul Kocialkowski wrote:
Some power on reasons are not desirable (e.g. too short press on the power button), battery plug. Thus, power off the device when one of those occurs.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!

Reboot mode garbage is found on cold reset and might be seen as valid on the next warm reset, thus it has to be cleared on cold reset.
Signed-off-by: Paul Kocialkowski contact@paulk.fr --- board/amazon/kc1/kc1.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/board/amazon/kc1/kc1.c b/board/amazon/kc1/kc1.c index 54e3fa3..ca63af8 100644 --- a/board/amazon/kc1/kc1.c +++ b/board/amazon/kc1/kc1.c @@ -110,6 +110,9 @@ int misc_init_r(void)
omap_reboot_mode_clear(); } else { + /* Reboot mode garbage may still be valid, so clear it. */ + omap_reboot_mode_clear(); + /* * When not rebooting, valid power on reasons are either the * power button, charger plug or USB plug.

On Sat, Feb 27, 2016 at 07:19:15PM +0100, Paul Kocialkowski wrote:
Reboot mode garbage is found on cold reset and might be seen as valid on the next warm reset, thus it has to be cleared on cold reset.
Signed-off-by: Paul Kocialkowski contact@paulk.fr
Applied to u-boot/master, thanks!
participants (2)
-
Paul Kocialkowski
-
Tom Rini