3154|2

2

帖子

0

TA的资源

一粒金砂(初级)

楼主
 

单片机mc9s12dg128和ADS1115配合采集但一电压,最后串口输出的结果时不时输出00000 [复制链接]

include       
#include    
#pragma LINK_INFO DERIVATIVE "mc9s12dg128b"
#define SDA PORTA_BIT6
#define SCL PORTA_BIT7
#define uint8_t unsigned char

//变量定义
uint8_t I2C_ERROR=1;  /*应答标志位*/
uint8_t reader;
byte table[4];
char out_str[]={"00000\n"};





void Delay1us(int c)
{
  int cnt=0;
  for(cnt=0;cnt   {
  _asm NOP; _asm NOP;_asm NOP;_asm NOP;_asm NOP;
  _asm NOP; _asm NOP;_asm NOP;
  }

}



void delay(int ms)
{   
   int i,j;
   for(i=0;i    for(j=0;j<1300;j++);
}
/***************************************/
/*串口初始化及发送*/
/***************************************/  
void Sci0open(void)
{
SCI0BD=54;     //9600波特率设置
SCI0CR1=0x00;  //正常8位模式,无奇偶校验位
SCI0CR2=0X2C;  //接收中断允许
}

void Sci_send(char k)   //发一个字符
{
SCI0SR1_TDRE=1;
SCI0DRL=k;
}
void Sci_send_String(char *p)    //发字符串
{
  while(*p)
  {
    Sci_send(*p);
    p++;
    delay(2);
  }
}



/*******************************************************************
                      起动总线函数               
函数原型: void   Start_I2c();  
功能:      启动I2C总线,即发送I2C起始条件.  
********************************************************************/
void I2C_START()
{
   SDA=1;            /*发送起始条件的数据信号*/
   Delay1us(20);
   SCL=1;
   Delay1us(20);      /*起始条件建立时间大于4us,延时*/

   SDA=0;            /*发送起始信号*/
   Delay1us(20);      /* 起始条件锁定时间大于4μs*/

   SCL=0;            /*钳住I2C总线,准备发送或接收数据 */
   Delay1us(20);
}
/*******************************************************************
            结束总线函数               
函数原型: void   Stop_I2c();  
功能:      结束I2C总线,即发送I2C结束条件.  
********************************************************************/
void  I2C_STOP()
{
   SDA=0;    /*发送结束条件的数据信号*/
   Delay1us(20);     /*发送结束条件的时钟信号*/
   SCL=1;    /*结束条件建立时间大于4us*/
   Delay1us(20);

   SDA=1;    /*发送I2C总线结束信号*/
   Delay1us(20);
}
/*******************************************************************/
void send_nack()
{
  SDA=0;
  Delay1us(20);
  SCL=1;
  Delay1us(20);
  SCL=0;
  Delay1us(20);
}

/*******************************************************************               
                              检查应答位
********************************************************************/

void check_ack()
{
  Delay1us(20);
  SCL=0;
  Delay1us(20);
  DDRA_BIT6=0;
  Delay1us(20);
  SDA=1;
  Delay1us(20);
  SCL=1;
  Delay1us(20);
  if(SDA==1)
    I2C_ERROR=1;
  else
    I2C_ERROR=0;
  SCL=0;
  Delay1us(20);
  DDRA_BIT6=1;
}

/*******************************************************************
                               发送1字节数据
********************************************************************/
void I2C_send(uint8_t data)
{
  uint8_t i=8;
  uint8_t m=data;
  uint8_t temp;
  for(i=8;i>0;i--)
  {
    temp=m&0x80;
     if(temp==0x80)
      SDA=1;
     else
      SDA=0;
      Delay1us(1);
      SCL=1;
      Delay1us(1);
      SCL=0;
      m=m<<1;   
}
}
/********************************************************************
                               接收1字节数据
********************************************************************/
byte I2C_receive1byte()
{
  uint8_t i=8;
  uint8_t j=0;
  DDRA_BIT6=0; Delay1us(20);
  SDA=1;
  for(i=8;i>0;i--)
  {
    SCL=1;
    Delay1us(20);
if(SDA==1)
    j=j|0x01;
    else j=j;
    SCL=0;

  if(i!=1)
   {
    j=j<<1;  Delay1us(20);
    }
  }
  DDRA_BIT6=1;   Delay1us(20);
  reader=j;//把reader定义成全局变量
  return reader;
}



/*******************************************************************
通过I2C总线配置ADS1113
注意:ADS115地址为1001000
此处程序需要修改
********************************************************************/
void Confige1113 (void)
{
    unsigned char  i;
    table[0] = 0x90;     //CMD_Write,ADS115地址为1001000;
    table[1] = 0x01;     //指向配置寄存器
    table[2] = 0x90;     //设置配置寄存器的高八位0000 0000;连续转换模式
    table[3] = 0x00;     //设置配置寄存器的低八位1000 0000,即转换速率为128SPS
    I2C_START();         //发送起始信号
    for(i=0;i<4;i++)
    {   
      I2C_send(table[i]);//将table里面的数写入ads1115
      check_ack();       //检查ADS1115的ACK信号
      if(I2C_ERROR==1)   //如果ADS115无ACK信号则退出
          break;
    }
    I2C_STOP();          //发送停止信号
}


/*******************************************************************
通过I2C总线读取ADS1113的采样值
注意:ADS115地址为1001000,
此处程序需要修改
********************************************************************/
//指向ADS1113指针寄存器用于准备读取数据
void PointRegister (void)
{
    unsigned char i;
    table[0] = 0x90;//写
    table[1] = 0x00;//指针指向转换寄存器
    I2C_START();    //发送起始信号
    for(i=0;i<2;i++)
    {
      I2C_send(table[i]);//将table里面的数写入ads1113
      check_ack();       //检查ADS1113的ACK信号
      if(I2C_ERROR==1)   //如果ADS113无ACK信号则退出
        break;
    }
    I2C_STOP();       //发送停止信号
}
//读转换寄存器里面的值
word read_data()
{  
  word result,resulth,resultl;
    I2C_START();    //发送起始信号
    I2C_send(0x91); //发送从地址位,读命令
    check_ack();       //检查ADS1115的ACK信号
    if(I2C_ERROR==0)   //如果ADS115有ACK信号则读数据
     {

       resulth = I2C_receive1byte();  //高八位
       Delay1us(5);  
       send_nack();   //发送主机的ACK信号            
       resultl = I2C_receive1byte();  //底八位
       Delay1us(5);
       send_nack();   //发送主机的ACK信号
     }
    else
    {
       resulth = 0;
       resultl = 0;
    }  
    I2C_STOP();       //发送停止信号
    result=(resulth<<8)|resultl;
    if(result>0x7fff)
      result=~result+1;//用于测量负电压,负电压从8000~ffff,负电压与正关于0有类似对称关系,按位取反后+1相同
    return result;          
}

/*******************************************************************
通过I2C总线读数据
此程序包括对ADS1113的配置过程和从ADS1113读出采样数据2个过程   
********************************************************************/
word read_ads1113()
{
  word value;
  Confige1113();   //配置ADS1113
  Delay1us(5);
  PointRegister();
  Delay1us(5);
  value=read_data();     //读取数据
  return value;
}



/***************************************/
/*主函数*/                                                                        
/***************************************/   
void main(void)
{
  word AD_date;
  DDRA=0xC0;
  PORTA=0xff;
//  PTJ=0x00;
// PPSJ=0x00;
  Sci0open();
  EnableInterrupts;
  for(;;)
  {  
  AD_date=read_ads1113();  
  out_str[0]=AD_date/10000+0x30;
  out_str[1]=AD_date/1000%10+0x30;
  out_str[2]=AD_date/100%10+0x30;        
  out_str[3]=AD_date/10%10+0x30;
  out_str[4]=AD_date%10+0x30;
  delay(100);

    Sci_send_String(out_str) ;

  }

}






此帖出自单片机论坛

最新回复

read_data()函数出问题了呗,多加点出错处理机制,只有正确的时候才输出结果。  详情 回复 发表于 2017-2-20 15:17
点赞 关注
 

回复
举报

664

帖子

104

TA的资源

纯净的硅(中级)

沙发
 
read_data()函数出问题了呗,多加点出错处理机制,只有正确的时候才输出结果。
此帖出自单片机论坛
 
 

回复

2

帖子

0

TA的资源

一粒金砂(初级)

板凳
 
我现在能让他数值对了再发送,但我就是想知道它为什么会出现0,用示波器看了它的时序,发现前面都对,就是读转换数据的时候sda线上都是低电平,想不明白
此帖出自单片机论坛
 
 
 

回复
您需要登录后才可以回帖 登录 | 注册

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/10 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表