我写的这段18B20的程序中,怎么也采集不到温度数值,可能是卡在初始化的while里了,感觉时序也没什么问题了,实在不知道什么原因,求大侠帮忙。
部分代码如下,(显示部分为1602的LCD,调试无误,不贴出来了)
u8 Data;
u16 temp;
u8 value;
float temperature;
void delay_nus(unsigned long n) //经示波器验证,这个延时时间绝对精确
{
unsigned long j;
while (n--)
{j=8;
while (j--);
}
}
void delay_nms(unsigned long n) //延时nms
{
while(n--)
delay_nus(1100);
}
void GPIO_Configuration(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7;
//PC0到PC7表示LCD的DB0--DB7
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOC, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0| GPIO_Pin_13 | GPIO_Pin_14| GPIO_Pin_15;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOB, &GPIO_InitStructure);
}
//18B20复位
void DS18b20_reset(void)
{
u8 DQ;
GPIO_Configuration();
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
delay_nus(10);
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_RESET) ;
delay_nus(500); //延时500us
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
//给18B20发出复位信号
delay_nus(45);//45us
DQ=GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_0);
//检测18B20发出的存在脉冲"0",判断复位是否成功
while(DQ!=0)
{
DQ=GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_0);
}
delay_nus(150); //延时150us
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
}
//18B20写一字节
void write_byte(u8 val)
{ int i;
u8 Data;
GPIO_Configuration();
for (i=0; i<8; i++)
{
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_RESET) ;
delay_nus(15); //延时15us
Data = val & 0x01; //最低位保留
GPIO_Write(GPIOB,Data);
delay_nus(45); //45us延时
val >>= 1; //右移一位
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
}
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
}
//18B20读一字节
u8 read_byte(void)
{ int i;
u8 value=0;
u8 DQ;
GPIO_Configuration();
for (i=0; i<8; i++)
{
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
delay_nus(2); //延时 2us
value >>= 1;
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_RESET) ;
delay_nus(3); //3us
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
delay_nus(5); //5us
DQ=GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_0);
if(DQ)
value|=0x80; //若DQ为1则把数据1给value的最高位,然后value向右移 否则直接往右移
delay_nus(60); //60us
}
GPIO_WriteBit(GPIOB,GPIO_Pin_0,Bit_SET) ;
return(value);
}
//18B20启动温度转换 与 读取温度
u16 gettemperature(void)
{ u8 temp_data[2];
u16 temp;
DS18b20_reset();
write_byte(0xCC); // 发Skip ROM命令
write_byte(0x44); // 发温度转换命令
delay_nms(2);//延时2ms
write_byte(0xCC); // 发Skip ROM命令
write_byte(0xBE); //读RAM中9字节内容
temp_data[0]=read_byte(); //温度低8位
temp_data[1]=read_byte(); //温度高8位
temp=temp_data[1];//温度高字节
temp=temp<<8;//移到高8位中
temp=temp|temp_data[0];//16位温度值
temp=temp&0x07ff;//temp取后11位
temperature=temp*0.0625; //最终的温度数据
return temperature;
}
|