STM32模拟IIC协议驱动AD7991/AD7995/AD7999芯片

AD7991/AD7995/AD7999是12位/10位/8位 4通道模拟输入的AD转换芯片

通信方式采用的是:I2C

芯片供电VDD电压范围为:2.7V---5.5V

参考电压REF范围为:1.2V---VDD

模拟输入电压范围为:0-VREF

下面以AD7995为例,以STM32F103为平台对该芯片的驱动程序及电路进行说明:

1、AD电路原理图

注:这里I2C的两根SCL和SDA线需各接一个4.7K的上拉电阻。

2、芯片引脚分析 

AD7995引脚介绍
引脚标号 名称 描述
1 SCL I2C串行总线时钟
2 SDA I2C双向串行数据线
3 VIN0 模拟输入接口0
4 VIN1 模拟输入接口1
5 VIN2 模拟输入接口2
6 VIN3/VREF 模拟输入接口3/参考电压输入
7 GDN
8 VDD 电源
设备地址
产品标号 I2C地址
AD7991-0 010 1000
AD7991-1 010 1001
AD7995-0 010 1000
AD7995-1 010 1001
AD7999-1 010 1001

 3、AD7995——8bit控制字寄存器

该8位控制字寄存器只能通过I2C进行数据的写操作,用于设置AD7995的工作模式。

控制字说明
名称 描述
D7 通道CH3或VREF参考电压 具体看D3脚的功能描述
D6---D4 通道CH2---通道0 在需要打开的通道下置1
D3 CH3功能选择

置1:CH3引脚将作为参考电压输入脚;

置0:CH3引脚将作为模拟电压输入脚,芯片将以VDD作为参考电压

D2 I2c过滤使能 置1:忽略过滤;置0:使能过滤.    默认1
D1 位试验延时 默认1关闭
D0 取样延时 默认1关闭

4、AD7995——转换结果寄存器

转换结果寄存器是一个16位,只能通过I2C读操作的寄存器。用于读取AD7995的AD转换结果

转换结果寄存器说明
名称 描述
D15---D14 无效位  
D13---D12 通道标号

表示当前转换结果是来自哪个通道。

00:通道0,

01:通道1,

10:通道2,

11:通道3

D11---D0 转换结果

AD7991转换结果全部来自这12位。

AD7995转换结果来自前10位,其余为0。

AD7999转换结果来自前8位,其余为0

5、写操作时序图

该写时序共分为2个阶段:

第一阶段。主机通过I2C向AD7995发送一个START信号,接着发送AD7995-0的地址:010 1000(详情看第2小节的设备地址),在下一个时钟脉冲(也就是第8个)的时候R/W位 设置为0,表示该命令为写操作,然后第9个时钟脉冲添加ACK信号。

第二个阶段。主机再发送8位控制字内容,然后再第9个脉冲添加ACK信号,最后发送STOP信号结束通信。

6、读操作时序图

该读时序共分为3个阶段:

第一阶段。 主机通过I2C向AD7995发送一个START信号,接着发送AD7995-0的地址:010 1000(详情看第2小节的设备地址),在下一个时钟脉冲(也就是第8个)的时候R/W位 设置为1,表示该命令为读操作,然后第9个时钟脉冲添加ACK信号。

第二阶段。主机通过I2C向AD7995发送共8个时钟脉冲,且每发送一个脉冲且脉冲处于高电平的时候,读取SDA线上信号,该信号为转换结果寄存器的高8位,然后再第9个脉冲添加ACK信号。

第三阶段。主机再通过I2C向AD7995发送共8个时钟脉冲,且每发送一个脉冲且脉冲处于高电平的时候,读取SDA线上信号,该信号为转换结果寄存器的低8位,然后再第9个脉冲添加No_ACK信号,最后发送STOP信号结束通信。

7、STM32——AD7995驱动代码

AD7995.c文件

#include "AD7995.h"
#include "delay.h"void AD7995_Init(){IIC_Init();}//初始化IIC
void IIC_Init(void)
{                        GPIO_InitTypeDef GPIO_InitStructure;RCC_APB2PeriphClockCmd(    RCC_APB2Periph_GPIOB, ENABLE ); //使能GPIOB时钟GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6|GPIO_Pin_7;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ;   //推挽输出GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_Init(GPIOB, &GPIO_InitStructure);GPIO_SetBits(GPIOB,GPIO_Pin_6|GPIO_Pin_7);   //PB6,PB7 输出高
}
//产生IIC起始信号
void IIC_Start(void)
{SDA_OUT();     //sda线输出IIC_SDA=1;       IIC_SCL=1;delay_us(4);IIC_SDA=0;//START:when CLK is high,DATA change form high to low delay_us(4);IIC_SCL=0;//钳住I2C总线,准备发送或接收数据
}
//产生IIC停止信号
void IIC_Stop(void)
{SDA_OUT();//sda线输出IIC_SCL=0;IIC_SDA=0;//STOP:when CLK is high DATA change form low to highdelay_us(4);IIC_SCL=1; IIC_SDA=1;//发送I2C总线结束信号delay_us(4);
}
//等待应答信号到来
//返回值:1,接收应答失败
//        0,接收应答成功
u8 IIC_Wait_Ack(void)
{u8 ucErrTime=0;SDA_IN();      //SDA设置为输入  IIC_SDA=1;delay_us(1);    IIC_SCL=1;delay_us(1);   while(READ_SDA){ucErrTime++;if(ucErrTime>250){IIC_Stop();return 1;}}IIC_SCL=0;//时钟输出0       return 0;
}
//产生ACK应答
void IIC_Ack(void)
{IIC_SCL=0;SDA_OUT();IIC_SDA=0;delay_us(2);IIC_SCL=1;delay_us(2);IIC_SCL=0;
}
//不产生ACK应答
void IIC_NAck(void)
{IIC_SCL=0;SDA_OUT();IIC_SDA=1;delay_us(2);IIC_SCL=1;delay_us(2);IIC_SCL=0;
}
//IIC发送一个字节
//返回从机有无应答
//1,有应答
//0,无应答
void IIC_Send_Byte(u8 txd)
{                        u8 t;   SDA_OUT();         IIC_SCL=0;//拉低时钟开始数据传输for(t=0;t<8;t++){              if((txd&0x80)>>7)IIC_SDA=1;elseIIC_SDA=0;txd<<=1;      delay_us(2);   //对TEA5767这三个延时都是必须的IIC_SCL=1;delay_us(2); IIC_SCL=0;    }
}
//读2个字节,ack=1时,发送ACK,ack=0,发送nACK
u16 IIC_Read_Byte(unsigned char ack)
{unsigned char i;u16 receive=0;SDA_IN();//SDA设置为输入for(i=0;i<8;i++ ){IIC_SCL=0; delay_us(2);IIC_SCL=1;if(READ_SDA)receive|=1<<(15-i);delay_us(2); }          IIC_Ack(); //发送ACK   for(i=0;i<8;i++ ){IIC_SCL=0; delay_us(2);IIC_SCL=1;if(READ_SDA)receive|=1<<(7-i);delay_us(2); }         if (!ack)IIC_NAck();//发送nACKelseIIC_Ack(); //发送ACK   return receive;
}//在AD7995指定地址读出一个数据
//ReadAddr:开始读数的地址
//返回值  :读到的数据
u16 AD7995_ReadOneByte(u8 ReadAddr)
{                 u16 temp=0;ReadAddr=ReadAddr<<1|0x01; //读数据IIC_Start();  IIC_Send_Byte(ReadAddr);//发送地址IIC_Ack();   temp=IIC_Read_Byte(0);   //0不继续转换      IIC_Stop();//产生一个停止条件     return temp;
}//在AD7995指定地址写入一个数据
//WriteAddr  :写入数据的目的地址
//DataToWrite:要写入的数据
void AD7995_WriteOneByte(u8 WriteAddr,u8 DataToWrite)
{                       WriteAddr=WriteAddr<<1;  //写数据   IIC_Start();  IIC_Send_Byte(WriteAddr);     //发送地址IIC_Ack();                                                       IIC_Send_Byte(DataToWrite);     //发送字节                              IIC_Ack();                  IIC_Stop();//产生一个停止条件 delay_ms(10);
}

AD7995.h文件

#ifndef __AD7995_H
#define __AD7995_H#include "stm32f10x.h"
#include "sys.h"#define AD7991_0      0x28
#define AD7991_1        0x29
#define AD7995_0        0x28
#define AD7995_1        0x29
#define AD7999_1        0x29//IO方向设置
#define SDA_IN()  {GPIOB->CRL&=0X0FFFFFFF;GPIOB->CRL|=(u32)8<<28;}
#define SDA_OUT() {GPIOB->CRL&=0X0FFFFFFF;GPIOB->CRL|=(u32)3<<28;}//IO操作函数
#define IIC_SCL    PBout(6) //SCL
#define IIC_SDA    PBout(7) //SDA
#define READ_SDA   PBin(7)  //输入SDA //IIC所有操作函数
void IIC_Init(void);                //初始化IIC的IO口
void IIC_Start(void);               //发送IIC开始信号
void IIC_Stop(void);                //发送IIC停止信号
void IIC_Send_Byte(u8 txd);         //IIC发送一个字节
u16 IIC_Read_Byte(unsigned char ack);//IIC读取两个字节
u8 IIC_Wait_Ack(void);              //IIC等待ACK信号
void IIC_Ack(void);                 //IIC发送ACK信号
void IIC_NAck(void);                //IIC不发送ACK信号void IIC_Write_One_Byte(u8 daddr,u8 addr,u8 data);
u8 IIC_Read_One_Byte(u8 daddr,u8 addr);  //AD7995所有操作函数
void AD7995_Init();
u16 AD7995_ReadOneByte(u8 ReadAddr);
void AD7995_WriteOneByte(u8 WriteAddr,u8 DataToWrite);
#endif

STM32模拟IIC协议驱动AD7991/AD7995/AD7999芯片相关推荐

  1. STM32模拟SPI协议驱动AD7908芯片

    最近时间,由于项目需求用到了AD7908的AD采集芯片,通过查阅其相关的技术手册之后,成功的实现了其AD采集的功能,下面分享一下我的一些经验. AD7908是一个8位高速.低功耗.8通道的ADC芯片, ...

  2. 【五一特刊】FPGA零基础学习:IIC协议驱动设计

    本系列将带来FPGA的系统性学习,从最基本的数字电路基础开始,最详细操作步骤,最直白的言语描述,手把手的"傻瓜式"讲解,让电子.信息.通信类专业学生.初入职场小白及打算进阶提升的职 ...

  3. STM32基于IIC协议的OLED模块的使用

    前言 一.项目涉及的内容 项目简介 二.模块实操 1. IIC模块 1.1 IIC协议格式 1.2 开始信号与停止信号 1.3 写数据 1.3.1 硬件IIC代码编写 1.3.2 软件模拟IIC代码编 ...

  4. STM32模拟I2C协议获取MLX90615红外温度传感器测温数据(Open Drain管脚配置)

    STM32模拟I2C协议获取MLX90615红外温度传感器测温数据(Open Drain管脚配置) STM32的GPIO管脚可以配置为Open Drain输出模式,并且有两个功能: 可以设置内部上拉, ...

  5. FPGA零基础学习:IIC协议驱动设计

    FPGA零基础学习:IIC协议驱动设计 本系列将带来FPGA的系统性学习,从最基本的数字电路基础开始,最详细操作步骤,最直白的言语描述,手把手的"傻瓜式"讲解,让电子.信息.通信类 ...

  6. 使用STM32+硬件IIC+DMA驱动GT系列触摸屏(GT911)

    使用STM32+硬件IIC+DMA驱动GT系列触摸屏(GT911) 初始化代码 /** @brief GT911 初始化程序* @param None* @retval None*/ void GT9 ...

  7. STM32模拟IIC驱动sht30温湿度传感器

    最近有在使用sht30这个传感器,相比于新手常用的dht11传感器,sht30更精确,自己花了半小时调好了 所以拿出来分享给大家. sht30外观 驱动不是自己写的, 是采用CSDN上的一位朋友的 , ...

  8. STM32模拟IIC读取PCF8563

    作者第一次开写博客,本着学习的态度,附上自己总结的代码,希望大家多多指点! 一.首先是对于PCF8563芯片的介绍与使用说明: PCF8563 是PHILIPS 公司推出的一款工业级内含I2C 总线接 ...

  9. STM32通过SPI协议驱动OLED屏

    坚持就是胜利 一.SPI协议介绍 01 简介 02 SPI物理层 03 SPI基本通讯过程 二.OLED显示器介绍 01 简介 02 接口定义 03 与STM32接线图 三.汉字取模软件介绍 01 下 ...

最新文章

  1. React 的性能优化(一)当 PureComponent 遇上 ImmutableJS
  2. python invalid type promotion_17个新手常见Python运行时错误
  3. 屏蔽机房设计时需要注意什么 ?如何更好维护使用屏蔽机房?
  4. 【OS学习笔记】三十五 保护模式十:中断描述符表、中断门和陷阱门
  5. 网页字段位置php改变,php实现子字符串位置相互对调互换的方法
  6. python动态爬取知乎_python爬虫从小白到高手 Day2 动态页面的爬取
  7. 谈谈Intranet与Internet的区别和联系
  8. easyui datagrid java_java_easyui体系之DataGrid(4)[转]
  9. nginx配置和安装
  10. 人工智能数据集文本处理Onehot/TF/TFIDF矩阵的生成
  11. Android推送服务——百度云推送
  12. 3GPP 5G 常用协议规范下载整理
  13. 「js基础」JavaScript入门,难不难你来说
  14. 加州房价--决策树与随机森林
  15. 你的领英账号总被封?实战总结避免和解决领英帐号被封的最强攻略
  16. 想要创业,却没货源?答应我,别只在阿里妈妈上找了好吗
  17. 信息学奥赛一本通1336:寻找树根和孩子(图论算法-树)详细讲解
  18. js网页繁体简体转换(备忘)
  19. MATLAB新手简明使用教程(七)——使用matlab建立多项式以及求导,商求导乘积求导等——新手来看,保证看懂。
  20. Facade in Java

热门文章

  1. java毕业设计‘网上宠物店(附源码、数据库)
  2. 第五届双态IT乌镇用户大会-智能运维算法研讨会圆满落幕
  3. ERROR:Module not found: Error: Can‘t resolve ‘core-js/modules/es.promise.js‘ in ‘address‘
  4. 基于鸿蒙系统 + Hi3861 的wifi小车,可以通过电脑、手机控制
  5. 随缘php企业网站管理系统V2.0 shownews.php注入漏洞
  6. 【人脸识别实战二】服务器端设计与实现
  7. python 监控框架_httprunner+locusts+python接口测试框架
  8. jQuery--CSS样式操作及动画操作
  9. [个人心得]敏捷管理Agile中Epic, story 和task的用途和管理目标
  10. 【模式识别】最小风险贝叶斯决策