?? ds18b20_driver.c
字號:
//------------------------------------------------------------------------------
// 文件名:DS18B20_driver.c
// 說明: DS18B20驅動頭文件
// 功能: 實現1-wire器件的讀寫
// 使用方法: void Delay_nus(unsigned int n); //延時n微秒函數
// unsigned char reset_18B20(void); //18B20復位
// void write_bit_18B20(char bitval); //寫一位到18B20
// unsigned char read_bit_18B20(void); //讀一位從18B20
// void write_byte_18B20(unsigned char data); //寫一字節(jié)到18B20
// unsigned char read_18B20(void); //讀一字節(jié)到18B20
//
// 運行平臺: AVR 8bit (M128已驗證)
// 依存關系: DS18B20_driver.h DS18B20基本驅動頭文件(函數聲明)
// 移植人: 劉大川
// 最后修改: 2008-6-3
//------------------------------------------------------------------------------
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#include "DS18B20_driver.h"
#define CL_DQ PORTD&=~(1<<PD0)
#define SET_DQ PORTD|=(1<<PD0)
#define SET_OUT DDRD|=(1<<PD0)
#define SET_IN DDRD&=~(1<<PD0)
#define IN_DQ PIND&(1<<PD0)
//------------------------------------------------------------------------------
// 延時N微秒程序 供控制讀寫DS18B20時序使用
//------------------------------------------------------------------------------
void Delay_nus(unsigned int n){
while(n--){
_delay_us(1);
}
}
//------------------------------------------------------------------------------
// 1-wire總線復位
//------------------------------------------------------------------------------
unsigned char reset_18B20(void)
{
char bus_flag;
cli();
SET_DQ;
SET_OUT;
Delay_nus(2);
CL_DQ;
Delay_nus(550); //拉低至少480us時間
SET_DQ; //釋放
SET_IN; //輸入
Delay_nus(60);
//while(IN_DQ); //等待回復
bus_flag = IN_DQ;
Delay_nus(240); //回復的低電平在60到240US
SET_OUT;
SET_DQ; //回到初始DQ=1;
sei();
if(bus_flag){
return FALSE;
}else{
return TRUE;
}
}
//------------------------------------------------------------------------------
// 寫一位到總線
//------------------------------------------------------------------------------
void write_bit_18B20(char bitval)
{
SET_OUT;
CL_DQ;
Delay_nus(2);
if(bitval){ //寫數據,從低位開始
SET_DQ;
}else{
CL_DQ;
}
Delay_nus(40); //15~60us
SET_DQ;
Delay_nus(10);
}
//------------------------------------------------------------------------------
// 讀一位從總線
//------------------------------------------------------------------------------
unsigned char read_bit_18B20(void)
{
unsigned char k;
SET_OUT;
CL_DQ; //讀時間片開始,拉低總線至少1us
Delay_nus(2);
//SET_DQ;
SET_IN;
Delay_nus(5);
k=IN_DQ; //讀數據,從低位開始
Delay_nus(10);
SET_DQ;
SET_OUT;
if(k){
return 1;
}else{
return 0;
}
}
//------------------------------------------------------------------------------
// 寫一個字節(jié)到總線
//------------------------------------------------------------------------------
void write_byte_18B20(unsigned char data)
{
unsigned char i;
cli();
for(i=0;i<8;i++)
{
/*
CL_DQ;
Delay_nus(2);
if(data&(1<<i)){ //寫數據,從低位開始
SET_DQ;
}else{
CL_DQ;
}
Delay_nus(60); //15~60us
SET_DQ;
Delay_nus(10);
*/
write_bit_18B20(data&(1<<i));
}
SET_DQ;
sei();
return;
}
//------------------------------------------------------------------------------
// 讀一個字節(jié)
//------------------------------------------------------------------------------
unsigned char read_byte_18B20(void)
{
unsigned char temp,n;
cli();
temp=0;
for(n=0;n<8;n++)
{
/*
//主機讀過程
CL_DQ; //讀時間片開始,拉低總線至少1us
Delay_nus(1);
SET_DQ;
SET_IN;
Delay_nus(4);
k=IN_DQ; //讀數據,從低位開始
SET_OUT;
*/
if(read_bit_18B20()){
temp|=(1<<n);
}else{
temp&=~(1<<n);
}
Delay_nus(70); //60~120us
}
sei();
return (temp);
}
//------------------------------------------------------------------------------
// 應用函數部分! 供外部調用
//------------------------------------------------------------------------------
//------------------------------------------------------------------------------
// 單器件:讀器件ID
//------------------------------------------------------------------------------
void get_ID(char * id_addr)
{
unsigned char i;
reset_18B20();
write_byte_18B20(0x33);
for(i=0;i<8;i++){
id_addr[i] = read_byte_18B20();
}
return;
}
//------------------------------------------------------------------------------
// 單器件/多器件:開始轉換
//------------------------------------------------------------------------------
void convert_T(void)
{
if(reset_18B20()){
write_byte_18B20(0xcc);
write_byte_18B20(0x44);
}
}
//------------------------------------------------------------------------------
// 單器件:讀溫度,返回INIT8U型溫度數據(原始數據)
//------------------------------------------------------------------------------
unsigned int read_T(void)
{
unsigned int value=0;
if(reset_18B20()){
write_byte_18B20(0xcc);
write_byte_18B20(0xbe);
}
value = (unsigned int)read_byte_18B20();
value += ((unsigned int)(read_byte_18B20()))<<8;
return(value);
}
//------------------------------------------------------------------------------
// 多器件:讀指定id的溫度
//------------------------------------------------------------------------------
unsigned int read_id_T(char * id_addr)
{
unsigned int value = 0;
unsigned char i;
//復位總線
reset_18B20();
//匹配ROM
write_byte_18B20(0x55);
//發(fā)ID
for(i=0;i<8;i++)
{
write_byte_18B20(id_addr[i]);
}
//發(fā)讀溫度命令
write_byte_18B20(0xbe);
//讀2字節(jié)溫度值
value = (unsigned int)read_byte_18B20();
value += ((unsigned int)(read_byte_18B20()))<<8;
return(value);
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -