怎么写DS18B20底层驱动?
1、DS18B20操作流程:
1)初始化(复位、应答)
2)ROM操作命令(“跳过”ROM【0xCC】)
3)暂存缓存器操作命令(读暂存缓存器【0xBE】--温度高、低字节)
4)处理数据


2、端口设置宏定义(头文件中,PA0):
//IO 口方向设置
#define DS18B20_IO_IN() {GPIOA->CRL&=0xFFFFFFF0;GPIOA->CRL|=8<<0;} //上拉/下拉输入
#define DS18B20_IO_OUT() {GPIOA->CRL&=0xFFFFFFF0;GPIOA->CRL|=3<<0;} //通用推挽输出
//IO数据操作
#define DQ_OUT_H (GPIOA->ODR |= 0x01) //端口输出寄存器
#define DQ_OUT_L (GPIOA->ODR &= 0xFE)
#define DQ_IN (GPIOA->IDR & 0x01) //端口输入寄存器

1、复位:
void DS18B20_Rst(void)
{
DS18B20_IO_OUT(); //SET PA0 OUTPUT
DQ_OUT_L; //拉低DQ
Delay_Us(750); //拉低750us
DQ_OUT_H; //DQ=1
Delay_Us(15); //15US
}
2、应答:
//返回1:未检测到DS18B20的存在
//返回0:存在
u8 DS18B20_Check(void)
{
u8 retry=0;
DS18B20_IO_IN();//SET PA0 INPUT
while (DQ_IN && retry<200)
{
retry++;
Delay_Us(1);
}
if(retry>=200)return 1;
else retry=0;
while(!DQ_IN&&retry<240)//再次检查应答
{
retry++;
Delay_Us(1);
}
if(retry>=240)return 1;
return 0;
}

3、读一字节数据:
//从DS18B20读取一个位
//返回值:1/0
u8 DS18B20_Read_Bit(void) // read one bit
{
u8 data;
DS18B20_IO_OUT();//SET PA0 OUTPUT
DQ_OUT_L;
Delay_Us(2);
DQ_OUT_H; //主机释放总线
DS18B20_IO_IN();//SET PA0 INPUT
Delay_Us(12);
if(DQ_IN)data=1; //
else data=0;
Delay_Us(50);
return data;
}
//从DS18B20读取一个字节
//返回值:读到的数据
u8 DS18B20_Read_Byte(void) // read one byte
{
u8 i,j,dat;
dat=0;
for (i=1;i<=8;i++)
{
j=DS18B20_Read_Bit();
dat=(j<<7)|(dat>>1);
}
return dat;
}

4、写一字节数据:
//写一个字节到DS18B20
//dat:要写入的字节
void DS18B20_Write_Byte(u8 dat)
{
u8 j;
u8 testb;
DS18B20_IO_OUT();//SET PA0 OUTPUT;
for (j=1;j<=8;j++)
{
testb=dat&0x01;
dat=dat>>1;
if(testb)
{
DQ_OUT_L;// Write 1
Delay_Us(2);
DQ_OUT_H;
Delay_Us(60);
}
else
{
DQ_OUT_L;// Write 0
Delay_Us(60);
DQ_OUT_H;
Delay_Us(2);
}
}
}

1、所有的对DS18B20的操作已经完成,现在就是对DS18B20进行,底层操作时序。
2、附上端口初始化程序:
//返回1:不存在
//返回0:存在
u8 DS18B20_Init(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); //使能PORTA口时钟
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; //PORTA0 推挽输出
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_SetBits(GPIOA,GPIO_Pin_0); //输出1
DS18B20_Rst(); //DS18B20复位
return DS18B20_Check(); //DS18B20检测
}