From 6fa43bcfa4e948db5a37c8b298cb7a3e7894fd97 Mon Sep 17 00:00:00 2001 From: Koen Kooi Date: Mon, 21 May 2012 10:07:52 +0200 Subject: [PATCH] beaglebone 3.2: add patches from Bas to set mux automagically from the EEPROM + Bebopr cape support Signed-off-by: Koen Kooi --- ...nmux-data-array-in-EEPROM-data-struc.patch | 27 ++ ...-Cape-configuration-from-EEPROM.-Onl.patch | 363 ++++++++++++++++++ ...onal-debug-code-by-pr_debug-statemen.patch | 188 +++++++++ ...oards-with-mistaken-ASCII-interpreta.patch | 31 ++ ...EPROM-contents-blocking-further-I2C-.patch | 30 ++ ...EPROM-revision-to-prevent-interpreti.patch | 60 +++ 6 files changed, 699 insertions(+) create mode 100644 patches/beaglebone/0053-Fixed-size-of-pinmux-data-array-in-EEPROM-data-struc.patch create mode 100644 patches/beaglebone/0054-Implemented-Bone-Cape-configuration-from-EEPROM.-Onl.patch create mode 100644 patches/beaglebone/0055-Replaced-conditional-debug-code-by-pr_debug-statemen.patch create mode 100644 patches/beaglebone/0056-Workaround-for-boards-with-mistaken-ASCII-interpreta.patch create mode 100644 patches/beaglebone/0057-Workaround-for-EEPROM-contents-blocking-further-I2C-.patch create mode 100644 patches/beaglebone/0058-Added-check-on-EEPROM-revision-to-prevent-interpreti.patch diff --git a/patches/beaglebone/0053-Fixed-size-of-pinmux-data-array-in-EEPROM-data-struc.patch b/patches/beaglebone/0053-Fixed-size-of-pinmux-data-array-in-EEPROM-data-struc.patch new file mode 100644 index 00000000..be397904 --- /dev/null +++ b/patches/beaglebone/0053-Fixed-size-of-pinmux-data-array-in-EEPROM-data-struc.patch @@ -0,0 +1,27 @@ +From 2e9dc362b2bc80caf93a505fec5c675f5bbe840e Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Sun, 13 May 2012 18:07:59 +0200 +Subject: [PATCH 53/58] Fixed size of pinmux data array in EEPROM data struct. + +Signed-off-by: Bas Laarhoven +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 2 +- + 1 files changed, 1 insertions(+), 1 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index ece4e46..c6ec997 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -483,7 +483,7 @@ struct beaglebone_cape_eeprom_config { + char partnumber[16]; + u16 numpins; + char serial[12]; +- u8 muxdata[170]; ++ u16 muxdata[74]; + u16 current_3v3; + u16 current_vdd5v; + u16 current_sys5v; +-- +1.7.7.6 + diff --git a/patches/beaglebone/0054-Implemented-Bone-Cape-configuration-from-EEPROM.-Onl.patch b/patches/beaglebone/0054-Implemented-Bone-Cape-configuration-from-EEPROM.-Onl.patch new file mode 100644 index 00000000..e200f4dd --- /dev/null +++ b/patches/beaglebone/0054-Implemented-Bone-Cape-configuration-from-EEPROM.-Onl.patch @@ -0,0 +1,363 @@ +From 6eca3f772576459095fc5ef0144c188a2f5ccd2d Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Sun, 13 May 2012 18:14:22 +0200 +Subject: [PATCH 54/58] Implemented Bone Cape configuration from EEPROM. Only + used for BEBOPR cape for now. + +Signed-off-by: Bas Laarhoven +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 304 +++++++++++++++++++++++++++++++++ + arch/arm/mach-omap2/mux33xx.c | 14 ++ + 2 files changed, 318 insertions(+), 0 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index c6ec997..7fb8295 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -2231,6 +2231,304 @@ static void tt3201_init(int evm_id, int profile) + + am33xx_d_can_init(1); + } ++ ++static const char* cape_pins[] = { ++/* ++ From SRM RevA5.0.1: ++*/ ++ /* offset 88 - P9-22 */ "uart2_rxd", ++ /* offset 90 - P9-21 */ "uart2_txd", ++ /* offset 92 - P9-18 */ "spi0_d1", ++ /* offset 94 - P9-17 */ "spi0_cs0", ++ /* offset 96 - P9-42 */ "ecap0_in_pwm0_out", ++ /* offset 98 - P8-35 */ "lcd_data12", ++ /* offset 100 - P8-33 */ "lcd_data13", ++ /* offset 102 - P8-31 */ "lcd_data14", ++ /* offset 104 - P8-32 */ "lcd_data15", ++ /* offset 106 - P9-19 */ "uart1_rtsn", ++ /* offset 108 - P9-20 */ "uart1_ctsn", ++ /* offset 110 - P9-26 */ "uart1_rxd", ++ /* offset 112 - P9-24 */ "uart1_txd", ++ /* offset 114 - P9-41 */ "xdma_event_intr1", ++ /* offset 116 - P8-19 */ "gpmc_ad8", ++ /* offset 118 - P8-13 */ "gpmc_ad9", ++ /* offset 120 - P8-14 */ "gpmc_ad10", ++ /* offset 122 - P8-17 */ "gpmc_ad12", ++ /* offset 124 - P9-11 */ "gpmc_wait0", ++ /* offset 126 - P9-13 */ "gpmc_wpn", ++ /* offset 128 - P8-25 */ "gpmc_ad0", ++ /* offset 130 - P8-24 */ "gpmc_ad1", ++ /* offset 132 - P8- 5 */ "gpmc_ad2", ++ /* offset 134 - P8- 6 */ "gpmc_ad3", ++ /* offset 136 - P8-23 */ "gpmc_ad4", ++ /* offset 138 - P8-22 */ "gpmc_ad5", ++ /* offset 140 - P8- 3 */ "gpmc_ad6", ++ /* offset 142 - P8- 4 */ "gpmc_ad7", ++ /* offset 144 - P8-12 */ "gpmc_ad12", ++ /* offset 146 - P8-11 */ "gpmc_ad13", ++ /* offset 148 - P8-16 */ "gpmc_ad14", ++ /* offset 150 - P8-15 */ "gpmc_ad15", ++ /* offset 152 - P9-15 */ "gpmc_a0", ++ /* offset 154 - P9-23 */ "gpmc_a1", ++ /* offset 156 - P9-14 */ "gpmc_a2", ++ /* offset 158 - P9-16 */ "gpmc_a3", ++ /* offset 160 - P9-12 */ "gpmc_be1n", ++ /* offset 162 - P8-26 */ "gpmc_csn0", ++ /* offset 164 - P8-21 */ "gpmc_csn1", ++ /* offset 166 - P8-20 */ "gpmc_csn2", ++ /* offset 168 - P8-18 */ "gpmc_clk", ++ /* offset 170 - P8-7 */ "gpmc_advn_ale", ++ /* offset 172 - P8-9 */ "gpmc_ben0_cle", ++ /* offset 174 - P8-10 */ "gpmc_wen", ++ /* offset 176 - P8-8 */ "gpmc_csn3", ++ /* offset 178 - P8-45 */ "lcd_data0", ++ /* offset 180 - P8-46 */ "lcd_data1", ++ /* offset 182 - P8-43 */ "lcd_data2", ++ /* offset 184 - P8-44 */ "lcd_data3", ++ /* offset 186 - P8-41 */ "lcd_data4", ++ /* offset 188 - P8-42 */ "lcd_data5", ++ /* offset 190 - P8-39 */ "lcd_data6", ++ /* offset 192 - P8-40 */ "lcd_data7", ++ /* offset 194 - P8-37 */ "lcd_data8", ++ /* offset 196 - P8-38 */ "lcd_data9", ++ /* offset 198 - P8-36 */ "lcd_data10", ++ /* offset 200 - P8-34 */ "lcd_data11", ++ /* offset 202 - P8-27 */ "lcd_vsync", ++ /* offset 204 - P8-29 */ "lcd_hsync", ++ /* offset 206 - P8-28 */ "lcd_pclk", ++ /* offset 208 - P8-30 */ "lcd_ac_bias_en", ++ /* offset 210 - P9-29 */ "mcasp0_fsx", ++ /* offset 212 - P9-30 */ "mcasp0_axr0", ++ /* offset 214 - P9-28 */ "mcasp0_ahclkr", ++ /* offset 216 - P9-27 */ "mcasp0_fsr", ++ /* offset 218 - P9-31 */ "mcasp0_aclkx", ++ /* offset 220 - P9-25 */ "mcasp0_ahclkx", ++ /* offset 222 - P9-39 */ "ain0", ++ /* offset 224 - P9-40 */ "ain1", ++ /* offset 226 - P9-37 */ "ain2", ++ /* offset 228 - P9-38 */ "ain3", ++ /* offset 230 - P9-33 */ "ain4", ++ /* offset 232 - P9-36 */ "ain5", ++ /* offset 234 - P9-35 */ "ain6", ++}; ++ ++#define BIG_ENDIAN_16( i) ( ((i & 255) << 8) | ((i >> 8) & 255) ) ++#define NR_ITEMS( x) (sizeof( (x)) / sizeof( *(x))) ++ ++extern int am33xx_mux_get_entry( int index, struct omap_mux** mux); ++ ++typedef union { ++/* ++ From SRM RevA5.0.1: ++ Bit 15 Pin is used or not: 0=Unused by Cape 1=Used by Cape ++ Bit 14-13 Pin Direction: 10=Output 01=Input 11=BDIR ++ Bit 12-7 Reserved ++ Bit 6 Slew Rate: 0=Fast 1=Slow ++ Bit 5 Rx Enable: 0=Disabled 1=Enabled ++ Bit 4 Pull Up/Dn Select: 0=Pulldown 1=PullUp ++ Bit 3 Pull Up/DN enabled: 0=Enabled 1=Disabled ++ Bit 2-0 Mux Mode Selection: Mode 0-7 ++*/ ++ struct { ++ uint16_t mux : 3; ++ uint16_t pull_enable : 1; ++ uint16_t pull_up : 1; ++ uint16_t rx_enable : 1; ++ uint16_t slew_rate : 1; ++ uint16_t reserved : 6; ++ uint16_t direction : 2; ++ uint16_t used : 1; ++ }; ++ uint16_t value; ++} pin_def; ++ ++#define DEBUG_EEPROM_CONFIG 0 ++ ++static int bone_io_get_mux_setting( pin_def setting) ++{ ++ int pin_setting; ++ ++ switch (setting.direction) { ++ case 1: ++ /* input */ ++ if (setting.pull_enable) { ++ if (setting.pull_up) { ++ pin_setting = AM33XX_PIN_INPUT_PULLUP; ++ } else { ++ pin_setting = AM33XX_PIN_INPUT_PULLDOWN; ++ } ++ } else { ++ pin_setting = AM33XX_PIN_INPUT; ++ } ++ if (!setting.rx_enable) { ++#if DEBUG_EEPROM_CONFIG ++ pr_warning( " pin is set as input but the receiver is not enabled!\n"); ++#endif ++ } ++ break; ++ case 2: ++ /* output */ ++ pin_setting = AM33XX_PIN_OUTPUT; ++ break; ++ case 3: ++ /* bi-dir */ ++ default: ++ /* reserved */ ++#if DEBUG_EEPROM_CONFIG ++ pr_warning( " pin ignored because it uses an unsupported mode: 0x%04x\n", ++ setting.direction); ++#endif ++ return -1; ++ } ++#if DEBUG_EEPROM_CONFIG ++ pr_info(" pin is configured as %s\n", ++ (pin_setting & AM33XX_PIN_INPUT) ? "input" : "output"); ++#endif ++ switch (setting.mux) { ++ case 0: pin_setting |= OMAP_MUX_MODE0; break; ++ case 1: pin_setting |= OMAP_MUX_MODE1; break; ++ case 2: pin_setting |= OMAP_MUX_MODE2; break; ++ case 3: pin_setting |= OMAP_MUX_MODE3; break; ++ case 4: pin_setting |= OMAP_MUX_MODE4; break; ++ case 5: pin_setting |= OMAP_MUX_MODE5; break; ++ case 6: pin_setting |= OMAP_MUX_MODE6; break; ++ case 7: pin_setting |= OMAP_MUX_MODE7; break; ++ } ++ return pin_setting; ++} ++ ++static struct omap_mux* bone_io_pin_lookup( const char* pin_name) ++{ ++ int index = 0; ++ struct omap_mux* mux; ++ ++ for (;;) { ++ if (am33xx_mux_get_entry( index, &mux) < 0) { ++ /* no more entries */ ++#if DEBUG_EEPROM_CONFIG ++ pr_warning( " configuration error, pin '%s' not found in mux database\n", ++ pin_name); ++#endif ++ return NULL; ++ } ++ if (mux != NULL && ++ mux->muxnames[ 0] != NULL && ++ strcmp( mux->muxnames[ 0], pin_name) == 0) ++ { ++ /* entry found */ ++#if DEBUG_EEPROM_CONFIG ++ pr_info( " found pin '%s' at index %d in mux database'\n", ++ pin_name, index); ++#endif ++ return mux; ++ } ++ ++index; ++ } ++} ++ ++static int bone_io_config_pin( const char* pin_name, pin_def eeprom_setting) ++{ ++ struct omap_mux* mux; ++ char* signal_name; ++ int pin_setting = bone_io_get_mux_setting( eeprom_setting); ++ int l1, l2; ++ char full_name[ 50]; ++ ++ if (pin_setting < 0) { ++ return -1; ++ } ++ ++ mux = bone_io_pin_lookup( pin_name); ++ ++ if (mux == NULL) { ++ return -1; ++ } ++ ++ signal_name = mux->muxnames[ eeprom_setting.mux]; ++ ++ if (signal_name == NULL) { ++#if DEBUG_EEPROM_CONFIG ++ pr_warning( " Configuration error, no signal found for pin '%s' in mode %d\n", ++ pin_name, eeprom_setting.mux); ++#endif ++ return -1; ++ } ++ ++#if DEBUG_EEPROM_CONFIG ++ pr_info( " setting pin '%s' to signal '%s'\n", ++ pin_name, signal_name); ++#endif ++ l1 = strlen( pin_name); ++ l2 = strlen( signal_name); ++ ++ if (l1 + 1 + l2 + 1 > sizeof( full_name)) { ++#if DEBUG_EEPROM_CONFIG ++ pr_warning( " Internal error, combined signal name too long\n"); ++#endif ++ return -1; ++ } else { ++ memcpy( full_name, pin_name, l1); ++ full_name[ l1] = '.'; ++ memcpy( full_name + l1 + 1, signal_name, l2); ++ full_name[ l1 + 1 + l2] = '\0'; ++ if (omap_mux_init_signal( full_name, pin_setting) < 0) { ++ return -1; ++ } ++#if DEBUG_EEPROM_CONFIG ++ pr_info( " mux '%s' was set to mode 0x%04x\n", ++ full_name, pin_setting); ++#endif ++ } ++ // return 0 for input, 1 for output ++ return (pin_setting & AM33XX_PIN_INPUT) ? 0 : 1; ++} ++ ++#define RULER( x) \ ++ do { \ ++ char* p = status; \ ++ int i = 0; \ ++ int cnt = x; \ ++ status[ cnt] = '\0'; \ ++ while (cnt--) { \ ++ if (++i == 10) { \ ++ *p++ = '+'; \ ++ i = 0; \ ++ } else { \ ++ *p++ = '-'; \ ++ } \ ++ } \ ++ pr_info( "+%s+\n", status); \ ++ } while (0) ++ ++static void bone_io_config_from_cape_eeprom( void) ++{ ++ int i; ++ int cnt = BIG_ENDIAN_16( cape_config.numpins); ++ u16* pmuxdata; ++ char status[ NR_ITEMS( cape_config.muxdata) + 1]; ++ ++ pr_info( "BeagleBone cape: configuring %2d out of %2d signals:\n", ++ cnt, NR_ITEMS( cape_config.muxdata)); ++ RULER( NR_ITEMS( cape_config.muxdata)); ++ for (i = 0, pmuxdata = cape_config.muxdata ; i < NR_ITEMS( cape_config.muxdata) ; ++i, ++pmuxdata) { ++ const char* pin_name = cape_pins[ i]; ++ pin_def pin_setting = { .value = BIG_ENDIAN_16( *pmuxdata) }; ++ ++ if (pin_setting.used) { ++ switch (bone_io_config_pin( pin_name, pin_setting)) { ++ case 0: status[ i] = 'i'; break; ++ case 1: status[ i] = 'o'; break; ++ default: status[ i] = '#'; break; ++ } ++ } else { ++ status[ i] = ' '; ++ } ++ } ++ status[ NR_ITEMS( cape_config.muxdata)] = '\0'; ++ pr_info( "|%s|\n", status); ++ RULER( NR_ITEMS( cape_config.muxdata)); ++} ++ + static void beaglebone_cape_setup(struct memory_accessor *mem_acc, void *context) + { + int ret; +@@ -2280,6 +2578,12 @@ static void beaglebone_cape_setup(struct memory_accessor *mem_acc, void *context + snprintf(tmp, sizeof(cape_config.partnumber) + 1, "%s", cape_config.partnumber); + pr_info("BeagleBone cape partnumber: %s\n", tmp); + ++ if (!strncmp( "BEBOPR", cape_config.name, 6)) { ++ pr_info( "BeagleBone cape: initializing BEBOPR cape\n"); ++ bone_io_config_from_cape_eeprom(); ++ return; // if configured from eeprom, skip all other initialization ++ } ++ + if (!strncmp("BB-BONE-DVID-01", cape_config.partnumber, 15)) { + pr_info("BeagleBone cape: initializing DVI cape\n"); + +diff --git a/arch/arm/mach-omap2/mux33xx.c b/arch/arm/mach-omap2/mux33xx.c +index 72ac899..43c8989 100644 +--- a/arch/arm/mach-omap2/mux33xx.c ++++ b/arch/arm/mach-omap2/mux33xx.c +@@ -616,6 +616,20 @@ int __init am33xx_mux_init(struct omap_board_mux *board_subset) + AM33XX_CONTROL_PADCONF_MUX_SIZE, am33xx_muxmodes, + NULL, board_subset, NULL); + } ++ ++#define NR_ITEMS( x) (sizeof( (x)) / sizeof( *(x))) ++ ++int am33xx_mux_get_entry( int index, struct omap_mux** mux) ++{ ++ if (index >= 0 && index < NR_ITEMS( am33xx_muxmodes)) { ++ *mux = &am33xx_muxmodes[ index]; ++ return 0; ++ } else { ++ *mux = NULL; ++ return -1; ++ } ++} ++ + #else + int __init am33xx_mux_init(struct omap_board_mux *board_subset) + { +-- +1.7.7.6 + diff --git a/patches/beaglebone/0055-Replaced-conditional-debug-code-by-pr_debug-statemen.patch b/patches/beaglebone/0055-Replaced-conditional-debug-code-by-pr_debug-statemen.patch new file mode 100644 index 00000000..89111de7 --- /dev/null +++ b/patches/beaglebone/0055-Replaced-conditional-debug-code-by-pr_debug-statemen.patch @@ -0,0 +1,188 @@ +From f35a319e78e3c88dd77618a4affbbbfa399609af Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Mon, 14 May 2012 14:31:37 +0200 +Subject: [PATCH 55/58] Replaced conditional debug code by pr_debug statements + for cleaner code. + +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 91 +++++++++++++-------------------- + 1 files changed, 36 insertions(+), 55 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index 7fb8295..d6a607a 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -2323,23 +2323,23 @@ typedef union { + Bit 15 Pin is used or not: 0=Unused by Cape 1=Used by Cape + Bit 14-13 Pin Direction: 10=Output 01=Input 11=BDIR + Bit 12-7 Reserved +- Bit 6 Slew Rate: 0=Fast 1=Slow +- Bit 5 Rx Enable: 0=Disabled 1=Enabled +- Bit 4 Pull Up/Dn Select: 0=Pulldown 1=PullUp +- Bit 3 Pull Up/DN enabled: 0=Enabled 1=Disabled ++ Bit 6 Slew Rate: 0=Fast 1=Slow ++ Bit 5 Rx Enable: 0=Disabled 1=Enabled ++ Bit 4 Pull Up/Dn Select: 0=Pulldown 1=PullUp ++ Bit 3 Pull Up/DN enabled: 0=Enabled 1=Disabled + Bit 2-0 Mux Mode Selection: Mode 0-7 + */ + struct { +- uint16_t mux : 3; +- uint16_t pull_enable : 1; +- uint16_t pull_up : 1; +- uint16_t rx_enable : 1; +- uint16_t slew_rate : 1; +- uint16_t reserved : 6; +- uint16_t direction : 2; +- uint16_t used : 1; ++ uint16_t mux : 3; ++ uint16_t pull_enable : 1; ++ uint16_t pull_up : 1; ++ uint16_t rx_enable : 1; ++ uint16_t slew_rate : 1; ++ uint16_t reserved : 6; ++ uint16_t direction : 2; ++ uint16_t used : 1; + }; +- uint16_t value; ++ uint16_t value; + } pin_def; + + #define DEBUG_EEPROM_CONFIG 0 +@@ -2351,39 +2351,33 @@ static int bone_io_get_mux_setting( pin_def setting) + switch (setting.direction) { + case 1: + /* input */ +- if (setting.pull_enable) { ++ if (setting.pull_enable) { + if (setting.pull_up) { +- pin_setting = AM33XX_PIN_INPUT_PULLUP; ++ pin_setting = AM33XX_PIN_INPUT_PULLUP; + } else { +- pin_setting = AM33XX_PIN_INPUT_PULLDOWN; ++ pin_setting = AM33XX_PIN_INPUT_PULLDOWN; + } + } else { +- pin_setting = AM33XX_PIN_INPUT; ++ pin_setting = AM33XX_PIN_INPUT; + } + if (!setting.rx_enable) { +-#if DEBUG_EEPROM_CONFIG +- pr_warning( " pin is set as input but the receiver is not enabled!\n"); +-#endif ++ pr_debug( " pin is set as input but the receiver is not enabled!\n"); + } + break; + case 2: + /* output */ +- pin_setting = AM33XX_PIN_OUTPUT; ++ pin_setting = AM33XX_PIN_OUTPUT; + break; + case 3: + /* bi-dir */ + default: + /* reserved */ +-#if DEBUG_EEPROM_CONFIG +- pr_warning( " pin ignored because it uses an unsupported mode: 0x%04x\n", +- setting.direction); +-#endif ++ pr_debug( " pin ignored because it uses an unsupported mode: 0x%04x\n", ++ setting.direction); + return -1; + } +-#if DEBUG_EEPROM_CONFIG +- pr_info(" pin is configured as %s\n", ++ pr_debug(" pin is configured as %s\n", + (pin_setting & AM33XX_PIN_INPUT) ? "input" : "output"); +-#endif + switch (setting.mux) { + case 0: pin_setting |= OMAP_MUX_MODE0; break; + case 1: pin_setting |= OMAP_MUX_MODE1; break; +@@ -2404,11 +2398,9 @@ static struct omap_mux* bone_io_pin_lookup( const char* pin_name) + + for (;;) { + if (am33xx_mux_get_entry( index, &mux) < 0) { +- /* no more entries */ +-#if DEBUG_EEPROM_CONFIG +- pr_warning( " configuration error, pin '%s' not found in mux database\n", +- pin_name); +-#endif ++ /* no more entries */ ++ pr_debug( " configuration error, pin '%s' not found in mux database\n", ++ pin_name); + return NULL; + } + if (mux != NULL && +@@ -2416,10 +2408,8 @@ static struct omap_mux* bone_io_pin_lookup( const char* pin_name) + strcmp( mux->muxnames[ 0], pin_name) == 0) + { + /* entry found */ +-#if DEBUG_EEPROM_CONFIG +- pr_info( " found pin '%s' at index %d in mux database'\n", +- pin_name, index); +-#endif ++ pr_debug( " found pin '%s' at index %d in mux database'\n", ++ pin_name, index); + return mux; + } + ++index; +@@ -2447,37 +2437,28 @@ static int bone_io_config_pin( const char* pin_name, pin_def eeprom_setting) + signal_name = mux->muxnames[ eeprom_setting.mux]; + + if (signal_name == NULL) { +-#if DEBUG_EEPROM_CONFIG +- pr_warning( " Configuration error, no signal found for pin '%s' in mode %d\n", +- pin_name, eeprom_setting.mux); +-#endif ++ pr_debug( " Configuration error, no signal found for pin '%s' in mode %d\n", ++ pin_name, eeprom_setting.mux); + return -1; + } +- +-#if DEBUG_EEPROM_CONFIG +- pr_info( " setting pin '%s' to signal '%s'\n", ++ pr_debug( " setting pin '%s' to signal '%s'\n", + pin_name, signal_name); +-#endif +- l1 = strlen( pin_name); ++ l1 = strlen( pin_name); + l2 = strlen( signal_name); + + if (l1 + 1 + l2 + 1 > sizeof( full_name)) { +-#if DEBUG_EEPROM_CONFIG +- pr_warning( " Internal error, combined signal name too long\n"); +-#endif ++ pr_debug( " Internal error, combined signal name too long\n"); + return -1; + } else { +- memcpy( full_name, pin_name, l1); ++ memcpy( full_name, pin_name, l1); + full_name[ l1] = '.'; + memcpy( full_name + l1 + 1, signal_name, l2); + full_name[ l1 + 1 + l2] = '\0'; + if (omap_mux_init_signal( full_name, pin_setting) < 0) { + return -1; + } +-#if DEBUG_EEPROM_CONFIG +- pr_info( " mux '%s' was set to mode 0x%04x\n", ++ pr_debug( " mux '%s' was set to mode 0x%04x\n", + full_name, pin_setting); +-#endif + } + // return 0 for input, 1 for output + return (pin_setting & AM33XX_PIN_INPUT) ? 0 : 1; +@@ -2516,8 +2497,8 @@ static void bone_io_config_from_cape_eeprom( void) + + if (pin_setting.used) { + switch (bone_io_config_pin( pin_name, pin_setting)) { +- case 0: status[ i] = 'i'; break; +- case 1: status[ i] = 'o'; break; ++ case 0: status[ i] = 'i'; break; ++ case 1: status[ i] = 'o'; break; + default: status[ i] = '#'; break; + } + } else { +-- +1.7.7.6 + diff --git a/patches/beaglebone/0056-Workaround-for-boards-with-mistaken-ASCII-interpreta.patch b/patches/beaglebone/0056-Workaround-for-boards-with-mistaken-ASCII-interpreta.patch new file mode 100644 index 00000000..fb33e465 --- /dev/null +++ b/patches/beaglebone/0056-Workaround-for-boards-with-mistaken-ASCII-interpreta.patch @@ -0,0 +1,31 @@ +From dcca06c3a4eae09eb26e42956134b9314eb2c365 Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Mon, 14 May 2012 14:36:23 +0200 +Subject: [PATCH 56/58] Workaround for boards with (mistaken) ASCII + interpretation for the numpins field. + +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 6 ++++++ + 1 files changed, 6 insertions(+), 0 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index d6a607a..0a1738a 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -2488,6 +2488,12 @@ static void bone_io_config_from_cape_eeprom( void) + u16* pmuxdata; + char status[ NR_ITEMS( cape_config.muxdata) + 1]; + ++ // Workaround for capes that have encoded this as ASCII ++ if (cnt > 256) { ++ pr_info( "BeagleBone cape: workaround for bad 'numpins' setting\n"); ++ cnt = (cape_config.numpins & 255) - '0'; ++ cnt = 10 * cnt + ((cape_config.numpins >> 8) & 255) - '0'; ++ } + pr_info( "BeagleBone cape: configuring %2d out of %2d signals:\n", + cnt, NR_ITEMS( cape_config.muxdata)); + RULER( NR_ITEMS( cape_config.muxdata)); +-- +1.7.7.6 + diff --git a/patches/beaglebone/0057-Workaround-for-EEPROM-contents-blocking-further-I2C-.patch b/patches/beaglebone/0057-Workaround-for-EEPROM-contents-blocking-further-I2C-.patch new file mode 100644 index 00000000..3e6efca9 --- /dev/null +++ b/patches/beaglebone/0057-Workaround-for-EEPROM-contents-blocking-further-I2C-.patch @@ -0,0 +1,30 @@ +From 74d6fd8c6381b98295bd33f3ac39b99bf6e4ce22 Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Mon, 14 May 2012 15:07:43 +0200 +Subject: [PATCH 57/58] Workaround for EEPROM contents blocking further I2C + bus access. + +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 5 ++++- + 1 files changed, 4 insertions(+), 1 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index 0a1738a..0fa8a32 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -2501,7 +2501,10 @@ static void bone_io_config_from_cape_eeprom( void) + const char* pin_name = cape_pins[ i]; + pin_def pin_setting = { .value = BIG_ENDIAN_16( *pmuxdata) }; + +- if (pin_setting.used) { ++ // Detect broken I2C configuration to prevent bus hangup! ++ if (i >= 9 && i <= 10) { ++ status[ i] = '-'; ++ } else if (pin_setting.used) { + switch (bone_io_config_pin( pin_name, pin_setting)) { + case 0: status[ i] = 'i'; break; + case 1: status[ i] = 'o'; break; +-- +1.7.7.6 + diff --git a/patches/beaglebone/0058-Added-check-on-EEPROM-revision-to-prevent-interpreti.patch b/patches/beaglebone/0058-Added-check-on-EEPROM-revision-to-prevent-interpreti.patch new file mode 100644 index 00000000..f2ecbb6a --- /dev/null +++ b/patches/beaglebone/0058-Added-check-on-EEPROM-revision-to-prevent-interpreti.patch @@ -0,0 +1,60 @@ +From d59c0cba57c7ce40458fbfac44ca2f2d3f186ecb Mon Sep 17 00:00:00 2001 +From: Bas Laarhoven +Date: Tue, 15 May 2012 10:00:47 +0200 +Subject: [PATCH 58/58] Added check on EEPROM revision to prevent interpreting + unknown formats. + +Signed-off-by: Koen Kooi +--- + arch/arm/mach-omap2/board-am335xevm.c | 16 +++++++++++++--- + 1 files changed, 13 insertions(+), 3 deletions(-) + +diff --git a/arch/arm/mach-omap2/board-am335xevm.c b/arch/arm/mach-omap2/board-am335xevm.c +index 0fa8a32..68ddfe2 100644 +--- a/arch/arm/mach-omap2/board-am335xevm.c ++++ b/arch/arm/mach-omap2/board-am335xevm.c +@@ -2481,12 +2481,21 @@ static int bone_io_config_pin( const char* pin_name, pin_def eeprom_setting) + pr_info( "+%s+\n", status); \ + } while (0) + +-static void bone_io_config_from_cape_eeprom( void) ++static int bone_io_config_from_cape_eeprom( void) + { + int i; + int cnt = BIG_ENDIAN_16( cape_config.numpins); + u16* pmuxdata; + char status[ NR_ITEMS( cape_config.muxdata) + 1]; ++ char revision[ NR_ITEMS( cape_config.format_revision) + 1]; ++ ++ strncpy( revision, cape_config.format_revision, NR_ITEMS( revision) - 1); ++ revision[ NR_ITEMS( revision) - 1] = '\0'; ++ if (strcmp( revision, "A0") != 0) { ++ pr_warn( "BeagleBone cape: configuration revision '%s' is not supported\n", ++ revision); ++ return -1; ++ } + + // Workaround for capes that have encoded this as ASCII + if (cnt > 256) { +@@ -2494,8 +2503,8 @@ static void bone_io_config_from_cape_eeprom( void) + cnt = (cape_config.numpins & 255) - '0'; + cnt = 10 * cnt + ((cape_config.numpins >> 8) & 255) - '0'; + } +- pr_info( "BeagleBone cape: configuring %2d out of %2d signals:\n", +- cnt, NR_ITEMS( cape_config.muxdata)); ++ pr_info( "BeagleBone cape: revision %s format, configuring %2d out of %2d signals:\n", ++ revision, cnt, NR_ITEMS( cape_config.muxdata)); + RULER( NR_ITEMS( cape_config.muxdata)); + for (i = 0, pmuxdata = cape_config.muxdata ; i < NR_ITEMS( cape_config.muxdata) ; ++i, ++pmuxdata) { + const char* pin_name = cape_pins[ i]; +@@ -2517,6 +2526,7 @@ static void bone_io_config_from_cape_eeprom( void) + status[ NR_ITEMS( cape_config.muxdata)] = '\0'; + pr_info( "|%s|\n", status); + RULER( NR_ITEMS( cape_config.muxdata)); ++ return 0; + } + + static void beaglebone_cape_setup(struct memory_accessor *mem_acc, void *context) +-- +1.7.7.6 +