湯沁 徐學軍 彭地卓 李驥
【摘要】 本文介紹了高速模數轉換芯片ADS1298R與ARM11微控制器S3C6410利用串行外設接口(SPI)進行數據通信的應用方案,給出了兩者SPI接口的連接圖和Linux操作系統下驅動的具體實現方法,最后編寫了應用程序進行測試,論證了該方法的可行性。ADS1298R和S3C6410基于SPI的串行通信方式為嵌入式高速數據采集系統提供了一個解決方案。
【關鍵詞】 SPI驅動 ADS1298R S3C6410 Linux
SPI總線是一種同步串行外設接口, MCU通過它可以與各種外圍設備進行數據通信[7]。SPI總線只需3~4根數據線和控制線即可擴展具有SPI接口的各種I/O器件,其硬件功能很強,實現軟件相當簡單[1]。SPI為全雙工通信,顯得簡單高效,因而A/D轉換器與ARM通過SPI接口相結合而組成的基于Linux的數據采集系統顯得十分有效。
一、ADS1298R的特性和使用
ADS1298R是美國德州儀器公司推出的一款低功率,8通道,同步采樣,24位三角積分模數轉換器,此產品具有內置的可編程增益放大器(PGA),內部基準和一個板載振蕩器[4]。運行數據速率最高可達32KSPS,時鐘頻率2.048MHz,具有串行外設接口(SPI),并兼容串口。其引腳定義如圖1所示。
如圖2所示為ADS1298R的串行接口時序圖,串行時鐘為數據的輸入輸出提供了傳輸時序。當一次數據轉換完成后,DRDY變低,表示有數據可進行傳輸,將片選信號CS拉低,串行時鐘開始工作,DRDY電平在SCLK的第一個時鐘下降沿升高,在SCLK上升沿往外部控制設備傳數據,在下降沿從外部控制設備讀數據命令。數據傳輸階段CS必須保持低電平,傳輸一組數據需要216個串行時鐘周期。
二、S3C6410概述
S3C6410是三星公司推出的一款采用RISC架構的16/32位微控制器,它基于ARM1176JZF-S內核,高效的八級流水線使其貫通率比以前的ARM內核提高了40%[6]。最高時鐘頻率可達667MHz。
S3C6410含有2通道的SPI接口,可來實現串行數據的傳輸。每個SPI通道含有兩個獨立的32位發送和接收數據寄存器和兩個32位移位寄存器,以及兩個64字節的接收和發送FIFO,三者在SPI通信中的關系如圖3所示。
三、SPI驅動
設備驅動是從操作系統當中提取物理或者虛擬設備的軟件,是連接硬件與操作系統的橋梁。SPI驅動程序屬于流接口驅動程序,導出標準的流接口函數,由流接口驅動管理器向應用程序提供文件系統,應用程序通過對文件系統的處理來完成對設備的操作[2,3]。
根據SPI接口連接原理,將ADS1298R和S3C6410的SPI接口引腳按圖4所示的方式進行連接。
為了實現S3C6410與ADS1298R的數據通信,編寫了基于嵌入式Linux操作系統下混雜設備驅動程序,該SPI驅動主要由以下幾個函數構成。
(1)spi_init_function()完成SPI的初始化工作。首先將對應I/O口配置成SPI功能模式,然后對S3C6410的SPI寄存器進行如下順序的配置。
●將SPI傳輸模式(CPOL&CPHA)配置成與ADS1298R一致。
●設置串行時鐘配置寄存器CLK_CFG。
●設置SPI FIFO控制寄存器MODE_CFG。
●開Tx或Rx通道。
●將片選設置成手動模式,將NSSOUT設置成低并開始傳輸或接收數據[5]。
static void spi_init_function(void)
{······
CH_CFG = ((0 << 6) | (0 << 5) | (0 << 4) | (0 << 3) | (1 << 2) | (0 << 1) | (0 << 0));
CLK_CFG = ((0 << 9) | (1 << 8) | (0x4 << 0));
MODE_CFG = ((0 << 29) | (0 << 19) | (0 << 17) | (1 << 11) | (1 << 5)
| (0 << 2) | (0 << 1) | (0 << 0));
SLAVE_SEL = (0x00);
······}
(2)spi_write()用于向ADS1298R傳遞控制命令。S3C6420通過spi_write()函數向ADS1298R傳遞命令,使其工作在對應狀態。傳數據時開發送通道,并將CS信號拉低,然后將用戶層傳遞過來的命令通過圖3的發送通道傳送至ADS1298R,ADS1298R在SCLK的下降沿從DIN將數據讀入。
static ssize_t spi_write(struct file *filp,const char __user *buff,size_t count,loff_t *offp)
{······
SPI_CS_LOW( );
for(i=0;i writeByte(kbuf[i]); SPI_CS_HIGH(); ······} (3)spi_read( )用于讀取經AD轉換后的數據。ADS1298R將轉換的數據準備好后,DRDY信號變低,S3C6410便可開接收通道,并拉低CS,然后通過圖3的接收通道接收數據,ADS1298R在SCLK的上升沿將數據從DOUT送出。 static ssize_t spi_read(struct file *filp, char __user *buff, size_t count, loff_t *offp)
{······
SPI_CS_LOW( );
while(!DRDY);
for(i=0;i<9;i++)
tab[i] = readByte( );
SPI_CS_HIGH( );
······}
四、SPI測試程序
為了測試驅動的正確性,編寫了測試應用程序對驅動進行測試。為了方便對ADS1298R工作模式和狀態的控制,我們將對ADS1298R的控制命令放在了應用程序里。對ADS1298R的控制主要是對其23個可讀可寫寄存器的配置。用ADS1298R內部自帶測試信號進行測試。測試程序包括兩部分,第一部分目的是通過傳遞命令方式配置ADS1298R相應寄存器,本測試程序對ADS1298R的控制命令集為:
ADS1299RegVal[27]=
{0x41,0x18,0x85,0x10,0xdc,0x03,0x05,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x0a,0xe3};
第二部分循環讀ADS1298R,并將讀到的數據以數據流的形式存入文件中。
由以下兩個函數實現:
read(spi_fd,&data,3);
fprintf(stream,"%06lx\40",data);
測試結果如圖5所示。
并且我們還用信號源輸出正弦波形進行了單通道測試,其中正弦波幅值為100mVpp,頻率為10Hz。測試結果如圖6所示,由于配置的A/D增益為6,故輸出波形幅值為600mVpp。
對采集的波形進行功率譜分析,結果如圖7所示。
五、結論
經測試本SPI驅動能實現ADS1298R與S3C6410之間的串行數據通信。使用帶SPI接口的A/D與微控制器相連進行數據采集系統的開發具有占微控制器I/O資源少,硬件連接方便,軟件開發易于實現的特點。此SPI驅動只需稍加修改便可與其他帶SPI接口的A/D相連,具有很好的可移植性。帶SPI接口的A/D與ARM微控制器結合能很好的應用于具有信號采集功能的嵌入式系統,如抄表系統、醫療儀器、監控設備等領域。endprint
{······
SPI_CS_LOW( );
while(!DRDY);
for(i=0;i<9;i++)
tab[i] = readByte( );
SPI_CS_HIGH( );
······}
四、SPI測試程序
為了測試驅動的正確性,編寫了測試應用程序對驅動進行測試。為了方便對ADS1298R工作模式和狀態的控制,我們將對ADS1298R的控制命令放在了應用程序里。對ADS1298R的控制主要是對其23個可讀可寫寄存器的配置。用ADS1298R內部自帶測試信號進行測試。測試程序包括兩部分,第一部分目的是通過傳遞命令方式配置ADS1298R相應寄存器,本測試程序對ADS1298R的控制命令集為:
ADS1299RegVal[27]=
{0x41,0x18,0x85,0x10,0xdc,0x03,0x05,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x0a,0xe3};
第二部分循環讀ADS1298R,并將讀到的數據以數據流的形式存入文件中。
由以下兩個函數實現:
read(spi_fd,&data,3);
fprintf(stream,"%06lx\40",data);
測試結果如圖5所示。
并且我們還用信號源輸出正弦波形進行了單通道測試,其中正弦波幅值為100mVpp,頻率為10Hz。測試結果如圖6所示,由于配置的A/D增益為6,故輸出波形幅值為600mVpp。
對采集的波形進行功率譜分析,結果如圖7所示。
五、結論
經測試本SPI驅動能實現ADS1298R與S3C6410之間的串行數據通信。使用帶SPI接口的A/D與微控制器相連進行數據采集系統的開發具有占微控制器I/O資源少,硬件連接方便,軟件開發易于實現的特點。此SPI驅動只需稍加修改便可與其他帶SPI接口的A/D相連,具有很好的可移植性。帶SPI接口的A/D與ARM微控制器結合能很好的應用于具有信號采集功能的嵌入式系統,如抄表系統、醫療儀器、監控設備等領域。endprint
{······
SPI_CS_LOW( );
while(!DRDY);
for(i=0;i<9;i++)
tab[i] = readByte( );
SPI_CS_HIGH( );
······}
四、SPI測試程序
為了測試驅動的正確性,編寫了測試應用程序對驅動進行測試。為了方便對ADS1298R工作模式和狀態的控制,我們將對ADS1298R的控制命令放在了應用程序里。對ADS1298R的控制主要是對其23個可讀可寫寄存器的配置。用ADS1298R內部自帶測試信號進行測試。測試程序包括兩部分,第一部分目的是通過傳遞命令方式配置ADS1298R相應寄存器,本測試程序對ADS1298R的控制命令集為:
ADS1299RegVal[27]=
{0x41,0x18,0x85,0x10,0xdc,0x03,0x05,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x0a,0xe3};
第二部分循環讀ADS1298R,并將讀到的數據以數據流的形式存入文件中。
由以下兩個函數實現:
read(spi_fd,&data,3);
fprintf(stream,"%06lx\40",data);
測試結果如圖5所示。
并且我們還用信號源輸出正弦波形進行了單通道測試,其中正弦波幅值為100mVpp,頻率為10Hz。測試結果如圖6所示,由于配置的A/D增益為6,故輸出波形幅值為600mVpp。
對采集的波形進行功率譜分析,結果如圖7所示。
五、結論
經測試本SPI驅動能實現ADS1298R與S3C6410之間的串行數據通信。使用帶SPI接口的A/D與微控制器相連進行數據采集系統的開發具有占微控制器I/O資源少,硬件連接方便,軟件開發易于實現的特點。此SPI驅動只需稍加修改便可與其他帶SPI接口的A/D相連,具有很好的可移植性。帶SPI接口的A/D與ARM微控制器結合能很好的應用于具有信號采集功能的嵌入式系統,如抄表系統、醫療儀器、監控設備等領域。endprint