主题中讨论的其他器件:OPT3001
工具/软件:Code Composer Studio
您好!
我一直在研究 DriverLib 示例、并尝试开发 i2c 驱动器、以读取/写入 opt3001 ALS。 我对了解中断和 ISR 比较陌生、认为我在调试代码时遇到了一些问题、在 i2c_write 结束时、器件进入 LPM0+GIE、大概通过 ISR、但我无法单步执行或退出 LPM 和相应的 ISR。
由于我不熟悉中断、我的 ISR 代码很可能不正确、但由于我无法单步执行、我有一个硬时间引脚指出发生了什么错误。 第113行是我第一次遇到问题的地方,但我希望155也会有同样的问题。
有什么问题吗?
"MSP430:不能单步执行目标程序:CPU 当前处于关闭状态、调试功能将受到限制。"
/* i2c_driver.c * *创建日期:2014年7月16日 * 作者:a0272990 * *版权所有2014 Texas Instruments Incorporated。 保留所有权利。 * */ //********************** //#includes //********* #include "driverlib.h" #include "i2c_driver.h" #include "QmathLib.h" #include "IQmathLib.h" #include "math.h" //********* //#defines //********* #define OPT3001_ADDRESS 0x44 // OPT3001的 I2C 地址 #define CHECK_POLARITY 0x80 //极性标志(MSB 的 MSB) //********* //全局变量 //********* #define RXCOUNT 0x05 #define TXLENGTH 0x04 uint8_t i2c_transmitCounter = 0;//可用于存储 I2C uint8_t i2c_transmitData[40]的发送状态的变量; // uint8_t * p_i2c_transmitData; //发送数据的指针 uint8_t i2c_receivedCounter = 0; //可用于存储 I2C uint8_t i2c_receivedBuffer[40]的接收状态的变量; // uint8_t * p_i2c_receivedBuffer; //指向接收数据的指针 //无符号字符接收缓冲区[10]={0x01、0x01、0x01、0x01、0x01、0x01、 0x01、0x01、0x01、0x01、0x01}; //unsigned char * receiveBufferPointer; //unsigned char receiveCount = 0; uint16_t i2c_mode = 0; //用于存储 i2c 模式(TX 或 Rx)的变量 //********* // I2C 库函数 //********* void init_i2c (void) { //将 I2C 引脚分配给 USCI_B1 GPIO_setPeripheralModuleFunctionInputPin (GPIO_PORT_P4、GPIO_PIN1 + GPIO_PIN2); //初始化主控 USCI_B_I2C_initMasterParam param ={0}; param.selectClockSource = USCI_B_I2C_CLOCKSOURCE_SMCLK; param.i2cClk = UCS_getSMCLK (); param.datarate = USCI_B_I2C_SET_DATA_RATE_100KBPS;USCI_B1_initMaster_B (USCI_B1) param);// 启用 I2C 模块以启动操作 USCI_B_I2C_ENABLE (USCI_B1_base); //启用主器件接收中断 USCI_B_I2C_enableInterrupt (USCI_B1_base、USCI_B_I2C_receive_interrupt); } void i2c_write (uint8_t slave_address) {&t //初始化主设备 USCI_B_I2C_initMasterParam param ={0}; param.selectClockSource = USCI_B_I2C_CLOCKSOURCE_SMCLK; param.i2cClk = UCS_getSMCLK (); param.datarate = USCI_B_I2C_SET_DATA_RATE_400KBPS; USCI_B_I2C_initMaster (USCI_B1_base、¶m); //指定从器件地址 USCI_B_I2C_setSlaveAddress (USCI_B1_BASE、SLAVE_ADDRESS ); //设置发送模式 USCI_B_I2C_setMode (USCI_B1_BASE、 USCI_B_I2C_Transmit 模式 ); //启用 I2C 模块以启动操作 USCI_B_I2C_ENABLE (USCI_B1_BASE); while (1) { //启用发送中断 USCI_B_I2C_clearInterrupt (USCI_B1_base、USCI_B_I2C_Transmit 中断); USCI_B_I2C_enableInterrupt (USCI_B1_base、USCI_B_I2C_Transmit _interrupt); //每次传输之间的延迟 _DELAY_CYCLES (50);//替换为计时器 ISR? //加载 TX 字节计数器 I2C_transmitCounter = 1; //启动开始并发送第一个字符 USCI_B_I2C_masterSendMultiByteStart (USCI_B1_base、i2c_transmitData[0]); //输入启用中断的 LPM0 _bis_SR_register (LPM0_bits + GIE); __no_operation(); //延迟直到传输完成 while (USCI_B_I2C_isBusy (USCI_B1_base)); } } void i2c_read_Byte (uint8_t slave_address、uint8_t byte_count) { //初始化主设备 USCI_B_I2C_initMasterParam param ={0}; param.selectClockSource = USCI_B_I2C_CLOCKSOURCE_SMCLK; param.i2cClk = UCS_getSMCLK (); param.datarate = USCI_B_I2C_SET_DATA_RATE_100KBPS; USCI_B_I2C_initMaster (USCI_B1_base、¶m); //指定从器件地址 USCI_B_I2C_setSlaveAddress (USCI_B1_BASE、SLAVE_ADDRESS); //设置接收模式 USCI_B_I2C_setMode (USCI_B1_base、USCI_B_I2C_Receive_mode); //启用 I2C 模块以启动操作 USCI_B_I2C_ENABLE (USCI_B1_BASE); //启用主机接收中断 USCI_B_I2C_enableInterrupt (USCI_B1_base、USCI_B_I2C_receive_interrupt); //等待总线空闲 while (USCI_B_I2C_isBusy (USCI_B1_base)); while (1) { P_i2c_receivedBuffer =(unsigned char *) i2c_receivedBuffer; I2C_receivedCounter = i2c_receivedBuffer 的大小; //初始化多接收 USCI_B_I2C_masterReceiveMultiByteStart (USCI_B1_BASE); //进入启用中断的低功耗模式0。 _bis_SR_register (LPM0_bits + GIE); __no_operation(); } } void OPT3001_init (void) { uint8_t OPT3001_Config_SW_RESET[3]= { 0x01、//CDC 配置寄存器地址 0xC2、//MSB 配置(设置100ms 转换时间、单次触发模式) 0x10 //LSB 配置 }; P_i2c_transmitData =(uint8_t *) OPT3001_Config_sw_reset;//传输阵列起始地址 I2C_transmitCounter = OPT3001_Config_SW_RESET 的大小; //加载发送字节计数器 I2C_WRITE (OPT3001_ADDRESS); __DELAY_CYCLES (DELAY_10_MS); } Int32_t OPT3001_SingleRead (void) { //uint8_t CDC_Config[2]={0};//测试变量 uint8_t Lux_Measur1_MSB[2]={0x00、0x00};//电容 MEAS1的 MSB //uint32_t luxVal=0; int32_t Lux_MEAS1 = 0;来自 MEAS1的//24位 Lux 值(32位变量) uint8_t OPT3001_initMEAS1[3]= { 0x01、//选择配置寄存器地址 0xC2、//MSB 配置(设置100ms 转换时间、单次触发模式) 0x10 //LSB 配置 }; const uint8_t OPT3001_ResultAddr[1]={0x00};//Lux_MEAS1_MSB 寄存器地址 P_i2c_transmitData =(uint8_t *) OPT3001_initMEAS1; //发送阵列起始地址 I2C_transmitCounter = OPT3001_initMEAS1的大小; //加载发送字节计数器 I2C_WRITE (OPT3001_ADDRESS); _delay_cycles (delay_10_ms); P_i2c_transmitData =(uint8_t *) OPT3001_ResultAddr;//传输阵列起始地址 I2C_transmitCounter = OPT3001_ResultAddr 的大小; //加载发送字节计数器 I2C_WRITE (OPT3001_ADDRESS); P_i2c_receivedBuffer =(uint8_t *) Lux_Measur1_MSB; //接收阵列起始地址 I2C_READ_BYTE (OPT3001_ADDRESS、LUX_Meas1_MSB 的大小);//读取两个字节的 lux 数据形式结果寄存器 LUX_MEAS1 = 0x0FFF &(uint16_t) LUX_Measur1_MSB[0]<< 8 |(uint16_t) LUX_Measur1_MSB[1]; int8_t exp = lux_Meas1_MSB[0]>4;//指数是前四位 Lux_MEAS1 = 0.01 * pow (2、exp)* Lux_MEAS1; 返回 LUX_MEAS1; } //********* // ////这是 USCI_B1中断矢量处理例程。 //// ********* #if defined (__TI_Compiler_version__)|| defined (__IAR_systems_icc_) #pragma vector=USCI_B1_vector __interrupt #elif defined (__GNU__) __attribute__(INTERRUPT (USCI_B1_vector))) #endif void USCI_B1_ISR (void )(void) 开关(_偶数_在范围内(UCB1IV、12)){ USCI_I2C_UCTXIFG 案例: { //检查 TX 字节计数器 IF (i2c_transmitCounter < i2c_transmitData 的大小) { //启动从主设备到从设备的字符发送 USCI_B_I2C_masterSendMultiByteNext (USCI_B1_BASE、 I2C_transmitData[i2c_transmitCounter] ); //递增 TX 字节计数器 I2C_transmitCounter++; } 其他 { //仅启动停止 USCI_B_I2C_masterSendMultiByteStop (USCI_B1_BASE); //清除主机中断状态 USCI_B_I2C_clearInterrupt (USCI_B1_base、 USCI_B_I2C_Transmit 中断); //在中断返回时退出 LPM0 __BIC_SR_REGISTER_ON_EXIT (LPM0_Bits); } 中断; } USCI_I2C_UCRXIFG 案例: { //递减 RX 字节计数器 I2C_receivedCounter--; if (i2c_receivedCounter) { if (i2c_receivedCounter = 1) { //启动接收结束->接收字节与 NAK *p_i2c_receivedBuffer++= USCI_B_I2C_masterReceiveMultiByteFinish ( USCI_B1_BASE ); } 其他 { //每次接收一个字节 *p_i2c_receivedBuffer++= USCI_B_I2C_masterReceiveMultiByteNext ( USCI_B1_BASE ); } } 其他 { //接收最后一个字节 *p_i2c_receivedBuffer = USCI_B_I2C_masterReceiveMultiByteNext ( USCI_B1_BASE ); __BIC_SR_REGISTER_ON_EXIT (LPM0_Bits); } 中断; } }