最近重寫了一次DS18B20 的驅動程式,略有心得,跟大家分享下。程式寫的不好,多多包涵。
在主程式中,采用中斷分時呼叫的方法,間隔1S左右呼叫啟動轉換和讀取轉換兩個函式。以下程式是在AVR mega8上開發的,編譯器是ICC AVR 7.2
需要特別注意,DS18B20對時隙要求比較嚴格。根據手冊,要得到12位精度的溫度資料,轉換時間要750ms,所有啟動轉換后,間隔1S再進行讀取。如果只有單個任務,可以用回圈延時的方法。多任務的時候,建議用中斷時間片輪詢的方式呼叫。程式經過測驗可用。
/*******************************************
Function Name : DS18B20_Reset
Function : Reset DS18B20.Verify that the DS18B20 is online.
Description
Parameter : None
Return Value : online = 0; offline = 1;
/********************************************/
void DS18B20A_Reset(void)
{
DS18B20_PinA_OUT(); //Set DS18B20 Pin output
DS18B20_DQA_H();
asm("nop");
DS18B20_DQA_L(); //Set DS18B20 Pin Low
delay_us(750);
DS18B20_DQA_H(); //Set DS18B20 Pin High
delay_us(30);
}
/*******************************************
Function Name : u8 DS18B20_Check(void)
Function : Verify that the DS18B20 is online.
Description online = 1
offline = 0
Parameter : None
Return Value : online return 0 ; offline return 1;
/********************************************/
unsigned char DS18B20A_Check(void)
{
unsigned char retry = 0 ; //init DS18B20 statu
DS18B20_PinA_IN(); //Set DS18B20 Pin Input
DS18B20_DQA_H();
while(DS18B20_DQA_Read() && (retry < 200))
{
retry++;
delay_us(1);
}
if(retry >= 200)
{
return 1;
}
else
{
return 0;
}
while(!DS18B20_DQA_Read() && (retry < 240))
{
retry++;
delay_us(1);
}
if(retry >= 240)
{
return 1;
}
else
{
return 0;
}
}
/*******************************************
Function Name : u8 DS18B20_Init(void)
Function : Init DS18B20.Master Tx Reset pulse.
Description Verify that the DS18B20 is online.
online = 0
offline = 1
Parameter : None
Return Value : online return 0 ; offline return 1;
/********************************************/
unsigned char DS18B20A_Init(void)
{
unsigned char error = 0;
DS18B20A_Reset();
error = DS18B20A_Check();
delay_us(500);
return error;
}
/*******************************************
Function Name : u8 DS18B20_Read_Bit(void)
Function : read DS18B20 1bit data
Description
Parameter : None
Return Value : return data 1/0
/********************************************/
unsigned char DS18B20A_Read_Bit(void)
{
unsigned char test_bit = 0;
unsigned char bit_data = 0; //init return data
DS18B20_PinA_OUT(); //Set DS18B20 Pin Output
DS18B20_DQA_L(); //Set DS18B20 Pin Low
delay_us(1);
asm("nop");
DS18B20_PinA_IN();
DS18B20_DQA_H();
delay_us(1);
test_bit = TESTBIT(PINC,PC1);
if(test_bit)
{
bit_data = 1;
}
else
{
bit_data = 0;
}
delay_us(50);
return bit_data;
}
/*******************************************
Function Name : u8 DS18B20_Read_Byte(void)
Function : read DS18B20 1 byte data
Description
Parameter : None
Return Value : return data 1/0
/********************************************/
unsigned char DS18B20A_Read_Byte(void)
{
unsigned char i = 0;
unsigned char j = 0;
unsigned char byte_data = 0;
for(i=1; i<=8; i++)
{
byte_data >>= 1;
j = DS18B20A_Read_Bit();
if(j)
{
byte_data |= 0x80;
}
}
return byte_data;
}
/*******************************************
Function Name : DS18B20_Write_Byte(unsigned char data)
Function : Write 1 byte data to DS18B20
Description
Parameter : 1 byte data
Return Value : none
/********************************************/
void DS18B20A_Write_Byte(unsigned char data)
{
unsigned char i = 0;
for(i=0;i<8;i++) //Bit counter
{
DS18B20_PinA_OUT(); //DS18B20 Pin set output
DS18B20_DQA_L(); //DS18B20 Pin set low,start write data
delay_us(1); //waite 1 us
if(data & 0x01) //test data bit=1?
{
DS18B20_DQA_H(); //data bit =1,DS18B20 Pin =High
}
else
{
DS18B20_DQA_L(); //data bit =0,DS18B20 Pin =Low
}
delay_us(50); //delay 50us
DS18B20_DQA_H();
data >>= 1; //右移,為寫入新的資料位做準備
}
delay_us(50); //等待50微秒
}
/*******************************************
Function Name : DS18B20_Start(void)
Function : DS18B20 start temperature conversion
Description
Parameter : none
Return Value : none
/********************************************/
unsigned char DS18B20A_Start_Conver(void)
{
unsigned char online = 0;
online = DS18B20A_Init();
DS18B20A_Write_Byte(0xCC); //Skip ROM
DS18B20A_Write_Byte(0x44); //Start convert
return online;
}
/*******************************************
Function Name : int DS18B20_Get_Temp(void)
Function : Get DS18B20 Data
Description
Parameter : none
Return Value : DS18B20 temperature(-55 ~125)
/********************************************/
unsigned int DS18B20A_Get_Temp(void)
{
unsigned char temp = 0;
unsigned char TL = 0;
unsigned char TH = 0;
unsigned char error = 0;
unsigned int temp_value = 0;
error =DS18B20A_Init();
DS18B20A_Write_Byte(0xCC);
DS18B20A_Write_Byte(0xBE);
TL = DS18B20A_Read_Byte();
TH = DS18B20A_Read_Byte();
if(error)
{
temp_value =256;
}
else
{
temp_value = ((unsigned int)TH)<<8;
temp_value = temp_value | (((unsigned int)TL) & 0x00ff);
temp_value >>= 4;
}
return temp_value;
}
uj5u.com熱心網友回復:
之前我也除錯過
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/119806.html
標籤:單片機/工控
