summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMary Ruthven <mruthven@google.com>2019-02-22 11:24:56 -0800
committerchrome-bot <chrome-bot@chromium.org>2019-03-05 18:06:10 -0800
commit049ab52a120f3bff4e862fd2e98098bc66ef1b03 (patch)
tree71fa4d5365906b2e6c7f778d9839251680169fe1
parent3fbe166bd408941407ee1f706bf20c41360fcead (diff)
downloadchrome-ec-049ab52a120f3bff4e862fd2e98098bc66ef1b03.tar.gz
cr50: use board prop to mask straps if config is ambiguous
Cr50 tries to determine SPI vs I2C by checking that there are pullups on only the I2C or SPI straps. If there are pullups on both, it can't use the straps to determine SPI vs I2C, so it just defaults to the default board properties (I2C and PLT_RST_L). This change uses last board properties to determine I2C vs SPI if the straps can't be used to make this determination. The actual strap pins are only connected to the pullup or pulldown being used for the straps. It's pretty likely these strap readings are correct. The unused straps are connected to the AP which can interfere with these readings if it has a pullup on any of these signals. This change uses the last board property configuration to determine I2C vs SPI and mask unused straps to try and remove signals the AP is interfering with. If this masked config isn't valid, then cr50 will still fall back to using I2C and PLT_RST_L. BUG=b:124777847 BRANCH=cr50 TEST=manual flash mistral. Reboot cr50. Make sure it doesn't switch to I2C config # Verify cr50 selects spi Ambiguous strap config. Use spi based on old brdprop. Use DBG image to set invalid I2C and SPI board property settings rollback to the image that checks if I2C and SPI brdprop settings are invalid. Verify Mistral can't find a valid strap and uses I2C. Use DBG image to select SPI and I2C board properties. Make sure this is rejected as invalid. # enable writing to long life scratch 1 rw 0x40000128 2 # write old board properties with i2c and spi rw 0x40000130 (OLD_BRDPROP | 3) for mistral - rw 0x40000130 0x811143 # rollback to image that checks old board properties if # straps are ambiguous rollback # Verify Mistral doesn't use old AP bus setting and # defaults to the default properties. Invalid strap pins! Default properties = 0x42 Use DBG image to select neither the SPI or I2C board property. Make sure this is rejected as invalid. # enable writing to long life scratch 1 rw 0x40000128 2 # write old board properties without i2c or spi rw 0x40000130 (OLD_BRDPROP & ~3) for mistral - rw 0x40000130 0x811140 # rollback to image that checks old board properties if # straps are ambiguous rollback # Verify Mistral doesn't use old AP bus setting and # defaults to the default properties. Invalid strap pins! Default properties = 0x42 Use dbg image to modify board properties to select I2C. rollback and make sure Cr50 continues using I2C. # enable writing to long life scratch 1 rw 0x40000128 2 # write old board properties with i2c for mistral - rw 0x40000130 0x811142 # write old board properties with i2c rollback # Verify cr50 selects i2c Ambiguous strap config. Use i2c based on old brdprop. Change-Id: I409e2f3ab1339aafe450b35259adc3c4c5d870ae Signed-off-by: Mary Ruthven <mruthven@google.com> Reviewed-on: https://chromium-review.googlesource.com/1483816 Commit-Ready: ChromeOS CL Exonerator Bot <chromiumos-cl-exonerator@appspot.gserviceaccount.com> Tested-by: Mary Ruthven <mruthven@chromium.org> Reviewed-by: Keith Short <keithshort@chromium.org>
-rw-r--r--board/cr50/board.c38
1 files changed, 32 insertions, 6 deletions
diff --git a/board/cr50/board.c b/board/cr50/board.c
index 67908dc388..e7e19a4577 100644
--- a/board/cr50/board.c
+++ b/board/cr50/board.c
@@ -1206,8 +1206,10 @@ static int get_strap_config(uint8_t *config)
enum strap_list s0;
int lvl;
int flags;
- uint8_t pull_a;
- uint8_t pull_b;
+ uint8_t use_i2c;
+ uint8_t i2c_prop;
+ uint8_t use_spi;
+ uint8_t spi_prop;
/*
* There are 4 pins that are used to determine Cr50 board strapping
@@ -1313,13 +1315,37 @@ static int get_strap_config(uint8_t *config)
* config table entries.
*/
- pull_a = *config & 0xa0;
- pull_b = *config & 0xa;
- if ((!pull_a && !pull_b) || (pull_a && pull_b))
+ use_i2c = *config & 0xa0;
+ use_spi = *config & 0x0a;
+ /*
+ * The strap signals should have at least one pullup. Nothing can
+ * interfere with these. If we did not read any pullups, these are
+ * invalid straps. The config can't be salvaged.
+ */
+ if (!use_i2c && !use_spi)
return EC_ERROR_INVAL;
+ /*
+ * The unused strap signals are used for the bus to the AP. If the AP
+ * has added pullups to the signals, it could interfere with the strap
+ * readings. If pullups are found on both the SPI and I2C straps, use
+ * the board properties to determine SPI vs I2C. We can use this to mask
+ * unused config pins the AP is interfering with.
+ */
+ if (use_i2c && use_spi) {
+ spi_prop = (GREG32(PMU, LONG_LIFE_SCRATCH1) &
+ BOARD_SLAVE_CONFIG_SPI);
+ i2c_prop = (GREG32(PMU, LONG_LIFE_SCRATCH1) &
+ BOARD_SLAVE_CONFIG_I2C);
+ /* Make sure exactly one interface is selected */
+ if ((i2c_prop && spi_prop) || (!spi_prop && !i2c_prop))
+ return EC_ERROR_INVAL;
+ use_spi = spi_prop;
+ CPRINTS("Ambiguous strap config. Use %s based on old "
+ "brdprop.", use_spi ? "spi" : "i2c");
+ }
/* Now that I2C vs SPI is known, mask the unused strap bits. */
- *config &= *config & 0xa ? 0xf : 0xf0;
+ *config &= use_spi ? 0xf : 0xf0;
return EC_SUCCESS;
}