我参照 877的例程 拷到 887里面结果仿真的时候出现问题,但现在问题不知道出现在什么地方? 我看了数据手册 感觉没有什么变化啊。 主机的程序
#include <pic.h>
//__CONFIG (HS & LVPDIS & WDTDIS);
#define B1 RC0 // 按键B1状态由RC0端口输入
#define XTAL_FREQ 4 // 外接晶振主频,单位为MHz
void DelayMS(unsigned int ms) //定义延时函数
{
unsigned int j=0;
for(ms;ms>0;ms--)
for(j=27*XTAL_FREQ;j>0;j--) // 1MHz时约是27,其它主频请酌情修改
{
}
}
void main( void )
{
unsigned char i=1;
// TRISC0=1; // RC0用于读取按钮B1的状态
SSPEN=0; // 关闭MSSP模块,初始化完毕后再打开
TRISC3=1; // 把SCL设为输入引脚
TRISC4=1; // 把SDA设为输入引脚
SSPCON2=0;
WCOL=0; // 写冲突检测位清零,若发送数据不正确请检查此位
SSPM3=1; //SSPM=1000,I2C主模式
SSPM2=0;
SSPM1=0;
SSPM0=0;
SMP=1;
// I2C波特率=Fosc/(4*(SSPADD+1))
// SSPADD=[(Fosc/(BandRate*4)]-1
SSPADD = 0x9; // 当主频为4Mhz时波特率为100kbps
CKP=1;
CKE=0; // 使用I2C协议规范电平
// 关闭斜率控制
SSPIF=0; //若使用SSPIF作为信号发送状态位则需要清空此位
SSPEN=1; // 使能MSSP模块
while (1)
{
// if(B1==0) // 若按键B1有变化
// {
//DelayMS(100); // 消除机械按键前沿抖动
// if(B1==0) // 再判断为0说明是一次正常按键
// {
SEN=1; // 发送起始位
while(SEN); // SEN=1说明未发送完毕
// 循环退出说明SEN=0,即发送完毕
SSPBUF = 0b10010000; // 从机地址为0b1001000,写操作
while(R_nW); //RW=1说明数据发送进行中
// 循环退出说明RW=0,即发送完毕
if(ACKSTAT) // ACKSTAT为1说明未收到从机应答
while(1); // 死循环,便于调试,实际项目中应做错误处理
SSPBUF = i; //向从机写入数据i,即发送数据i
while(R_nW); //RW=1说明数据发送进行中
// 循环退出说明RW=0,即发送完毕
if(ACKSTAT) // ACKSTAT为1说明未收到从机应答
while(1); // 死循环,便于调试,实际项目中应做错误处理
PEN=1; // 发送停止位
while(PEN); // PEN=1说明未发送完毕
// 循环退出说明PEN=0,即发送完毕
i++; // 为了能看到效果,发生数据自加一
DelayMS(100); // 过滤机械按键的后沿抖动
//}
// }
}
}
从机的程序
/* PIC16F877 I2C从机模式接收数据例程
* 把收到的数据显示在数码管上
*
*/
#include <pic.h> // 改用PIC16F877控制
// __CONFIG (HS & LVPDIS & WDTDIS);
const char NumFont[10]={0x3F,0x06,0x5B,0x4F,0x66,
0x6D,0x7D,0X07,0x7F,0x6F}; // 共阴极数码管字形码
interrupt ISR(void)
{
char tmp;
if(SSPIF==1)
{
SSPIF=0;
if(D_nA==1) // 1 是数据
{
if(BF==1) // 缓冲区满,说明从主机收到一个字节
{
tmp=SSPBUF; // 保存收到的普通数据
PORTD=NumFont[tmp]; // 显示收到的数据
}
else // BF=0,主机读取结束
{
if(R_nW==1) // 读标志位有效,说明主机还在继续读数据
{
SSPBUF=0x06; // 把主机要的数据保存在SSPBUF中等待主机读取
}
else
{ // 读标志位无效,说明主机已经读取完最后一个字节了
}
}
}
else //0 是地址
{
tmp=SSPBUF;
if( (tmp & 0b00000001)!=0) // R/W =1,read
{
SSPBUF=0x06; // 准备好数据等待下一次主机读取
}
else //R/W=0, write
{
// 等待下一次主机来数据放到SSPBUF中
}
}
}
CKP=1;
SSPOV=0; // 从机释放SCL
}
I2C_Init()
{
SSPSTAT=0;
TRISC3=1;
TRISC4=1;
SSPCON2=0B10000000;
SSPADD=0B10010000; // 从机地址码范围:1001000x
SSPCON=0B00110110;
SSPIE=1; // 允许SSPIF产生中断
GIE=1;
PEIE=1;
}
void main( void )
{
unsigned char i=0,EEP_Address=0,EEP_Data=0;
TRISD=0; // 为了读取按钮B1的状态
PORTD=0;
I2C_Init(); // 初始化I2C
while (1)
{ // 等待中断产生
}
在用887 仿真的时候会出现如图所示的错误 难道是不可以通用还是有什么其他的问题啊?
} |