请大家帮我看看ADS1100程序哪里错了?!
老得不到数据出来的都是乱码
我是按网上给的程序写的
//24M晶掁
#include <reg2051.H>
#include <INTRINS.H>
#define uchar unsigned char
#define uint unsigned int
#define ulong unsigned long
#define true 1
#define false 0
#define dis_null 0x11//数码管全灭段码 17
#define dis_full 0x12//数码管全亮段码 18
#define null 0x00//数据缺省状态为零
#define Nop() _nop_()
/*********ADS1100引脚定义**************/
sbit SDA = P1^0;
sbit SCL = P1^1;//加了上拉电阻1K
/**********变量定义*****************/
uchar ACK;
uchar adc_h;
uchar adc_l;
uint adc;
uint adc_data;
/*************ad模块子程序*****************************/
void ads_start(void); //开始
void ads_stop(void); //停止
uchar ack_check(void); //应答
void ads_sendBYTE(uchar send_data);// 发送一个字节
uchar ads_reciveBYTE(void); //接受一个字节
void send_ack(void); //发送应答信号
void send_nack(void); //发送非应答信号
void write_ads(uchar snd_data); //写器件地址和配置字。
uint read_ads(void); //从ADS1100中读出数据,返回 adc=(adc_h<<8)+adc_l;
//void dis_adc();
/************主程序********************/
void main()
{
// delayms(500);
init_mcu();
SDA=1;
SCL=1;
write_ads(0x8C);//写配置字 转换速率8sps,16位1倍增益,连续转换
// write_ads(0x93);//转换速率128sps,12位, 8倍增益,单次转换,一次AD转换完后自动掉电
while(1)
{
adc_data=read_ads();//读取ad转换值
dis_buf=adc_l<<4;/*这一段只是我的显示程序,没全贴上来,我只是看看转换后的16位数是多少
dis_buf=adc_l>>4;
dis_buf=adc_h<<4;
dis_buf=adc_h>>4;
display_some(0,4);
}
}
/*****************ads1100模块区*******************************************************/
/*****************************************************/
/* 函数原型: void ads_start (void) */
/* 功 能: 提供I2C总线工作时序中的起始位。 */
/*****************************************************/
void ads_start (void) //在SCL高的情况下,SDA由高到低的变化造成START。
{
SDA=1;
_nop_();
_nop_();
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SDA=0;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SCL=0;
_nop_();
_nop_();
_nop_();
_nop_();
}
/**********************************************************/
/* 函数原型: void ads_stop(void) */
/* 功 能: 提供I2C总线工作时序中的停止位。 */
/**********************************************************/
void ads_stop(void) //在SCL高的情况下,SDA由低到高的变化造成STOP。
{
SDA=0;
_nop_();
_nop_();
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SDA=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SCL=0;
_nop_();
_nop_();
_nop_();
_nop_();
}
/*****************************************************************************/
/* 函数原型: uchar ack_check(void) */
/* 功 能: 提供I2C总线的时钟信号, 并返回在时钟电平为高期间SDA 信号线上状*/
/* 态。本函数可用于数据发送, 也可用于数据接收。 */
/*****************************************************************************/
uchar ack_check(void) // 检查 从机 应答信号 SDA为低电平为应答
{
//SCL=0;
SCL=1;
_nop_();
_nop_();
if(SDA) ACK = 1;
elseACK = 0;
SCL=0;
return(ACK);// 如果收到ACK应答则返回0, 否则返回1。
}
/*******************************************************/
/* 函数原型: void ads_sendBYTE(uch data) */
/* 功 能: 向I2C总线发送8位数据。 */
/*******************************************************/
void ads_sendBYTE(uchar send_data) // 发送一个字节
{
uchar bitcount=8; // 发送8位数据。
do
{
if((send_data&0x80)==0x80)SDA=1; //写 1
else SDA=0; //写 0
SCL=0; //在时钟大于4u秒期间写数据
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SCL=0;
send_data=send_data<<1; // 待送数据左移一位.
bitcount--;
}while(bitcount);//等待数据写完
SDA=1; //释放总线等待应答
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
}
/***************************************************************************/
/* 函数原型: ads_reciveBYTE(void) */
/* 功 能: 从I2C总线上接收8位数据信号, 并将接收到8位数据作为一个字节*/
/* 返回, 不回送应答信号ACK。主函数在调用本函数之前应保证SDA信 */
/* 号线处于浮置状态, 即使8052的Px.x脚置1。 */
/***************************************************************************/
uchar ads_reciveBYTE(void) //接受一个字节
{
uchar in_data=0;
uchar bitcount1=8;
do
{
SCL=0; //在时钟大于4u秒期间读数据
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
if(SDA) in_data=in_data|0x01; //读 1
else in_data=in_data&0xfe; //读 0
SCL=0;
if(bitcount1-1) in_data=in_data<<1;
bitcount1--;
}while(bitcount1);
return(in_data);
}
/****************************************************************************/
/* 函数原型: voidsend_Ack(void); */
/* 功 能: 向I2C总线发送一个应答信号ACK, 用于连续数据读取时。 */
/****************************************************************************/
void send_ack(void) // 发送连续读信号 主机应答信号
{
SDA=0; //低电平应答
SCL=0;
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SCL=0;
}
void send_nack(void) // 发送不连续读信号 非应答信号
{
SDA=1; //高电平非应答
SCL=0;
SCL=1;
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
SCL=0;
}
/*********************************************************/
/* 函数原型: void write_ads(uchar snd_data) */
/* 功 能: 写器件地址和配置字。 */
/*********************************************************/
void write_ads(uchar snd_data)//写器件地址和配置字
{
ads_start(); //开始写
ads_sendBYTE(0x90); //写器件地址(写) 1001(固定) 000(器件编号) 0(写)
do
{
;
}while(ack_check()); //等待应答
ads_sendBYTE(snd_data); //写配置字
do
{
;
}while(ack_check()); //等待应答
ads_stop(); //结束写
}
/******************************************************/
/* 函数原型: read_ads(void) */
/* 功 能: 数据读取。 */
/******************************************************/
uint read_ads(void) //从ADS1100中读出数据
{
uchar adc_cfg;
ads_start(); //开始读
ads_sendBYTE(0x91); //写器件地址(读) 1001(固定) 000(器件编号) 1(读)
do
{
;
}while(ack_check()); //等待应答
adc_h = ads_reciveBYTE(); //读高8位
send_ack(); //连续读
adc_l = ads_reciveBYTE(); //读低8位
send_ack(); //连续读
adc_cfg = ads_reciveBYTE(); //读配置字
send_nack(); //发送不连续读信号
ads_stop(); //结束读
adc=(adc_h<<8)+adc_l;
return adc;
}
/**********************************************************************************************/ if((send_data&0x80)==0x80)SDA=1; //写 1
else SDA=0; //写 0
SCL=0; //在时钟大于4u秒期间写数据
SCL=1;
这里不对吧,应该是scl=0时改变sda,你这里怎么先改变sda,再scl啊
iic关键的一点scl==0时改变sda 没用过,但帮你顶下. 知道错在哪了
我的显示写错了,应该是
dis_buf=adc_l&0x0f
dis_buf=adc_l>>4;
dis_buf=adc_h&0x0f;
dis_buf=adc_h>>4;
郁闷,害我调了一天,时序看了好遍。 zhuyi2576老兄留个qq好吗,请教一下,谢谢 标记,正在调试ADS1100
页:
[1]