请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
器件型号:MSP430G2452 大家好、
我正在尝试与 Intersil 的 RTC IC 建立 I2C 通信。 在尝试对其进行故障排除之前、我想验证 I2C 通信是否正常。 我初始化器件并为 I2C 配置 USI 外设、但似乎外设未正确初始化。 至少、当我设置 USICNTx 时、不会发生任何情况。 我假设我设置了很多控制寄存器中的一个错误、但尽管已经查看了几个小时、但似乎没有任何变化。 这让我相信、我缺少一些重要的东西、比如时钟源或全局中断设置。
我出了什么问题?
我使用的是 Code Composer Studio 6.2.0。 代码编译正确、LED 按预期闪烁。 但是 SDA/SCL 上没有任何变化。
代码:
#include
//#include "USI_I2CMaster.h"
//*
main.c
*//
时钟:DCOCLK 1MHz。 校准值被加载到 io_init()
void i2c_init (void){
__disable_interrupt ();//启用所有中断
//将 USI 外设设置为 I2C 模式
USICTL0 |= USISWRST;//在 CONFIG 期间将 USI 保持在 SW 复位状态
//USICTL0 &=~USILSB;//USILSB 被清零 [USICTL0.4]不在 TI 示例中
USICTL0 |= USIPE6; //USIPE6置1 [USICTL0.6]
USICTL0 |= USIPE7; //USIPE7置1 [USICTL0.7]
USICTL0 |= USIMST; //USIMST 置位 [USICTL0.3]
USICTL1 |= USII2C; //USII2C 置位 [USICTL1.6]
USICTL1 |= USIIE;//USIIE 设置[USICTL1.4?] 如果我设置此位、器件会崩溃/挂起。
//USICTL1 &=~USICKPH;//USICKPH 已清除[USICTL1.7]、TI 示例中未清除
USICKCTL |= USIDIV_7;//时钟分频器 X128 [USICKCTL567]
USICKCTL |= USISSEL_2;//clock = SMCLOCK [USICKCTL234]
USICKCTL |= USICKPL;//USICKPL 置1 [USICKCTL.1]
//USICNT &=~USI16B;//USI16B 被清零 [USICNT.6]不在 TI 示例中
USICNT |= USIIFGCC;//禁用自动清除控制
USISRL = 0x00;//清除 SR 低电平
USISRH = 0x00;//清除 SR 高电平
USICTL0 |=~USISWRST;//Config Done、释放 RESET
USICTL1 &=~USIIFG;//清除中断标志
__ENABLE_INTERRUPT ();//启用所有中断
}
void device_init (void){
WDTCTL = WDTPW + WDTHOLD; //如果
(CALBC1_1MHz=0xFF)则停止看门狗//如果校准常数被擦除
{
while (1); //不加载,陷阱 CPU!!
}
DCOCTL = 0; //选择最低 DCOx 和 MODx 设置
BCSCTL1 = CALBC1_1MHZ; //将出厂校准值加载到时钟配置寄存器
DCOCTL = CALDCO_1MHz;
//现在时钟的运行频率为1MHz +/- 0.5%典型值。 在3V 和0-85摄氏度
时、//设置 LED 和按钮的 I/O
P1OUT = 0xC1;
P1REN= 0xC0;
P1DIR |= BIT0;
P1IE |= BIT3;// P1.3中断被启用
P1IFG &=~BIT3;// P1.3 IFG 被清零
P1SEL |= 0xC0;
P1SEL2 &= 0x3F;
P2OUT = 0;
P2DIR = 0xFF;
}
void i2c_start (void){
//生成启动条件
USISRL = 0x00; //将 MSB 设置为零以将 SDA 拉低
USICTL0 |= USIGE;//make 输出锁存透明
USICTL0 |= USIOE;//make 输出锁存透明
USICTL0 &=~USIGE;//恢复时钟锁存功能并在 SDA 线上保持0
}
void i2c_stop (void){
//生成停止条件
USICTL0 |= USIOE; //使输出锁存透明
USISRL = 0x00;//清除移位寄存器
USICNT = 1; //发送一位
USISRL = 0xFF; //将移位寄存器设置为全1
USICTL0 |= USIGE; //使输出锁存透明
USICTL0 &=~(USIGE+USIOE);//恢复时钟锁存功能并在 SDA 线上保持1
}
void led_on (void){
P1OUT |= BIT0;
}
void led_off (void){
P1OUT &=~BIT0;
}
int SEND_BYTE (int data){
USISRL =数据; //加载字节以发送到 USISRL
USICTL0 |= USIOE; //通过设置 USIOE 启用输出
USICNT =(USICNT & 0xE0)+ 8; //将位数写入 USICNTx 时开始传输。 在全部8个位被发送后、USIIFG 被自动置位并且时钟被停止。
USICTL0 &=~USIOE; //USIOE 位必须用软件清零并且 USICNTx 被载入1。 这会自动清除 USIIFG 并且一个位被接收到 USISRL 中。
USICNT =(USICNT & 0xE0)+ 1;
return (USISRL & 0x01);
}
void main (void){
device_init();
i2c_init();
while (1){
LED_ON();
// MFRC522的从地址= 0x50
I2C_start();
if (!send_Byte (0x50)){
I2C_STOP();
}
LED_OFF ();
__DELAY_CYCLES (1000000);//等待1s
}
}