/* * ======== SPICC3200DMA_hwiFxn ======== * ISR for the SPI when we use the DMA is used. */ void SPICC3200DMA_hwiFxn(uintptr_t arg) { SPI_Transaction *msg; SPICC3200DMA_Object *object = ((SPI_Handle)arg)->object; SPICC3200DMA_HWAttrs const *hwAttrs = ((SPI_Handle)arg)->hwAttrs; uint32_t intCode = 0; DebugP_log1("SPI:(%p) interrupt context start", hwAttrs->baseAddr); intCode = MAP_SPIIntStatus(hwAttrs->baseAddr, false); if (intCode & SPI_INT_DMATX) { /* DMA finished transfering; clear & disable interrupt */ MAP_SPIIntDisable(hwAttrs->baseAddr, SPI_INT_DMATX); MAP_SPIIntClear(hwAttrs->baseAddr, SPI_INT_DMATX); } /* Determine if the TX & RX DMA channels have completed */ if ((object->transaction) && (MAP_uDMAChannelIsEnabled(hwAttrs->rxChannelIndex) == false) && (MAP_uDMAIntStatus() & (1 << hwAttrs->rxChannelIndex))) { MAP_SPIDisable(hwAttrs->baseAddr); MAP_SPICSDisable(hwAttrs->baseAddr); MAP_SPIIntDisable(hwAttrs->baseAddr, SPI_INT_DMARX); MAP_SPIIntClear(hwAttrs->baseAddr, SPI_INT_DMARX); MAP_SPIIntClear(hwAttrs->baseAddr, SPI_INT_EOW); /* * Clear any pending interrupt * As the TX DMA channel interrupt gets service, it may be possible * that the RX DMA channel finished in the meantime, which means * the IRQ for RX DMA channel is still pending... */ HwiP_clearInterrupt(hwAttrs->intNum); /* * Use a temporary transaction pointer in case the callback function * attempts to perform another SPI_transfer call */ msg = object->transaction; /* Indicate we are done with this transfer */ object->transaction = NULL; /* Release constraint since transaction is done */ Power_releaseConstraint(PowerCC3200_DISALLOW_DEEPSLEEP); DebugP_log2("SPI:(%p) DMA transaction: %p complete", hwAttrs->baseAddr, (uintptr_t)msg); object->transferCallbackFxn((SPI_Handle)arg, msg); } DebugP_log1("SPI:(%p) interrupt context end", hwAttrs->baseAddr); }
/* * ======== SPICC3200DMA_close ======== * @pre Function assumes that the handle is not NULL */ void SPICC3200DMA_close(SPI_Handle handle) { uintptr_t key; SPICC3200DMA_Object *object = handle->object; SPICC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; MAP_SPIDisable(hwAttrs->baseAddr); MAP_SPICSDisable(hwAttrs->baseAddr); MAP_SPIDmaDisable(hwAttrs->baseAddr, SPI_RX_DMA | SPI_TX_DMA); MAP_SPIFIFODisable(hwAttrs->baseAddr, SPI_RX_FIFO | SPI_TX_FIFO); /* Release power dependency on SPI. */ Power_releaseDependency(getPowerMgrId(hwAttrs->baseAddr)); Power_releaseDependency(PowerCC3200_PERIPH_UDMA); Power_unregisterNotify(&(object->notifyObj)); if (object->hwiHandle) { HwiP_delete(object->hwiHandle); } if (object->transferComplete) { SemaphoreP_delete(object->transferComplete); } DebugP_log1("SPI:(%p) closed", hwAttrs->baseAddr); key = HwiP_disable(); object->isOpen = false; HwiP_restore(key); }
/* * ======== dmaErrorHwi ======== */ static void dmaErrorHwi(uintptr_t arg) { DebugP_log1("DMA error code: %d\n", MAP_DMA_getErrorStatus()); MAP_DMA_clearErrorStatus(); DebugP_log0("DMA error!!\n"); while(1); }
/* * ======== readIsrTextBlocking ======== * Function that is called by the ISR */ static bool readIsrTextBlocking(UART_Handle handle) { int readIn; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; readIn = MAP_UART_receiveData(hwAttrs->baseAddr); if (readIn == '\r') { /* Echo character if enabled. */ if (object->state.readEcho) { MAP_UART_transmitData(hwAttrs->baseAddr, '\r'); } readIn = '\n'; } if (RingBuf_put(&object->ringBuffer, (unsigned char) readIn) == -1) { DebugP_log1("UART:(%p) Ring buffer full!!", hwAttrs->baseAddr); return (false); } DebugP_log2("UART:(%p) buffered '0x%02x'", hwAttrs->baseAddr, (unsigned char) readIn); if (object->state.readEcho) { MAP_UART_transmitData(hwAttrs->baseAddr, (unsigned char) readIn); } if (object->state.callCallback) { object->state.callCallback = false; object->readCallback(handle, NULL, 0); } return (true); }
/* * ======== readIsrBinaryCallback ======== */ static bool readIsrBinaryCallback(UART_Handle handle) { int readIn; bool ret = true; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; readIn = MAP_UART_receiveData(hwAttrs->baseAddr); if (RingBuf_put(&object->ringBuffer, (unsigned char)readIn) == -1) { DebugP_log1("UART:(%p) Ring buffer full!!", hwAttrs->baseAddr); ret = false; } DebugP_log2("UART:(%p) buffered '0x%02x'", hwAttrs->baseAddr, (unsigned char) readIn); /* * Check and see if a UART_read in callback mode told use to continue * servicing the user buffer... */ if (object->state.drainByISR) { readTaskCallback(handle); } return (ret); }
/* * ======== PWMTimerMSP432_close ======== * @pre Function assumes that the handle is not NULL */ void PWMTimerMSP432_close(PWM_Handle handle) { uintptr_t key; PWMTimerMSP432_Object *object = handle->object; PWMTimerMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; MAP_Timer_A_setCompareValue(hwAttrs->baseAddr, hwAttrs->compareRegister, 0); key = HwiP_disable(); /* Mark the output as unused */ (object->pwmTimerStatus)->activeOutputsMask &= ~(object->pwmCompareOutputBit); /* Stop timer & clear all status if no other PWM instances are being used */ if ((object->pwmTimerStatus)->activeOutputsMask == 0) { MAP_Timer_A_stopTimer(hwAttrs->baseAddr); (object->pwmTimerStatus)->cyclesPerMicroSec = 0; (object->pwmTimerStatus)->period = 0; (object->pwmTimerStatus)->prescalar = 0; } object->isOpen = false; HwiP_restore(key); /* Remove power constraints */ Power_releaseConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); Power_releaseConstraint(PowerMSP432_DISALLOW_SHUTDOWN_0); Power_releaseConstraint(PowerMSP432_DISALLOW_SHUTDOWN_1); DebugP_log1("PWM: (%p) closed", (uintptr_t) handle); }
/* * ======== SPICC3200DMA_transfer ======== * @pre Function assumes that handle and transaction is not NULL */ bool SPICC3200DMA_transfer(SPI_Handle handle, SPI_Transaction *transaction) { uintptr_t key; SPICC3200DMA_Object *object = handle->object; SPICC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; /* This is a limitation by the micro DMA controller */ if ((transaction->count == 0) || (transaction->count > 1024) || !(transaction->rxBuf || transaction->txBuf) || (!(transaction->rxBuf && transaction->txBuf) && !hwAttrs->scratchBufPtr)) { return (false); } /* Check if a transfer is in progress */ key = HwiP_disable(); if (object->transaction) { HwiP_restore(key); DebugP_log1("SPI:(%p) ERROR! Transaction still in progress", ((SPICC3200DMA_HWAttrs const *)(handle->hwAttrs))->baseAddr); return (false); } else { object->transaction = transaction; HwiP_restore(key); } /* Set constraints to guarantee transaction */ Power_setConstraint(PowerCC3200_DISALLOW_DEEPSLEEP); SPICC3200DMA_configDMA(handle, transaction); MAP_SPIIntClear(hwAttrs->baseAddr, SPI_INT_DMARX | SPI_INT_DMATX | SPI_INT_EOW); MAP_SPIIntEnable(hwAttrs->baseAddr, SPI_INT_DMARX | SPI_INT_DMATX | SPI_INT_EOW); MAP_SPIEnable(hwAttrs->baseAddr); MAP_SPICSEnable(hwAttrs->baseAddr); if (object->transferMode == SPI_MODE_BLOCKING) { DebugP_log1("SPI:(%p) transfer pending on transferComplete semaphore", ((SPICC3200DMA_HWAttrs const *)(handle->hwAttrs))->baseAddr); SemaphoreP_pend(object->transferComplete, SemaphoreP_WAIT_FOREVER); } return (true); }
/* * ======== SPICC3200DMA_transferCallback ======== * Callback function for when the SPI is in SPI_MODE_BLOCKING * * @pre Function assumes that the handle is not NULL */ static void SPICC3200DMA_transferCallback(SPI_Handle handle, SPI_Transaction *transaction) { SPICC3200DMA_Object *object = handle->object; DebugP_log1("SPI:(%p) posting transferComplete semaphore", ((SPICC3200DMA_HWAttrs const *)(handle->hwAttrs))->baseAddr); SemaphoreP_post(object->transferComplete); }
/* * ======== errorCallback ======== * Generic log function for when unexpected events occur. */ static void errorCallback(UART_Handle handle, uintptr_t error) { if (error & EUSCI_A_UART_OVERRUN_ERROR) { DebugP_log1("UART:(%p): OVERRUN ERROR", ((UARTMSP432_HWAttrs const *)handle->hwAttrs)->baseAddr); } if (error & EUSCI_A_UART_BREAK_DETECT) { DebugP_log1("UART:(%p): BREAK ERROR", ((UARTMSP432_HWAttrs const *)handle->hwAttrs)->baseAddr); } if (error & EUSCI_A_UART_PARITY_ERROR) { DebugP_log1("UART:(%p): PARITY ERROR", ((UARTMSP432_HWAttrs const *)handle->hwAttrs)->baseAddr); } if (error & EUSCI_A_UART_FRAMING_ERROR) { DebugP_log1("UART:(%p): FRAMING ERROR", ((UARTMSP432_HWAttrs const *)handle->hwAttrs)->baseAddr); } }
/* * ======== UARTMSP432_write ======== */ int UARTMSP432_write(UART_Handle handle, const void *buffer, size_t size) { uintptr_t key; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; if (!size) { return 0; } key = HwiP_disable(); if (object->writeCount) { HwiP_restore(key); DebugP_log1("UART:(%p) Could not write data, uart in use.", hwAttrs->baseAddr); return (UART_ERROR); } /* Save the data to be written and restore interrupts. */ object->writeBuf = buffer; object->writeSize = size; object->writeCount = size; HwiP_restore(key); /* * Set power constraint to keep peripheral active during transfer and * to prevent a performance level change */ Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_setConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); /* Enabling TX interrupt will trigger the Hwi which will handle the write */ MAP_UART_enableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_TRANSMIT_INTERRUPT); /* If writeMode is blocking, block and get the state. */ if (object->state.writeMode == UART_MODE_BLOCKING) { /* Pend on semaphore and wait for Hwi to finish. */ if (SemaphoreP_pend(object->writeSem, object->writeTimeout) != SemaphoreP_OK) { /* Semaphore timed out, make the write empty and log the write. */ MAP_UART_disableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_TRANSMIT_INTERRUPT); object->writeCount = 0; DebugP_log2("UART:(%p) Write timed out, %d bytes written", hwAttrs->baseAddr, object->writeCount); } return (object->writeSize - object->writeCount); } return (0); }
int CameraCC3200DMA_capture(Camera_Handle handle, void *buffer, unsigned int bufferlen) { CameraCC3200DMA_Object *object = handle->object; CameraCC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; uintptr_t key; key = HwiP_disable(); if (object->inUse) { HwiP_restore(key); DebugP_log1("Camera:(%p) Could not capture data, camera in use.", ((CameraCC3200DMA_HWAttrs const *) (handle->hwAttrs))->baseAddr); return (CAMERA_STATUS_UNDEFINEDCMD); } object->captureBuf = buffer; object->bufferlength = bufferlen; object->frameLength = 0; object->cameraDMAxIntrRcvd = 0; object->inUse = 1; object->cameraDMA_PingPongMode = 0; HwiP_restore(key); /* Set constraints to guarantee transaction */ Power_setConstraint(PowerCC3200_DISALLOW_DEEPSLEEP); /* Start the DMA transfer */ CameraCC3200DMA_configDMA(handle); MAP_CameraCaptureStart(hwAttrs->baseAddr); /* If operationMode is blocking, block and get the status. */ if (object->operationMode == Camera_MODE_BLOCKING) { /* Pend on semaphore and wait for Hwi to finish. */ if (SemaphoreP_pend(object->captureSem, object->captureTimeout) != SemaphoreP_OK) { DebugP_log2("Camera:(%p) Capture timed out, %d bytes captured", ((CameraCC3200DMA_HWAttrs const *) (handle->hwAttrs))->baseAddr, object->frameLength); } else { MAP_CameraCaptureStop(hwAttrs->baseAddr, true); return (object->frameLength); } } return (0); }
/* * ======== 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); }
/* * ======== readIsrTextCallback ======== */ static bool readIsrTextCallback(UART_Handle handle) { int readIn; bool ret = true; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; readIn = MAP_UART_receiveData(hwAttrs->baseAddr); if (readIn == '\r') { /* Echo character if enabled. */ if (object->state.readEcho) { /* Wait until TX is ready */ while (!MAP_UART_getInterruptStatus(hwAttrs->baseAddr, EUSCI_A_UART_TRANSMIT_INTERRUPT_FLAG)) {} MAP_UART_transmitData(hwAttrs->baseAddr, '\r'); } readIn = '\n'; } if (RingBuf_put(&object->ringBuffer, (unsigned char) readIn) == -1) { DebugP_log1("UART:(%p) Ring buffer full!!", hwAttrs->baseAddr); ret = false; } DebugP_log2("UART:(%p) buffered '0x%02x'", hwAttrs->baseAddr, (unsigned char) readIn); if (object->state.readEcho) { /* Wait until TX is ready */ while (!MAP_UART_getInterruptStatus(hwAttrs->baseAddr, EUSCI_A_UART_TRANSMIT_INTERRUPT_FLAG)) {} MAP_UART_transmitData(hwAttrs->baseAddr, (unsigned char)readIn); } /* * Check and see if a UART_read in callback mode told use to continue * servicing the user buffer... */ if (object->state.drainByISR) { readTaskCallback(handle); } return (ret); }
/* * ======== UARTMSP432_close ======== */ void UARTMSP432_close(UART_Handle handle) { unsigned int i; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; MAP_UART_disableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_RECEIVE_INTERRUPT | EUSCI_A_UART_TRANSMIT_INTERRUPT); MAP_UART_disableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_RECEIVE_ERRONEOUSCHAR_INTERRUPT | EUSCI_A_UART_BREAKCHAR_INTERRUPT); MAP_UART_disableModule(hwAttrs->baseAddr); if (object->hwiHandle) { HwiP_delete(object->hwiHandle); } if (object->writeSem) { SemaphoreP_delete(object->writeSem); } if (object->readSem) { SemaphoreP_delete(object->readSem); } /* Remove power constraints */ for (i = 0; object->perfConstraintMask; i++) { if (object->perfConstraintMask & 0x01) { Power_releaseConstraint(PowerMSP432_DISALLOW_PERFLEVEL_0 + i); } object->perfConstraintMask >>= 1; } if (object->state.rxEnabled) { Power_releaseConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); } Power_releaseConstraint(PowerMSP432_DISALLOW_SHUTDOWN_0); Power_releaseConstraint(PowerMSP432_DISALLOW_SHUTDOWN_1); Power_unregisterNotify(&object->perfChangeNotify); object->state.opened = false; DebugP_log1("UART:(%p) closed", hwAttrs->baseAddr); }
/* * ======== readIsrBinaryBlocking ======== * Function that is called by the ISR */ static bool readIsrBinaryBlocking(UART_Handle handle) { int readIn; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; readIn = MAP_UART_receiveData(hwAttrs->baseAddr); if (RingBuf_put(&object->ringBuffer, (unsigned char) readIn) == -1) { DebugP_log1("UART:(%p) Ring buffer full!!", hwAttrs->baseAddr); return (false); } DebugP_log2("UART:(%p) buffered '0x%02x'", hwAttrs->baseAddr, (unsigned char) readIn); if (object->state.callCallback) { object->state.callCallback = false; object->readCallback(handle, NULL, 0); } return (true); }
/* * ======== CameraCC3200DMA_close ======== */ void CameraCC3200DMA_close(Camera_Handle handle) { CameraCC3200DMA_Object *object = handle->object; CameraCC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; /* Disable Camera and interrupts. */ MAP_CameraIntDisable(hwAttrs->baseAddr,CAM_INT_FE); MAP_CameraDMADisable(hwAttrs->baseAddr); if (object->hwiHandle) { HwiP_delete(object->hwiHandle); } if (object->captureSem) { SemaphoreP_delete(object->captureSem); } Power_releaseDependency(PowerCC3200_PERIPH_CAMERA); Power_releaseDependency(PowerCC3200_PERIPH_UDMA); object->opened = false; DebugP_log1("Camera:(%p) closed", hwAttrs->baseAddr); }
/* * ======== UARTMSP432_read ======== */ int UARTMSP432_read(UART_Handle handle, void *buffer, size_t size) { uintptr_t key; UARTMSP432_Object *object = handle->object; key = HwiP_disable(); if ((object->state.readMode == UART_MODE_CALLBACK) && object->readSize) { HwiP_restore(key); DebugP_log1("UART:(%p) Could not read data, uart in use.", ((UARTMSP432_HWAttrs const *)(handle->hwAttrs))->baseAddr); return (UART_ERROR); } /* Save the data to be read and restore interrupts. */ object->readBuf = buffer; object->readSize = size; object->readCount = size; HwiP_restore(key); return (object->readFxns.readTaskFxn(handle)); }
/* * ======== PWMTimerMSP432_setDuty ======== * @pre Function assumes that handle is not NULL */ void PWMTimerMSP432_setDuty(PWM_Handle handle, uint32_t duty) { uintptr_t key; uint16_t period; uint32_t newDuty; PWMTimerMSP432_Object *object = handle->object; PWMTimerMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; key = HwiP_disable(); period = MAP_Timer_A_getCaptureCompareCount(hwAttrs->baseAddr, TIMER_A_CAPTURECOMPARE_REGISTER_0); switch(object->dutyMode) { case PWM_DUTY_COUNTS: /* Duty specified as PWM timer counts */ DebugP_assert(duty <= period); newDuty = duty; break; case PWM_DUTY_TIME: /* Duty is specified in microseconds */ DebugP_assert(duty <= (object->pwmTimerStatus)->period); newDuty = (duty * (object->pwmTimerStatus)->cyclesPerMicroSec) / (object->pwmTimerStatus)->prescalar; break; case PWM_DUTY_SCALAR: /* Duty specified as a number [0 - 65535] scaled to the period */ DebugP_assert(duty <= maxDutyValue); if (duty >= maxDutyValue) { newDuty = period; } else { newDuty = (period * 100) / maxDutyValue; newDuty = (newDuty * duty) / 100; } break; default: DebugP_log1("PWM: (%p) unsupported PWM duty mode; duty unchanged", (uintptr_t) handle); return; } /* * This condition ensures that the output will remain active if the newDuty * is greater or equal to the period. */ if (newDuty >= period) { newDuty = (period + 1); } MAP_Timer_A_setCompareValue(hwAttrs->baseAddr, hwAttrs->compareRegister, newDuty); HwiP_restore(key); DebugP_log2("PWM: (%p) duty set to: %d", (uintptr_t) handle, duty); }
/* * ======== PWMTimerMSP432_open ======== * @pre Function assumes that the handle is not NULL */ PWM_Handle PWMTimerMSP432_open(PWM_Handle handle, PWM_Params *params) { uintptr_t key; bool timerIsRunning; uint8_t cyclesPerMicroSec; uint32_t clockFreq; uint32_t tempPeriod; Timer_A_PWMConfig pwmConfig; PowerMSP432_Freqs powerFreqs; PWMTimerMSP432_Object *object = handle->object; PWMTimerMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; if(params == NULL) { params = (PWM_Params *) &PWM_defaultParams; } key = HwiP_disable(); /* * Before opening the PWM instance, we must verify that the Timer is not * already open or being used by another source (possibly the Kernel). * Additionally, the Timer peripheral could have already been initialized * by another PWM instance, so we must verify if any other PWM driver * (on the same Timer) is initialized. */ timerIsRunning = (TIMER_A_CMSIS(hwAttrs->baseAddr)->rCTL.b.bMC != TIMER_A_STOP_MODE); if (object->isOpen || (timerIsRunning && (object->pwmTimerStatus)->activeOutputsMask == 0)) { /* Timer already opened or used by source other than PWM driver */ HwiP_restore(key); DebugP_log1("PWM:(%p) timer used by another source.", (uintptr_t) handle); return (NULL); } /* * Timer capture/compare register 0 is used as the period. It cannot be * used to generate PWM output. */ DebugP_assert(hwAttrs->compareRegister != TIMER_A_CAPTURECOMPARE_REGISTER_0); /* * Add power management support - PWM driver does not allow performance * level changes, low power modes or shutdown while open. */ Power_setConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_0); Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_1); PowerMSP432_getFreqs(Power_getPerformanceLevel(), &powerFreqs); clockFreq = powerFreqs.SMCLK; cyclesPerMicroSec = clockFreq / 1000000; /* Assert if period is too large for peripheral */ tempPeriod = params->period * cyclesPerMicroSec; DebugP_assert(tempPeriod <= maxPrescalarValue * maxDutyValue); /* * Verify if timer has been initialized by another PWM instance. If so, * make sure PWM periods are the same, do not open driver if otherwise. */ if ((object->pwmTimerStatus)->period && (object->pwmTimerStatus)->period != params->period) { HwiP_restore(key); DebugP_log1("PWM:(%p) differing PWM periods, cannot open driver.", (uintptr_t) handle); PWMTimerMSP432_close(handle); return (NULL); } else { /* PWM timer has not been initialized */ (object->pwmTimerStatus)->cyclesPerMicroSec = cyclesPerMicroSec; (object->pwmTimerStatus)->prescalar = PWMTimerMSP432_calculatePrescalar(tempPeriod); (object->pwmTimerStatus)->period = params->period; } /* Mark driver as being used */ object->isOpen = true; (object->pwmTimerStatus)->activeOutputsMask |= object->pwmCompareOutputBit; HwiP_restore(key); /* Store PWM instance parameters */ object->dutyMode = params->dutyMode; /* Configure PWM output & start timer */ pwmConfig.clockSource = TIMER_A_CLOCKSOURCE_SMCLK; pwmConfig.clockSourceDivider = (object->pwmTimerStatus)->prescalar; pwmConfig.timerPeriod = tempPeriod / (object->pwmTimerStatus)->prescalar; pwmConfig.compareRegister = hwAttrs->compareRegister; pwmConfig.compareOutputMode = outputPolarity[params->polarity]; pwmConfig.dutyCycle = 0; MAP_Timer_A_generatePWM(hwAttrs->baseAddr, &pwmConfig); MAP_Timer_A_startCounter(hwAttrs->baseAddr, TIMER_A_UP_MODE); DebugP_log2("PWM:(%p) opened; period set to: %d", (uintptr_t) handle, params->period); return (handle); }
/* * ======== UARTMSP432_control ======== * @pre Function assumes that the handle is not NULL */ int UARTMSP432_control(UART_Handle handle, unsigned int cmd, void *arg) { int bufferCount; unsigned char data; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; bufferCount = RingBuf_peek(&object->ringBuffer, &data); switch (cmd) { /* Common UART CMDs */ case (UART_CMD_PEEK): *(int *)arg = (bufferCount) ? data : UART_ERROR; DebugP_log2("UART:(%p) UART_CMD_PEEK: %d", hwAttrs->baseAddr, *(uintptr_t*)arg); return (UART_STATUS_SUCCESS); case (UART_CMD_ISAVAILABLE): *(bool *)arg = (bufferCount != 0); DebugP_log2("UART:(%p) UART_CMD_ISAVAILABLE: %d", hwAttrs->baseAddr, *(uintptr_t*)arg); return (UART_STATUS_SUCCESS); case (UART_CMD_GETRXCOUNT): *(int *)arg = bufferCount; DebugP_log2("UART:(%p) UART_CMD_GETRXCOUNT: %d", hwAttrs->baseAddr, *(uintptr_t*)arg); return (UART_STATUS_SUCCESS); case (UART_CMD_RXENABLE): if (!object->state.rxEnabled) { /* * Set power constraints to keep peripheral active receiving * RX interrupts and prevent a performance level change. */ Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_setConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); MAP_UART_enableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_RECEIVE_INTERRUPT); object->state.rxEnabled = true; DebugP_log1("UART:(%p) UART_CMD_RXENABLE: Enabled", hwAttrs->baseAddr); DebugP_log1("UART:(%p) UART_control set read power constraint", hwAttrs->baseAddr); return (UART_STATUS_SUCCESS); } DebugP_log1("UART:(%p) UART_CMD_RXENABLE: Already enabled", hwAttrs->baseAddr); return (UART_STATUS_ERROR); case (UART_CMD_RXDISABLE): if (object->state.rxEnabled) { MAP_UART_disableInterrupt(hwAttrs->baseAddr, EUSCI_A_UART_RECEIVE_INTERRUPT); /* * Remove constraints, this will allow the device to enter * LPM3 and higher as well as allow performance level changes * by the application. */ Power_releaseConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); object->state.rxEnabled = false; DebugP_log1("UART:(%p) UART_CMD_RXDISABLE: Disabled", hwAttrs->baseAddr); DebugP_log1("UART:(%p) UART_control released read power " "constraint", hwAttrs->baseAddr); return (UART_STATUS_SUCCESS); } DebugP_log1("UART:(%p) UART_CMD_RXDISABLE: Already disabled", hwAttrs->baseAddr); return (UART_STATUS_ERROR); default: DebugP_log2("UART:(%p) UART CMD undefined: %d", hwAttrs->baseAddr, cmd); return (UART_STATUS_UNDEFINEDCMD); } }
/* * ======== UARTMSP432_open ======== */ UART_Handle UARTMSP432_open(UART_Handle handle, UART_Params *params) { unsigned int i; uintptr_t key; uint32_t clockFreq; uint8_t numPerfLevels; int32_t baudrateIndex; union { ClockP_Params clockParams; HwiP_Params hwiParams; SemaphoreP_Params semParams; } portsParams; PowerMSP432_Freqs powerFreqs; UARTMSP432_Object *object = handle->object; UARTMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; if (params == NULL) { params = (UART_Params *) &UART_defaultParams; } /* Check that a callback is set */ DebugP_assert((params->readMode != UART_MODE_CALLBACK) || (params->readCallback != NULL)); DebugP_assert((params->writeMode != UART_MODE_CALLBACK) || (params->writeCallback != NULL)); key = HwiP_disable(); if (object->state.opened) { HwiP_restore(key); DebugP_log1("UART:(%p) already in use.", hwAttrs->baseAddr); return (NULL); } object->state.opened = true; HwiP_restore(key); /* Ensure a supported clock source is used */ if (hwAttrs->clockSource != EUSCI_A_UART_CLOCKSOURCE_ACLK && hwAttrs->clockSource != EUSCI_A_UART_CLOCKSOURCE_SMCLK) { DebugP_log1("UART:(%p) Error! Using unsupported clock source.", hwAttrs->baseAddr); object->state.opened = false; return (NULL); } /* * Add power management support - Disable performance transitions while * opening the driver is open. This constraint remains active until a * UART_control() disables receive interrupts. Afterwards performance * levels can be changed by the application. A UART_control() call can * enable RX interrupts again and set the pertinent constraints. */ Power_setConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); /* * Verify that the driver can be opened at current performance level and * set constraints for other performance levels. */ numPerfLevels = PowerMSP432_getNumPerfLevels(); PowerMSP432_getFreqs(Power_getPerformanceLevel(), &powerFreqs); if (hwAttrs->clockSource == EUSCI_A_UART_CLOCKSOURCE_ACLK) { /* * Verify if driver can be opened with ACLK; ACLK does not change * in any performance level. */ baudrateIndex = findBaudDividerIndex(hwAttrs->baudrateLUT, hwAttrs->numBaudrateEntries, params->baudRate, powerFreqs.ACLK); if (baudrateIndex == -1) { DebugP_log3("UART:(%p) unable to find a valid buadrate %d " "configuration at clock input clock freq %d", hwAttrs->baseAddr, params->baudRate, powerFreqs.ACLK); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); object->state.opened = false; return (NULL); } clockFreq = powerFreqs.ACLK; } else { /* hwAttrs->clockSource == EUSCI_A_UART_CLOCKSOURCE_SMCLK */ baudrateIndex = findBaudDividerIndex(hwAttrs->baudrateLUT, hwAttrs->numBaudrateEntries, params->baudRate, powerFreqs.SMCLK); if (baudrateIndex == -1) { DebugP_log3("UART:(%p) unable to find a valid buadrate %d " "configuration at clock input clock freq %d", hwAttrs->baseAddr, params->baudRate, powerFreqs.SMCLK); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); object->state.opened = false; return (NULL); } clockFreq = powerFreqs.SMCLK; /* * SMCLK changes with performance levels. Set constraints for * unsupported performance levels. */ for (i = 0; i < numPerfLevels; i++) { PowerMSP432_getFreqs(i, &powerFreqs); baudrateIndex = findBaudDividerIndex(hwAttrs->baudrateLUT, hwAttrs->numBaudrateEntries, params->baudRate, powerFreqs.SMCLK); if (baudrateIndex == -1) { /* Set constraint and keep track of it in perfConstraintMask */ object->perfConstraintMask |= (1 << i); Power_setConstraint(PowerMSP432_DISALLOW_PERFLEVEL_0 + i); } } } /* * Shutdown not supported while driver is open. The DEEPSLEEP_0 constraint * keeps stops the device from going into LPM3 or higher. This is done * to keep the UART peripheral receiving in the background and storing data * in the internal ring buff. */ Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_0); Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_1); /* Register function to reconfigure peripheral on perf level changes */ Power_registerNotify(&object->perfChangeNotify, PowerMSP432_START_CHANGE_PERF_LEVEL | PowerMSP432_DONE_CHANGE_PERF_LEVEL, perfChangeNotifyFxn, (uintptr_t) handle); /* Create the Hwi for this UART peripheral */ HwiP_Params_init(&(portsParams.hwiParams)); portsParams.hwiParams.arg = (uintptr_t) handle; portsParams.hwiParams.priority = hwAttrs->intPriority; object->hwiHandle = HwiP_create(hwAttrs->intNum, UARTMSP432_hwiIntFxn, &(portsParams.hwiParams)); if (object->hwiHandle == NULL) { DebugP_log1("UART:(%p) HwiP_create() failed", hwAttrs->baseAddr); UARTMSP432_close(handle); return (NULL); } SemaphoreP_Params_init(&(portsParams.semParams)); portsParams.semParams.mode = SemaphoreP_Mode_BINARY; if (params->writeMode == UART_MODE_BLOCKING) { /* If write mode is blocking create a semaphore and set callback. */ object->writeSem = SemaphoreP_create(0, &(portsParams.semParams)); if (object->writeSem == NULL) { DebugP_log1("UART:(%p) SemaphoreP_create() failed.", hwAttrs->baseAddr); UARTMSP432_close(handle); return (NULL); } object->writeCallback = &writeSemCallback; } else { /* UART_MODE_CALLBACK - Store application callback */ object->writeCallback = params->writeCallback; } if (params->readMode == UART_MODE_BLOCKING) { /* If read mode is blocking create a semaphore and set callback. */ object->readSem = SemaphoreP_create(0, &(portsParams.semParams)); if (object->readSem == NULL) { DebugP_log1("UART:(%p) SemaphoreP_create() failed.", hwAttrs->baseAddr); UARTMSP432_close(handle); return (NULL); } object->readCallback = &readSemCallback; ClockP_Params_init(&(portsParams.clockParams)); portsParams.clockParams.arg = (uintptr_t) handle; object->timeoutClk = ClockP_create((ClockP_Fxn) &readBlockingTimeout, &(portsParams.clockParams)); if (object->timeoutClk == NULL) { DebugP_log1("UART:(%p) ClockP_create() failed.", hwAttrs->baseAddr); UARTMSP432_close(handle); return (NULL); } } else { object->state.drainByISR = false; object->readCallback = params->readCallback; } /* * Initialize UART read buffer - will store received bytes until * UART_read is invoked. */ RingBuf_construct(&object->ringBuffer, hwAttrs->ringBufPtr, hwAttrs->ringBufSize); /* * Store UART parameters & initialize peripheral. These are used to * re/initialize the peripheral when opened or changing performance level. */ object->state.readMode = params->readMode; object->state.writeMode = params->writeMode; object->state.readReturnMode = params->readReturnMode; object->state.readDataMode = params->readDataMode; object->state.writeDataMode = params->writeDataMode; object->state.readEcho = params->readEcho; object->readTimeout = params->readTimeout; object->writeTimeout = params->writeTimeout; object->baudRate = params->baudRate; object->stopBits = params->stopBits; object->parityType = params->parityType; object->readFxns = staticFxnTable[object->state.readMode][object->state.readDataMode]; object->writeBuf = NULL; object->readBuf = NULL; object->writeCount = 0; object->readCount = 0; object->writeSize = 0; object->readSize = 0; object->state.writeCR = false; object->state.txEnabled = false; object->state.rxEnabled = true; initHw(object, hwAttrs, clockFreq); DebugP_log1("UART:(%p) opened", hwAttrs->baseAddr); /* Return the handle */ return (handle); }
/* * ======== CameraCC3200DMA_open ======== */ Camera_Handle CameraCC3200DMA_open(Camera_Handle handle, Camera_Params *params) { uintptr_t key; CameraCC3200DMA_Object *object = handle->object; CameraCC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; unsigned long hSyncPolarityConfig; unsigned long vSyncPolarityConfig; unsigned long byteOrderConfig; unsigned long interfaceSync; unsigned long pixelClkConfig; HwiP_Params hwiParams; SemaphoreP_Params semParams; /* If params are NULL use defaults. */ if (params == NULL) { params = (Camera_Params *) &Camera_defaultParams; } /* Timeouts cannot be 0 */ DebugP_assert((params->captureTimeout != 0)); /* Check that a callback is set */ DebugP_assert((params->captureMode != Camera_MODE_CALLBACK) || (params->captureCallback != NULL)); /* Disable preemption while checking if the Camera is open. */ key = HwiP_disable(); /* Check if the Camera is open already with the base addr. */ if (object->opened == true) { HwiP_restore(key); DebugP_log1("Camera:(%p) already in use.", hwAttrs->baseAddr); return (NULL); } object->opened = true; HwiP_restore(key); object->operationMode = params->captureMode; object->captureCallback = params->captureCallback; object->captureTimeout = params->captureTimeout; /* Set Camera variables to defaults. */ object->captureBuf = NULL; object->bufferlength = 0; object->frameLength = 0; object->inUse = 0; /* * Register power dependency. Keeps the clock running in SLP * and DSLP modes. */ Power_setDependency(PowerCC3200_PERIPH_CAMERA); Power_setDependency(PowerCC3200_PERIPH_UDMA); /* Disable the Camera interrupt. */ MAP_CameraIntDisable(hwAttrs->baseAddr, (CAM_INT_FE | CAM_INT_DMA)); HwiP_clearInterrupt(hwAttrs->intNum); /* Create Hwi object for the Camera peripheral. */ /* Register the interrupt for this Camera peripheral. */ HwiP_Params_init(&hwiParams); hwiParams.arg = (uintptr_t)handle; hwiParams.priority = hwAttrs->intPriority; object->hwiHandle = HwiP_create(hwAttrs->intNum, CameraCC3200DMA_hwiIntFxn, &hwiParams); if (object->hwiHandle == NULL) { CameraCC3200DMA_close(handle); return (NULL); } MAP_IntEnable(INT_CAMERA); SemaphoreP_Params_init(&semParams); semParams.mode = SemaphoreP_Mode_BINARY; /* If capture is blocking create a semaphore and set callback. */ if (object->operationMode == Camera_MODE_BLOCKING) { object->captureSem = SemaphoreP_create(0, &semParams); if (object->captureSem) { CameraCC3200DMA_close(handle); return (NULL); } object->captureCallback = &captureSemCallback; } MAP_CameraReset(hwAttrs->baseAddr); if (params->hsyncPolarity == Camera_HSYNC_POLARITY_HIGH) { hSyncPolarityConfig = CAM_HS_POL_HI; } else { hSyncPolarityConfig = CAM_HS_POL_LO; } if (params->vsyncPolarity == Camera_VSYNC_POLARITY_HIGH) { vSyncPolarityConfig = CAM_VS_POL_HI; } else { vSyncPolarityConfig = CAM_VS_POL_LO; } if (params->byteOrder == Camera_BYTE_ORDER_SWAP) { byteOrderConfig = CAM_ORDERCAM_SWAP; } else { byteOrderConfig = 0; } if (params->interfaceSync == Camera_INTERFACE_SYNC_OFF) { interfaceSync = CAM_NOBT_SYNCHRO; } else { interfaceSync = CAM_NOBT_SYNCHRO | CAM_IF_SYNCHRO | CAM_BT_CORRECT_EN; } if (params->pixelClkConfig == Camera_PCLK_CONFIG_RISING_EDGE) { pixelClkConfig = CAM_PCLK_RISE_EDGE; } else { pixelClkConfig = CAM_PCLK_FALL_EDGE; } MAP_CameraParamsConfig(hwAttrs->baseAddr, hSyncPolarityConfig, vSyncPolarityConfig, byteOrderConfig | interfaceSync | pixelClkConfig); /*Set the clock divider based on the output clock */ MAP_CameraXClkConfig(hwAttrs->baseAddr, PRCMPeripheralClockGet(PRCM_CAMERA), params->outputClock); /*Setting the FIFO threshold for a DMA request */ MAP_CameraThresholdSet(hwAttrs->baseAddr, 8); MAP_CameraIntEnable(hwAttrs->baseAddr, (CAM_INT_FE | CAM_INT_DMA)); MAP_CameraDMAEnable(hwAttrs->baseAddr); DebugP_log1("Camera:(%p) opened", hwAttrs->baseAddr); /* Return the handle */ return (handle); }
/* * ======== SPICC3200DMA_open ======== * @pre Function assumes that the handle is not NULL */ SPI_Handle SPICC3200DMA_open(SPI_Handle handle, SPI_Params *params) { uintptr_t key; SPICC3200DMA_Object *object = handle->object; SPICC3200DMA_HWAttrs const *hwAttrs = handle->hwAttrs; SemaphoreP_Params semParams; HwiP_Params hwiParams; key = HwiP_disable(); if(object->isOpen == true) { HwiP_restore(key); return (NULL); } object->isOpen = true; HwiP_restore(key); if (params == NULL) { params = (SPI_Params *) &SPI_defaultParams; } DebugP_assert((params->dataSize >= 4) && (params->dataSize <= 32)); /* Determine if we need to use an 8, 16 or 32-bit frameSize for the DMA */ if (params->dataSize <= 8) { object->frameSize = SPICC3200DMA_8bit; } else if (params->dataSize <= 16) { object->frameSize = SPICC3200DMA_16bit; } else { object->frameSize = SPICC3200DMA_32bit; } /* Store SPI mode of operation */ object->spiMode = params->mode; object->transferMode = params->transferMode; object->transaction = NULL; object->rxFifoTrigger = (1 << object->frameSize); object->txFifoTrigger = (1 << object->frameSize); object->bitRate = params->bitRate; object->frameFormat = params->frameFormat; object->dataSize = params->dataSize; /* Register power dependency - i.e. power up and enable clock for SPI. */ Power_setDependency(getPowerMgrId(hwAttrs->baseAddr)); Power_setDependency(PowerCC3200_PERIPH_UDMA); Power_registerNotify(&(object->notifyObj), PowerCC3200_AWAKE_LPDS, SPICC3200DMA_postNotify, (uintptr_t)handle); HwiP_Params_init(&hwiParams); hwiParams.arg = (uintptr_t)handle; hwiParams.priority = hwAttrs->intPriority; object->hwiHandle = HwiP_create(hwAttrs->intNum, SPICC3200DMA_hwiFxn, &hwiParams); if (object->hwiHandle == NULL) { SPICC3200DMA_close(handle); return (NULL); } if (object->transferMode == SPI_MODE_BLOCKING) { DebugP_log1("SPI:(%p) in SPI_MODE_BLOCKING mode", hwAttrs->baseAddr); SemaphoreP_Params_init(&semParams); semParams.mode = SemaphoreP_Mode_BINARY; object->transferComplete = SemaphoreP_create(0, &semParams); if (object->transferComplete == NULL) { SPICC3200DMA_close(handle); return (NULL); } object->transferCallbackFxn = SPICC3200DMA_transferCallback; } else { DebugP_log1("SPI:(%p) in SPI_MODE_CALLBACK mode", hwAttrs->baseAddr); DebugP_assert(params->transferCallbackFxn != NULL); object->transferCallbackFxn = params->transferCallbackFxn; } if (uDMAControlBase == NULL) { uDMAControlBase = MAP_uDMAControlBaseGet(); } SPICC3200DMA_initHw(handle); DebugP_log3("SPI:(%p) CPU freq: %d; SPI freq to %d", hwAttrs->baseAddr, PRCMPeripheralClockGet(hwAttrs->spiPRCM), params->bitRate); DebugP_log1("SPI:(%p) opened", hwAttrs->baseAddr); return (handle); }
/* * ======== WatchdogMSP432_open ======== */ Watchdog_Handle WatchdogMSP432_open(Watchdog_Handle handle, Watchdog_Params *params) { uintptr_t key; HwiP_Params hwiParams; WatchdogMSP432_Object *object = handle->object; WatchdogMSP432_HWAttrs const *hwAttrs = handle->hwAttrs; /* If params are NULL use defaults. */ if (params == NULL) { params = (Watchdog_Params *) &Watchdog_defaultParams; } /* Ensure a callbackFxn is specified if using watchdog in interval mode */ DebugP_assert((params->resetMode == Watchdog_RESET_ON) || (params->callbackFxn != NULL)); /* Don't allow preemption */ key = HwiP_disable(); /* Check if the Watchdog is open already with the HWAttrs */ if (object->isOpen) { HwiP_restore(key); DebugP_log1("Watchdog: Handle %x already in use.", (uintptr_t) handle); return (NULL); } object->isOpen = true; HwiP_restore(key); /* * Add power management support - Disable performance transitions while * opening the driver. */ Power_setConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); if (params->resetMode == Watchdog_RESET_ON || hwAttrs->clockSource == WDT_A_CLOCKSOURCE_SMCLK || hwAttrs->clockSource == WDT_A_CLOCKSOURCE_ACLK) { /* * Do not support power modes lower than LPM0 if in watchdog mode or * in interval mode and using SMCLK or ACLK as clock sources. * Additionally, LPM3.5 cannot be reached. */ Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_0); Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_0); } else { /* * Interval mode and not using SMCLK and ACLK as clock sources. Can * be configured as a LPM3.5 wake up source, so we do not set the * SHUTDOWN_0 constraint. */ Power_setConstraint(PowerMSP432_DISALLOW_DEEPSLEEP_1); } /* SHUTDOWN_1 (LPM4.5) not supported while driver is open */ Power_setConstraint(PowerMSP432_DISALLOW_SHUTDOWN_1); /* Construct Hwi object for watchdog */ if (params->callbackFxn) { HwiP_Params_init(&hwiParams); hwiParams.arg = (uintptr_t) handle; hwiParams.priority = hwAttrs->intPriority; object->hwiHandle = HwiP_create(hwAttrs->intNum, params->callbackFxn, &hwiParams); if (!object->hwiHandle) { DebugP_log0("Watchdog: HwiP_create() failed"); Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); WatchdogMSP432_close(handle); return (NULL); } } /* Configure and initialize WDT */ object->resetMode = params->resetMode; if (object->resetMode == Watchdog_RESET_ON) { MAP_WDT_A_initWatchdogTimer(hwAttrs->clockSource, hwAttrs->clockDivider); } else { MAP_WDT_A_initIntervalTimer(hwAttrs->clockSource, hwAttrs->clockDivider); } MAP_WDT_A_startTimer(); /* Allow performance level changes */ Power_releaseConstraint(PowerMSP432_DISALLOW_PERF_CHANGES); DebugP_log1("Watchdog: (0x%x) opened and enabled.", (uintptr_t) handle); /* Return handle of the Watchdog object */ return (handle); }
/* * ======== 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); }