liangxliao 发表于 2007-11-26 20:46:01

CS5460A芯片读取数据时经常出现读回0的状况,请教各位了.

CS5460A芯片读取数据时经常出现读回0的状况,但有时读的数据准确.请教各位了.有人说是SPI的时序问题.但现在还没查明!下面是我的SPI的读写时序.请大家帮我看看.
//////////////////////////////////////////////////
void send_5460a(unsigned char dat)
{
   unsigned char i,d=dat;
   for(i=0;i<8;i++)
   {
      SCLK=0;
      if(d&0x80)
          SDI=1;
          else
          SDI=0;
               
      SCLK=1;
      d<<=1;
      SCLK=0;
   }
   SDI=1;
}
///////////////////////////////////////////
unsigned char receive_5460a(void)
{
   unsigned char i,result=0;
   SDI=1;
   for(i=0;i<8;i++)
   {
      //if(i==7)SDI=0;
      //SCLK=0;
      result<<=1;
      SCLK=1;
      if(SDO)
         result|=1;
      SCLK=0;
   }
   //SDI=1;
   return(result);
}
//////////////////////////////////////////////////
void write_5460a(void)
{
    unsigned char i;
    CS=0;
    NOP();
    NOP();
    NOP();
    send_5460a(buf);
        //sec= 0;
        //while(SDO&& sec< 1000);
    for(i=1;i<4;i++)
      {
      send_5460a(buf);
      }
    NOP();
    NOP();
    NOP();
    CS=1;   
}
////////////////////////////////////////////////
void read_5460a(unsigned char cmd)
{
    unsigned char i;
    CS=0;
    NOP();
    NOP();
    NOP();
    send_5460a(cmd);
        sec= 0;
        while(SDO&& sec< 1000);
    for(i=0;i<3;i++)
      {
       buf=receive_5460a();
      }
    NOP();
    NOP();
    NOP();
    CS=1;
}
//////////////////////////////////////////

liangxliao 发表于 2007-11-26 21:36:50

自己顶一下了./emotion/em035.gif

liangxliao 发表于 2007-11-27 10:48:01

哪位大哥指点一下了!

liangxliao 发表于 2007-11-27 15:18:37

还是自己顶一下!

jsb8016 发表于 2007-11-27 23:22:12

unsigned char i,result=0;
改成unsigned char i,result=0XFE;
大概就可以了

liangxliao 发表于 2007-11-28 15:38:29

unsigned char i,result=0;
改成unsigned char i,result=0XFE;
大概就可以了

谢谢楼上的!

似乎与这没多大的关系.改了,但还是不行.读数据并不是一直不行,而是可以读到正确数据,但会频繁出现读回来是0的状况.还有个问题我现在使用3片单片机.只有一片出现上面说的情况.其它两片连正确的数据都还不能读到(同一程序,运行结果不一样)!

agency 发表于 2007-11-28 16:30:25

void Send_5460(uchar send_data)
        {
                uchar i;
       
                SCLK=1;                       
                   for(i=0;i<8;i++)
                {                       
              if(send_data&0x80)               
                         SDI=1;               
              else
                           SDI=0;
          
          SCLK = 0;                       
          send_data<<=1;       
          SCLK=1;                               
                                                          
            }
            SDI=1;
        }

liangxliao 发表于 2007-11-29 08:35:04

TO;agency
按你说的那样改了还是没见效!真是郁闷了,你的完整读写程序程序能否共享一下了.

哥们再帮我看看是哪里出问题了.谢谢!

liangxliao 发表于 2007-11-29 09:34:45

期待着高手的解答!!.......~^~

zhangsai 发表于 2007-11-29 13:23:00

unsigned char receive_5460a(void)
{
   unsigned char i,result=0;
   SDI=1;
   for(i=0;i<8;i++)
   {
      //if(i==7)SDI=0; //此处有没有,好像这些地方都要有,即读的同时 要发送0xfe
      //SCLK=0;
      result<<=1;
      SCLK=1;
      if(SDO)
         result|=1;
      SCLK=0;
   }
   //SDI=1;
   return(result);
}

zhangsai 发表于 2007-11-29 13:26:36

signed long cs5460a_read_3byte(uchar read_comm_byte)
{
        uchar i,j;
        uchar input_data={0xfe,0xfe,0xfe,0xfe};
unionUL_temp return_data;
return_data.L_tmp=0;
DDRA&=~(_BV(CS5460A_SDO));
PORTA|=_BV(CS5460A_SDO);
        cs5460a_init();
                        asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
        EN_CS5460A_CS;
        cs5460a_write_byte(read_comm_byte);
        for (i=3;i>0;i--)
        {
               for(j=0;j<8;j++)
                {
                        return_data.P_tmp=return_data.P_tmp<<0x01;
                        if((PINA&_BV(CS5460A_SDO))==0x10)
                       {
                                return_data.P_tmp=return_data.P_tmp|0x01;
                       }
                        if((input_data&0x80)==0x00)
                                {
                                        CLR_CS5460A_SDI;
                                }
                        else
                                {
                                        SET_CS5460A_SDI;
                                }
                        input_data=input_data<<1;
                       asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
                  SET_CS5460A_SCLK;
                   asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
          CLR_CS5460A_SCLK;
             asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
                }
        }
        CN_CS5460A_CS;
return_data.P_tmp=0x00;
//dprintf(0,string_20,return_data.P_tmp,return_data.P_tmp,return_data.P_tmp,return_data.P_tmp);

        return return_data.L_tmp;
}
这是我的成熟产品中的一部分,供你参考

liangxliao 发表于 2007-11-29 14:25:27

读的同时要一边发送OXFE吗?这步我好像没做到.

谢谢.我马上试试.

liangxliao 发表于 2007-11-30 17:47:52

问题有些转机了!!现在可以读到数据,暂时还没发现频繁读到0的状况.
非常高兴!在此谢谢回复过的朋友与关注的朋友.再次谢谢你们了!

woodtower 发表于 2007-11-30 18:46:08

注意这个芯片直接看英文资料,就是从中文官方那里下的资料也别看,全是错误,国人都太不负责了吧!那几天差点搞死我,还好,最后醒悟了全部扔掉了。

liangxliao 发表于 2007-11-30 21:25:56

呵呵.实在是翻译得不好.像有"O"就搞成是"0"了.真是晕倒.

yanrz 发表于 2009-5-23 19:16:43

请教,读出来的功率数据如何转换为实际的功率?满量程的功率大约是多少?
以下是我的电路图:
http://cache.amobbs.com/bbs_upload782111/files_15/ourdev_447258.JPG
接线原理图 (原文件名:接线原理图.JPG)
都回来的数据如下:
9V电压,1.955A电流,81/20W功率
03DB70V 0958F1A 00004Bw 000472W FED2F8v FC9CBCa
9V电压,1.955A/2电流,81/40W功率
03BD7CV 0488A3A 000D6Fw 000212W FD7A4Cv FCE1FAa
请问如何转换呢??
谢谢大侠的回答!!!

yanrz 发表于 2009-6-9 12:47:05

上面给的原理图出错了,应该在电流互感器哪里还有一个10欧姆的电阻

http://cache.amobbs.com/bbs_upload782111/files_15/ourdev_452144.jpg
接线图 (原文件名:接线图.jpg)

dergege 发表于 2009-6-9 21:22:51

同志们还在吗?我把11楼的程序改了改:

void SPI_MasterTransmit_8(unsigned char Data8)
{
unsigned char i;
CS_L;
//delay(2);
SCLK_L;
for(i=0;i<8;i++)
{
if(Data8&0x80) SDI_H;
else SDI_L;
Data8<<=1;
//delay(2);
SCLK_H;
NOP();
SCLK_L;
NOP();
}
NOP();
CS_H;
}

void cs5460a_read_3byte(unsigned char read_comm_byte)
{
      unsigned char tmp;
                unsigned char i,j;
      unsigned char input_data={0xfe,0xfe,0xfe,0xfe};
DDRA&=~(1<<PC3);
PORTA|=(1<<PC3);
         
                        asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
      CS_L;
      SPI_MasterTransmit_8(read_comm_byte);
      for (i=3;i>0;i--)
      {
               for(j=0;j<8;j++)
                {
                        tmp=tmp<<0x01;
                        if((PINC&(1<<PC3))==0x08)
                         {
                              tmp=tmp|0x01;
                         }
                        if((input_data&0x80)==0x00)
                              {
                                        SDI_L;
                              }
                        else
                              {
                                        SDI_H;
                              }
                        input_data=input_data<<1;
                         asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
                  SCLK_H;
                   asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
            SCLK_L;
             asm("nop");
             asm("nop");
             asm("nop");
             asm("nop");
                }
      }
      CS_H;
                put_char(tmp);
                put_char(tmp);
                put_char(tmp);
}

void main(void)
{
init_devices();
while(1) cs5460a_read_3byte(0x0c);
}

我用的是CS5460,现在的情况是,我只接了电源,以及SDI,SDO,CS,SCLK,上点后,我就读一个寄存器,但是读出来的值不正确。
大家帮忙看一下,我SPI发送函数的时序或者其他地方有问题吗?谢谢了!

dergege 发表于 2009-6-9 22:01:34

越来越惨了,现在读出来全部是零了……

zhuxianglin 发表于 2009-6-10 01:15:55

我做的项目和你一样用到这个芯片,有机会交流一下,zhuxianglin@yeah.net

yanrz 发表于 2009-6-12 22:47:17

我还以为是有人给我解答了,呵呵,程序应该是没有问题的,只要你的寄存器没做错的话,有空大家交流下,我也是用这个做项目,不过我想选cs5463,但是我现在手上的只有cs5460的样板,只能先做5460的。

zlbloveng 发表于 2009-7-23 16:43:23

为什么看SPI发的程序都是模拟的啊,

jujishou_0 发表于 2011-7-15 17:47:55

回复【21楼】yanrz yanrz
-----------------------------------------------------------------------

请问我状态寄存器状态位总是不对,以前正常使用过好长一段时间,最近又不行了,是怎么回事

qsm627421059 发表于 2011-8-1 13:19:36

求助-我的CS5460A读出寄存器的数据一直是0????
http://cache.amobbs.com/bbs_upload782111/files_43/ourdev_663129JY5T4O.jpg
(原文件名:5460硬件图.jpg)


#include<reg52.h>
#include<intrins.h>
#include<stdio.h>
#include<stdlib.h>
#include <math.h>

#define uchar unsigned char
#define uint unsigned int

unsigned char read;//功率暂存器
uchar code table[]= "I=";

//lcd管脚定义
#define   LCDIO      P0         //P0口LCD数据线
sbit rs=P2^7;
sbit rd=P2^6;
sbit lcden=P2^5;

//以下是cs5460的管脚定义:

sbit INT=P3^2;
sbit Cs5460_cs=P1^7;
sbit Cs5460_RET=P1^3;
sbit Cs5460_sdo=P1^2;
sbit Cs5460_clk=P1^1;
sbit Cs5460_sdi=P1^0;

//以下是cs5460的函数声明
void Write_Cs5460_Byte(unsigned char temp);
void Write_Cs5460(unsigned char *write,unsigned char n);
unsigned char Read_Cs5460_Byte();
void Read_Cs5460(unsigned char address,unsigned char *read1);
/******************************
原型:void delay(uint n)
行参:uint n
返回值:无
功能:延时n ms
*****************************/
void _delay(uint n)
{
        uint x,y;
        for(x=n;x>0;x--)
                for(y=115;y>0;y--);//12Mhz时延时1MS//
}

void delay1(uint n)
{
        uint x,y;
        for(x=n;x>0;x--)
                for(y=2;y>0;y--);//12Mhz时延时1uS//
}
//LCD函数声明
void write_com(uchar com)                     //lcd写命令函数
{
        rs=0;
        rd=0;
        lcden=0;
        P0=com;
        _delay(2);
        lcden=1;
        _delay(2);
        lcden=0;       
}

void write_date(uchar date)                  //lcd写命数据函数         
{
        rs=1;
        rd=0;
        lcden=0;
        P0=date;
        _delay(2);
        lcden=1;
        _delay(2);
        lcden=0;       
}

void initLCD()                              //lcd初始化函数
{
    uint num;
        lcden=0;
        write_com(0x38);
        write_com(0x0c);
        write_com(0x06);
        write_com(0x01);
        _delay(5);
    write_com(0x80);                     //lcd在第一行第一个位置开始显示

        for(num=0;num<2;num++)   
                {
                        write_date(table);      //显示‘I=’      
                        _delay(1);
                }
}

void display(uchar *x_date)                           //参数显示
{
        uchar t=0x82,a,i;
        uchar temp1,temp2;

for(i=0;i<3;i++)
        {   
                a=x_date;
                temp1=a; //temp1为待显示的十六进制数 @@@@这里buff只是高两位的电流值@@@@//
           temp1 = (temp1 >>4) & 0x0F;//先显示高4位
                if(temp1 < 0x0A) //0-9时
          {
              temp1 = temp1 + 0x30;
      }        
                else temp1 = temp1 + 0x37;//a-f时
                  write_com(t);
       write_date(temp1);
      _delay(50);
      
                  temp2=a; //temp1为待显示的十六进制数
              temp2 = temp2 & 0x0F;//显示低4位
        if(temp2 < 0x0A) //0-9时
          {
              temp2 = temp2 + 0x30;
      }
                else temp2 = temp2 + 0x37;//a-f时
              write_com(t+1);
       write_date(temp2);
      _delay(500);
                t=t+3;
    }
}

////////////CS5460声明//////////////////////
void Write_Cs5460_Byte(unsigned char temp)      //写入一个字节
{
unsigned char i;
   Cs5460_clk=0;
for(i=0;i<8;i++)   //循环8次 写入数据
   {
    Cs5460_clk=0;
    Cs5460_sdi=(bit)(temp&0x80);   //每次传输高字节
        Cs5460_clk=1;
        temp<<=1;
   }
Cs5460_clk=0;
}
//******可选择写入一个命令字或者读寄存器名后加三个字节的内容****//
void Write_Cs5460(unsigned char *write,unsigned char n)
{
        unsigned char i;
        Cs5460_cs=1;
        delay1(2);
        Cs5460_clk=0;
        delay1(2);
        Cs5460_cs=0;

        for(i=0;i<n;i++)
{
        Write_Cs5460_Byte(*(write+i));
}
        Cs5460_clk=0;
        delay1(2);
        Cs5460_cs=1;

       
   
}
//**********读出一个字节***********//@@@@@@@@@有问题@@@@@@@@@@@//

unsigned char Read_Cs5460_Byte()
{
    unsigned char i,tmp,read_data;
        bit c_temp,a;
        tmp = 0xfe;
        Cs5460_clk=0;
    for(i=0;i<8;i++)   //循环8次 写入数据
{
        Cs5460_clk=0;
        Cs5460_sdi=(bit)(tmp&0x80);
        a=Cs5460_sdi;
        c_temp = Cs5460_sdo;
        read_data = read_data|c_temp;
        tmp = tmp<<1;
        if(i!=7)
           {
                read_data = read_data<<1;
           }
        Cs5460_clk=1;
}
    Cs5460_clk=0;      
        return(read_data);
}
                           
   //上一段改为
//**************************************************************//
/*unsigned char Read_Cs5460_Byte()
{
    unsigned int i,tmp=0;
   for(i=0;i<7;i++)   //循环8次 写入数据
{
        Cs5460_clk=0;
        _delay(2);
        Cs5460_sdi=1;            //发送SYS0同步命令0xFE高7位
        Cs5460_clk=1;

        if(Cs5460_sdo) tmp|=0x80>>i;

}
    i=7;
        Cs5460_clk=0;
        _delay(2);
        Cs5460_sdi=0;         //发送SYS0同步命令0xFE最低位
        Cs5460_clk=1;
        if(Cs5460_sdo) tmp|=0x80>>i;
    return(tmp);
}
*/
//************************************************************//
void Read_Cs5460(unsigned char address,unsigned char *read1)
{
       unsigned char i;
          Cs5460_cs=1;
          delay1(2);
      Cs5460_clk=0;
          delay1(2);
          Cs5460_cs=0;
       //static unsigned char tmp,k=0;
      Write_Cs5460_Byte(address);
       for(i=0;i<3;i++)
    {
          *(read1+i)=Read_Cs5460_Byte();
        }
          Cs5460_clk=0;
          delay1(2);
      Cs5460_cs=1;   
}
//*************CS5460初始化函数*********//
void Init_Cs5460()
{   
        unsigned char buff1;
        Cs5460_cs=0;
        delay1(2);
    Cs5460_RET=0;
    _delay(30);              //复位30ms
       
    Cs5460_RET=1;
        _delay(50);
       
      
buff1=0xff;//SYNC1
buff1=0xff;//SYNC1
buff1=0xff;//SYNC1
buff1=0xff;//SYNC0
Write_Cs5460(buff1,4);//写串口初始化//


buff1=0xff;//SYNC1
buff1=0xff;//SYNC1
buff1=0xff;//SYNC1
buff1=0xfe;//SYNC0
Write_Cs5460(buff1,4);//写串口初始化//


buff1=0x40;//写配置寄存器
buff1=0x00;//GI=0电流通道增益=10
buff1=0x18;//中断形式:00-高电平08-低电平10-下降沿18-上升沿
buff1=0xe1;//DLCK=MCLK/1
Write_Cs5460(buff1,4);


buff1=0x5e;
buff1=0xff;
buff1=0xff;
buff1=0xff;
Write_Cs5460(buff1,4);//清状态寄存器


buff1=0x74;
buff1=0x00;
buff1=0x00;
buff1=0x00;
Write_Cs5460(buff1,4);//写屏蔽中断寄存器


buff1=0x78;
buff1=0x00;
buff1=0x00;
buff1=0x00;
Write_Cs5460(buff1,4);//写控制寄存器

/*
buff1=0x4c;
buff1=0x00;
buff1=0x34;
buff1=0x9c;
Write_Cs5460(buff1,4);//写EOUT脉冲输出寄存器
_delay(50);
*/
buff1=0x4A;
buff1=0x00;
buff1=0x0F;
buff1=0xA0;          //每秒计算1次,N=4000
Write_Cs5460(buff1,4);//写CYCLE COUNT寄存器


buff1=0x44;
buff1=0x40;//增益1
buff1=0x00;
buff1=0x00;
Write_Cs5460(buff1,4);//写电流增益寄存器



buff1=0x48;
buff1=0x40;//增益1
buff1=0x00;
buff1=0x00;
Write_Cs5460(buff1,4);//写电压增益寄存器


Read_Cs5460(0x1e,read);//读状态寄存器

//_delay(50);
buff1=read;
buff1=read;
buff1=read;
buff1=0x5e;
Write_Cs5460(buff1,4);//写状态寄存器


buff1=0xe8;
Write_Cs5460(buff1,1);//启动Cs5460,执行连续周期计算


}

void main()
{
//long I;//U,P;
//unsigned char ret6,ret5,ret4,ret3,ret2,ret1;//定义位的值
initLCD();
_delay(70);
Init_Cs5460();

         //Read_Cs5460(0x12,buff);//读取上次功率值
         //Read_Cs5460(0x14,buff);//读取上次能量值
         //Read_Cs5460(0x16,buff);//读取上次电流有效值
         //Read_Cs5460(0x18,buff);//读取上次电压有效值
         
         
/******************************************************此处老师看一下转化有没有问题
         I=0;                                        //后面的乘10取整还没有写
               I=buff;
         I=I<<8;
               I=I+buff;
         I=I<<8;
         I=I+buff;//六位十六进制数
   
    ret6=I/0x100000;                   //取出十万位的值,注意0x100000是个十六进制数
    I=I<<4;                     //I变量左移四位
    ret5=I/0x100000;                  //取出位的值
    I=I<<4;                     //I变量左移四位
    ret4=I/0x100000;                  //取出位的值               
    I=I<<4;                     //I变量左移四位
    ret3=I/0x100000;
    I=I<<4;                     //I变量左移四位
    ret2=I/0x100000;                  //取出位的值
    I=I<<4;                     //I变量左移四位
    ret1=I/0x100000;                  //取出位的值            
    I=ret6*pow(16,-1)+ret5*pow(16,-2)+ret4*pow(16,-3)+ret3*pow(16,-4)+ret2*pow(16,-5)+ret1*pow(16,-6);
        //各位的值乘以位权,完成十六转十进制
**********************************************************************************/
   
while(1)
{
   Read_Cs5460(0x0E,read);//读取上次电流值
    _delay(50);
   display(read);

}                     

      /*
   
                Read_Cs5460(0x10,buff);//读取上次电压值
         
   
               
        */       

}

qsm627421059 发表于 2011-8-1 13:22:20

上面是连接图和程序,希望各位大侠指点~
忙了半个月了,找不出错误!!!./emotion/em101.gif

qsm627421059 发表于 2011-8-4 12:00:49

问题已经解决了,程序没错,是硬件有点小问题
数据都可以读出来,但不知道怎么转成实际值,求高人指点~

fxk1220 发表于 2012-11-2 11:14:26

你好,能否请教下,你最后查出来的问题是什么。我也遇到同样的问题,一直读出来数据为0.

tscyds 发表于 2012-11-22 22:10:49

怎么判断读出的数据是否正确,求各位大神解答

xylslss 发表于 2013-5-12 10:34:01

qsm627421059 发表于 2011-8-4 12:00 static/image/common/back.gif
问题已经解决了,程序没错,是硬件有点小问题
数据都可以读出来,但不知道怎么转成实际值,求高人指点~ ...

大侠,请问你后来是怎么解决CS5460A的问题的?我现在也是CS5460A读取回来的数据全是0

xylslss 发表于 2013-5-12 11:09:36

楼主,你后来调出CS5460A了吗?遇到同样问题,求援助……

wangkangming 发表于 2016-2-19 17:21:40

xylslss 发表于 2013-5-12 11:09
楼主,你后来调出CS5460A了吗?遇到同样问题,求援助……

你好,读数一直为0,解决了吗?怎么解决的啊?
页: [1]
查看完整版本: CS5460A芯片读取数据时经常出现读回0的状况,请教各位了.