完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
扫一扫,分享给好友
上面是利用GPIO模拟IIC时序
应用测试程序:
开发环境:OK6410+LINUX3.0.1 问题:写入数据,没有反应,PCF8574经检测是正常的,是不是我时序模拟出了问题? |
|
相关推荐
3个回答
|
|
一般I2C 的驱动都是有包的, 楼主可以在添加一下debug信息,看看你的程序进展到哪一步出现了这样的问题。
|
|
|
|
i2c_ack()的时序有点乱
|
|
|
|
参考一下这个吧,写的很详细:
#define SDA 254 //定义SDA所对应的GPIO接口编号 #define SCL 255 //定义SCL所对应的GPIO接口编号 #define OUTP 1 //表示GPIO接口方向为输出 #define INP 0 //表示GPIO接口方向为输入 /* I2C起始条件 */ int i2c_start() { //初始化GPIO口 set_gpio_direction(SDA, OUTP); //设置SDA方向为输出 set_gpio_direction (SCL, OUTP); //设置SCL方向为输出 set_gpio_value(SDA, 1); //设置SDA为高电平 set_gpio_value(SCL, 1); //设置SCL为高电平 delay(); //延时 //起始条件 set_gpio_value(SDA, 0); //SCL为高电平时,SDA由高变低 delay(); } /* I2C终止条件 */ void i2c_stop() { set_gpio_value(SCL, 1); set_gpio_direction(SDA, OUTP); set_gpio_value(SDA, 0); delay(); set_gpio_value(SDA, 1); //SCL高电平时,SDA由低变高 } /* I2C读取ACK信号(写数据时使用) 返回值 :0表示ACK信号有效;非0表示ACK信号无效 */ unsigned char i2c_read_ack() { unsigned char r; set_gpio_direction(SDA, INP); //设置SDA方向为输入 set_gpio_value(SCL,0); // SCL变低 r = get_gpio_value(SDA); //读取ACK信号 delay(); set_gpio_value(SCL,1); // SCL变高 delay(); return r; } /* I2C发出ACK信号(读数据时使用) */ int i2c_send_ack() { set_gpio_direction(SDA, OUTP); //设置SDA方向为输出 set_gpio_value(SCL,0); // SCL变低 set_gpio_value(SDA, 0); //发出ACK信号 delay(); set_gpio_value(SCL,1); // SCL变高 delay(); } /* I2C字节写 */ void i2c_write_byte(unsigned char b) { int i; set_gpio_direction(SDA, OUTP); //设置SDA方向为输出 for (i=7; i>=0; i--) { set_gpio_value(SCL, 0); // SCL变低 delay(); set_gpio_value(SDA, b & (1< set_gpio_value(SCL, 1); // SCL变高 delay(); } i2c_read_ack(); //检查目标设备的ACK信号 } /* I2C字节读 */ unsigned char i2c_read_byte() { int i; unsigned char r = 0; set_gpio_direction(SDA, INP); //设置SDA方向为输入 for (i=7; i>=0; i--) { set_gpio_value(SCL, 0); // SCL变低 delay(); r = (r <<1) | get_gpio_value(SDA); //从高位到低位依次准备数据进行读取 set_gpio_value(SCL, 1); // SCL变高 delay(); } i2c_send_ack(); //向目标设备发送ACK信号 return r; } /* I2C读操作 addr:目标设备地址 buf:读缓冲区 len:读入字节的长度 */ void i2c_read(unsigned char addr, unsigned char* buf, int len) { int i; unsigned char t; i2c_start(); //起始条件,开始数据通信 //发送地址和数据读写方向 t = (addr << 1) | 1; //低位为1,表示读数据 i2c_write_byte(t); //读入数据 for (i=0; i i2c_stop(); //终止条件,结束数据通信 } /* I2C写操作 addr:目标设备地址 buf:写缓冲区 len:写入字节的长度 */ void i2c_write (unsigned char addr, unsigned char* buf, int len) { int i; unsigned char t; i2c_start(); //起始条件,开始数据通信 //发送地址和数据读写方向 t = (addr << 1) | 0; //低位为0,表示写数据 i2c_write_byte(t); //写入数据 for (i=0; i i2c_stop(); //终止条件,结束数据通信 } |
|
|
|
只有小组成员才能发言,加入小组>>
「含关键代码」基于AM3352/AM3354/AM3359的Linux开发案例分享
4894 浏览 0 评论
87411 浏览 0 评论
【高手问答】如何做到精通linux技术?资深工程师带你突破难点
4725 浏览 2 评论
3620 浏览 2 评论
解读Linux :先从创建一个文件夹用来存放jdk压缩文件开始
2483 浏览 0 评论
1999浏览 3评论
1286浏览 1评论
求解:aarch64交叉编译工具已经安装成功,环境变量已经配置,怎么将系统架构切换为ARM的架构
1344浏览 0评论
电脑和虚拟机可以互ping,电脑和开发板也可以互ping,但是虚拟机和开发板ping不通是什么原因
1236浏览 0评论
1174浏览 0评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-23 10:31 , Processed in 1.021042 second(s), Total 52, Slave 46 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号