diff options
author | Vic Yang <victoryang@chromium.org> | 2014-05-20 15:44:58 -0700 |
---|---|---|
committer | chrome-internal-fetch <chrome-internal-fetch@google.com> | 2014-05-21 04:09:37 +0000 |
commit | 64e5cc33d99568c665d59040908b6d2452e9983f (patch) | |
tree | 7920891460625f0b1571e52758c36c1645d9e9c3 | |
parent | 951ee9e37944b7f1eea9d9a7921727c663665fd6 (diff) | |
download | chrome-ec-64e5cc33d99568c665d59040908b6d2452e9983f.tar.gz |
Keyborg: make a copy of response before transmitting
Before transmitting the response back to the master, the slave should
make a copy of it. Otherwise, if the buffer is reused, we run the risk
of overwriting the last response before it's sent out. We got away with
this before because we didn't overwrite it fast enough. Let's fix this
to be safe.
BUG=None
TEST=Build and boot
BRANCH=None
Change-Id: If3c50692d554119de9ff0f0ae0de450b923b11af
Signed-off-by: Vic Yang <victoryang@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/200672
Reviewed-by: Vincent Palatin <vpalatin@chromium.org>
-rw-r--r-- | board/keyborg/spi_comm.c | 12 |
1 files changed, 7 insertions, 5 deletions
diff --git a/board/keyborg/spi_comm.c b/board/keyborg/spi_comm.c index 8d459d3ae5..f795c3a8f6 100644 --- a/board/keyborg/spi_comm.c +++ b/board/keyborg/spi_comm.c @@ -31,7 +31,6 @@ static const struct dma_option dma_rx_option = { static uint8_t out_msg[SPI_PACKET_MAX_SIZE + 2]; static uint8_t in_msg[SPI_PACKET_MAX_SIZE]; -static uint8_t * const reply_msg = out_msg + 1; static inline int wait_for_signal(uint32_t port, uint32_t mask, int value, int timeout_us) @@ -324,11 +323,14 @@ int spi_slave_send_response_async(struct spi_comm_packet *resp) if (size > SPI_PACKET_MAX_SIZE) return EC_ERROR_OVERFLOW; + if (out_msg != (uint8_t *)resp) + memcpy(out_msg, resp, size); + master_slave_sync(100); if (spi->sr & STM32_SPI_SR_RXNE) in_msg[0] = spi->dr; - spi->dr = *((uint8_t *)resp); + spi->dr = out_msg[0]; /* Set N_CHG (master SPI_NSS) to high */ STM32_GPIO_BSRR(GPIO_A) = 1 << 1; @@ -340,7 +342,7 @@ int spi_slave_send_response_async(struct spi_comm_packet *resp) dma_clear_isr(STM32_DMAC_SPI1_TX); dma_clear_isr(STM32_DMAC_SPI1_RX); dma_start_rx(&dma_rx_option, size - 1, in_msg); - dma_prepare_tx(&dma_tx_option, size - 1, ((uint8_t *)resp)+1); + dma_prepare_tx(&dma_tx_option, size - 1, out_msg + 1); dma_go(dma_get_channel(STM32_DMAC_SPI1_TX)); master_slave_sync(5); @@ -367,7 +369,7 @@ int spi_slave_send_response_flush(void) static void spi_slave_nack(void) { - struct spi_comm_packet *resp = (struct spi_comm_packet *)reply_msg; + struct spi_comm_packet *resp = (struct spi_comm_packet *)out_msg; resp->cmd_sts = EC_ERROR_UNKNOWN; resp->size = 0; @@ -376,7 +378,7 @@ static void spi_slave_nack(void) static void spi_slave_hello_back(const struct spi_comm_packet *cmd) { - struct spi_comm_packet *resp = (struct spi_comm_packet *)reply_msg; + struct spi_comm_packet *resp = (struct spi_comm_packet *)out_msg; uint8_t buf[SPI_PACKET_MAX_SIZE]; int i, sz; |