void motorSetup() { /* Set pin mode for Hbridge output pins */ MAP_PinTypeGPIO(AIN1, PIN_MODE_0, false); /* Ain 1 */ MAP_PinTypeGPIO(AIN2, PIN_MODE_0, false); /* Bin 1 */ MAP_PinTypeGPIO(BIN1, PIN_MODE_0, false); /* Bin 2 */ MAP_PinTypeGPIO(BIN2, PIN_MODE_0, false); /* Ain 2 */ /* Get port name and bin number from GPIO number (TI lookup table) */ GPIO_IF_GetPortNPin(AIN1x, &port_ain1, &pin_ain1); GPIO_IF_GetPortNPin(AIN2x, &port_ain2, &pin_ain2); GPIO_IF_GetPortNPin(BIN1x, &port_bin1, &pin_bin1); GPIO_IF_GetPortNPin(BIN2x, &port_bin2, &pin_bin2); /* Set pin direction */ GPIODirModeSet(port_ain1, pin_ain1, 1); GPIODirModeSet(port_ain2, pin_ain2, 1); GPIODirModeSet(port_bin1, pin_bin1, 1); GPIODirModeSet(port_bin2, pin_bin2, 1); /* Set value to write to PIN */ bitA1 = 1 << (AIN1x % 8); bitA2 = 1 << (AIN2x % 8); bitB1 = 1 << (BIN1x % 8); bitB2 = 1 << (BIN2x % 8); // Enable timer A peripheral MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA0); // Split channels and configure for periodic interrupts MAP_TimerConfigure(TIMERA0_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_PERIODIC | TIMER_CFG_B_PERIODIC); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_A, 0); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_B, 0); // Set compare interrupt MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMA_MATCH); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_MATCH); // Configure compare interrupt, start with 0 speed MAP_TimerMatchSet(TIMERA0_BASE, TIMER_A, 0); MAP_TimerMatchSet(TIMERA0_BASE, TIMER_B, 0); // Set timeout interrupt MAP_TimerIntRegister(TIMERA0_BASE, TIMER_A, TimerBaseIntHandlerA); MAP_TimerIntRegister(TIMERA0_BASE, TIMER_B, TimerBaseIntHandlerB); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMA_TIMEOUT); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_TIMEOUT); // Turn on timers MAP_TimerLoadSet(TIMERA0_BASE, TIMER_A, MOTOR_PRESCALER); MAP_TimerLoadSet(TIMERA0_BASE, TIMER_B, MOTOR_PRESCALER); MAP_TimerEnable(TIMERA0_BASE, TIMER_A); MAP_TimerEnable(TIMERA0_BASE, TIMER_B); }
void motorSetup() { pinMode(AIN1x, OUTPUT); pinMode(AIN2x, OUTPUT); pinMode(BIN1x, OUTPUT); pinMode(BIN2x, OUTPUT); bitA1 = digitalPinToBitMask(AIN1x); bitA2 = digitalPinToBitMask(AIN2x); bitB1 = digitalPinToBitMask(BIN1x); bitB2 = digitalPinToBitMask(BIN2x); portA1 = digitalPinToPort(AIN1x); portA2 = digitalPinToPort(AIN2x); portB1 = digitalPinToPort(BIN1x); portB2 = digitalPinToPort(BIN2x); baseA1 = (uint32_t) portBASERegister(portA1); baseA2 = (uint32_t) portBASERegister(portA2); baseB1 = (uint32_t) portBASERegister(portB1); baseB2 = (uint32_t) portBASERegister(portB2); // Enable timer A peripheral MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA0); // Split channels and configure for periodic interrupts MAP_TimerConfigure(TIMERA0_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_PERIODIC | TIMER_CFG_B_PERIODIC); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_A, 0); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_B, 0); // Set compare interrupt MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMA_MATCH); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_MATCH); // Configure compare interrupt, start with 0 speed MAP_TimerMatchSet(TIMERA0_BASE, TIMER_A, 0); MAP_TimerMatchSet(TIMERA0_BASE, TIMER_B, 0); // Set timeout interrupt MAP_TimerIntRegister(TIMERA0_BASE, TIMER_A, TimerBaseIntHandlerA); MAP_TimerIntRegister(TIMERA0_BASE, TIMER_B, TimerBaseIntHandlerB); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMA_TIMEOUT); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_TIMEOUT); // Turn on timers MAP_TimerLoadSet(TIMERA0_BASE, TIMER_A, MOTOR_PRESCALER); MAP_TimerLoadSet(TIMERA0_BASE, TIMER_B, MOTOR_PRESCALER); MAP_TimerEnable(TIMERA0_BASE, TIMER_A); MAP_TimerEnable(TIMERA0_BASE, TIMER_B); }
void tone(uint8_t pin, unsigned int frequency, unsigned long duration) { /* Use TIMERA0B since it is not on any pin */ tone_timer = digitalPinToTimer(pin); if(tone_timer == NOT_ON_TIMER) return; if(tone_state != 0 && pin != current_pin) return; g_duration = duration; current_pin = pin; tone_state = 2; MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA0); MAP_TimerConfigure(TIMERA0_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_B_PERIODIC); MAP_TimerIntRegister(TIMERA0_BASE, TIMER_B, ToneIntHandler); MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_TIMEOUT); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_B, 7); MAP_TimerLoadSet(TIMERA0_BASE, TIMER_B, (F_CPU / 8) / 1000); MAP_TimerEnable(TIMERA0_BASE, TIMER_B); PWMWrite(pin, 256, 128, frequency); }
//**************************************************************************** // //! Setup the timer in PWM mode //! //! \param ulBase is the base address of the timer to be configured //! \param ulTimer is the timer to be setup (TIMER_A or TIMER_B) //! \param ulConfig is the timer configuration setting //! \param ucInvert is to select the inversion of the output //! //! This function //! 1. The specified timer is setup to operate as PWM //! //! \return None. // //**************************************************************************** void SetupTimerPWMMode(unsigned long ulBase, unsigned long ulTimer, unsigned long ulConfig, unsigned char ucInvert) { // // Set GPT - Configured Timer in PWM mode. // MAP_TimerConfigure(ulBase,ulConfig); MAP_TimerPrescaleSet(ulBase,ulTimer,0); // // Inverting the timer output if required // MAP_TimerControlLevel(ulBase,ulTimer,ucInvert); // // Load value set to ~0.5 ms time period // MAP_TimerLoadSet(ulBase,ulTimer,TIMER_INTERVAL_RELOAD); // // Match value set so as to output level 0 // MAP_TimerMatchSet(ulBase,ulTimer,TIMER_INTERVAL_RELOAD); }
/* * @brief Initialize MSP430. * * use 400us interrupt for SPI comms. This lets us xmit our 24-byte message in 9.6 * ms. At the end, we use a 32us interrupt for SPI comms. This is about as fast * as the MSP430 can read bytes from the buffer. This double byte signals the end of the * message for synchronizing the two processors * @returns void */ void msp430Init(void) { // Set up the message index MSP430MessageIdx = 0; // Default expand0 to off expand0Disable(); // timer 1a is used for the ir interrupt. timer 1b is used for the MSP430 message interrupt //ir_init initializes the timer 1, so timer1 shouldn't be enabled and configured here //MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER1); //MAP_TimerConfigure(TIMER1_BASE, TIMER_CFG_16_BIT_PAIR | TIMER_CFG_A_PERIODIC | TIMER_CFG_B_ONE_SHOT); // end shared timer init code MAP_TimerIntEnable(TIMER1_BASE, TIMER_TIMB_TIMEOUT); MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, MSP430_SPI_BYTE_PERIOD); MAP_TimerEnable(TIMER1_BASE, TIMER_B); // Enable the interrupt in the NVIC with the right priority for FreeRTOS IntPrioritySet(INT_TIMER1B, SYSTEM_INTERRUPT_PRIORITY); MAP_IntEnable(INT_TIMER1B); // Have a flag to show the first valid communication from the MSP430 systemMSP430CommsValid = FALSE; // Set up normal operations between the MSP430 and the 8962 systemMSP430Command = MSP430_CMD_COMMAND_NORMAL; checksumFailure = 0; }
static void EmitStart(unsigned long nDelay) { // 10Hz MAP_TimerLoadSet(s_ulTimerEmitCtrl,TIMER_A,nDelay);//g_ulE0Delay[s_nEmitIndex]); // Enable GPT MAP_TimerEnable(s_ulTimerEmitCtrl,TIMER_A); }
//**************************************************************************** // //! The delay function uses timer to implement the delay time in milliseconds //! //! \param time in millisecond // //! \return void //**************************************************************************** static void delay(int time_ms) { // Initialize Timer 0B as one-shot down counter. MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA0); MAP_TimerConfigure(TIMERA0_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_B_ONE_SHOT); MAP_TimerPrescaleSet(TIMERA0_BASE, TIMER_B, PRESCALE); //Load the value in milisecond MAP_TimerLoadSet(TIMERA0_BASE, TIMER_B, MILLISECONDS_TO_TICKS(time_ms)); // Enable the timer MAP_TimerEnable(TIMERA0_BASE, TIMER_B); //Stall during debug MAP_TimerControlStall(TIMERA0_BASE, TIMER_B, 1); // Enable interrupt upon Time-out MAP_TimerIntEnable(TIMERA0_BASE, TIMER_TIMB_TIMEOUT); // Clear Interrupt Flag MAP_TimerIntClear(TIMERA0_BASE, MAP_TimerIntStatus(TIMERA0_BASE, true)); //Wait until timer time-out while (MAP_TimerIntStatus(TIMERA0_BASE, true) != TIMER_TIMB_TIMEOUT){} //Disable the timer MAP_TimerDisable(TIMERA0_BASE, TIMER_B); //Disable Interrupt MAP_TimerIntDisable(TIMERA0_BASE, TIMER_TIMB_TIMEOUT); MAP_TimerIntUnregister(TIMERA0_BASE, TIMER_B); }
//***************************************************************************** // //! starts the timer //! //! \param ulBase is the base address for the timer. //! \param ulTimer selects amoung the TIMER_A or TIMER_B or TIMER_BOTH. //! \param ulValue is the time delay in mSec after that run out, //! timer gives an interrupt. //! //! This function //! 1. Load the Timer with the specified value. //! 2. enables the timer. //! //! \return none //! //! \Note- HW Timer runs on 80MHz clock // //***************************************************************************** void Timer_IF_Start(unsigned long ulBase, unsigned long ulTimer, unsigned long ulValue) { MAP_TimerLoadSet(ulBase,ulTimer,MILLISECONDS_TO_TICKS(ulValue)); // // Enable the GPT // MAP_TimerEnable(ulBase,ulTimer); }
static i32 hwt32_config_periodic(struct hw_timer32 *hwt, u32 expires) { /* Count downwards from value of 'expires' to zero */ MAP_TimerConfigure(hwt->base_addr, TIMER_CFG_PERIODIC); MAP_TimerLoadSet(hwt->base_addr, TIMER_A, expires); /* Countdown value */ hwt->irq_mask = TIMER_TIMA_TIMEOUT; /* IRQ: when down counter reaches 0*/ return 0; }
//***************************************************************************** // //! Initializes the CPU usage measurement module. //! //! \param ulClockRate is the rate of the clock supplied to the timer module. //! \param ulRate is the number of times per second that CPUUsageTick() is //! called. //! \param ulTimer is the index of the timer module to use. //! //! This function prepares the CPU usage measurement module for measuring the //! CPU usage of the application. //! //! \return None. // //***************************************************************************** void CPUUsageInit(unsigned long ulClockRate, unsigned long ulRate, unsigned long ulTimer) { // // Check the arguments. // ASSERT(ulClockRate > ulRate); ASSERT(ulTimer < 4); // // Save the timer index. // g_ulCPUUsageTimer = ulTimer; // // Determine the number of system clocks per measurement period. // g_ulCPUUsageTicks = ulClockRate / ulRate; // // Set the previous value of the timer to the initial timer value. // g_ulCPUUsagePrevious = 0xffffffff; // // Enable peripheral clock gating. // MAP_SysCtlPeripheralClockGating(true); // // Enable the third timer while the processor is in run mode, but disable // it in sleep mode. It will therefore count system clocks when the // processor is running but not when it is sleeping. // MAP_SysCtlPeripheralEnable(g_pulCPUUsageTimerPeriph[ulTimer]); MAP_SysCtlPeripheralSleepDisable(g_pulCPUUsageTimerPeriph[ulTimer]); // // Configure the third timer for 32-bit periodic operation. // MAP_TimerConfigure(g_pulCPUUsageTimerBase[ulTimer], TIMER_CFG_PERIODIC); // // Set the load value for the third timer to the maximum value. // MAP_TimerLoadSet(g_pulCPUUsageTimerBase[ulTimer], TIMER_A, 0xffffffff); // // Enable the third timer. It will now count the number of system clocks // during which the processor is executing code. // MAP_TimerEnable(g_pulCPUUsageTimerBase[ulTimer], TIMER_A); }
static i32 hwt32_config_monotone(struct hw_timer32 *hwt, u32 expires) { /* Count upwards until counter value matches 'expires' */ MAP_TimerConfigure(hwt->base_addr, TIMER_CFG_PERIODIC_UP); MAP_TimerLoadSet(hwt->base_addr, TIMER_A, 0xFFFFFFFF); /* Rollover Val */ MAP_TimerMatchSet(hwt->base_addr, TIMER_A, expires); /* User match Val */ /* IRQ(s) when up counter rollsover and counter reaches 'expires' */ hwt->irq_mask = TIMER_TIMA_TIMEOUT | TIMER_TIMA_MATCH; return 0; }
void SysTimerConfig(void) { /// Enable TIMER0 MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0); /// Configure TIMER0 MAP_TimerConfigure(TIMER0_BASE, TIMER_CFG_A_PERIODIC); MAP_TimerLoadSet(TIMER0_BASE,TIMER_A, MAP_SysCtlClockGet()/100); MAP_TimerEnable(TIMER0_BASE, TIMER_A); /// \todo Set it statically? TimerIntRegister(TIMER0_BASE, TIMER_A, SysTimerHandler); MAP_TimerIntEnable(TIMER0_BASE, TIMER_TIMA_TIMEOUT); }
void hw_timer0a_set_timeout(unsigned long uS) { #ifdef DEBUG if (uS > 1000000) { dbg_puts("uS > 1000000"); dbg_trace(); tn_halt(); } #endif // DEBUG MAP_TimerLoadSet(TIMER0_BASE, TIMER_A, MAP_SysCtlClockGet() / 1000000 * uS); }
/* * @brief * This method is used to initialize the MSP430 and interrupts for the BSL * @returns void */ void msp430BSLInit(void){ MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, MSP430_BSL_BYTE_PERIOD); MAP_TimerEnable(TIMER1_BASE, TIMER_B); armState = ARM_STATE_SYNC; spiState = SPI_STATE_XMIT; currentSection = 0; dataStartAddress = MSP430_PROGRAM[currentSection].MSP430_SECTION_ADDRESS; dataIndex = 0; dataLength = 0; transmissionState = BSL_VALID_TRANSMISSION; blinkyLEDToggleState = FALSE; setMSP430SPIOperationState(MSP430_SPI_BOOT_LOADER_MODE); }
void hw_timer1a_start_once(unsigned long uS) { #ifdef DEBUG if (uS > 1000000) { dbg_puts("uS > 1000000"); dbg_trace(); tn_halt(); } #endif // DEBUG MAP_TimerLoadSet(TIMER1_BASE, TIMER_A, MAP_SysCtlClockGet() / 1000000 * uS); MAP_TimerEnable(TIMER1_BASE, TIMER_A); }
void controller_setup(){ // Enable timer A peripheral MAP_PRCMPeripheralClkEnable(PRCM_TIMERA1, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA1); // Configure one channel for periodic interrupts MAP_TimerConfigure(TIMERA1_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_PERIODIC); MAP_TimerPrescaleSet(TIMERA1_BASE, TIMER_A, IMU_CONTROLLER_PRESCALER); // Set timeout interrupt MAP_TimerIntRegister(TIMERA1_BASE, TIMER_A, ControllerIntHandler); MAP_TimerIntEnable(TIMERA1_BASE, TIMER_TIMA_TIMEOUT); // Turn on timers MAP_TimerLoadSet(TIMERA1_BASE, TIMER_A, IMU_CONTROLLER_STARTUP); MAP_TimerEnable(TIMERA1_BASE, TIMER_A); }
void OneMsTaskTimer::start(uint32_t timer_index) { uint32_t load = (F_CPU / 1000); //// !!!! count = 0; overflowing = 0; // Base address for first timer g_ulBase = TIMERA0_BASE + (timer_index <<12); // Configuring the timers MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0 + timer_index, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA0 + timer_index); MAP_TimerConfigure(g_ulBase,TIMER_CFG_PERIODIC); MAP_TimerPrescaleSet(g_ulBase,TIMER_A,0); // Setup the interrupts for the timer timeouts. MAP_TimerIntRegister(g_ulBase, TIMER_A, OneMsTaskTimer_int); MAP_TimerIntEnable(g_ulBase, TIMER_TIMA_TIMEOUT); // Turn on the timers MAP_TimerLoadSet(g_ulBase,TIMER_A, load); // Enable the GPT MAP_TimerEnable(g_ulBase,TIMER_A); }
void odometer_controller_setup(void){ //acc_value_startup = get_accelerometer_default_offset(); // Enable timer A peripheral MAP_PRCMPeripheralClkEnable(PRCM_TIMERA3, PRCM_RUN_MODE_CLK); MAP_PRCMPeripheralReset(PRCM_TIMERA3); // Configure one channel for periodic interrupts MAP_TimerConfigure(TIMERA3_BASE, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_PERIODIC); MAP_TimerPrescaleSet(TIMERA3_BASE, TIMER_A, ODOMETER_CONTROLLER_PRESCALER); // Set timeout interrupt MAP_TimerIntRegister(TIMERA3_BASE, TIMER_A, OdometerControllerIntHandler); MAP_TimerIntEnable(TIMERA3_BASE, TIMER_TIMA_TIMEOUT); // Turn on timers MAP_TimerLoadSet(TIMERA3_BASE, TIMER_A, ODOMETER_CONTROLLER_STARTUP); MAP_TimerEnable(TIMERA3_BASE, TIMER_A); }
uint8 bottomBoardISR() { uint32 data, i; uint32 timerLoadPeriod; uint8 checksum; long val; TimerIntClear(TIMER1_BASE, TIMER_TIMB_TIMEOUT); // Multiplex SPI (bottomboard/radio) if (MSPSPIState == MSPSPI_STATE_XMIT_BYTE) { radioIntDisable(); SPISelectDeviceISR(SPI_MSP430); timerLoadPeriod = MSP430_SPI_DESELECT_PERIOD; } else if (MSPSPIState == MSPSPI_STATE_DESELECT_SPI) { SPIDeselectISR(); radioIntEnable(); if (bootloaderSet && MSP430MessageIdx == 0) { // Deselect but then set the boot-loader to operate. msp430BSLInit(); bootloaderSet = FALSE; } else { timerLoadPeriod = MSP430_SPI_BYTE_PERIOD; } } // Set delay MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, timerLoadPeriod); MAP_TimerEnable(TIMER1_BASE, TIMER_B); // Transmit message to bottomboard if (MSPSPIState == MSPSPI_STATE_XMIT_BYTE) { // Pack new message at the beginning of each cycle if (MSP430MessageIdx == 0) { // Pack code for (i = 0; i < MSP430_CODE_LENGTH; i++) { MSP430MessageOut[i] = MSP430Code[i]; } // Build and pack payload switch (msp430SystemGetCommandMessage()) { case MSP430_CMD_COMMAND_NORMAL: blinkySystemBuildMessage(&MSP430MessageOut[MSP430_CMD_SYSTEM_LED_IDX]); buttonsBuildMessage(&MSP430MessageOut[MSP430_CMD_BUTTONS_IDX]); ledsBuildMessage(&MSP430MessageOut[MSP430_CMD_LED_IDX]); break; case MSP430_CMD_COMMAND_REPROGRAM: bootloaderSet = TRUE; break; default: // Do nothing for shutdown or reset break; } msp430SystemCommandBuildMessage(&MSP430MessageOut[MSP430_CMD_COMMAND_IDX]); MSP430MessageOut[MSP430_CMD_CHECKSUM_IDX] = messageChecksum(MSP430MessageOut, MSP430_CODE_LENGTH, MSP430_MSG_LENGTH); } // Shift receive buffer shiftBuffer(MSP430MessageIn, MSP430_MSG_LENGTH); // Put data into the transmit buffer val = MAP_SSIDataPutNonBlocking(SSI0_BASE, (uint32)MSP430MessageOut[MSP430MessageIdx]); if (val == 0) { SPIBusError_SSIDataPutNonBlocking = 1; } // Retrieve the received byte MAP_SSIDataGet(SSI0_BASE, &data); // Put byte the the end of the receive buffer MSP430MessageIn[MSP430_MSG_LENGTH - 1] = data; // Check to see if we have a complete message, with correct code and checksum if (MSP430MessageIdx == 0) { // Checkcode for (i = 0; i < MSP430_CODE_LENGTH; i++) { if (MSP430MessageIn[i] != MSP430Code[i]) break; } if (i == MSP430_CODE_LENGTH) { // Checksum checksum = messageChecksum(MSP430MessageIn, MSP430_CODE_LENGTH, MSP430_MSG_LENGTH); if (checksum == MSP430MessageIn[MSP430_MSG_LENGTH - 1]) { // Process incoming message bumpSensorsUpdate(MSP430MessageIn[MSP430_MSG_BUMPER_IDX]); accelerometerUpdate(&MSP430MessageIn[MSP430_MSG_ACCEL_START_IDX]); gyroUpdate(&MSP430MessageIn[MSP430_MSG_GYRO_START_IDX]); systemBatteryVoltageUpdate(MSP430MessageIn[MSP430_MSG_VBAT_IDX]); systemUSBVoltageUpdate(MSP430MessageIn[MSP430_MSG_VUSB_IDX]); systemPowerButtonUpdate(MSP430MessageIn[MSP430_MSG_POWER_BUTTON_IDX]); systemMSPVersionUpdate(MSP430MessageIn[MSP430_MSG_VERSION_IDX]); reflectiveSensorsUpdate(&MSP430MessageIn[MSP430_MSG_REFLECT_START_IDX]); if((MSP430MessageIn[MSP430_MSG_VERSION_IDX] != 0) && (!systemMSP430CommsValid)) { systemMSP430CommsValid = TRUE; } } else { checksumFailure++; // Fail checksum if (showError) {cprintf("Bsum ");} } } else { // Fail checkcode if (showError) {cprintf("Bcod ");} } // Toggle MSP boards, regardless of result if (expand0En) { MSPSelect = MSP_EXPAND0_BOARD_SEL; } } // Increment index, wrap back to 0 if it exceeds the range MSP430MessageIdx++; if (MSP430MessageIdx >= MSP430_MSG_LENGTH) { MSP430MessageIdx = 0; } // Toggle states MSPSPIState = MSPSPI_STATE_DESELECT_SPI; } else if (MSPSPIState == MSPSPI_STATE_DESELECT_SPI) { // Toggle states MSPSPIState = MSPSPI_STATE_XMIT_BYTE; } return 0; }
//***************************************************************************** // //! starts the timer //! //! \param ulBase is the base address for the timer. //! \param ulTimer selects between the TIMER A and TIMER B. //! \param ulValue is timer reload value (mSec) after which the timer will run out and gives an interrupt. //! //! This function //! 1. Reload the Timer with the specified value. //! //! \return none // //***************************************************************************** void Timer_IF_ReLoad(unsigned long ulBase, unsigned long ulTimer, unsigned long ulValue) { MAP_TimerLoadSet(ulBase,ulTimer,MILLISECONDS_TO_TICKS(ulValue)); }
/* * @brief MSP430 Boot Loader Handler * * This method sends bytes periodically to the MSP430 to handle the boot loader function * It transmits bytes about every 32us, which is about as fast as the MSP430 can Handle * @returns void */ void msp430BSLHandler(){ uint32 data; // clear the timer interrupt for the next time TimerIntClear(TIMER1_BASE, TIMER_TIMB_TIMEOUT); if(spiState == SPI_STATE_DESELECT){ SPIDeselectISR(); spiState = SPI_STATE_XMIT; MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, MSP430_BSL_BYTE_PERIOD); MAP_TimerEnable(TIMER1_BASE, TIMER_B); } else if(spiState == SPI_STATE_XMIT){ //get ready to transmit and set spiState to deselect soon SPISelectDeviceISR(SPI_MSP430); spiState = SPI_STATE_DESELECT; MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, MSP430_BSL_DESELECT_PERIOD); MAP_TimerEnable(TIMER1_BASE, TIMER_B); switch(armState){ case ARM_STATE_SYNC: { uint32 i; // short delay to make sure the bottomboard is ready for (i = 0; i < 10000; i++); // Send a ready message and wait for a response that the MSP is also ready armMessage = (ARM_MSG_VALID_MSG_BITS | ARM_MSG_READY_BIT); MAP_SSIDataPutNonBlocking(SSI0_BASE, (uint32)armMessage); MAP_SSIDataGet(SSI0_BASE, &data); if((uint8)data == (MSP430_MSG_VALID_MSG_BITS | MSP430_MSG_READY_BIT)) { armState = ARM_STATE_INIT_TRANSMISSION_1; } else { // Failure this time, try again armState = ARM_STATE_SYNC; } break; } case ARM_STATE_INIT_TRANSMISSION_1: // Send the message that we want to start armMessage = (ARM_MSG_VALID_MSG_BITS | ARM_MSG_NEW_TRANS_BIT); MAP_SSIDataPutNonBlocking(SSI0_BASE, (uint32)armMessage); MAP_SSIDataGet(SSI0_BASE, &data); // Get the response armState = ARM_STATE_INIT_TRANSMISSION_2; break; case ARM_STATE_INIT_TRANSMISSION_2: // Get the response back, data that is sent is junk armMessage = (ARM_MSG_VALID_MSG_BITS | ARM_MSG_READY_BIT); MAP_SSIDataPutNonBlocking(SSI0_BASE, (uint32)armMessage); MAP_SSIDataGet(SSI0_BASE, &data); if((uint8)data == (MSP430_MSG_VALID_MSG_BITS | MSP430_MSG_CONFIRM_BIT)){ // Toggle the Blinky LED blinkyLEDToggleState = !blinkyLEDToggleState; blinkyLedSet(blinkyLEDToggleState); //the last transmission was validated. We need to set up a new section of data for TX if(transmissionState == BSL_VALID_TRANSMISSION){ if(dataIndex == MSP430_PROGRAM[currentSection].MSP430_SECTION_SIZE){ // the previous data transmission included the last portion of the previous data section // so we need to increment the currentSection variable to indicate we are now on the next // data section currentSection++; dataStartAddress = MSP430_PROGRAM[currentSection].MSP430_SECTION_ADDRESS; dataIndex = 0; } else { //The previous data transmission left off somewhere in the middle of a large chunk of data. dataStartAddress = MSP430_PROGRAM[currentSection].MSP430_SECTION_ADDRESS + dataIndex; } } else if(transmissionState == BSL_INVALID_TRANSMISSION){ //last section of data failed validation. Bring dataIndex back to the starting address //of previous section for retransmission dataIndex = 0; transmissionState = BSL_VALID_TRANSMISSION; } // Calculate the length of the data to send if((dataIndex + 64) > MSP430_PROGRAM[currentSection].MSP430_SECTION_SIZE){ //we cannot construct another transmission of 64 bytes so we need to make the message //end at the end of section of data. dataLength = MSP430_PROGRAM[currentSection].MSP430_SECTION_SIZE - dataIndex; } else { dataLength = 64; } // Set up the data fields setupData[0] = dataLength; setupData[1] = (uint8)(dataStartAddress >> 8); setupData[2] = (uint8)(dataStartAddress); checksum = calcMessageChecksum(setupData, 0, 3); setupData[3] = (uint8)(checksum >> 8); setupData[4] = (uint8)checksum; setupIndex = 0; armState = ARM_STATE_SETUP_TRANSMISSION; } else {
//***************************************************************************** // //! Main test implementation function //! //! It uses 3 different timers to test that interrupts can be enabled //! and disabled successfully and that preemption occurs as expected when //! different priority levels are assigned. // //! \return Returns 1 on Success. // //***************************************************************************** int DoInterruptTest() { tTestResult eResult; // // indicate that the test is started. // UART_PRINT("Interrupt test starting...\n\r\n\r"); // // Assume we will pass until we determine otherwise. // eResult = TEST_PASSED; // // Perform any required initialization prior to performing the test. // InterruptTestInit(); // // Set up the 3 timers we use in this test. Timer A0 - 500uS. // Timer A1 - 500 uS. Timer A2 - 500 uS // MAP_TimerConfigure(TIMERA0_BASE, TIMER_CFG_ONE_SHOT); MAP_TimerLoadSet(TIMERA0_BASE, TIMER_A, MICROSECONDS_TO_TICKS(SLOW_TIMER_DELAY_uS/4)); MAP_TimerConfigure(TIMERA1_BASE, TIMER_CFG_ONE_SHOT); MAP_TimerLoadSet(TIMERA1_BASE, TIMER_A, MICROSECONDS_TO_TICKS(SLOW_TIMER_DELAY_uS/4)); MAP_TimerConfigure(TIMERA2_BASE, TIMER_CFG_ONE_SHOT); MAP_TimerLoadSet(TIMERA2_BASE, TIMER_A, MICROSECONDS_TO_TICKS(SLOW_TIMER_DELAY_uS/4)); // // Hook our interrupt handlers // MAP_TimerIntRegister(TIMERA0_BASE, TIMER_A, TimerA0IntHandler); MAP_TimerIntRegister(TIMERA1_BASE, TIMER_A, TimerA1IntHandler); MAP_TimerIntRegister(TIMERA2_BASE, TIMER_A, TimerA2IntHandler); UART_PRINT("Equal Priorities Testing. A0=A1=A2 \n\r"); UART_PRINT("Interrupt Triggering Order A0 => A1 => A2 \n\r"); UART_PRINT("**********************************************\n\r"); // // Scenario 1 - set three timers to the same interrupt priority. // In this case, we expect to see that the order of execuition of // interrupts are A0,A1,A2. // PerformIntTest(3, LOW_PRIORITY, LOW_PRIORITY,LOW_PRIORITY); // // Checking the Order of Execuition. A0,A1,A2. // if((g_ulA1IntCount == 0 && g_ulA2IntCount==0 ) || g_bA1CountChanged || g_bA2CountChanged ) { // // Something went wrong. Fail the test. // UART_PRINT("Interrupt failure.\n\r"); eResult = TEST_FAILED; return 0; } // // Scenario 2 : Increasing Priorities // Priorities are set as: A0 < A1 < A2 // if(eResult == TEST_PASSED) { UART_PRINT("Succesfully executed Equal Priority \n\r\n\r"); UART_PRINT("Increasing Priority : A0 < A1 < A2\n\r"); UART_PRINT("Interrupt Triggering Order A0 => A1 => A2 \n\r"); UART_PRINT("**********************************************\n\r"); // // Perform the test for this scenario. // PerformIntTest(3, LOW_PRIORITY,MIDDLE_PRIORITY, HIGH_PRIORITY); // // Order of Execuition should be as: A2,A1,A0. // if((g_ulA1IntCount == 0) || !g_bA1CountChanged || !g_bA2CountChanged) { // // Something went wrong. Fail the test. // UART_PRINT("Interrupt failure. \n\r"); eResult = TEST_FAILED; return 0; } } // // Scenario 3 - Decreasing Priorities // Priorities are set as: A0 > A1 > A2 // if(eResult == TEST_PASSED) { UART_PRINT("Succesfully executed Increasing Priority \n\r\n\r"); UART_PRINT("Decreasing Priority : A0 > A1 > A2\n\r"); UART_PRINT("Interrupt Triggering Order A0 => A1 => A2 \n\r"); UART_PRINT("**********************************************\n\r"); // // Perform the test for this scenario. // PerformIntTest(3, HIGH_PRIORITY, MIDDLE_PRIORITY, LOW_PRIORITY); // // Order of execuition should be : A0,A1,A2 // if((g_ulA1IntCount == 0) || g_bA1CountChanged || g_bA2CountChanged) { // // Something went wrong. Fail the test. // UART_PRINT("Interrupt failure\n\r"); eResult = TEST_FAILED; return 0; } } UART_PRINT("Succesfully executed Decreasing Priority \n\r\n\r"); // // Perform any clean up required after the test has completed. // InterruptTestTerm(); // // Let the user know that this test has completed. // UART_PRINT("Interrupt test ended.\n\r"); return 1; }
void InitUartInterface(uint32_t sys_clock) { uart_rx_read_index = 0; uart_rx_write_index = 0; const uint32_t dma_rx_primary = UDMA_CHANNEL_UART1RX | UDMA_PRI_SELECT; SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB); SysCtlPeripheralEnable(SYSCTL_PERIPH_UART1); SysCtlPeripheralSleepEnable(SYSCTL_PERIPH_UART1); //921600 //460800 uint32_t uart_config = UART_CONFIG_WLEN_8 | UART_CONFIG_STOP_ONE | UART_CONFIG_PAR_NONE; UARTConfigSetExpClk(UART1_BASE, sys_clock, 921600, uart_config); GPIOPinConfigure(GPIO_PB0_U1RX); GPIOPinConfigure(GPIO_PB1_U1TX); GPIOPinTypeUART(GPIO_PORTB_BASE, GPIO_PIN_0 | GPIO_PIN_1); UARTFIFOLevelSet(UART1_BASE, UART_FIFO_TX4_8, UART_FIFO_RX4_8); UARTEnable(UART1_BASE); //UARTDMAEnable(UART1_BASE, UART_DMA_RX | UART_DMA_TX); UARTDMAEnable(UART1_BASE, UART_DMA_RX); // Put the attributes in a known state for the uDMA UART1RX channel. These // should already be disabled by default. uint32_t dma_config = UDMA_ATTR_ALTSELECT | UDMA_ATTR_USEBURST | UDMA_ATTR_HIGH_PRIORITY | UDMA_ATTR_REQMASK; uDMAChannelAttributeDisable(UDMA_CHANNEL_UART1RX, dma_config); uint32_t dma_control = UDMA_SIZE_8 | UDMA_SRC_INC_NONE | UDMA_DST_INC_8 | UDMA_ARB_4; uDMAChannelControlSet(dma_rx_primary, dma_control); uDMAChannelTransferSet(dma_rx_primary, UDMA_MODE_BASIC, (void *)(UART1_BASE + UART_O_DR), &uart_rx_buf[uart_rx_write_index], UART_RX_BLOCK_SIZE); // Put the attributes in a known state for the uDMA UART1TX channel. These // should already be disabled by default. // uDMAChannelAttributeDisable(UDMA_CHANNEL_UART1TX, // UDMA_ATTR_ALTSELECT | // UDMA_ATTR_HIGH_PRIORITY | // UDMA_ATTR_REQMASK); // Set the USEBURST attribute for the uDMA UART TX channel. This will // force the controller to always use a burst when transferring data from // the TX buffer to the UART. This is somewhat more effecient bus usage // than the default which allows single or burst transfers. //uDMAChannelAttributeEnable(UDMA_CHANNEL_UART1TX, UDMA_ATTR_USEBURST); // Configure the control parameters for the UART TX. The uDMA UART TX // channel is used to transfer a block of data from a buffer to the UART. // The data size is 8 bits. The source address increment is 8-bit bytes // since the data is coming from a buffer. The destination increment is // none since the data is to be written to the UART data register. The // arbitration size is set to 4, which matches the UART TX FIFO trigger // threshold. // uDMAChannelControlSet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT, // UDMA_SIZE_8 | UDMA_SRC_INC_8 | // UDMA_DST_INC_NONE | // UDMA_ARB_4); // Set up the transfer parameters for the uDMA UART TX channel. This will // configure the transfer source and destination and the transfer size. // Basic mode is used because the peripheral is making the uDMA transfer // request. The source is the TX buffer and the destination is the UART // data register. // uDMAChannelTransferSet(UDMA_CHANNEL_UART1TX | UDMA_PRI_SELECT, // UDMA_MODE_BASIC, g_ui8TxBuf, // (void *)(UART1_BASE + UART_O_DR), // sizeof(g_ui8TxBuf)); // Now both the uDMA UART TX and RX channels are primed to start a // transfer. As soon as the channels are enabled, the peripheral will // issue a transfer request and the data transfers will begin. uDMAChannelEnable(UDMA_CHANNEL_UART1RX); //uDMAChannelEnable(UDMA_CHANNEL_UART1TX); // Enable the UART DMA TX/RX interrupts. //UARTIntEnable(UART1_BASE, UART_INT_DMATX | UART_INT_DMATX); UARTIntEnable(UART1_BASE, UART_INT_DMARX); IntEnable(INT_UART1); MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER0); MAP_TimerConfigure(TIMER0_BASE, TIMER_CFG_PERIODIC); MAP_TimerLoadSet(TIMER0_BASE, TIMER_A, sys_clock / 2000); MAP_IntEnable(INT_TIMER0A); MAP_TimerIntEnable(TIMER0_BASE, TIMER_TIMA_TIMEOUT); MAP_TimerEnable(TIMER0_BASE, TIMER_A); MAP_IntPrioritySet(INT_TIMER0A, 0xC0); }
void PWMWrite(uint8_t pin, uint32_t analog_res, uint32_t duty, uint32_t freq) { analog_res = analog_res * 1000; freq; uint32_t load = (F_CPU / freq) * 1000; uint32_t match = load / (analog_res / duty); match = match; load = load / 1000; uint16_t prescaler = load >> 16; uint16_t prescaler_match = match >> 16; uint8_t timer = digitalPinToTimer(pin); if(timer == NOT_ON_TIMER) return; MAP_PRCMPeripheralClkEnable(PRCM_TIMERA0 + (timer/2), PRCM_RUN_MODE_CLK); uint16_t pnum = digitalPinToPinNum(pin); switch(timer) { /* PWM0/1 */ case TIMERA0A: case TIMERA0B: MAP_PinTypeTimer(pnum, PIN_MODE_5); break; /* PWM2/3 */ case TIMERA1A: case TIMERA1B: MAP_PinTypeTimer(pnum, PIN_MODE_9); break; /* PWM4/5 */ case TIMERA2A: case TIMERA2B: MAP_PinTypeTimer(pnum, PIN_MODE_3); break; /* PWM6/7 */ case TIMERA3A: case TIMERA3B: MAP_PinTypeTimer(pnum, PIN_MODE_3); break; } uint32_t base = TIMERA0_BASE + ((timer/2) << 12); /* FIXME: If B is already opperational and configure A, B get's messed up. */ MAP_TimerConfigure(base, TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_PWM | TIMER_CFG_B_PWM); uint16_t timerab = timer % 2 ? TIMER_B : TIMER_A; MAP_TimerPrescaleSet(base, timerab, prescaler); MAP_TimerPrescaleMatchSet(base, timerab, prescaler_match); MAP_TimerControlLevel(base, timerab, 1); MAP_TimerLoadSet(base, timerab, load); MAP_TimerMatchSet(base, timerab, match); MAP_TimerEnable(base, timerab); }
void configureADC() { MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0); MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD); MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_TIMER1); MAP_SysCtlDelay(2); // Disable sequencer 0 MAP_ADCSequenceDisable(ADC0_BASE, 3); // // Configure GPIO Pin // MAP_GPIOPinTypeADC(GPIO_PORTD_BASE, GPIO_PIN_7); // ************************** // Configure timer // ************************** MAP_TimerConfigure(TIMER1_BASE, TIMER_CFG_PERIODIC); // Load timer for periodic sampling of ADC MAP_TimerLoadSet(TIMER1_BASE, TIMER_A, g_ui32SysClock/SAMPLING_RATE); // Enable ADC triggering MAP_TimerControlTrigger(TIMER1_BASE, TIMER_A, true); // Trigger ADC on timer A timeout MAP_TimerADCEventSet(TIMER1_BASE, TIMER_ADC_TIMEOUT_A); // ************************** // Configure ADC // ************************** // Clear the interrupt raw status bit (should be done early // on, because it can take several cycles to clear.) MAP_ADCIntClear(ADC0_BASE, 3); // ADC0, Seq 0, Timer triggered, Priority 0 MAP_ADCSequenceConfigure(ADC0_BASE, 3, ADC_TRIGGER_TIMER, 0); // MAP_ADCSequenceConfigure(ADC0_BASE, 3, ADC_TRIGGER_PROCESSOR, 0); /*// Set all 8 sequencer steps to sample from analog channel 5 (PD7) int i; for(i = 0; i < 1; i++) { MAP_ADCSequenceStepConfigure(ADC0_BASE, 0, i, ADC_CTL_CH5 | ADC_CTL_IE | ADC_CTL_END); } // Configure step 7 to trigger interrupt, and be the end of sequence // MAP_ADCSequenceStepConfigure(ADC0_BASE, 0, 7, ADC_CTL_CH5 | ADC_CTL_IE | ADC_CTL_END); */ MAP_ADCSequenceStepConfigure(ADC0_BASE, 3, 0, ADC_CTL_CH4 | ADC_CTL_IE | ADC_CTL_END); MAP_ADCSequenceEnable(ADC0_BASE, 3); // Enable interrupts when sample conversion complete MAP_ADCIntEnable(ADC0_BASE, 3); // Enable NVIC interrupt for ADC0 SS0 MAP_IntEnable(INT_ADC0SS3); MAP_IntMasterEnable(); MAP_TimerEnable(TIMER1_BASE, TIMER_A); }
//***************************************************************************** // //! Main Function // //***************************************************************************** int main() { // // Initialize Board configurations // BoardInit(); // // Pinmux for UART // PinMuxConfig(); // // Configuring UART // InitTerm(); // // Display Application Banner // DisplayBanner(APP_NAME); // // Enable pull down // MAP_PinConfigSet(PIN_05,PIN_TYPE_STD_PD,PIN_STRENGTH_6MA); // // Register timer interrupt hander // MAP_TimerIntRegister(TIMERA2_BASE,TIMER_A,TimerIntHandler); // // Configure the timer in edge count mode // MAP_TimerConfigure(TIMERA2_BASE, (TIMER_CFG_SPLIT_PAIR | TIMER_CFG_A_CAP_TIME)); // // Set the detection edge // MAP_TimerControlEvent(TIMERA2_BASE,TIMER_A,TIMER_EVENT_POS_EDGE); // // Set the reload value // MAP_TimerLoadSet(TIMERA2_BASE,TIMER_A,0xffff); // // Enable capture event interrupt // MAP_TimerIntEnable(TIMERA2_BASE,TIMER_CAPA_EVENT); // // Enable Timer // MAP_TimerEnable(TIMERA2_BASE,TIMER_A); while(1) { // // Report the calculate frequency // Report("Frequency : %d Hz\n\n\r",g_ulFreq); // // Delay loop // MAP_UtilsDelay(80000000/5); } }
/* * @brief Expansion0 MSP430 board ISR * * @returns void */ uint8 expand0BoardISR() { uint32 data, i; uint32 timerLoadPeriod; uint8 checksum; long val; static uint8 gripperData = 0; TimerIntClear(TIMER1_BASE, TIMER_TIMB_TIMEOUT); // Multiplex outputs (gripper/radio), set delay if (MSPSPIState == MSPSPI_STATE_XMIT_BYTE) { radioIntDisable(); SPISelectDeviceISR(SPI_EXPAND0); timerLoadPeriod = MSP430_SPI_DESELECT_PERIOD; } else if (MSPSPIState == MSPSPI_STATE_DESELECT_SPI) { SPIDeselectISR(); radioIntEnable(); timerLoadPeriod = (MSP430_SPI_BYTE_PERIOD); } MAP_TimerLoadSet(TIMER1_BASE, TIMER_B, timerLoadPeriod); MAP_TimerEnable(TIMER1_BASE, TIMER_B); // Transmit a byte or just switch state if (MSPSPIState == MSPSPI_STATE_XMIT_BYTE) { // Pack message if (expand0MessageIdx == 0) { // Grab next message from buffer if (!expand0MessageOutBufLock) { memcpy(expand0MessageOut, expand0MessageOutBuf, EXPAND0_MSG_LENGTH); } } // Rotate received buffer shiftBuffer(expand0MessageIn, EXPAND0_MSG_LENGTH); // Put data into the transmit buffer val = MAP_SSIDataPutNonBlocking(SSI0_BASE, (uint32)expand0MessageOut[expand0MessageIdx]); // Retrieve the received byte MAP_SSIDataGet(SSI0_BASE, &data); // Put byte the the end of the received buffer expand0MessageIn[EXPAND0_MSG_LENGTH - 1] = data; //Integrity checking if (expand0MessageIdx == 0) { // Checkcode for (i = 0; i < EXPAND0_CODE_LENGTH; i++) { if (expand0MessageIn[i] != expand0Code[i]) break; } if (i == EXPAND0_CODE_LENGTH) { // Checksum checksum = messageChecksum(expand0MessageIn, EXPAND0_CODE_LENGTH, EXPAND0_MSG_LENGTH); if (checksum == expand0MessageIn[EXPAND0_MSG_LENGTH - 1]) { // Avoid loading from buffer if the buffer is updating if (!expand0MessageInBufLock) { memcpy(expand0MessageInBuf, expand0MessageIn, EXPAND0_MSG_LENGTH); } } else { // Fail checksum if (showError) {cprintf("Gsum ");} } } else { // Fail checkcode if (showError) {cprintf("Gcod ");} } // Toggle MSP boards, regardless of result MSPSelect = MSP_BOTTOM_BOARD_SEL; } // Increment index, wrap back to 0 if it exceeds the range expand0MessageIdx++; if (expand0MessageIdx >= EXPAND0_MSG_LENGTH) { expand0MessageIdx = 0; } // Toggle states MSPSPIState = MSPSPI_STATE_DESELECT_SPI; } else if (MSPSPIState == MSPSPI_STATE_DESELECT_SPI) { // Toggle states MSPSPIState = MSPSPI_STATE_XMIT_BYTE; } return 0; }