我有两个项目正确地使用了 MSP430低功耗模式。 我了解需要将器件置于睡眠状态、但不了解在中断后需要清除该位。
到目前为止、我注意到了一些问题。 由于低频振荡器太慢、因此如果我想在115200处接收 UART 消息、我只能使用 LPM0。 我还必须特意退出/清除 I2C 中断例程中的 LPM0位、以便在 main 中处理它们。
因此、我不确定我的所有代码是否正确。 我希望有人可以进行审核并提出任何建议。
项目1.
//唤醒以处理在进入时通过 UART 接收的数据。 // I2C 从设备命令进入并做出适当响应时唤醒。 //还注意到我必须清除 lpm 位才能从 I2C 事务 int main (void) {中唤醒 //停止 WDT WDT_A_HOLD (WDT_A_base); initClockTo16MHz (); inituart(0); initGPIO(); initi2C(); while (1) { if (rxFlag = 1) { processorUART (); } __bis_SR_register (LPM0_Bits + GIE); } // UART 中断 #if defined (__TI_Compiler_version__)|| defined (__IAR_systems_icc_) #pragma = USCI_A0 ( void _if)(_COMPIAR _VERSION_IFIE_IFIE_IFIE_IFIE_IFIE_IFIE_IFIE_IFIE_COMPI_ IE_COMPI_ )#_COMPIACT_VERSION_ERSION_IFIE_IFIE_ERSION_A0 (#US_AULT_ERSION_ERSION_ERSION_IF #endif { switch (__evo_in_range (UCA0IV、USCI_UART_UCTXCPTIFG)) { USCI_NONE 案例:中断; USCI_UART_UCRXIFG 案例: UCA0IFG &=~ UCRXIFG; //清除中断 rxData = UCA0RXBUF; rxFlag = 1; _BIC_SR_REGISTER_ON_EXIT (LPM0_BITS);//在 TI 上退出 LPM0 中断; 案例 USCI_UART_UCTXIFG:中断; 案例 USCI_UART_UCSTTIFG:中断; 案例 USCI_UART_UCTXCPTIFG:break; } } //********* // I2C 中断 // #if defined (__TI_Compiler_version__)|| defined (__IAR_systems_icc_) #pragma vector = USCI_B0_vector __interrupt void USCI_B0_ISR (void) #Elif defined (__GNU__) void __attribute__(interrupt (USCI_B0_vector)#USCI_ISR vector (void )(void)#USCI_ISR vector 0! #endif { //必须从 UCB0RXBUF uint8_t Rx_val 读取; switch (_even_in_range (UCB0IV、USCI_I2C_UCBIT9IFG) ){ USCI_NONE 案例: 中断; //向量0:无中断 USCI_I2C_UCALIFG 案例:中断; //向量2:ALIFG USCI_I2C_UCNACKIFG 案例: //向量4:NACKIFG 中断; 案例 USCI_I2C_UCSTTIFG:中断; //向量6:STTIFG USCI_I2C_UCSTPIFG 案例: UCB0IFG &=~(UCTXIFG0); 中断; //向量8:STPIFG USCI_I2C_UCRXIFG3案例:中断; //向量10:RXIFG3 USCI_I2C_UCTXIFG3案例:中断; //向量12:TXIFG3 USCI_I2C_UCRXIFG2案例:中断; //向量14:RXIFG2 USCI_I2C_UCTXIFG2案例:中断; //向量16:TXIFG2 USCI_I2C_UCRXIFG1案例:中断; //向量18:RXIFG1 USCI_I2C_UCTXIFG1案例:中断; //向量20:TXIFG1 USCI_I2C_UCRXIFG0案例: //向量22:RXIFG0 RX_val = UCB0RXBUF; 切换(SlaveMode) { 情况(RX_REG_ADDRESS_MODE): ReceiveRegAddr = Rx_val; I2C_Slave_ProcessCMD (ReceiveRegAddr); 中断; 情况(RX_DATA_MODE): ReceiveBuffer[ReceiveIndex++]= Rx_val; RXByteCtr---; IF (RXByteCtr = 0) { //完成接收 MSG SlaveMode = RX_REG_ADDRESS_MODE; UCB0IE &=~(UCTXIE); UCB0IE |= UCRXIE; //启用 RX 中断 I2C_Slave_TransactionDone (ReceiveRegAddr); __BIC_SR_REGISTER_ON_EXIT (LPM0_BITS);//在 RETI 上退出 LPM0 } 中断; 默认值: __no_operation(); 中断; } 中断; USCI_I2C_UCTXIFG0案例: //向量24:TXIFG0 UCB0TXBUF =传输缓冲器[TransmitIndex++]; TXByteCtr --; IF (TXByteCtr = 0) { //完成发送 MSG SlaveMode = TX_REG_ADDRESS_MODE; UCB0IE &=~(UCTXIE); UCB0IE |= UCRXIE; //启用 RX 中断 I2C_Slave_TransactionDone (ReceiveRegAddr); } 中断; //中断矢量:I2C 模式:UCTXIFG 默认值:中断; } }
项目2.
int main (void){
//停止 WDT
WDT_A_HOLD (WDT_A_base);
initClockTo16MHz();
inituart();
/*初始化外设*/
initGPIO();
initPWM();
initi2C();
initrtc();
while (1)
{
currentSample();
LED_CURRENT_READING = ADC_Conversion_Result;
tempSample ();
CURRENT_TEMP_READING = ADC_Conversion_Result;
doOtherStudioff ();
//LPM3、RTC 或 I2C 将强制退出
_bis_SR_register (LPM3_bits + GIE);
}
void currentSample (void)
{
ENABLE_ADC10 (ADCINCH_0);
_DELAY_CYCLES (15);
//启用并开始转换
//在单通道、单次转换模式中
ADC_startConversion (ADC_base、ADC_SINGLECHANNEL);
//LPM3、ADC 转换完成将强制退出
_bis_SR_register (LPM0_bits + GIE);
disable_ADC10 ();
}
void tempSample (void)
{
ENABLE_ADC10 (ADCINCH_12);
_DELAY_CYCLES (15);
//启用并开始转换
//在单通道、单次转换模式中
ADC_startConversion (ADC_base、ADC_SINGLECHANNEL);
//LPM3、ADC 转换完成将强制退出
_bis_SR_register (LPM0_bits + GIE);
disable_ADC10 ();
}
void disable_ADC10 (void){
adc_disableConversions (adc_base、0);
adc_disable (adc_base);
}
void enable_adc10 (uint8_t adc_channel){
//初始化 ADC 模块
adc_init (adc_base、adc_SAMPLEHOLDCOSC_base);}void adc_oc_oc_oc_enable、adc_oc_oc_occe_enc (uint1、adce_oc_oc_oc_oc_base);
ADC_setupSamplingTimer (ADC_base、ADC_CYCLEHOLD_1024_cycles、ADC_MULTIPLESAMPLESDISABLE);
IF (ADC_CHANNEL = ADCINCH_12)
{
ADC_configureMemory (ADC_base、ADC_channel、ADC_VREFPS_INT、ADC_VREFNEG_AVSS);
}
否则
{
ADC_configureMemory (ADC_base、ADC_channel、ADC_VREFPOS_AVCC、ADC_VREFNEG_AVSS);// driverlib 中 A1的通道错误映射?
}
ADC_clearInterrupt (ADC_base、ADC_completed_interrupt);
//启用存储器缓冲器中断
ADC_enableInterrupt (ADC_base、ADC_completed_interrupt);
}
// ADC 中断服务例程
#if defined (__TI_Compiler_version__)|| defined (__IAR_systems_icc_)
#pragma vector=ADC_complete_interrupt
(_ void)(_adc)(nvoid _interrupt)(_inc)(nvoid _inc)(void _interrupt (n_inc)(void _interrupt)(_inc)(_ vector (_inc)_ vo
#endif
{
ADC_Conversion_Result = ADCMEM0;
__BIC_SR_register_ON_EXIT (LPM3_BITS); //睡眠定时器退出 LPM3
}
// RTC 中断服务例程
#if defined (__TI_Compiler_version__)|| Defined (__IAR_systems_ICC__)
#pragma vector=RTC_vector
__interrupt void RTC_ISR (void)
#Elif defined (__GCOMPILE__)
void __attribute__(interrupt (interrupt (rtc_vector)#rTC
!#pru_ISR (void)#rc!#rc!错误!
#endif
{
_BIC_SR_REGISTER_ON_EXIT (LPM3_BITS); //计时器退出 LPM3
开关(__evo_in_range (RTCIV、RTCIV_RTCIF)
{
案例 RTCIV_NONE:中断; //无中断
案例 RTCIV_RTCIF: // RTC 溢出
P2OUT ^= BIT3;
中断;
默认值:中断
;}
//
*********
// I2C 中断
//
#if defined (__TI_Compiler_version__)|| defined (__IAR_systems_icc_)
#pragma vector = USCI_B0_vector
__interrupt void USCI_B0_ISR (void)
#Elif defined (__GNU__)
void __attribute__(interrupt (USCI_B0_vector)#USCI_ISR vector (void
)(void)#USCI_ISR vector 0!
#endif
{
//必须从 UCB0RXBUF
uint8_t Rx_val 读取;
switch (_even_in_range (UCB0IV、USCI_I2C_UCBIT9IFG)
){
USCI_NONE 案例: 中断; //向量0:无中断
USCI_I2C_UCALIFG 案例:中断; //向量2:ALIFG
USCI_I2C_UCNACKIFG 案例: //向量4:NACKIFG
中断;
案例 USCI_I2C_UCSTTIFG:中断; //向量6:STTIFG
USCI_I2C_UCSTPIFG 案例:
UCB0IFG &=~(UCTXIFG0);
中断; //向量8:STPIFG
USCI_I2C_UCRXIFG3案例:中断; //向量10:RXIFG3
USCI_I2C_UCTXIFG3案例:中断; //向量12:TXIFG3
USCI_I2C_UCRXIFG2案例:中断; //向量14:RXIFG2
USCI_I2C_UCTXIFG2案例:中断; //向量16:TXIFG2
USCI_I2C_UCRXIFG1案例:中断; //向量18:RXIFG1
USCI_I2C_UCTXIFG1案例:中断; //向量20:TXIFG1
USCI_I2C_UCRXIFG0案例: //向量22:RXIFG0
RX_val = UCB0RXBUF;
切换(SlaveMode)
{
情况(RX_REG_ADDRESS_MODE):
ReceiveRegAddr = Rx_val;
I2C_Slave_ProcessCMD (ReceiveRegAddr); /
中断;
情况(RX_DATA_MODE):
ReceiveBuffer[ReceiveIndex++]= Rx_val;
RXByteCtr---;
IF (RXByteCtr = 0)
{
//完成接收 MSG
SlaveMode = RX_REG_ADDRESS_MODE;
UCB0IE &=~(UCTXIE);
UCB0IE |= UCRXIE; //启用 RX 中断
I2C_Slave_TransactionDone (ReceiveRegAddr);
//我们应该在这里这么做吗?
__BIC_SR_REGISTER_ON_EXIT (LPM0_BITS);//在 RETI 上退出 LPM0
}
中断;
默认值:
__no_operation();
中断;
}
中断;
USCI_I2C_UCTXIFG0案例: //向量24:TXIFG0
UCB0TXBUF =传输缓冲器[TransmitIndex++];
TXByteCtr --;
IF (TXByteCtr = 0)
{
//完成发送 MSG
SlaveMode = TX_REG_ADDRESS_MODE;
UCB0IE &=~(UCTXIE);
UCB0IE |= UCRXIE; //启用 RX 中断
I2C_Slave_TransactionDone (ReceiveRegAddr);
}
中断; //中断矢量:I2C 模式:UCTXIFG
默认值:中断;
}
}