snifer

[原创]ADI AD8555可编程放大器的体验

0
阅读(3574)

最近公司引入了一款新的压力传感器,在调理信号的时候使用的很多AD转换器都不合适,老是出现各种漂移,几位老大都很苦恼,昨晚上我们加班,在公司查阅了很多案例,看到了ADI 的 AD8555数字可编程放大器,这款芯片一款增益及输出失调,可数字编程的零漂移桥式传感放大器,特别适合于多点或多参量测量系统的前向通道,可对各种传感器信号进行调理,所以我决定试一试,大家也比较认可。

这款芯片工作电压为2.7 V~5.5 V,工作温度范围为-40℃~125℃;其数字可编程增益控制范围为70~l 280;DC和ACCMRR高达96 dB;输入失调电压低(最大为10μV),输入失调电压漂移50 nV/℃;通过外接电容器,可以方便地实现低通滤波功能;输入和输出范围很宽,能驱动低电压ADC。另外,AD8555还具有开路和短路故障保护以及输出摆幅限制功能。这个特性为我们整个项目的成败起到了决定性作用。

晚上找硬件部的制版后,参照图纸,一直在写程序,加了一晚上班,我觉得很有成就感,迫不及待的拿出来给大家欣赏:这款芯片的控制芯片是ADUC841,

#include<ADuc841.h>
#include<stdio.h>

#define  Function  2  
                      // 0:改变感应电流。当AD8555通电后,向高附加值的意义当前默认值。
                      // 1:模拟模式
 // 2: 程序模式
 // 3:读模式

#define Second_stage_gain  0  //(<<AD8555 Data Sheet>> Table 7)
                              //Code--获取
                              // 0----17.5
                              // 1----25
 // 2----35
 // 3----50
 // 4----70
 // 5----100
 // 6----140
 // 7----200 

#define First_stage_gain 0  //(<<AD8555 Data Sheet>> Table 6 )
                           //参照AD8555数据表定义

#define Output_offset   128    

#define tw1  64  
#define tw0  0
#define tws  8

void send_bit(unsigned int);
void delay(int);
void simulate();            
void program();       
void read();    
void current();    
void field();    
void fieldII(unsigned int);       
void fieldIII();                
void fieldIV(int);       
void fieldIV_program(int);        
void fieldV();                     
sbit digin=P2^1;    //设置另外一个输出 ADuC841

int main(void)
{
     if(Function==0)current();     //0的时候
     else if (Function==1)simulate();//1的情况,下同
     else if (Function==2)program();
     else read();
while(1){digin=0;}
}

//模拟模式
 void simulate()
{
 unsigned int temp;
 digin=0;
 for(temp=1;temp<=3;temp++)
 {
   field();                                   
   send_bit(0);                          
   send_bit(1);
   fieldII(temp);            
   fieldIII();                   
   if(temp==1)
      fieldIV(Second_stage_gain);           
   else if(temp==2)
      fieldIV(First_stage_gain);                    
   else                            
      fieldIV(Output_offset);
   fieldV();                            
 }
 return;
}


//关键的程序模式,设计的难点
int j,flag,count,parity;
void program()
{
 int i;
 unsigned int temp;
 digin=0;
 parity=0;
 for(temp=1;temp<=5;temp++)
 {
      j=129;
 count=0;
 flag=1;
      while((j&0x00ff)>128)
     {
        field();  //发送0位数据包,下面分别是1,2,3,4
  send_bit(1);            
  send_bit(0);
fieldII(temp);              
  fieldIII();                     

if(temp==1)
      fieldIV_program(Second_stage_gain);  
     
  else if(temp==2)
  fieldIV_program(First_stage_gain);              
     
  else if(temp==3)
    fieldIV_program(Output_offset);              
else if(temp==4)  //blow the master fuse
{ for(i=0;i<7;i++)send_bit(0);
          send_bit(1);
 j=0;
}
else    
{  
 if(parity%2==1)   
   {for(i=0;i<5;i++)send_bit(0);  
    send_bit(1);
    send_bit(0);
    send_bit(0);
}
  else {for(i=0;i<8;i++)send_bit(0);}
  j=0;
}
     fieldV();                           
  delay(1280);                               
     }   
 }
 return;
}

//读模式
void read()
{
  int i,temp;   
  for(temp=1;temp<=3;temp++)
  {
    field();                       
    send_bit(1);
    send_bit(1);
    fieldII(temp);     
    fieldIII();     
    fieldIV(0);           
    fieldV();
  for(i=0;i<8;i++)send_bit(0);                        
  }  
   return;
}


//感应电流
void current()
{
  field();
  send_bit(0);  
  send_bit(0);
  fieldII(1);
  fieldIII();  
  fieldIV(1);                     
  fieldV();  
  return;
}

void send_bit(unsigned int log)
{
 if(log==0)
 {digin=0;
  delay(tws);
  digin=1;
  delay(tw0);
  digin=0;
  delay(tws);
 }
 if(log==1)  
  {digin=0;
   delay(tws);
   digin=1;
   delay(tw1);
   digin=0;
   delay(tws);
  }
  return;
}
void delay(int num)
  {while(num>0)
   num--;
  }  



void field()
{  int i;
   send_bit(1);                   
   for(i=0;i<10;i++)send_bit(0);  
   send_bit(1);   
   return;
}

void fieldII(unsigned int stage)
 {
   if(stage==1)            
    { 
 send_bit(0);                               
      send_bit(0);  
}

   else if(stage==2)
    {
send_bit(0);   
     send_bit(1);
}                                    
      
   else if(stage==3)
    { 
 send_bit(1);                               
      send_bit(0);  

else 
{                                              
 send_bit(1);  // The code is 11.
 send_bit(1);
}
   return;
 }




 void fieldIII()
 {
   send_bit(1);                           
   send_bit(0); //The code is 10.
   return;
 }




void fieldIV(int value)         
{   
   int i;   
   for(i=0;i<8;i++)
       {if((value<<i&128)==0)send_bit(0);
        else send_bit(1);
       }  
   return;
}




void fieldIV_program(int value)
{
          int i;

    for(i=0;i<8;i++)
      {j=value<<i;
 if((value&128>>i)==0)send_bit(0);
  
 else {
         if(count<i)flag=1;
         if(flag==1)
             {send_bit(1);
  parity+=1;  
  count=i;  
          for(i;i<7;i++)send_bit(0);s.
      flag=0;
     }
  else send_bit(0);
     
}                                     
      }
       return;
}




void fieldV()
{ int i;
  send_bit(0);                                 
  for(i=0;i<10;i++)send_bit(1);
  send_bit(0);
  return;
}

程序的整体结构我已经标出来了,也给出了注释,比较简单,当然设计中参考了ADI的大佬,非常感谢他们,把程序调通交给测试组的小弟们,我就头昏眼花了,回家睡觉了,下午去看效果。