小弟最近在做ADS1292R的单片机驱动程序,需要些程序例子,如果论坛你谁有做过,希望可以提供点参考程序,在下感激不尽!谢谢!
如果有谁做过ADS1292R的驱动希望不吝赐教,因为板子是自己根据参考资料做的,我无法确定是硬件出问题了,还是程序出问题。
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
你好,
不客气,希望附件的代码对你有帮助,至少spi的驱动和ads的驱动对你有帮助。
你好,
可以把SPI的波形和DRDY的波形贴出来吗?
你好,
我会帮你看看,但是需要一点时间。
另外,我不知道另外一个帖子是不是能解答您的问题或者给你debug提供一些解决思路,它是关于ADS1211的问题:
http://www.deyisupport.com/question_answer/analog/data_converters/f/58/t/61110.aspx
非常感谢你的支持!进过这些天的努力,我终于能够正常读写寄存器了。比如我向CONFIG2寄存器CLK_EN位写1,后CLK引脚可以输出512kHz的方波。我写入寄存器后也能正常回读数据。
以下是我读写寄存器的代码: 我使用的是STM32F103C8T6单片机,内部晶振,时钟频率64MHz,SPI波特率8MHz
unsigned char ADS_REG(unsigned char com,unsigned data)
{ unsigned char i;
for(i=0;i<45;i++); ADS_SPI(com);
for(i=0;i<45;i++);
ADS_SPI(0X00);
if((com&0x20)==0x20)//判断是否为读寄存器指令
{ for(i=0;i<45;i++);
ADS_SPI(0X00);
for(i=0;i<45;i++);
return (ADS_SPI(data)); }
else
{ for(i=0;i<45;i++);
ADS_SPI(data);
for(i=0;i<45;i++);
ADS_SPI(0x00); } }
在这里对时序要求非常严格,如果我将SPI波特率改为其他值,无论是降低还是提高都会造成无法正常读写寄存器。我想我要是需要改变SPI波特率的话,我需要改那个for(i=0;i<45;i++);这个短延迟里面的延迟参数。
虽然能正常读写存期了,但是我发现我无法正常读取AD转换结果。 根据数据手册中29页,Data Retrieval章节所写ADS1292R所输出的数据是24 status bits+24bitsX2channels=72位的数据,其中24 status bits=(1100+LOFF_STAT[4:0]+GPIO[1:0]+13 '0'S)。
也就说我要读取AD转换后的数据需要送出72个SCLK时钟脉冲,而ADS1292R也将返回数据给我,而我在读取数据的过程中发现我读到的数据根本就不是资料上说的那样。我回读到的数据是 XX C0 00 00 XX XX XX XX XX(16进制表示,其中XX表示不确定值)。我试着多读一个数据,也就是发送80个SCLK脉冲,而这样回读到的数据是C0 C0 00 00 XX XX XX XX XX XX ,这样的数据貌似正确的。而我设置将CH1关闭,CH2设置为测量内部1HZ信号。这样做读取到的数据位C0 C0 00 00 00 00 00 XX XX XX 好像是正确的,因为我将CH1关闭,读取到的数据是全零。可是我将CH2的信号进行处理后,得到的波形是方波,但是频率不是1Hz,占空比也不是50%。好像多读一位数据是错的。
纠结啊!在这里都调两天了,没有任何进展,很是焦急。
以下是DRDY和SCLK的波形。蓝色是DYDY,黄色是SCKL
从第三张图中可以看出,DRDY在SCLK的低一个下降沿跳变为高电平,这个和资料30页图35的一样,没有错。
好吧!等待回复实在太慢了,昨晚通宵搞了一晚,现在终于有点样子了!
一晚上的调试我发现其实我读取到的数据是正确的,只是在我使用USART向电脑发送数据时波特率太低,造成当前数据还没发送完,新的数据又再次刷新,从而造成我在读取ADS1292R内部的1HZ测试信号时读取到的波形是方波,但频率和占空比不对。现在我将USART的波特率改为115200,这样我就可以读取到1HZ的方波了,但是幅值貌似有点不对。下面是我使用Excel,对读取到的1000个数据进行处理的波形。
从图形中看出,方波的高电平约为20000,低电平约为22500左右,根据资料手册所写这个方波的幅值应该是1mV*(Vref/2.4),而我芯片内部设置Vref=2.42V,PGA=6,也就是说这个方波测量到的应该是6mV左右,而将这个电压转换成数字码应该是20979,也就是说我正电压部分是正确的,但负电压貌似偏差比较大,不知道是不是我硬件的问题。我对VREFP引脚进行测量,得到的电压是2.411V,与理论值有些偏差,供电电压是3.288V。
还有我读取到的数据是C0 C0 00 00 00 00 00 XX XX XX这样的数据,因为我将CH1通道关闭,那么CH1对应的数值也应该为零,好像是正确的,而我做波形处理使用的数据是最后面的三个字节,得到的方波。好像这样是正确的。 但是根据资料手册中29页Data Retrieval小节里面所讲的,我需要发送72个SCLK脉冲,读取到72位的数据,但是我这样做读取到的数据是错的。而我发送80个SCLK脉冲读取到80位的数据,这个数据反而是正确的,真是令我郁闷。
还是在资料手册中29页Data Retrieval小节最后一句话“The ADS1291, ADS1292, and ADS1292R also provide a multiple readback feature. Data can be read out multiple times by simply giving more SCLKs, in which case the MSB data byte repeats after reading the last byte.”这句话不知道如何翻译“该ADS1291,ADS1292以及ADS1292R还提供了多种回读功能。数据可以通过简单地给予更多个SCLK,在这种情况下读出的最后一个字节之后的数据的MSB字节被重复读出多次。”这个是谷歌翻译的结果。但我用其他翻译软件翻译结果又有些不同。我在想这一句貌似能解释我发送80个SCLK脉冲反而是正确的原因。
你好,你的是用stm32吗,可以发份程序1292R给我,我做呼吸检测,想参考下,谢谢,695216755@qq.com
您好,我刚好也在用1292R弄心电显示,现在我能正常写寄存器,因为我进行写寄存器操作,就是写CLK_EN=1 让内部时钟频率从CLK pin 输出,用示波器能看到时512kHz 可是关闭通道1 ,打开通道2接内部测试1Hz方波测试信号的时候,发现在模拟输出端PGA2N接示波器的地,PGA2P接示波器的正极,结果波形像是噪声引起的杂波那样 等下我上图给你看看
第一张 黄色的方波是芯片上CLK pin输出的内部晶振波形图
你好,我有设置的,我把通道2寄存器的BIT[3:0]设置成0101,选择测试信号,再按照datasheet上写设置config2寄存器INT_TEST位用来turn on the test signal ,设置TEST_FREQ位为1,用来选择1Hz方波, 可是结果就是想图片显示的那样,不知道为啥,感觉有可能是我的芯片有问题
你好,我也在做ADS1292R,,我用的是内部晶振,现在的问题是读出来的寄存器状态不对,clk没有波形,下面是我的程序。
#include <msp430x14x.h>
char MST_Data = 0xAA,SLV_Data = 0xff;
unsigned char a[12];
unsigned char b[12];
#define SPI_ENABLE P2OUT &=~0x08;
#define SPI_DISABLE P2OUT |=0x08;
unsigned char regdata[11]={0x02,0xeb,0x18,0x00,0x00,0x30,0x0f,0x40,0x02,0x01,0x03};//二通道心电测试信号,无呼吸
void Stop_Read_Data_Continuous (void)
{
unsigned int i=0;
SPI_ENABLE; // /CS enable
//for(i=0;i<10;i++);
//while (!(IFG1&URXIFG0)); // Clear flag
TXBUF1 =0x11; // Send SDATAC
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
// UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag 可能自动复位(zhao)
SPI_DISABLE; // /CS disable
for(i=0;i<10;i++);
}
void Start_Read_Data_Continuous (void)
{
unsigned int i=0;
SPI_ENABLE;
// while (!(IFG1&URXIFG0)); // Clear flag
TXBUF1 =0x10; // Send RDATAC
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
// UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag
// UCA0IFG &= ~UCRXIFG; // Clear flag
SPI_DISABLE;
for(i=0;i<10;i++);
}
void SPI_RegRead(unsigned char addr, unsigned char *buffer, unsigned char count)
{
unsigned int i=0,j=0;
//P1OUT |=BIT1;
//退出连续读数模式
Stop_Read_Data_Continuous (); //When in RDATAC mode, the RREG command is ignored.Send SDATAC MUST BE SENT
//for(i=0;i<50;i++);
SPI_ENABLE; // /CS enable
TXBUF1 =addr+0x20; // Send address
while ((IFG2 & UTXIFG1) == 0); // USART0 TX buffer ready?
// UCA0IFG &= ~(IFG+UCTXIFG); // Clear flag
TXBUF1 = count-1; // regedit count ge shu
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
// UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag
for (i = 0; i<count;i++)
{
TXBUF1 = 0x55; //Initiate next data RX, meanwhile..
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
buffer[i] = RXBUF1; // Store data from last data RX
TXBUF0=RXBUF1;
while (!(IFG2&URXIFG1)); // Wait for TXBUF ready
for(j=0;j<10;j++);
P2OUT =~0X04;
}
SPI_DISABLE; // /CS disable
//P1OUT = 0x00;
for(i=0;i<10;i++);
//回到连续模式方便读数
Start_Read_Data_Continuous ();
for(i=0;i<10;i++);
}
void SPI_Regwrite(unsigned char addr,unsigned char *data,unsigned char count)
{
unsigned int i=0,j=0;
//P1OUT |=BIT1;
//退出连续读数模式
Stop_Read_Data_Continuous ();
SPI_ENABLE; // /CS enable
//UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag
TXBUF1 =addr+0x40; //发送地址信息; 首地址是0x01;(zhao)
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
// UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag
TXBUF1 =count-1; //发送header; //发送的寄存器数量为10个(zhao)
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
for (i = 0; i<count;i++)
{
//UCA0IFG &= ~(UCRXIFG+UCTXIFG); // Clear flag
TXBUF1 =data[i];
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
for(j=0;j<30;j++);
}
SPI_DISABLE; // /CS disable
//回到连续模式方便读数
Start_Read_Data_Continuous ();
}
void intSPI1()
{
P5SEL |= 0x0E; // P5.1,2,3 SPI option select
P5OUT &= ~0x01;
P5DIR |= 0x01;
U1CTL = CHAR + SYNC + MM + SWRST; // 8-bit, SPI, Master
U1TCTL = CKPL + SSEL1 + STC; // Polarity, SMCLK, 3-wire
U1BR0 = 0x00; // SPICLK = SMCLK/2
U1BR1 = 0x03;
U1MCTL = 0x00;
ME2 |= USPIE1; // Module enable
U1CTL &= ~SWRST; // SPI enable
IE2 |= URXIE1 ; // RX and TX interrupt enable
}
void intUART0()
{
P3SEL |= 0x30; // P3.4,5 = USART0 TXD/RXD
ME1 |= UTXE0 + URXE0; // Enable USART0 TXD/RXD
UCTL0 |= CHAR; // 8-bit character
UTCTL0 |= SSEL0; // UCLK = ACLK
UBR00 = 0x03; // 32k/9600 - 3.41
UBR10 = 0x00; //
UMCTL0 = 0x4A; // Modulation
UCTL0 &= ~SWRST; // Initialize USART state machine
IE1 |= URXIE0; // Enable USART0 RX interrupt
}
void Delay_ms(unsigned int n)
{
unsigned int l,m;
for(l=0;l<n;l++)
for(m=0;m<1000;m++);
}
void main( void )
{
WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
P1OUT = 0x000;
P1DIR |= 0x001; //设置P1.0为输出
P1SEL = 0x010;
P2DIR |= 0x00f; //0,1,2,3输出
P2OUT |=0x01; //START,RST高电平
P5SEL = 0x020; //设置P3端口为SPI模式
intSPI1();
intUART0();
Delay_ms(5);
//SPI_RegRead(0x00,a,12); //读取初始寄存器,检验电路连接是否正确
SPI_Regwrite(0x01,regdata,11); //写入配置寄存器,
Delay_ms(5);
SPI_RegRead(0x00,b,12); // 再次读出寄存器 检验是否写入正确
Delay_ms(5);
P2OUT |=0x02; //START,RST高电平
SPI_ENABLE;
_EINT();
// TXBUF0 = MST_Data; //传输第一个字符
while(1)
{
};
//LPM0; //关CPU,进入低功耗模式
}
#pragma vector=USART1RX_VECTOR
__interrupt void SPI1_rx (void)
{
unsigned char j=0;
// unsigned char j=0;
for(j=0;j<9;j++)
{
// while((UCA0IFG&UCTXIFG)==0);
TXBUF1 = 0x55;
while (!(IFG2&UTXIFG1)); // Wait for TXBUF ready
//TXBUF0 = RXBUF1;
// buffer[i]= UCA0RXBUF;
}
}
#pragma vector=UART0RX_VECTOR
__interrupt void usart0_rx (void)
{
while (!(IFG1 & UTXIFG0)); // USART0 TX buffer ready?
// RXBUF0 to TXBUF0
_BIC_SR_IRQ(LPM3_bits); // Clear LPM3 bits from 0(SR)
}