tom dunigan / Mbed 2 deprecated leo_spiperf

Dependencies:   mbed

Files at this revision

API Documentation at this revision

Comitter:
manitou
Date:
Tue Nov 10 12:07:03 2015 +0000
Commit message:
DMA SPI proof of concept, wire speed 44.3 mbs

Changed in this revision

main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Tue Nov 10 12:07:03 2015 +0000
@@ -0,0 +1,119 @@
+//nucleo DMA SPI from pyboard SPI   proof of concept
+// need DMA channel for TX and another for RX
+//tx DMA2_Stream5, DMA_CHANNEL_3   rx DMA2_Stream2, DMA_CHANNEL_3
+// SPI1 and 4 max 45mbs    SPI3 4  max 22.5mbs
+#include "mbed.h"
+
+#define PRREG(z) printf(#z" 0x%x\n",z)
+Timer tmr;
+DigitalOut CSpin(D10);
+SPI spi(SPI_MOSI, SPI_MISO, SPI_SCK); // mosi, miso, sclk  SPI1
+
+#define SPI_BUFF_SIZE 1024
+uint8_t rx_buffer[SPI_BUFF_SIZE];
+uint8_t tx_buffer[SPI_BUFF_SIZE];
+
+void spiperf(int mhz) {
+    int i, us;
+
+    spi.frequency(mhz*1000000);
+    CSpin=0;
+    us = tmr.read_us();
+    for(i=0;i<SPI_BUFF_SIZE;i++) spi.write(tx_buffer[i]);
+    us = tmr.read_us()-us;
+    CSpin=1;
+    printf("spi %d mhz %d us %.2f mbs  %0x\n",mhz,us,8.*SPI_BUFF_SIZE/us,SPI1->CR1);
+}
+
+// need to re-create SPI firmware to access SPI handle
+static SPI_HandleTypeDef SpiHandle;
+  
+static void spiInit() {
+    SpiHandle.Instance = SPI1;
+
+    __HAL_SPI_DISABLE(&SpiHandle);
+
+    SpiHandle.Init.Mode              = SPI_MODE_MASTER;
+    SpiHandle.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_16;  // 2 is 45 mhz    32 is 2.81mhz
+    SpiHandle.Init.Direction         = SPI_DIRECTION_2LINES;
+    SpiHandle.Init.CLKPhase          = SPI_PHASE_1EDGE;  // mode 0
+    SpiHandle.Init.CLKPolarity       = SPI_POLARITY_LOW;
+    SpiHandle.Init.CRCCalculation    = SPI_CRCCALCULATION_DISABLED;
+    SpiHandle.Init.CRCPolynomial     = 7;
+    SpiHandle.Init.DataSize          = SPI_DATASIZE_8BIT;
+    SpiHandle.Init.FirstBit          = SPI_FIRSTBIT_MSB;
+    SpiHandle.Init.NSS               = SPI_NSS_SOFT;
+    SpiHandle.Init.TIMode            = SPI_TIMODE_DISABLED;
+
+    if (HAL_SPI_Init(&SpiHandle) != HAL_OK) {
+        error("Cannot initialize SPI");
+    }
+
+    __HAL_SPI_ENABLE(&SpiHandle);
+}
+
+DMA_HandleTypeDef tx_DMA_Handle, rx_DMA_Handle;
+
+static void dmaInit() {
+    __DMA2_CLK_ENABLE();
+    tx_DMA_Handle.Instance = DMA2_Stream5;
+
+    // Need to deinit DMA first
+    tx_DMA_Handle.State = HAL_DMA_STATE_READY;
+    HAL_DMA_DeInit(&tx_DMA_Handle);
+
+    tx_DMA_Handle.Init.Channel = DMA_CHANNEL_3;
+    tx_DMA_Handle.Init.Direction = DMA_MEMORY_TO_PERIPH;
+    tx_DMA_Handle.Init.PeriphInc = DMA_PINC_DISABLE;
+    tx_DMA_Handle.Init.MemInc = DMA_MINC_ENABLE;
+    tx_DMA_Handle.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE;
+    tx_DMA_Handle.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE;
+    tx_DMA_Handle.Init.Mode = DMA_NORMAL;
+    tx_DMA_Handle.Init.Priority = DMA_PRIORITY_LOW;
+    tx_DMA_Handle.Init.FIFOMode = DMA_FIFOMODE_DISABLE;
+    tx_DMA_Handle.Init.FIFOThreshold = DMA_FIFO_THRESHOLD_FULL;
+    tx_DMA_Handle.Init.MemBurst = DMA_MBURST_INC4;
+    tx_DMA_Handle.Init.PeriphBurst = DMA_PBURST_INC4;
+    HAL_DMA_Init(&tx_DMA_Handle);
+    //__HAL_LINKDMA(spiHandle, DMA_Handle, tx_DMA_Handle);   // TODO macro
+    tx_DMA_Handle.Parent = &SpiHandle;
+    SpiHandle.hdmatx = &tx_DMA_Handle;
+    SpiHandle.hdmarx = NULL;
+}
+
+
+static void  spiSend(uint8_t *data, uint16_t bytes) {
+    // ? need SPI handle
+    HAL_SPI_Transmit_DMA(&SpiHandle, data, bytes);  // TODO
+    HAL_DMA_PollForTransfer(&tx_DMA_Handle, HAL_DMA_FULL_TRANSFER , 2000);
+    // while (tx_DMA_Handle.Instance->CR & DMA_SxCR_EN);   // spin
+}
+  
+int main() {
+    uint32_t us, i;
+    
+    printf("SystemCoreClock %d  %s %s\n",SystemCoreClock,__TIME__,__DATE__);
+    tmr.start();
+    CSpin =1;
+    for(i=0;i<SPI_BUFF_SIZE;i++) tx_buffer[i]=i;
+    PRREG(SPI1->CR1);
+    PRREG(SPI1->CR2);
+    PRREG(SPI1->SR);
+
+    spiperf(1);
+    spiperf(2);
+    spiperf(4);
+    spiperf(8);
+    spiperf(15);
+    spiperf(30);
+    spiperf(45);
+
+    spiInit();
+    dmaInit();
+    CSpin = 0;
+    us = tmr.read_us();
+    spiSend(tx_buffer,SPI_BUFF_SIZE);
+    us = tmr.read_us()-us;
+    CSpin=1;
+    printf("DMAspi  %d us %.2f mbs  %0x\n",us,8.*SPI_BUFF_SIZE/us,SPI1->CR1);
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Tue Nov 10 12:07:03 2015 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/mbed_official/code/mbed/builds/9296ab0bfc11
\ No newline at end of file