|
ad7705單片機(jī)源程序如下:
- ------------AD7705頭文件開始-------------------
- #ifndef _AD7705_H
- #define _AD7705_H
- //通訊寄存器地址定義
- #define WR_SETUP_REG 0x10 //選中寫設(shè)置寄存器
- #define RD_SETUP_REG 0x18 //選中寫設(shè)置寄存器
- #define WR_CLOCK_REG 0x20 //選中寫時(shí)鐘寄存器
- #define RD_DATA_REG 0x38 //選中數(shù)據(jù)寄存器讀
- #define WR_OFFSET_REG 0x60 //選中寫offset寄存器
- #define RD_OFFSET_REG 0x68 //選中讀offset寄存器
- #define WR_FULL_REG 0x70 //選中寫full scale寄存器
- #define RD_FULL_REG 0x78 //選中讀full scale寄存器
- #define SYS_ZERO_CALI 0x80 //系統(tǒng)零校準(zhǔn)模式
- #define SYS_FULL_CALI 0xC0 //系統(tǒng)滿量程校準(zhǔn)模式
- #define ZERO_CALIBRATION 0x00 //系統(tǒng)零校準(zhǔn)
- #define FULL_CALIBRATION 0x01 //系統(tǒng)滿量程校準(zhǔn)
- //CLOCK寄存器設(shè)置,無分頻,50HZ輸出更新速率
- #define CLOCK_REG_SET 0X04
- //函數(shù)聲明
- void reset_AD7705(void);
- unsigned char read_AD7705_byte(void);
- unsigned int read_AD7705_word(void);
- unsigned long int read_AD7705_dword(void);
- void write_AD7705_byte(unsigned char data);
- void write_AD7705_word(unsigned int data);
- void write_AD7705_dword(unsigned long int data);
- void ReadData7705(unsigned int *const pdata);
- void AD7705_calibration(void);
- void start_AD7705(void);
- #endif
- -----------AD7705主文件開始--------------
- #include <util/delay.h>
- #include <avr/eeprom.h>
- #include "ad7705.h"
- #include "main.h"
- #include "crc16.h"
- #include "Usart.h"
- //針對(duì)四個(gè)量程的設(shè)置寄存器的設(shè)置內(nèi)容
- //(1)對(duì)于單極性V級(jí)別輸入0-5V、0-20mA、0-10V這三個(gè)量程,輸入范圍為0-2V,無極性,增益為1,緩沖模式--0-2V
- //(2)對(duì)于雙極性V級(jí)別輸入+-2.5V、+-5V這兩個(gè)量程,輸入范圍為+-1V,雙極性,增益為2,緩沖模式--+-2V
- //(3)對(duì)于雙精度mV級(jí)別輸入+-500mV,增益為4,雙極性,緩沖模式--+-2V
- //(4)對(duì)雙精度mV級(jí)別+-50mV,增益為32,雙極性,緩沖模式--+-1.6V
- //----MD1(0) MD0(0) G2(0) G1(0) G0(0) B/U(0) BUF(0) FSYNC(0)--------------------//
- const unsigned char text_of_setup[4]={0X06,0X0A,0X12,0X2A}; //緩沖模式,數(shù)字濾波同步
- extern volatile unsigned char command[7]; //校準(zhǔn)命令全局?jǐn)?shù)組
- extern volatile unsigned char scale; //記錄系統(tǒng)量程
- extern volatile unsigned char NO_CALI_TYPE; //未校準(zhǔn)類型
- extern volatile unsigned long int ZS,GS; //當(dāng)前量程的校準(zhǔn)系數(shù)
- extern volatile unsigned char time_count; //超時(shí)標(biāo)志
- //----------------------------------------------------------------------------
- //函數(shù):reset_AD7705
- //功能:AD7705串行接口失步后將其復(fù)位。復(fù)位后要延時(shí)500us再訪問
- //參數(shù):無
- //返回:無
- //變量:無
- //備注:無
- //----------------------------------------------------------------------------
- void reset_AD7705(void)
- {
- unsigned char i;
-
- AD_DIN1;
- for( i=0; i<36; i++ )
- {
- AD_CLK0;
- asm("nop");
- asm("nop");
- asm("nop");
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- }
- _delay_us(30);
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):read_AD7705_byte
- //功能:從AD7705讀一個(gè)字節(jié)的數(shù)據(jù)
- //參數(shù):無
- //返回:讀到的一字節(jié)數(shù)據(jù)
- //變量:無
- //備注:無
- //------------------------------------------------------------------------------------------
- unsigned char read_AD7705_byte(void)
- {
- unsigned char data = 0;
- unsigned char i = 0;
-
- for( i=0; i<8; i++ )
- {
- data <<= 1;
- AD_CLK0;
- asm("nop");
- asm("nop");
- asm("nop");
- if(AD_DOUT)
- {
- data++;
- }
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- }
- return data;
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):read_AD7705_word
- //功能:從AD7705讀一個(gè)字的數(shù)據(jù),共16bit
- //參數(shù):無
- //返回:讀到的一字節(jié)數(shù)據(jù)
- //變量:無
- //備注:無
- //------------------------------------------------------------------------------------------
- unsigned int read_AD7705_word(void)
- {
- unsigned int data = 0;
- unsigned char i = 0;
-
- for( i=0; i<16; i++ )
- {
- data <<= 1;
- AD_CLK0;
- asm("nop");
- asm("nop");
- asm("nop");
- if(AD_DOUT)
- {
- data++;
- }
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- }
- return data;
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):read_AD7705_dword
- //功能:從AD7705讀一個(gè)24的數(shù)據(jù)
- //參數(shù):無
- //返回:讀到的一字節(jié)數(shù)據(jù)
- //變量:無
- //備注:AD7705是一個(gè)16位AD
- //------------------------------------------------------------------------------------------
- unsigned long int read_AD7705_dword(void)
- {
- unsigned long data = 0;
- unsigned char i = 0;
-
- for( i=0; i<24; i++ )
- {
- data <<= 1;
- AD_CLK0;
- asm("nop");
- asm("nop");
- asm("nop");
- if(AD_DOUT)
- {
- data++;
- }
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- }
- return data;
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):write_AD7705_byte
- //功能:往AD7705寫8位數(shù)據(jù)
- //參數(shù):IN - uint8_t data,要寫入AD7705的數(shù)據(jù)
- //返回:無
- //變量:無
- //備注:無
- //------------------------------------------------------------------------------------------
- void write_AD7705_byte(unsigned char data)
- {
- for(unsigned char i=0; i<8; i++)
- {
- AD_CLK0;
- if(data&0x80)
- AD_DIN1;
- else
- AD_DIN0;
- asm("nop");
- asm("nop");
- asm("nop");
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- data <<= 1;
- }
- AD_DIN1;
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):write_AD7705_dword
- //功能:往AD7705寫24位數(shù)據(jù),因?yàn)锳D7705是24位的器件
- //參數(shù):IN - int32_t data,要寫入AD7705的數(shù)據(jù)
- //返回:無
- //變量:無
- //備注:無
- //------------------------------------------------------------------------------------------
- void write_AD7705_dword(unsigned long int data)
- {
- for(unsigned char i = 0; i<24; i++)
- {
- AD_CLK0;
- if(data&0x800000)
- AD_DIN1;
- else
- AD_DIN0;
- asm("nop");
- asm("nop");
- asm("nop");
- AD_CLK1;
- asm("nop");
- asm("nop");
- asm("nop");
- data <<= 1;
- }
- AD_DIN1;
- }
- //------------------------------------------------------------------------------------------
- //函數(shù):AD7705_calibration
- //功能:根據(jù)cali_type的值對(duì)AD7705進(jìn)行系統(tǒng)0校正或系統(tǒng)滿量程校正,并將各校正值和校正標(biāo)志存入
- // EEPROM,數(shù)據(jù)保存為雙備份。數(shù)據(jù)塊格式為: 內(nèi)部0校正值(4byte), 內(nèi)部滿量程校正值(4byte),
- // 系統(tǒng)0校正值(4byte), 系統(tǒng)滿量程校正值(4byte), 系統(tǒng)0校正標(biāo)志(1byte),系統(tǒng)滿量程校正標(biāo)志
- // (1byte),CRC16校驗(yàn)值(2byte),共20byte。
- //參數(shù):IN - uint8_t board, 0 - 對(duì)主板進(jìn)行校正,1-對(duì)副板進(jìn)行校正
- // IN - uint8_t range, 需要校正的量程
- // IN - uint8_t cali_type, 校正類型,ZERO_CALIBRATION- 0校正;
- // FULL_CALIBRATION - 滿量程校正
- //返回:返回-1表示校準(zhǔn)失敗,非0表示校正成功,并返回相應(yīng)的索引值
- //變量:無
- //備注:做滿量程校正前必須先做零校正
- //------------------------------------------------------------------------------------------
- //校準(zhǔn)命令格式
- //STX Data Long Command Code Parameter CheckSum ETX
- //0x55 數(shù)據(jù)長(zhǎng)度(2) 量程指示 00H/01H CRC16(2) 0x0D
- //
- //校準(zhǔn)過程中要用到Command[]的數(shù)據(jù),所以校準(zhǔn)之前要關(guān)掉串口接收中斷
- void AD7705_calibration(void)
- {
- //記錄讀取EEPROM的次數(shù)
- unsigned char readtimes =0;
-
- //記錄上位機(jī)發(fā)送的校準(zhǔn)量程類型
- unsigned char cali_scale =0;
-
- //讀取24位校準(zhǔn)系數(shù)的臨時(shí)變量
- unsigned long int temp =0;
-
- //臨時(shí)的校準(zhǔn)系數(shù)數(shù)組,存放格式ZSL、ZSM、ZSH;GSL、GSM、GSH;CRCL、CRCH
- //并在校準(zhǔn)結(jié)束時(shí)作為參數(shù)傳遞給TXOUT()函數(shù),發(fā)送校準(zhǔn)系數(shù)給上位機(jī)
- unsigned char coefficient[8] ={0}; //test[8]={0};
-
- //16位校驗(yàn)和的臨時(shí)變量
- unsigned int crcvalue =0;
-
- AD_CS1;
-
- cali_scale = command[2]; //獲取上位機(jī)發(fā)送的要校準(zhǔn)的量程類型
-
- //讀取EEPROM的第一份校準(zhǔn)系數(shù)
- eeprom_busy_wait();
- eeprom_read_block( &coefficient[0], (void*)(ADDR_EEPROM_1+(cali_scale-1)*10), 8 );
- crcvalue = checksum( &coefficient[0], 6 ); //將6個(gè)值調(diào)用CRC校驗(yàn)函數(shù)得到校驗(yàn)
- if( (coefficient[7]*256+coefficient[6]) != crcvalue )
- {
- readtimes++;
- }
-
- //如果校準(zhǔn)系數(shù)不可用則讀取第二份
- if( 1 == readtimes )
- {
- eeprom_busy_wait();
- eeprom_read_block( &coefficient[0], (void*)(ADDR_EEPROM_2+(cali_scale-1)*10), 8 );
- crcvalue = checksum( &coefficient[0], 6 ); //將6個(gè)值調(diào)用CRC校驗(yàn)函數(shù)得到校驗(yàn)
- if( (coefficient[7]*256+coefficient[6]) != crcvalue )
- {
- readtimes++;
- }
- }
-
- //如果校準(zhǔn)系數(shù)不可用則讀取第三份
- if( 2 == readtimes )
- {
- eeprom_busy_wait();
- eeprom_read_block( &coefficient[0], (void*)(ADDR_EEPROM_3+(cali_scale-1)*10), 8 );
- }
-
- ADDR409_MASK; //切換到第一通道進(jìn)行校準(zhǔn)
-
- AD_CS0;
- _delay_us(5);
- reset_AD7705();
-
- //CLOCK寄存器設(shè)置,無分頻,50HZ輸出更新速率
- write_AD7705_byte( WR_CLOCK_REG );
- write_AD7705_byte( CLOCK_REG_SET );
-
- if( ZERO_CALIBRATION == command[3] ) //校準(zhǔn)命令為零校準(zhǔn)
- {
- //寫設(shè)置寄存器,選擇零校準(zhǔn)
- write_AD7705_byte( WR_SETUP_REG );
- write_AD7705_byte( text_of_setup[cali_scale-1] | SYS_ZERO_CALI );
-
- //等待校準(zhǔn)完成,系統(tǒng)校準(zhǔn)延時(shí)時(shí)間
- start_timer0();
- while( time_count < time_sys_cali );
- stop_timer0();
-
- while( AD_DRDY );//若將濾波器同步位FSYNC置為1,AD_DRDY信號(hào)將不會(huì)變低,這里將一直是死循環(huán)
-
- //讀OFFSET寄存器
- write_AD7705_byte( RD_OFFSET_REG );
- temp = read_AD7705_dword();
-
- if( cali_scale == scale)
- {
- ZS = temp; //如果是當(dāng)前量程零校準(zhǔn)還要更新ZS
- //如果是當(dāng)前量程的校準(zhǔn),還要將NO_CALI_TYPE賦值為1表示已經(jīng)經(jīng)過零校準(zhǔn)
- //更新上電沒有校準(zhǔn)時(shí)readEEPROM()函數(shù)的運(yùn)行狀態(tài)
- NO_CALI_TYPE = NO_FULL_CALIBRATION;
- }
-
- coefficient[0] = (unsigned char)( temp%256 );
- coefficient[1] = (unsigned char)( (temp/256)%256 );
- coefficient[2] = (unsigned char)( (temp/65536)%256 );
- }
- else if( FULL_CALIBRATION == command[3] )//系統(tǒng)滿量程校準(zhǔn)
- {
-
- //計(jì)算ZS,一定要作強(qiáng)制類型轉(zhuǎn)換,否則將出現(xiàn)錯(cuò)誤
- temp = (unsigned long int)(coefficient[0]) + (unsigned long int)(coefficient[1])*256
- + (unsigned long int)(coefficient[2])*65536;
-
- //將ZS寫入到AD7705的OFFSET寄存器
- write_AD7705_byte( WR_OFFSET_REG );
- write_AD7705_dword( temp );
-
- //寫設(shè)置寄存器,選擇滿量程校準(zhǔn)
- write_AD7705_byte( WR_SETUP_REG );
- write_AD7705_byte( text_of_setup[cali_scale-1] | SYS_FULL_CALI );
-
- //等待校準(zhǔn)完成,系統(tǒng)校準(zhǔn)延時(shí)時(shí)間
- start_timer0();
- while( time_count < time_sys_cali );
- stop_timer0();
-
- while( AD_DRDY );//若將濾波器同步位FSYNC置為1,AD_DRDY信號(hào)將不會(huì)變低,這里將一直是死循環(huán)
-
- //讀FULL寄存器
- write_AD7705_byte( RD_FULL_REG );
- temp = read_AD7705_dword();
-
- if( cali_scale == scale )
- {
- GS = temp; //如果是當(dāng)前量程滿量程校準(zhǔn)還要更新GS
- //如果是當(dāng)前量程的校準(zhǔn),還要將NO_CALI_TYPE賦值為2表示已經(jīng)經(jīng)過零校準(zhǔn)
- //更新上電沒有校準(zhǔn)的情況,讓readEEPROM()函數(shù)退出循環(huán)狀態(tài)
- NO_CALI_TYPE = ALREADY_CALIBRATION;
- }
-
- coefficient[3] = (unsigned char)( temp%256 );
- coefficient[4] = (unsigned char)( (temp/256)%256 );
- coefficient[5] = (unsigned char)( (temp/65536)%256 );
- }
- else
- {
- AD_CS1;
- _delay_us(5);
- return;
- }
-
- AD_CS1;
- _delay_us(5);
-
- crcvalue = checksum(&coefficient[0],6); //將6個(gè)校準(zhǔn)值調(diào)用CRC校驗(yàn)函數(shù)得到校驗(yàn)碼
- coefficient[6] = (unsigned char)(crcvalue%256);//取校驗(yàn)值的高8位和低8位
- coefficient[7] = (unsigned char)(crcvalue/256);
-
- //保存第一份校準(zhǔn)系數(shù)
- eeprom_busy_wait();
- ……………………
- …………限于本文篇幅 余下代碼請(qǐng)從51黑下載附件…………
復(fù)制代碼
所有資料51hei提供下載:
ad7705源程序.rar
(3.5 KB, 下載次數(shù): 27)
2018-4-17 13:44 上傳
點(diǎn)擊文件名下載附件
下載積分: 黑幣 -5
|
|