summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNicolas Boichat <drinkcat@chromium.org>2018-10-08 14:07:34 +0800
committerchrome-bot <chrome-bot@chromium.org>2018-10-14 23:31:10 -0700
commitc0847323192309878855a8e9e85fda91afac5c0d (patch)
tree99a3d17c0d8582a16940fc4ca86fb1fcc5b4e0c8
parent894861f0991192dd9f09087017aa3f76afc93dd9 (diff)
downloadchrome-ec-c0847323192309878855a8e9e85fda91afac5c0d.tar.gz
kukui/emmc: Wait 200us between dma_disable and flush SPI TX FIFO
For some unclear reason, SPI+DMA sometimes fails to transmit the first few bytes after it is activated the third time, that is, after the transmission is aborted twice (this looks like a hardware bug). It does appear that increasing the delay between DMA disabling and manually resetting ->dr to 0xff from 100us to 200us fixes the issue, but the reason is unclear. Also, print transfer try count to the console, to facilitate debugging. BRANCH=none BUG=b:117253718 TEST=Put kukui in a reboot loop, ~1000 sucessful boots without ever requiring a 4th transfer. Change-Id: I7e5f6bc4da45d9a70ad18447ffb15afd1b62a7a2 Signed-off-by: Nicolas Boichat <drinkcat@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/1267761 Reviewed-by: Yilun Lin <yllin@chromium.org>
-rw-r--r--board/kukui/emmc.c9
1 files changed, 7 insertions, 2 deletions
diff --git a/board/kukui/emmc.c b/board/kukui/emmc.c
index 36a9256817..af2d4b1701 100644
--- a/board/kukui/emmc.c
+++ b/board/kukui/emmc.c
@@ -89,13 +89,15 @@ static const struct dma_option dma_rx_option = {
/* Setup DMA to transfer bootblock. */
static void bootblock_transfer(void)
{
+ static int transfer_try;
+
dma_chan_t *txdma = dma_get_channel(STM32_DMAC_SPI_EMMC_TX);
dma_prepare_tx(&dma_tx_option, sizeof(bootblock_raw_data),
bootblock_raw_data);
dma_go(txdma);
- CPRINTS("transfer");
+ CPRINTS("transfer %d", ++transfer_try);
}
/* Abort an ongoing transfer. */
@@ -106,8 +108,11 @@ static void bootblock_stop(void)
/*
* Wait a bit to for DMA to stop writing (we can't really wait for the
* buffer to get empty, as the bus may not be clocked anymore).
+ *
+ * TODO(b:117253718): For some reason, a delay >=200us is necessary,
+ * else the SPI/DMA skips bytes when the transfer is resumed.
*/
- udelay(100);
+ udelay(200);
/* Then flush SPI FIFO, and make sure DAT line stays idle (high). */
STM32_SPI_EMMC_REGS->dr = 0xff;