}\r
\r
/* DMA Functions */\r
-tdma_t *tdma_open(tdma_chan_t chan, PinName pin, PinMode mode)\r
+tdma_t *tdma_open(tdma_chan_t chan, int alt, PinName pin, PinMode mode)\r
{\r
int req = pin >= PTD0 ? TDMA_REQ_PTD :\r
pin >= PTC0 ? TDMA_REQ_PTC :\r
| DMA_DCR_DINC_MASK // Dest increment\r
| DMA_DCR_SSIZE(0) // 32-bit access\r
| DMA_DCR_DSIZE(0) // 32-bit access\r
- | DMA_DCR_ERQ_MASK; // Enable port request\r
+ | DMA_DCR_D_REQ_MASK; // Only run once\r
\r
// Setup and enable DMA MUX\r
port->mux->cfg = DMAMUX_CHCFG_SOURCE(req) // Request source\r
\r
// Set pin to generate DMA req\r
port->pin->pcr = PORT_PCR_ISF_MASK // Clear ISR flag\r
- | PORT_PCR_MUX(3) // Pin mapping\r
+ | PORT_PCR_MUX(alt) // Pin mapping\r
| PORT_PCR_IRQC(ircq) // DMA on falling edge\r
| mode; // Pin pull up/down\r
\r
+ // Initial reset\r
+ tdma_reset(port);\r
+\r
return port;\r
}\r
\r
void tdma_reset(tdma_t *port)\r
{\r
+ if (!port)\r
+ return;\r
+\r
// Clear previous time\r
port->time[0] = 0;\r
port->time[1] = 0;\r
\r
+ // Freeze DMA channel\r
+ port->dma->dcr &= ~DMA_DCR_ERQ_MASK;\r
+\r
// Reset DMA channel\r
- port->dma->dsr = DMA_DSR_BCR_DONE_MASK;\r
+ port->dma->dsr = DMA_DSR_BCR_DONE_MASK;\r
\r
// Set addresses and size\r
- port->dma->sar = (uint32_t)&PIT->LTMR64H; // Global timer\r
- port->dma->dar = (uint32_t)&port->time; // Temp timer buffer\r
- port->dma->dsr = DMA_DSR_BCR_BCR(8); // 64-bit timer\r
+ port->dma->sar = (uint32_t)&PIT->LTMR64H; // Global timer\r
+ port->dma->dar = (uint32_t)&port->time; // Temp timer buffer\r
+ port->dma->dsr = DMA_DSR_BCR_BCR(8); // 64-bit timer\r
+\r
+ // Enable port request\r
+ port->dma->dcr |= DMA_DCR_ERQ_MASK;\r
}\r
\r
int tdma_stamp(tdma_t *port, uint64_t *time)\r
{\r
+ uint64_t clocks;\r
+\r
+ if (!port)\r
+ return 0;\r
+\r
if (port->dma->dsr & DMA_DSR_BCR_BCR_MASK)\r
return 0;\r
\r
// Read the timestamp\r
- *time = ((uint64_t)~port->time[0]) << 32\r
- | ((uint64_t)~port->time[1]) << 0;\r
+ clocks = ((uint64_t)~port->time[0]) << 32\r
+ | ((uint64_t)~port->time[1]) << 0;\r
\r
- // Debug output..\r
- //printf(" - sar:%08lx dar:%08lx pcr:%08lx dsr:%08lx time:%08lx:%08lx",\r
- // port->dma->sar, port->dma->dar,\r
- // port->pin->pcr, port->dma->dsr,\r
- // (uint32_t)(*time >> 32), (uint32_t)*time);\r
+ // Convert to nanoseconds\r
+ *time = clocks * 1000 / 24;\r
\r
return 1;\r
}\r
+\r
+uint64_t tdma_time(void)\r
+{\r
+ uint32_t tmh = PIT->LTMR64H;\r
+ uint32_t tml = PIT->LTMR64L;\r
+\r
+ // Read the timestamp\r
+ uint64_t clocks = ((uint64_t)~tmh) << 32\r
+ | ((uint64_t)~tml) << 0;\r
+\r
+ // Convert to nanoseconds\r
+ return clocks * 1000 / 24;\r
+}\r
+\r
+void tdma_debug(tdma_t *port)\r
+{\r
+ int dsr = port->dma->dsr;\r
+ int dcr = port->dma->dcr;\r
+\r
+ printf("dsr: %s %s %s %s %s %s %d\r\n",\r
+ dsr & DMA_DSR_BCR_CE_MASK ? "CE" : "ce",\r
+ dsr & DMA_DSR_BCR_BES_MASK ? "BSE" : "bse",\r
+ dsr & DMA_DSR_BCR_BED_MASK ? "BED" : "bed",\r
+ dsr & DMA_DSR_BCR_REQ_MASK ? "REQ" : "req",\r
+ dsr & DMA_DSR_BCR_BSY_MASK ? "BSY" : "bsy",\r
+ dsr & DMA_DSR_BCR_DONE_MASK ? "DONE" : "done",\r
+ dsr & DMA_DSR_BCR_BCR_MASK);\r
+\r
+ printf("dcr: %s %s %s %s %s %s %s %s ssize=%d:%d mod=%d:%d link=%d:%d:%d\r\n",\r
+ dcr & DMA_DCR_EINT_MASK ? "EINT" : "eint",\r
+ dcr & DMA_DCR_ERQ_MASK ? "ERQ" : "erq",\r
+ dcr & DMA_DCR_CS_MASK ? "CS" : "cs",\r
+ dcr & DMA_DCR_AA_MASK ? "AA" : "aa",\r
+ dcr & DMA_DCR_EADREQ_MASK ? "EADRREQ" : "eadrreq",\r
+ dcr & DMA_DCR_SINC_MASK ? "SINC" : "sinc",\r
+ dcr & DMA_DCR_DINC_MASK ? "DINC" : "dinc",\r
+ dcr & DMA_DCR_D_REQ_MASK ? "DREQ" : "dreq",\r
+ (dcr & DMA_DCR_SSIZE_MASK ) >> DMA_DCR_SSIZE_SHIFT,\r
+ (dcr & DMA_DCR_DSIZE_MASK ) >> DMA_DCR_DSIZE_SHIFT,\r
+ (dcr & DMA_DCR_SMOD_MASK ) >> DMA_DCR_SMOD_SHIFT,\r
+ (dcr & DMA_DCR_DMOD_MASK ) >> DMA_DCR_DMOD_SHIFT,\r
+ (dcr & DMA_DCR_LINKCC_MASK) >> DMA_DCR_LINKCC_SHIFT,\r
+ (dcr & DMA_DCR_LCH1_MASK ) >> DMA_DCR_LCH1_SHIFT,\r
+ (dcr & DMA_DCR_LCH2_MASK ) >> DMA_DCR_LCH2_SHIFT);\r
+}\r