/* * ======== CameraCC3200DMA_configDMA ======== */ static void CameraCC3200DMA_configDMA(Camera_Handle handle) { CameraCC3200DMA_Object *object = handle->object; CameraCC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; unsigned long **bufferPtr = (unsigned long**)&object->captureBuf; /* Setup ping-pong transfer */ MAP_uDMAChannelControlSet(hwAttrs->channelIndex, UDMA_SIZE_32 | UDMA_SRC_INC_32 | UDMA_DST_INC_32 | UDMA_ARB_8); MAP_uDMAChannelAttributeEnable(hwAttrs->channelIndex,UDMA_ATTR_USEBURST); MAP_uDMAChannelTransferSet(hwAttrs->channelIndex, UDMA_MODE_PINGPONG, (void *)CAM_BUFFER_ADDR, (void *)*bufferPtr, CameraCC3200DMA_DMA_TRANSFER_SIZE); MAP_uDMAChannelEnable(hwAttrs->channelIndex); /* Pong Buffer */ *bufferPtr += CameraCC3200DMA_DMA_TRANSFER_SIZE; MAP_uDMAChannelControlSet(hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_SIZE_32 | UDMA_SRC_INC_32 | UDMA_DST_INC_32 | UDMA_ARB_8); MAP_uDMAChannelAttributeEnable(hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_ATTR_USEBURST); MAP_uDMAChannelTransferSet(hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void *)CAM_BUFFER_ADDR, (void *)*bufferPtr, CameraCC3200DMA_DMA_TRANSFER_SIZE); MAP_uDMAChannelEnable(hwAttrs->channelIndex | UDMA_ALT_SELECT); /* Ping Buffer */ *bufferPtr += CameraCC3200DMA_DMA_TRANSFER_SIZE; DebugP_log1("Camera:(%p) DMA transfer enabled", hwAttrs->baseAddr); /* Set mode to Ping buffer initially */ object->cameraDMA_PingPongMode = 0; /* Clear any pending interrupt */ MAP_CameraIntClear(hwAttrs->baseAddr, CAM_INT_DMA); /* DMA Interrupt unmask from apps config */ MAP_CameraIntEnable(hwAttrs->baseAddr, CAM_INT_DMA); DebugP_log3("Camera:(%p) DMA receive, " "CaptureBuf: %p; Count: %d", hwAttrs->baseAddr, (uintptr_t)*bufferPtr, (uintptr_t)object->bufferlength); }
void DMASetupTransfer(unsigned long ulChannel, unsigned long ulMode, unsigned long ulItemCount, unsigned long ulItemSize, unsigned long ulArbSize, void *pvSrcBuf, unsigned long ulSrcInc, void *pvDstBuf, unsigned long ulDstInc) { MAP_uDMAChannelControlSet(ulChannel, ulItemSize | ulSrcInc | ulDstInc | ulArbSize); MAP_uDMAChannelAttributeEnable(ulChannel,UDMA_ATTR_USEBURST); MAP_uDMAChannelTransferSet(ulChannel, ulMode, pvSrcBuf, pvDstBuf, ulItemCount); MAP_uDMAChannelEnable(ulChannel); }
inline void kickoff_transfer(unsigned int channel, unsigned int bus, int base) { const int transfer = sizeof(busbuffer) / 2; _Static_assert(BUS_SIZE/2<=1024, "DMA Transfer must not be more than 1024"); MAP_uDMAChannelTransferSet(channel | UDMA_PRI_SELECT, UDMA_MODE_BASIC, (unsigned char*)(&framebuffer_output[bus]), (void *)(base + SSI_O_DR), transfer); MAP_uDMAChannelEnable(channel); }
/* * ======== CameraCC3200DMA_hwiIntFxn ======== * Hwi function that processes Camera interrupts. * * The Frame end,DMA interrupts is enabled for the camera. * The DMA interrupt is triggered for every 64 elements. * The ISR will check for Frame end interrupt to trigger the callback * in the non-blocking mode/post a semaphore in the blocking mode to * indicate capture complete. * * @param(arg) The Camera_Handle for this Hwi. */ static void CameraCC3200DMA_hwiIntFxn(uintptr_t arg) { uint32_t status; CameraCC3200DMA_Object *object = ((Camera_Handle)arg)->object; CameraCC3200DMA_HWAttrs const *hwAttrs = ((Camera_Handle)arg)->hwAttrs; unsigned long **bufferPtr = (unsigned long**)&object->captureBuf; status = MAP_CameraIntStatus(hwAttrs->baseAddr); if ((object->cameraDMAxIntrRcvd > 1) && (status & (CAM_INT_FE))) { DebugP_log2("Camera:(%p) Interrupt with mask 0x%x", hwAttrs->baseAddr,status); MAP_CameraIntClear(hwAttrs->baseAddr, CAM_INT_FE); object->captureCallback((Camera_Handle)arg, *bufferPtr, object->frameLength); DebugP_log2("Camera:(%p) capture finished, %d bytes written", hwAttrs->baseAddr, object->frameLength); object->inUse = 0; MAP_CameraCaptureStop(hwAttrs->baseAddr, true); Power_releaseConstraint(PowerCC3200_DISALLOW_DEEPSLEEP); } if (status & CAM_INT_DMA) { // Camera DMA Done clear MAP_CameraIntClear(hwAttrs->baseAddr, CAM_INT_DMA); object->cameraDMAxIntrRcvd++; object->frameLength += (CameraCC3200DMA_DMA_TRANSFER_SIZE*sizeof(unsigned long)); if (object->frameLength < object->bufferlength) { if (object->cameraDMA_PingPongMode == 0) { MAP_uDMAChannelControlSet(hwAttrs->channelIndex, UDMA_SIZE_32 | UDMA_SRC_INC_32 | UDMA_DST_INC_32 | UDMA_ARB_8); MAP_uDMAChannelAttributeEnable(hwAttrs->channelIndex, UDMA_ATTR_USEBURST); MAP_uDMAChannelTransferSet(hwAttrs->channelIndex, UDMA_MODE_PINGPONG, (void *)CAM_BUFFER_ADDR, (void *)*bufferPtr, CameraCC3200DMA_DMA_TRANSFER_SIZE); MAP_uDMAChannelEnable(hwAttrs->channelIndex); *bufferPtr += CameraCC3200DMA_DMA_TRANSFER_SIZE; object->cameraDMA_PingPongMode = 1; } else { MAP_uDMAChannelControlSet(hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_SIZE_32 | UDMA_SRC_INC_32 | UDMA_DST_INC_32 | UDMA_ARB_8); MAP_uDMAChannelAttributeEnable( hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_ATTR_USEBURST); MAP_uDMAChannelTransferSet( hwAttrs->channelIndex | UDMA_ALT_SELECT, UDMA_MODE_PINGPONG, (void *)CAM_BUFFER_ADDR, (void *)*bufferPtr, CameraCC3200DMA_DMA_TRANSFER_SIZE); MAP_uDMAChannelEnable(hwAttrs->channelIndex | UDMA_ALT_SELECT); *bufferPtr += CameraCC3200DMA_DMA_TRANSFER_SIZE; object->cameraDMA_PingPongMode = 0; } } else { // Disable DMA MAP_UtilsDelay(20000); MAP_uDMAChannelDisable(hwAttrs->channelIndex); MAP_CameraIntDisable(hwAttrs->baseAddr, CAM_INT_DMA); object->cameraDMA_PingPongMode = 0; object->captureCallback((Camera_Handle)arg, *bufferPtr, object->frameLength); DebugP_log2("Camera:(%p) capture finished, %d bytes written", hwAttrs->baseAddr, object->frameLength); MAP_CameraCaptureStop(hwAttrs->baseAddr, true); Power_releaseConstraint(PowerCC3200_DISALLOW_DEEPSLEEP); } } }
/* * ======== SPICC3200DMA_configDMA ======== * This functions configures the transmit and receive DMA channels for a given * SPI_Handle and SPI_Transaction * * @pre Function assumes that the handle and transaction is not NULL */ static void SPICC3200DMA_configDMA(SPI_Handle handle, SPI_Transaction *transaction) { uintptr_t key; SPIDataType dummy; void *buf; uint32_t channelControlOptions; SPICC3200DMA_Object *object = handle->object; SPICC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; /* Clear out the FIFO */ while (MAP_SPIDataGetNonBlocking(hwAttrs->baseAddr, &dummy)) {} /* Configure DMA for RX */ MAP_uDMAChannelAssign(hwAttrs->rxChannelIndex); MAP_uDMAChannelAttributeDisable(hwAttrs->rxChannelIndex, UDMA_ATTR_ALTSELECT); if (transaction->rxBuf) { channelControlOptions = dmaRxConfig[object->frameSize]; buf = transaction->rxBuf; } else { channelControlOptions = dmaNullConfig[object->frameSize]; buf = hwAttrs->scratchBufPtr; } MAP_uDMAChannelControlSet(hwAttrs->rxChannelIndex | UDMA_PRI_SELECT, channelControlOptions); MAP_uDMAChannelTransferSet(hwAttrs->rxChannelIndex | UDMA_PRI_SELECT, UDMA_MODE_BASIC, (void *)(hwAttrs->baseAddr + MCSPI_O_RX0), buf, transaction->count); /* Configure DMA for TX */ MAP_uDMAChannelAssign(hwAttrs->txChannelIndex); MAP_uDMAChannelAttributeDisable(hwAttrs->txChannelIndex, UDMA_ATTR_ALTSELECT); if (transaction->txBuf) { channelControlOptions = dmaTxConfig[object->frameSize]; buf = transaction->txBuf; } else { channelControlOptions = dmaNullConfig[object->frameSize]; *hwAttrs->scratchBufPtr = hwAttrs->defaultTxBufValue; buf = hwAttrs->scratchBufPtr; } MAP_uDMAChannelControlSet(hwAttrs->txChannelIndex | UDMA_PRI_SELECT, channelControlOptions); MAP_uDMAChannelTransferSet(hwAttrs->txChannelIndex | UDMA_PRI_SELECT, UDMA_MODE_BASIC, buf, (void *)(hwAttrs->baseAddr + MCSPI_O_TX0), transaction->count); DebugP_log1("SPI:(%p) DMA transfer enabled", hwAttrs->baseAddr); DebugP_log4("SPI: DMA transaction: %p, rxBuf: %p; txBuf: %p; Count: %d", (uintptr_t)transaction, (uintptr_t)transaction->rxBuf, (uintptr_t)transaction->txBuf, (uintptr_t)transaction->count); key = HwiP_disable(); MAP_uDMAChannelEnable(hwAttrs->rxChannelIndex); MAP_uDMAChannelEnable(hwAttrs->txChannelIndex); HwiP_restore(key); MAP_SPIWordCountSet(hwAttrs->baseAddr, transaction->count); }