|
DALLAS最新單線數(shù)字溫度傳感器DS18B20簡(jiǎn)介新的“一線器件”體積更小、適用電壓更寬、更經(jīng)濟(jì) Dallas 半導(dǎo)體公司的數(shù)字化溫度傳感器DS1820是世界上第一片支持 “一線總線”接口的溫度傳感器。一線總線獨(dú)特而且經(jīng)濟(jì)的特點(diǎn),使用戶可輕松地組建傳感器網(wǎng)絡(luò),為測(cè)量系統(tǒng)的構(gòu)建引入全新概念。DS18B20、 DS1822 “一線總線”數(shù)字化溫度傳感器 同DS1820一樣,DS18B20也 支持“一線總線”接口,測(cè)量溫度范圍為 -55°C~+125°C,在-10~+85°C范圍內(nèi),精度為±0.5°C。DS1822的精度較差為± 2°C ,F(xiàn)場(chǎng)溫度直接以“一線總線”的數(shù)字方式傳輸,大大提高了系統(tǒng)的抗干擾性。適合于惡劣環(huán)境的現(xiàn)場(chǎng)溫度測(cè)量,如:環(huán)境控制、設(shè)備或過程控制、測(cè)溫類消費(fèi)電子產(chǎn)品等。與前一代產(chǎn)品不同,新的產(chǎn)品支持3V~5.5V的電壓范圍,使系統(tǒng)設(shè)計(jì)更靈活、方便。而且新一代產(chǎn)品更便宜,體積更小。 DS18B20、 DS1822 的特性 DS18B20可以程序設(shè)定9~12位的分辨率,精度為±0.5°C?蛇x更小的封裝方式,更寬的電壓適用范圍。分辨率設(shè)定,及用戶設(shè)定的報(bào)警溫度存儲(chǔ)在EEPROM中,掉電后依然保存。DS18B20的性能是新一代產(chǎn)品中最好的!性能價(jià)格比也非常出色! DS1822與 DS18B20軟件兼容,是DS18B20的簡(jiǎn)化版本。省略了存儲(chǔ)用戶定義報(bào)警溫度、分辨率參數(shù)的EEPROM,精度降低為±2°C,適用于對(duì)性能要求不高,成本控制嚴(yán)格的應(yīng)用,是經(jīng)濟(jì)型產(chǎn)品。 繼“一線總線”的早期產(chǎn)品后,DS1820開辟了溫度傳感器技術(shù)的新概念。DS18B20和DS1822使電壓、特性及封裝有更多的選擇,讓我們可以構(gòu)建適合自己的經(jīng)濟(jì)的測(cè)溫系統(tǒng)。
DS18B20的內(nèi)部結(jié)構(gòu)
DS18B20內(nèi)部結(jié)構(gòu)主要由四部分組成:64位光刻ROM、溫度傳感器、非揮發(fā)的溫度報(bào)警觸發(fā)器TH和TL、配置寄存器。DS18B20的管腳排列如下:
 
光刻ROM中的64位序列號(hào)是出廠前被光刻好的,它可以看作是該DS18B20的地址序列碼。64位光刻ROM的排列是:開始8位(28H)是產(chǎn)品類型標(biāo)號(hào),接著的48位是該DS18B20自身的序列號(hào),最后8位是前面56位的循環(huán)冗余校驗(yàn)碼(CRC=X8+X5+X4+1)。光刻ROM的作用是使每一個(gè)DS18B20都各不相同,這樣就可以實(shí)現(xiàn)一根總線上掛接多個(gè)DS18B20的目的。
DS18B20中的溫度傳感器可完成對(duì)溫度的測(cè)量,以12位轉(zhuǎn)化為例:用16位符號(hào)擴(kuò)展的二進(jìn)制補(bǔ)碼讀數(shù)形式提供,以0.0625℃/LSB形式表達(dá),其中S為符號(hào)位。

這是12位轉(zhuǎn)化后得到的12位數(shù)據(jù),存儲(chǔ)在18B20的兩個(gè)8比特的RAM中,二進(jìn)制中的前面5位是符號(hào)位,如果測(cè)得的溫度大于0,這5位為0,只要將測(cè)到的數(shù)值乘于0.0625即可得到實(shí)際溫度;如果溫度小于0,這5位為1,測(cè)到的數(shù)值需要取反加1再乘于0.0625即可得到實(shí)際溫度。
例如+125℃的數(shù)字輸出為07D0H,+25.0625℃的數(shù)字輸出為0191H,-25.0625℃的數(shù)字輸出為FF6FH,-55℃的數(shù)字輸出為FC90H。

DS18B20溫度傳感器的存儲(chǔ)器
DS18B20溫度傳感器的內(nèi)部存儲(chǔ)器包括一個(gè)高速暫存RAM和一個(gè)非易失性的可電擦除的E2RAM,后者存放高溫度和低溫度觸發(fā)器TH、TL和結(jié)構(gòu)寄存器。
暫存存儲(chǔ)器包含了8個(gè)連續(xù)字節(jié),前兩個(gè)字節(jié)是測(cè)得的溫度信息,第一個(gè)字節(jié)的內(nèi)容是溫度的低八位,第二個(gè)字節(jié)是溫度的高八位。第三個(gè)和第四個(gè)字節(jié)是TH、TL的易失性拷貝,第五個(gè)字節(jié)是結(jié)構(gòu)寄存器的易失性拷貝,這三個(gè)字節(jié)的內(nèi)容在每一次上電復(fù)位時(shí)被刷新。第六、七、八個(gè)字節(jié)用于內(nèi)部計(jì)算。第九個(gè)字節(jié)是冗余檢驗(yàn)字節(jié)。

該字節(jié)各位的意義如下:
TM R1 R0 1 1 1 1 1
低五位一直都是1 ,TM是測(cè)試模式位,用于設(shè)置DS18B20在工作模式還是在測(cè)試模式。在DS18B20出廠時(shí)該位被設(shè)置為0,用戶不要去改動(dòng)。R1和R0用來設(shè)置分辨率,如下表所示:(DS18B20出廠時(shí)被設(shè)置為12位)
分辨率設(shè)置表:
|
R1 |
R0 |
分辨率 |
溫度最大轉(zhuǎn)換時(shí)間 |
|
0 |
0 |
9位 |
93.75ms |
|
0 |
1 |
10位 |
187.5ms |
|
1 |
0 |
11位 |
375ms |
|
1 |
1 |
12位 |
750ms |
根據(jù)DS18B20的通訊協(xié)議,主機(jī)控制DS18B20完成溫度轉(zhuǎn)換必須經(jīng)過三個(gè)步驟:每一次讀寫之前都要對(duì)DS18B20進(jìn)行復(fù)位,復(fù)位成功后發(fā)送一條ROM指令,最后發(fā)送RAM指令,這樣才能對(duì)DS18B20進(jìn)行預(yù)定的操作。復(fù)位要求主CPU將數(shù)據(jù)線下拉500微秒,然后釋放,DS18B20收到信號(hào)后等待16~60微秒左右,后發(fā)出60~240微秒的存在低脈沖,主CPU收到此信號(hào)表示復(fù)位成功。

DS1820使用中注意事項(xiàng)
DS1820雖然具有測(cè)溫系統(tǒng)簡(jiǎn)單、測(cè)溫精度高、連接方便、占用口線少等優(yōu)點(diǎn),但在實(shí)際應(yīng)用中也應(yīng)注意以下幾方面的問題:
(1)較小的硬件開銷需要相對(duì)復(fù)雜的軟件進(jìn)行補(bǔ)償,由于DS1820與微處理器間采用串行數(shù)據(jù)傳送,因此,在對(duì)DS1820進(jìn)行讀寫編程時(shí),必須嚴(yán)格的保證讀寫時(shí)序,否則將無(wú)法讀取測(cè)溫結(jié)果。在使用PL/M、C等高級(jí)語(yǔ)言進(jìn)行系統(tǒng)程序設(shè)計(jì)時(shí),對(duì)DS1820操作部分最好采用匯編語(yǔ)言實(shí)現(xiàn)。
(2)在DS1820的有關(guān)資料中均未提及單總線上所掛DS1820數(shù)量問題,容易使人誤認(rèn)為可以掛任意多個(gè)DS1820,在實(shí)際應(yīng)用中并非如此。當(dāng)單總線上所掛DS1820超過8個(gè)時(shí),就需要解決微處理器的總線驅(qū)動(dòng)問題,這一點(diǎn)在進(jìn)行多點(diǎn)測(cè)溫系統(tǒng)設(shè)計(jì)時(shí)要加以注意。
(3)連接DS1820的總線電纜是有長(zhǎng)度限制的。試驗(yàn)中,當(dāng)采用普通信號(hào)電纜傳輸長(zhǎng)度超過50m時(shí),讀取的測(cè)溫?cái)?shù)據(jù)將發(fā)生錯(cuò)誤。當(dāng)將總線電纜改為雙絞線帶屏蔽電纜時(shí),正常通訊距離可達(dá)150m,當(dāng)采用每米絞合次數(shù)更多的雙絞線帶屏蔽電纜時(shí),正常通訊距離進(jìn)一步加長(zhǎng)。這種情況主要是由總線分布電容使信號(hào)波形產(chǎn)生畸變?cè)斐傻。因此,在用DS1820進(jìn)行長(zhǎng)距離測(cè)溫系統(tǒng)設(shè)計(jì)時(shí)要充分考慮總線分布電容和阻抗匹配問題。
(4)在DS1820測(cè)溫程序設(shè)計(jì)中,向DS1820發(fā)出溫度轉(zhuǎn)換命令后,程序總要等待DS1820的返回信號(hào),一旦某個(gè)DS1820接觸不好或斷線,當(dāng)程序讀該DS1820時(shí),將沒有返回信號(hào),程序進(jìn)入死循環(huán)。這一點(diǎn)在進(jìn)行DS1820硬件連接和軟件設(shè)計(jì)時(shí)也要給予一定的重視。
測(cè)溫電纜線建議采用屏蔽4芯雙絞線,其中一對(duì)線接地線與信號(hào)線,另一組接VCC和地線,屏蔽層在源端單點(diǎn)接地。
軟件如下:
;這是關(guān)于DS18B20的讀寫程序,數(shù)據(jù)腳P2.2,晶振12MHZ ;溫度傳感器18B20匯編程序,采用器件默認(rèn)的12位轉(zhuǎn)化,最大轉(zhuǎn)化時(shí)間750微秒 ;可以將檢測(cè)到的溫度直接顯示到啟點(diǎn)開發(fā)板板的兩個(gè)數(shù)碼管上 ;顯示溫度00到99度,很準(zhǔn)確哦~~無(wú)需校正!
ORG 0000H
;單片機(jī)內(nèi)存分配申明! TEMPER_L EQU 29H;用于保存讀出溫度的低8位 TEMPER_H EQU 28H;用于保存讀出溫度的高8位 FLAG1 EQU 38H;是否檢測(cè)到DS18B20標(biāo)志位 a_bit equ 20h ;數(shù)碼管個(gè)位數(shù)存放內(nèi)存位置 b_bit equ 21h ;數(shù)碼管十位數(shù)存放內(nèi)存位置
MAIN:
LCALL GET_TEMPER;調(diào)用讀溫度子程序
;進(jìn)行溫度顯示,這里我們考慮用網(wǎng)站提供的兩位數(shù)碼管來顯示溫度 ;顯示范圍00到99度,顯示精度為1度 ;因?yàn)?2位轉(zhuǎn)化時(shí)每一位的精度為0.0625度,我們不要求顯示小數(shù)所以可以拋棄29H的低4位 ;將28H中的低4位移入29H中的高4位,這樣獲得一個(gè)新字節(jié),這個(gè)字節(jié)就是實(shí)際測(cè)量獲得的溫度 ;這個(gè)轉(zhuǎn)化溫度的方法可是我想出來的哦~~非常簡(jiǎn)潔無(wú)需乘于0.0625系數(shù)
MOV A,29H MOV C,40H;將28H中的最低位移入C RRC A MOV C,41H RRC A MOV C,42H RRC A MOV C,43H RRC A MOV 29H,A
LCALL DISPLAY;調(diào)用數(shù)碼管顯示子程序
CPL P1.0 AJMP MAIN
; 這是DS18B20復(fù)位初始化子程序 INIT_1820: SETB P2.2 NOP CLR P2.2 ;主機(jī)發(fā)出延時(shí)537微秒的復(fù)位低脈沖 MOV R1,#3 TSR1:MOV R0,#107 DJNZ R0,$ DJNZ R1,TSR1 SETB P2.2;然后拉高數(shù)據(jù)線 NOP NOP NOP MOV R0,#25H TSR2: JNB P2.2,TSR3;等待DS18B20回應(yīng) DJNZ R0,TSR2 LJMP TSR4 ; 延時(shí) TSR3: SETB FLAG1 ; 置標(biāo)志位,表示DS1820存在 CLR P1.7;檢查到DS18B20就點(diǎn)亮P1.7LED LJMP TSR5 TSR4: CLR FLAG1 ; 清標(biāo)志位,表示DS1820不存在 CLR P1.1 LJMP TSR7
TSR5: MOV R0,#117 TSR6: DJNZ R0,TSR6 ; 時(shí)序要求延時(shí)一段時(shí)間 TSR7: SETB P2.2 RET
; 讀出轉(zhuǎn)換后的溫度值 GET_TEMPER: SETB P2.2 LCALL INIT_1820;先復(fù)位DS18B20 JB FLAG1,TSS2 CLR P1.2 RET ; 判斷DS1820是否存在?若DS18B20不存在則返回 TSS2: CLR P1.3;DS18B20已經(jīng)被檢測(cè)到!!!!!!!!!!!!!!!!!! MOV A,#0CCH ; 跳過ROM匹配 LCALL WRITE_1820 MOV A,#44H ; 發(fā)出溫度轉(zhuǎn)換命令 LCALL WRITE_1820
;這里通過調(diào)用顯示子程序?qū)崿F(xiàn)延時(shí)一段時(shí)間,等待AD轉(zhuǎn)換結(jié)束,12位的話750微秒 LCALL DISPLAY
LCALL INIT_1820;準(zhǔn)備讀溫度前先復(fù)位
MOV A,#0CCH ; 跳過ROM匹配 LCALL WRITE_1820
MOV A,#0BEH ; 發(fā)出讀溫度命令 LCALL WRITE_1820
LCALL READ_18200; 將讀出的溫度數(shù)據(jù)保存到35H/36H CLR P1.4
RET
;寫DS18B20的子程序(有具體的時(shí)序要求) WRITE_1820: MOV R2,#8;一共8位數(shù)據(jù) CLR C WR1: CLR P2.2 MOV R3,#6 DJNZ R3,$ RRC A MOV P2.2,C MOV R3,#23 DJNZ R3,$ SETB P2.2 NOP DJNZ R2,WR1 SETB P2.2 RET
; 讀DS18B20的程序,從DS18B20中讀出兩個(gè)字節(jié)的溫度數(shù)據(jù) READ_18200: MOV R4,#2 ; 將溫度高位和低位從DS18B20中讀出 MOV R1,#29H ; 低位存入29H(TEMPER_L),高位存入28H(TEMPER_H) RE00: MOV R2,#8;數(shù)據(jù)一共有8位 RE01: CLR C SETB P2.2 NOP NOP CLR P2.2 NOP NOP NOP SETB P2.2
MOV R3,#9 RE10: DJNZ R3,RE10
MOV C,P2.2
MOV R3,#23 RE20: DJNZ R3,RE20
RRC A DJNZ R2,RE01 MOV @R1,A DEC R1 DJNZ R4,RE00 RET
;顯示子程序 display: mov a,29H;將29H中的十六進(jìn)制數(shù)轉(zhuǎn)換成10進(jìn)制 mov b,#10 ;10進(jìn)制/10=10進(jìn)制 div ab mov b_bit,a ;十位在a mov a_bit,b ;個(gè)位在b mov dptr,#numtab ;指定查表啟始地址 mov r0,#4 dpl1: mov r1,#250 ;顯示1000次 dplop: mov a,a_bit ;取個(gè)位數(shù) MOVC A,@A+DPTR ;查個(gè)位數(shù)的7段代碼 mov p0,a ;送出個(gè)位的7段代碼 clr p2.7 ;開個(gè)位顯示 acall d1ms ;顯示1ms setb p2.7 mov a,b_bit ;取十位數(shù) MOVC A,@A+DPTR ;查十位數(shù)的7段代碼 mov p0,a ;送出十位的7段代碼 clr p2.6 ;開十位顯示 acall d1ms ;顯示1ms setb p2.6 djnz r1,dplop ;100次沒完循環(huán) djnz r0,dpl1 ;4個(gè)100次沒完循環(huán) ret
;1MS延時(shí)(按12MHZ算) D1MS: MOV R7,#80 DJNZ R7,$ RET
;實(shí)驗(yàn)板上的7段數(shù)碼管0~9數(shù)字的共陰顯示代碼 numtab: DB 3fh,30h,6dh,79h,72h,5bh,5fh,31h,7fh,7bh
end
以下為C語(yǔ)言版:
#include sbit warmer=P1^4; sbit led_run=P1^0; sbit k_power=P3^3; sbit ge=P2^7; sbit shi=P2^6; sbit DQ =P2^2; //定義通信端口 //延時(shí)函數(shù) unsigned char tab[]={ 0x3f,0x30,0x6d,0x79,0x72,0x5b,0x5f,0x31,0x7f,0x7b,0x40}; //0, 1, 2 3 4 5 6 7 8 9 void delay(unsigned int i) { while(i--); } //初始化函數(shù) Init_DS18B20(void) { unsigned char x=0; DQ = 1; //DQ復(fù)位 delay(8); //稍做延時(shí) DQ = 0; //單片機(jī)將DQ拉低 delay(80); //精確延時(shí) 大于 480us DQ = 1; //拉高總線 delay(14); x=DQ; //稍做延時(shí)后 如果x=0則初始化成功 x=1則初始化失敗 delay(20); } //讀一個(gè)字節(jié) ReadOneChar(void) { unsigned char i=0; unsigned char dat = 0; for (i=8;i>0;i--) { DQ = 0; // 給脈沖信號(hào) dat>>=1; DQ = 1; // 給脈沖信號(hào) if(DQ) dat|=0x80; delay(4); } return(dat); } //寫一個(gè)字節(jié) WriteOneChar(unsigned char dat) { unsigned char i=0; for (i=8; i>0; i--) { DQ = 0; DQ = dat&0x01; delay(5); DQ = 1; dat>>=1; } delay(4); } //讀取溫度 ReadTemperature(void) { unsigned char a=0; unsigned char b=0; unsigned char t=0; Init_DS18B20(); WriteOneChar(0xCC); // 跳過讀序號(hào)列號(hào)的操作 WriteOneChar(0x44); // 啟動(dòng)溫度轉(zhuǎn)換 Init_DS18B20(); WriteOneChar(0xCC); //跳過讀序號(hào)列號(hào)的操作 WriteOneChar(0xBE); //讀取溫度寄存器等(共可讀9個(gè)寄存器) 前兩個(gè)就是溫度 a=ReadOneChar(); //讀取溫度值低位 b=ReadOneChar(); //讀取溫度值高位 a=a>>4; //低位右移4位,舍棄小數(shù)部分 t=b<<4; //高位左移4位,舍棄符號(hào)位 t=t|a; return(t); } void display_tempmain(unsigned char i) //主程序溫度顯示函數(shù) { P0=tab[i/10]; shi=0; ge=1; delay(1000); P0=tab[i%10]; shi=1; ge=0; } void main(void) {unsigned int temp;
while(1) //主循環(huán) { temp=ReadTemperature(); display_tempmain(temp); } }
|