在MSP430G2221上,我学习了例程msp430g2x21_usi_15.c,该例程把I2C配置成配置成slave mode,有几个问题请教:
(1)我观看其main中最后并没有while(1)让其MCU一直在跑,是程序有错,还是并不需要while(1)也可以让芯片一直收到I2C总线上发的消息?
void main(void)
{
WDTCTL = WDTPW + WDTHOLD; // Stop watchdog
if (CALBC1_1MHZ ==0xFF || CALDCO_1MHZ == 0xFF) { while(1); // If calibration constants erased
// do not load, trap CPU!!
} BCSCTL1 = CALBC1_1MHZ; // Set DCO
DCOCTL = CALDCO_1MHZ;
Setup_USI_Slave();
LPM0; // CPU off, await USI interrupt
_NOP();
}
(2)我想直接修改该例子实现我自己程序中的收发主I2C总线(Master)上的数据消息,上层系统是Linux上的I2C总线驱动,使用该例程上的程序应该可以和Linux下的I2C总线驱动通信吧?
(3)Slave mode可以主动发起通信会话发消息给I2C总线吗?
真诚感谢您的指导!!!
Lina Lian:
Kyle Wang,你好!
(1),因为有LPM0语句的存在,即让CPU进入Low Power Mode0,来数据的话,进入中断处理程序,从中断返回后,CPU仍旧处于LPM0.
(2).例程中I2C是按协议标准编的,但是请注意‘MSP430G2x21/G2x31 – I2C Slave Receiver / Slave Transmitter, multiple bytes’。
(3).Slave Mode应该是不能主动发起通信的,它需要等Start信号吧。
Kyle wang:
回复 Lina Lian:
Lina Lian,您好!
对于问题3,我的程序除了需要随时等待接收I2C总线上的消息,还需要实现在MSP430启动的时候主动发起通信给I2C总线,用于MSP430与主CPU一些状态的同步,如果Slave Mode补能主动发起通信,那要实现我的功能需求,是否在我需要主动发信息的时候,必须要将USI配置成Master I2C才行呢?
Lina Lian:
回复 Kyle wang:
Kyle wang, 作为I2C Slave,也是可以发送消息,但是主动发起的Start信号只能是I2C Master产生。
Kyle wang:
回复 Lina Lian:
Lina Lian,您好!
谢谢!I2C slave可以发送消息,例程里有程序,但是我程序是想主动让MSP430(SLAVE)发消息到I2C总线(MASTER),这是否可以?
按你的意思,I2C slave应该不能主动发消息,而是需要等待master的start信号
PS:我的程序是想PORT的 ISR里主动发消息到I2C总线上
Hardy Hu:
回复 Kyle wang:
对的,IIC通讯中,总线时钟CLK均由MASTER提供,START信号包含CLK的状态,故SLAVE是不能主动发起通讯的,但是可以发送STOP停止通讯,NACK告诉主机通讯错误,ACK告诉主机通讯成功
Kyle wang:
回复 Hardy Hu:
您好,
我的平台是NS115,采用ARM Cortex A9 MPCore,MSP430通过P1.6、P1.7与ARM核I2C总线通信,MSP430其他引脚上挂载众多其他设备模块,如射频、SIM卡等。
ARM上跑的是Linux系统,Linux内核有I2C总线驱动,单片机部分的程序有功能需求:
1. ARM端程序下发I2C命令通知MSP430关闭射频(ARM端->MSP430);
2. MSP430端程序检测到SIM卡插入(引脚中断检测),则发I2C命令通知ARM端进行相应的处理(MSP430 ->ARM端)。
所以,我除了写单片机部分的程序,还应该需要写ARM端这部分通信的I2C设备驱动程序。
因为我看点Linux的I2C总线驱动,似乎都是在充当着Master,所以,我想是否在单片机端都应该配置成slave,但是如果是slave的话,当实现需求2的时候,不能主动发起I2C命令….
以上求教如何实现?
Lina Lian:
回复 Kyle wang:
Kyle wang,你好。MSP430G2231这边的USI的I2C mode应该支持多 master形式,可以进行总线仲裁。具体请参照user guide的14.2.4.8 Arbitration。
Kyle wang:
回复 Young Hu:
这种方案可行,谢谢!