你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

基于STM32的DS18B20的问题  

[复制链接]
H_JEN 提问时间:2016-5-2 17:21 /
本人现在在做基于STM32的DS18B20的测温,但是一直不成功。就拿初始化来说,按照时序图是先给低电平480us或以上,再给15us的高电平,然后就放开总线,18B20就开始复位。我的初始化程序时要看18B20有没有复位完成。但是我用示波器来看的时候前面给的开始信号是正确的,但是后面读18B20的复位输出的时候,18B20一直处于高电平.......为什么呢?
  1. char ds18b20_Reset(void)
  2. {
  3.         uint8_t count = 0,i = 0;        

  4.         GPIO_Out_Config();

  5.         DQ_L;
  6.         Delay_us(480);

  7.         DQ_H;
  8.         Delay_us(15);

  9.         GPIO_In_Config();//IPU模式能读数,但是一直为1,18b20可能坏了        
  10.         Delay_us(10);

  11.         while(count < 100)
  12.         {
  13.                 i = DQ_Read;
  14.                 if(i == 1)
  15.                 {
  16.                 NOP();
  17.                 count++;
  18.                 }
  19.                 else
  20.                         break;
  21.         }

  22.         if(count >= 100)
  23.                 return 0;
  24.         else
  25.                 count = 0;
  26.         while(count <240)
  27.         {
  28.                 i = DQ_Read;
  29.                 if(i ==0)
  30.                 {
  31.                 NOP();
  32.                 count++;
  33.                 }
  34.                 break;
  35.         }
  36.         if(count >= 240)
  37.                 return 0;
  38.         else
  39.                 return 1;
  40. }
复制代码
以上是初始化的,GPIO的输出模式是PP推挽,GPIO的输入模式是IPU上拉输入;
求大神指点一二啊

单片机是STM32F103ZET的,现在经过修改后,能读出数据,但是高八位要么全0,要么全1;低八位总是全0。而且18b20复位完成后,不发送任何指令,直接读数据口,读出来的有时是1,有时是0。根据时序图,复位完成后,数据口应该是一直高电平才对。
完整的程序如下:
  1. #include "stm32_18b20.h"

  2. void ds18b20_Config(void)
  3. {
  4.         unsigned char Init_Flag;

  5.         Init_Flag = ds18b20_Reset();
  6.         if(Init_Flag)
  7.                 printf("\r\n 1 \r\n");//复位成功
  8.         else
  9.         {
  10.                 printf("\r\n -1 \r\n");//复位失败
  11.                 while(1);
  12.         }               
  13. }

  14. void ds18b20_WriteCmd(uint8_t cmd)
  15. {
  16.         uint8_t i, ch;        

  17.         GPIO_Out_Config();

  18.         for(i = 0; i < 8; i++)
  19.         {
  20.                 ch = cmd;
  21.                 ch = ch & 0x01;
  22.                 cmd = cmd >> 1;
  23.                
  24.                 DQ_L;
  25.                 Delay_us(15);//起始15us低电平

  26.                 if(ch)//写入1                                
  27.                 {                                       
  28.                         DQ_H;
  29.                         NOP();NOP();NOP();NOP();NOP();
  30.                         DQ_L;                        
  31.                         Delay_us(65);        
  32.                 }                                       
  33.                 else//写入0                                
  34.                 {                                       
  35.                         DQ_L;
  36.                         Delay_us(65);
  37.                         DQ_H;
  38.                         NOP();NOP();NOP();NOP();NOP();               
  39.                 }                                
  40.         }
  41. }

  42. uint8_t ds18b20_ReadData(void)
  43. {
  44.         uint8_t i,s = 0, dat = 0, data = 0;

  45.         ds18b20_Config();        

  46.         for(i = 0; i < 8; i++)
  47.         {
  48.                 data = data >> 1;

  49.                 DQ_L;
  50.                 NOP();
  51.                 DQ_H;
  52.                 Delay_us(12);//放开总线
  53.                 s = DQ_Read;
  54.                 if(s)
  55.                         dat = 1;
  56.                 else
  57.                         dat = 0;
  58.                 Delay_us(45);
  59.                 s = 0;
  60.                 data = data | (dat << 7);               
  61.         }
  62.         return data;        
  63. }

  64. char ds18b20_Reset(void)
  65. {
  66.         uint8_t count = 0,i = 0;        

  67.         GPIO_Out_Config();

  68.         DQ_L;
  69.         Delay_us(480);//复位信号

  70.         DQ_H;
  71.         Delay_us(15);//释放总线

  72.         while(count < 100)
  73.         {
  74.                 i = DQ_Read;
  75.                 if(i == 1)
  76.                 {
  77.                 Delay_us(1);
  78.                 count++;
  79.                 }
  80.                 else
  81.                         break;
  82.         }

  83.         if(count >= 100)
  84.                 return 0;
  85.         else
  86.                 count = 0;
  87.         while(count <240)
  88.         {
  89.                 i = DQ_Read;
  90.                 if(i ==0)
  91.                 {
  92.                 Delay_us(1);
  93.                 count++;
  94.                 }
  95.                 break;
  96.         }
  97.         
  98.         if(count >= 240)
  99.                 return 0;
  100.         else
  101.                 {
  102.                         Delay_us(750);
  103.                         i = DQ_Read;
  104.                         printf("\r\n i = %d\r\n ",i);
  105.                         return 1;
  106.                 }               
  107. }

  108. void ds18b20_TransCmd(void)
  109. {
  110.         ds18b20_Config();

  111.         ds18b20_WriteCmd(0xcc);//1100 1100
  112.         ds18b20_WriteCmd(0x44);//0100 0100
  113. }

  114. void ds18b20_ReadCmd(void)
  115. {
  116.         ds18b20_Config();

  117.         ds18b20_WriteCmd(0xcc);//1100 1100
  118.         ds18b20_WriteCmd(0xbe);//1011 1110
  119. }

  120. float ds18b20_GetTemp(void)
  121. {
  122.         uint8_t tempH = 0, tempL = 0, temp = 0;
  123.         float tem = 0;

  124.         ds18b20_TransCmd();
  125.         Delay_ms(1000);
  126.         
  127.         ds18b20_ReadCmd();

  128.         tempL = ds18b20_ReadData();
  129.         tempH = ds18b20_ReadData();

  130. //        printf("\r\n 0x%d \r\n", tempH);
  131. //        printf("\r\n 0x%d \r\n", tempL);
  132.         
  133.         temp = (tempH << 8) + tempL;
  134.         tem =temp * 0.0625;
  135.         printf("\r\n tem %f \r\n", tem);

  136.         return tem;
  137. }

  138. void NOP(void)
  139. {
  140.         uint8_t i = 1;
  141.         i--;
  142. }
复制代码
用示波器看过延时程序的实现是正确的。复位函数里的复位信号给的也是正确的。
电路图里左边是电源线,中间是数据线,右边是地线
IMG_20160508_161413.jpg
捕获.PNG
收藏 3 评论55 发布时间:2016-5-2 17:21

举报

55个回答
jtc_88 回答时间:2016-5-4 16:46:38
公司电脑 不太好弄 我有一个 STM32F030 读取DS18B20的程序 上传不上去  
《DS18B20.c》

#include "stm32f0xx_hal.h"
#include "tim.h"
#include "DS18B20.h"


/*
微秒级延时用函数
*/
void Delay_us(uint16_t nus)
{
        __HAL_TIM_SetCounter(&htim17, 0);

        __HAL_TIM_ENABLE(&htim17);       

        while(__HAL_TIM_GetCounter(&htim17) < (48 * nus));
         /* Disable the Peripheral */
        __HAL_TIM_DISABLE(&htim17);
}
/*
复位DS18B20
*/
void DS18B20_Rst()
{
        DS18B20_IO_OUT_SET();                                                                        //
        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_RESET);        //拉低DQ
        Delay_us(500);                                                                                       

//拉低500us
        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_SET);                //DQ = 1
        Delay_us(30);       
}

/*
等待DS18B20的响应
返回1:未检测到DS18B20的存在
返回0:存在
*/
uint8_t DS18B20_Check(void)
{
        uint8_t retry = 0;
       
        DS18B20_IO_IN_SET();
        while(HAL_GPIO_ReadPin(DS18B20_GPIO_Port, DS18B20_Pin) && (retry < 200))
        {
                retry++;
                Delay_us(1);
        }
        if(retry >= 200)
                return 1;
        else
                retry = 0;
       
        while(!HAL_GPIO_ReadPin(DS18B20_GPIO_Port, DS18B20_Pin) && (retry < 240))
        {
                retry++;
                Delay_us(1);
        }
        if(retry >= 240)
                return 1;
       
        return 0;
}

/*
从DS18B20读取一个位
返回值:1/0
*/
uint8_t DS18B20_Read_Bit(void)
{
        uint8_t data = 0;
       
        DS18B20_IO_OUT_SET();//推挽输出设置
        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_RESET);                //DQ = 0
        Delay_us(2);
        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_SET);                        //DQ

= 1
        DS18B20_IO_IN_SET();                                        //输入上拉
        Delay_us(12);
        if(HAL_GPIO_ReadPin(DS18B20_GPIO_Port, DS18B20_Pin))
                data = 1;
        else
                data = 0;
       
        Delay_us(50);
        return data;
}

/*
从DS18B20读取一个字节
返回值:读取到的数据
*/
uint8_t DS18B20_Read_Byte(void)                        //read one byte
{
        uint8_t i,j,dat;
       
        dat = 0;
       
        for(i = 1;i <= 8;i++)
        {
                j = DS18B20_Read_Bit();
                dat = (j << 7) | (dat >> 1);
        }
       
        return dat;
}

/*
写一个字节到DS18B20
dat:要写入的字节
*/
void DS18B20_Write_Byte(uint8_t dat)
{
        uint8_t j;
        uint8_t testb;
       
        DS18B20_IO_OUT_SET();//推挽输出设置
       
        for(j = 1;j <= 8;j++)
        {
                testb = dat & 0x01;
                dat = dat >> 1;
               
                if(testb)
                {
                        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_RESET);               

//DQ = 0        write 1
                        Delay_us(2);
                        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_SET);               

        //DQ = 1
                        Delay_us(60);
                }
                else
                {
                        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_RESET);               

//DQ = 0        write 0
                        Delay_us(60);
                        HAL_GPIO_WritePin(DS18B20_GPIO_Port, DS18B20_Pin, GPIO_PIN_SET);               

        //DQ = 1
                        Delay_us(2);
                }
        }
}

/*
开始温度转换
*/
void DS18B20_Start(void)        //ds18b20 start convert
{       
        DS18B20_Rst();
        DS18B20_Check();
        DS18B20_Write_Byte(0xcc);//skip rom
        DS18B20_Write_Byte(0x44);//convert
}       
/*
设置为9位精度
*/
void DS18B20_Comfig2(void)        //
{       
        DS18B20_Rst();
        DS18B20_Check();
        DS18B20_Write_Byte(0xcc);//skip rom
        DS18B20_Write_Byte(0x4e);//write
}
/*
初始化DS18B20的IO口DQ同时检测DS的存在
返回1:不存在
返回0:存在
*/
//uint8_t DS18B20_init(void)
//{
//        ;
//}

/*
从DS18B20得到温度值
精度:0.5摄氏度
返回值:温度值
*/
uint16_t DS18B20_Get_Temp(void)
{
        uint8_t temp;
        uint8_t i = 0;
        uint8_t TL,TH;
        uint16_t tem;
       
#ifdef        CONFIG_DS18B20
       
uint8_t                FD,FH,RG;
#endif       


#ifdef        CONFIG_DS18B20
               
                DS18B20_Comfig2();
                DS18B20_Write_Byte(100);
                DS18B20_Write_Byte(0);
                DS18B20_Write_Byte(0x1f);
               
               
//                DS18B20_Start();
#endif       
        DS18B20_Rst();
        i = DS18B20_Check();
        if(i == 1)
                return 0xffee;
        DS18B20_Write_Byte(0xcc);//skip rom
        DS18B20_Write_Byte(0xbe);//read data
        TL = DS18B20_Read_Byte();//LSB
        TH = DS18B20_Read_Byte();//MSB

#ifdef        CONFIG_DS18B20
       
        FD = DS18B20_Read_Byte();
        FH = DS18B20_Read_Byte();
        RG = DS18B20_Read_Byte();
        printf("RG = %X\r\n",RG);
#endif               

        if(TH > 7)
        {
                TH = ~TH;
                TL = ~TL;
                temp = 0;        //温度为负
        }
        else
                temp = 1;        //温度为正
       
        tem = TH;        //获得高8位
        tem <<= 8;
        tem += TL;//获得低8位
        tem = (float)(tem >> 3) * 0.5 *100;//转换
        if(temp)
                return tem;        //返回温度值
        else
                return -tem;
       
}

《DS18B20.h》
#ifndef __DS18B20_H
#define __DS18B20_H

#define DS18B20_IO_OUT_SET()        //{DS18B20_GPIO_Port->MODER &= 0xFFFFFFF3;GPIOF->MODER |= 1 << 2;GPIOF->PUPDR &= 0xFFFFFFF3;}        //输出推挽 其余设置 默认
#define DS18B20_IO_IN_SET()                //{DS18B20_GPIO_Port->MODER &= 0xFFFFFFF3;GPIOF->PUPDR &= 0xFFFFFFF3;GPIOF->PUPDR |= 1 << 2;}        //设置输入上拉

//#define                CONFIG_DS18B20                //设置DS18B20的 分辨率

/*
开始温度转换
*/
void DS18B20_Start(void);        //ds18b20 start convert
/*
从DS18B20得到温度值
精度:0.5摄氏度
返回值:温度值
*/
uint16_t DS18B20_Get_Temp(void);
/*
微秒级延时用函数
*/
void Delay_us(uint16_t nus);
#endif
《gpio.c》

/**
  ******************************************************************************
  * File Name          : gpio.c
  * Description        : This file provides code for the configuration
  *                      of all used GPIO pins.
  ******************************************************************************
  *
  * COPYRIGHT(c) 2016 STMicroelectronics
  *
  * Redistribution and use in source and binary forms, with or without modification,
  * are permitted provided that the following conditions are met:
  *   1. Redistributions of source code must retain the above copyright notice,
  *      this list of conditions and the following disclaimer.
  *   2. Redistributions in binary form must reproduce the above copyright notice,
  *      this list of conditions and the following disclaimer in the documentation
  *      and/or other materials provided with the distribution.
  *   3. Neither the name of STMicroelectronics nor the names of its contributors
  *      may be used to endorse or promote products derived from this software
  *      without specific prior written permission.
  *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
  ******************************************************************************
  */

/* Includes ------------------------------------------------------------------*/
#include "gpio.h"
/* USER CODE BEGIN 0 */

/* USER CODE END 0 */

/*----------------------------------------------------------------------------*/
/* Configure GPIO                                                             */
/*----------------------------------------------------------------------------*/
/* USER CODE BEGIN 1 */

/* USER CODE END 1 */

/** Configure pins as
        * Analog
        * Input
        * Output
        * EVENT_OUT
        * EXTI
*/
void MX_GPIO_Init(void)
{

  GPIO_InitTypeDef GPIO_InitStruct;

  /* GPIO Ports Clock Enable */
  __GPIOF_CLK_ENABLE();
  __GPIOA_CLK_ENABLE();
  __GPIOB_CLK_ENABLE();

  /*Configure GPIO pins : PAPin PAPin PAPin PAPin
                           PAPin */
  GPIO_InitStruct.Pin = CD4053_Pin|C_S1_Pin|C_S2_Pin|C_S3_Pin
                          |C_S4_Pin;
  GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  GPIO_InitStruct.Speed = GPIO_SPEED_LOW;
  HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /*Configure GPIO pin : PA7 */
  GPIO_InitStruct.Pin = GPIO_PIN_7;
  GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING;
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /*Configure GPIO pin : PtPin */
  GPIO_InitStruct.Pin = DS18B20_Pin;
  GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  GPIO_InitStruct.Speed = GPIO_SPEED_LOW;
  HAL_GPIO_Init(DS18B20_GPIO_Port, &GPIO_InitStruct);

  /* EXTI interrupt init*/
  HAL_NVIC_SetPriority(EXTI4_15_IRQn, 0, 0);
  HAL_NVIC_EnableIRQ(EXTI4_15_IRQn);

}

/* USER CODE BEGIN 2 */

/* USER CODE END 2 */

/**
  * @}
  */

/**
  * @}
  */

/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/


《tim.c》
/**
  ******************************************************************************
  * File Name          : TIM.c
  * Description        : This file provides code for the configuration
  *                      of the TIM instances.
  ******************************************************************************
  *
  * COPYRIGHT(c) 2016 STMicroelectronics
  *
  * Redistribution and use in source and binary forms, with or without modification,
  * are permitted provided that the following conditions are met:
  *   1. Redistributions of source code must retain the above copyright notice,
  *      this list of conditions and the following disclaimer.
  *   2. Redistributions in binary form must reproduce the above copyright notice,
  *      this list of conditions and the following disclaimer in the documentation
  *      and/or other materials provided with the distribution.
  *   3. Neither the name of STMicroelectronics nor the names of its contributors
  *      may be used to endorse or promote products derived from this software
  *      without specific prior written permission.
  *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
  ******************************************************************************
  */

/* Includes ------------------------------------------------------------------*/
#include "tim.h"

/* USER CODE BEGIN 0 */

/* USER CODE END 0 */

TIM_HandleTypeDef htim14;
TIM_HandleTypeDef htim16;
TIM_HandleTypeDef htim17;

/* TIM14 init function */
void MX_TIM14_Init(void)
{

  htim14.Instance = TIM14;
  htim14.Init.Prescaler = 0;
  htim14.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim14.Init.Period = 65535;
  htim14.Init.ClockDivision = TIM_CLOCKDIVISION_DIV2;
  HAL_TIM_Base_Init(&htim14);

}
/* TIM16 init function */
void MX_TIM16_Init(void)
{

  htim16.Instance = TIM16;
  htim16.Init.Prescaler = TIM16_PSC;
  htim16.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim16.Init.Period = 65535;
  htim16.Init.ClockDivision = TIM_CLOCKDIVISION_DIV2;
  htim16.Init.RepetitionCounter = 0;
  HAL_TIM_Base_Init(&htim16);

}
/* TIM17 init function */
void MX_TIM17_Init(void)
{

  htim17.Instance = TIM17;
  htim17.Init.Prescaler = 0;
  htim17.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim17.Init.Period = 65535;
  htim17.Init.ClockDivision = TIM_CLOCKDIVISION_DIV2;
  htim17.Init.RepetitionCounter = 0;
  HAL_TIM_Base_Init(&htim17);

}

void HAL_TIM_Base_MspInit(TIM_HandleTypeDef* htim_base)
{

  if(htim_base->Instance==TIM14)
  {
  /* USER CODE BEGIN TIM14_MspInit 0 */

  /* USER CODE END TIM14_MspInit 0 */
    /* Peripheral clock enable */
    __TIM14_CLK_ENABLE();
  /* USER CODE BEGIN TIM14_MspInit 1 */

  /* USER CODE END TIM14_MspInit 1 */
  }
  else if(htim_base->Instance==TIM16)
  {
  /* USER CODE BEGIN TIM16_MspInit 0 */

  /* USER CODE END TIM16_MspInit 0 */
    /* Peripheral clock enable */
    __TIM16_CLK_ENABLE();
  /* USER CODE BEGIN TIM16_MspInit 1 */

  /* USER CODE END TIM16_MspInit 1 */
  }
  else if(htim_base->Instance==TIM17)
  {
  /* USER CODE BEGIN TIM17_MspInit 0 */

  /* USER CODE END TIM17_MspInit 0 */
    /* Peripheral clock enable */
    __TIM17_CLK_ENABLE();
  /* USER CODE BEGIN TIM17_MspInit 1 */

  /* USER CODE END TIM17_MspInit 1 */
  }
}

void HAL_TIM_Base_MspDeInit(TIM_HandleTypeDef* htim_base)
{

  if(htim_base->Instance==TIM14)
  {
  /* USER CODE BEGIN TIM14_MspDeInit 0 */

  /* USER CODE END TIM14_MspDeInit 0 */
    /* Peripheral clock disable */
    __TIM14_CLK_DISABLE();
  /* USER CODE BEGIN TIM14_MspDeInit 1 */

  /* USER CODE END TIM14_MspDeInit 1 */
  }
  else if(htim_base->Instance==TIM16)
  {
  /* USER CODE BEGIN TIM16_MspDeInit 0 */

  /* USER CODE END TIM16_MspDeInit 0 */
    /* Peripheral clock disable */
    __TIM16_CLK_DISABLE();
  /* USER CODE BEGIN TIM16_MspDeInit 1 */

  /* USER CODE END TIM16_MspDeInit 1 */
  }
  else if(htim_base->Instance==TIM17)
  {
  /* USER CODE BEGIN TIM17_MspDeInit 0 */

  /* USER CODE END TIM17_MspDeInit 0 */
    /* Peripheral clock disable */
    __TIM17_CLK_DISABLE();
  /* USER CODE BEGIN TIM17_MspDeInit 1 */

  /* USER CODE END TIM17_MspDeInit 1 */
  }
}

/* USER CODE BEGIN 1 */

/* USER CODE END 1 */

/**
  * @}
  */

/**
  * @}
  */

/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/






评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

Taonsh 回答时间:2016-5-9 08:58:36
H_JEN 发表于 2016-5-8 16:19
还没解决。现在能读数据了,但是读出来的数据,高八位要么全为0,要么全为1;低八位总是为0 ...

如果时序没有问题,很有可能是你延时没有正确造成的,要么就是你拿的器件有问题,可以换一个18B20看看,我上传部分我的代码,你参考一下;
/****************************************************************************************
Include file
****************************************************************************************/
#include "stm32f10x.h"
#include "stm32f10x_tim.h"
#include "stm32f10x_rcc.h"
#include "stm32f10x_gpio.h"

#include "DS18B20.h"
#include "DS18B20_hal.h"

/****************************************************************************************
全局变量定义
****************************************************************************************/

/****************************************************************************************
函 数 名:static void DS18B20RccInit(void)
参数描述:
返回值描述:无
特殊算法:无
注意事项:
****************************************************************************************/
static void DS18B20RccInit(void)
{
        RCC->BitAPB2ENR.IOPCEN = 1;
        RCC->BitAPB2ENR.AFIOEN = 1;
}

/****************************************************************************************
函数名:static void SetDQPortOutput(void)
函数功能:设DQ为输出模式
参数描述:
返回值描述:无
特殊算法:无
注意事项:
****************************************************************************************/
static void SetDQPortOutput(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;
        //配置LED的管脚为开漏输出
        GPIO_InitStructure.GPIO_Pin = DS18B20_DQ_PIN;                        //DQ试制电路板PC0,(原PA1)
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;                //GPIO_Mode_Out_PP;GPIO_Mode_AF_PP
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;       
        GPIO_Init(DS18B20_DQ_PORT, &GPIO_InitStructure);
}

/****************************************************************************************
函数名:static void  SetDQPortInput(void)
函数功能:设DQ为输入模式
参数描述:
返回值描述:无
特殊算法:无
注意事项:
****************************************************************************************/
static void SetDQPortInput(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;

        GPIO_InitStructure.GPIO_Pin =DS18B20_DQ_PIN;                    //DQ(PA1)
        GPIO_InitStructure.GPIO_Mode =GPIO_Mode_IN_FLOATING;            // GPIO_Mode_IPU;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;       
        GPIO_Init(DS18B20_DQ_PORT, &GPIO_InitStructure);
}

/****************************************************************************************
函 数 名:static void DS12B20TimInit()
函数功能:定时器初始化配置
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static void DS18B20TimInit()
{
        TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
        //计数频率 72000000/72 = 1MHz
        TIM_TimeBaseStructure.TIM_Prescaler = 72-1;                     //时钟预分频数
        TIM_TimeBaseStructure.TIM_Period = 1;                           //arr 设置自动重装载寄存器 arr  1MHz  1us溢出时间
        TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;         //采样不分频  
        TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;         //向上计数模式
        TIM_TimeBaseInit(DS18B20_TIM, &TIM_TimeBaseStructure);
        TIM_ClearFlag(DS18B20_TIM, TIM_FLAG_Update);                         //清除溢出标志
}

/****************************************************************************************
函 数 名:static void DS18B20_5us(void)
函数功能:定时器延时5*byDelay个us
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static void DS18B20_5us(uint8_t byDelay)
{
        TIM_SetCounter(DS18B20_TIM, 0);                                 //清计数器
        TIM_SetAutoreload(DS18B20_TIM, 5*byDelay);                      //设置自动重载,定时器计时==5ms*byDelay;
        TIM_Cmd(DS18B20_TIM, ENABLE);

        while(TIM_GetFlagStatus(DS18B20_TIM, TIM_FLAG_Update) == RESET)
        {
                ;
        }
        TIM_ClearFlag(DS18B20_TIM,TIM_FLAG_Update);                     //清除溢出标志
        TIM_Cmd(DS18B20_TIM, DISABLE);
}

/****************************************************************************************
函 数 名:static void Init_DS18B20(void)
函数功能:
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static uint8_t Init_DS18B20(void)
{
        uint8_t byCount = 0;
        SetDQPortOutput();
        DS18B20_DQ_H;                                                   //DQ= 1复位
        DS18B20_5us(12);
        DS18B20_DQ_L;                                                   //DQ= 0
        DS18B20_5us(120);                                               //延时600微秒(该时间的时间范围可以从480到960微秒)

        DS18B20_DQ_H;
        DS18B20_5us(1);

        SetDQPortInput();

        while((GPIO_ReadInputDataBit(DS18B20_DQ_PORT, DS18B20_DQ_PIN)) && (byCount < 200))
        {
                byCount ++;
                DS18B20_5us(1);
        }

        DS18B20_5us(80);

        SetDQPortOutput();
        DS18B20_DQ_H;
        DS18B20_5us(1);

        return byCount;
}

/****************************************************************************************
函数名:void Ap3156Open(void)
函数功能:初始化Ap3156管脚电平
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
void DS18B20_Open(void)
{
        DS18B20RccInit();

        RCC->BitAPB1ENR.TIM2EN = 1;
        DS18B20TimInit();
        TIM_ClearITPendingBit(DS18B20_TIM, TIM_IT_Update);
        TIM_ClearFlag(DS18B20_TIM, TIM_FLAG_Update);
        TIM_Cmd(DS18B20_TIM, DISABLE);

        Init_DS18B20();
}

/****************************************************************************************
函数名:void WriteOneChar(void)
函数功能:写一个字节
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static void WriteOneChar(unsigned char dat)
{
         SetDQPortOutput();
         for(uint8_t i=8; i>0; i--)
         {
                 if(dat&0x01)     //写1
                 {
                        DS18B20_DQ_L;
                        DS18B20_5us(1);
                        DS18B20_DQ_H;
                        DS18B20_5us(16);
                 }
                 else             //写0
                 {
                         DS18B20_DQ_L;
                         DS18B20_5us(18);
                         DS18B20_DQ_H;
                         DS18B20_5us(1);
                 }
                 dat>>=1;
         }
}

/****************************************************************************************
函数名:void ReadOneChar(void)
函数功能:读一个字节
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static unsigned char ReadOneChar(void)
{
        unsigned char dat = 0;
        for(uint8_t ii=8; ii > 0; ii--)
        {
                SetDQPortOutput();
                DS18B20_DQ_L;
                for(uint8_t i = 0;i < 100; ++i);

                DS18B20_DQ_H;
                dat>>=1;

                SetDQPortInput();
                for(uint8_t i = 0;i < 20; ++i);         //75,50

                if(GPIO_ReadInputDataBit(DS18B20_DQ_PORT, DS18B20_DQ_PIN))
                {
                    dat |= 0x80;
                }
                SetDQPortOutput();
                DS18B20_DQ_H;
                DS18B20_5us(15);
        }
        return(dat);
}

/****************************************************************************************
函数名:short Read18B20(void)
函数功能:读18B20温度
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
static short Read18B20(void)
{
        uint8_t byDataL=0;
        uint8_t byDataH=0;
        short Temperature = 0;

        if(!(Init_DS18B20() < 200))                                     //初始化失败
                if(!(Init_DS18B20() < 200))
                        return 4000;
        WriteOneChar(0xCC);                                             //跳过读序号列号的操作
        WriteOneChar(0x44);                                             //启动温度转换

        if(!(Init_DS18B20() < 200))                                     //初始化失败
                if(!(Init_DS18B20() < 200))
                        return 4000;
        WriteOneChar(0xCC);                                             //跳过读序号列号的操作
        WriteOneChar(0xBE);                                             //读取温度寄存器

        byDataL = ReadOneChar();                                        //读低8位
        byDataH = ReadOneChar();                                        //读高8位
        DS18B20_5us(10);

        Temperature = (short)((byDataH << 8) | byDataL);

        return (Temperature * 5 / 8 - 10);                              //*0.625,1摄氏度校准
}

/****************************************************************************************
函数名:void ReadTemperature(void)
函数功能:读18B20温度
参数描述:
返回值描述:
特殊算法:
注意事项:
****************************************************************************************/
short ReadTemperature(void)
{
        short Temperature1 = 0;
        short Temperature2 = 0;

        Temperature1 = Read18B20();
        DS18B20_5us(200);
        Temperature2 = Read18B20();
        if((Temperature1 < Temperature2 - 10)||(Temperature1 > Temperature2 + 10))
        {
                Temperature1 = Read18B20();
                DS18B20_5us(200);
                Temperature2 = Read18B20();
                if((Temperature1 < Temperature2 - 10) || (Temperature1 > Temperature2 + 10))
                {
                        Temperature1 = Read18B20();
                        DS18B20_5us(200);
                        Temperature2 = Read18B20();
                        if((Temperature1 < Temperature2 - 10) || (Temperature1 > Temperature2 + 10))
                                return 4000;
                }
        }
        return (Temperature1 + Temperature2)/2;
}


依然自我 回答时间:2017-2-23 15:34:35
本帖最后由 依然自我 于 2017-2-23 15:36 编辑

STM32F103 DQ不用改变输入输出,只要初始化设置为推挽输出,外接上拉电阻,本人用PB8跟PB10作为DQ是可以的,正点原子例程改为下面两句。
#define DS18B20_IO_IN()    {;}//{GPIOB->CRH&=0XFFFFFFF0;GPIOB->CRH|=8<<8;}
#define DS18B20_IO_OUT() {;}//{GPIOB->CRH&=0XFFFFFFF0;GPIOB->CRH|=3<<8;}
aszrf 回答时间:2016-5-4 13:23:37
埃斯提爱慕 回答时间:2016-5-4 13:25:54
提示: 作者被禁止或删除 内容自动屏蔽
a6552918 回答时间:2016-5-4 13:26:10
应该配置为输入浮空。

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

jinglixixi 回答时间:2016-5-4 13:27:41
DS18B20数据端是否加了上拉电阻。

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

zhoupxa 回答时间:2016-5-4 13:32:37
GPIO应设置为漏极开路

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

huaiqiao 回答时间:2016-5-4 13:37:57
其实这种Onewire的,要注意时序问题

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

power568 回答时间:2016-5-4 13:41:29
确定总线时间和手册给出的时间是否严格匹配,最好留有余量。。。

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

wolfgang 回答时间:2016-5-4 13:44:23
检查电路,DQ是否做了上拉

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

风子 回答时间:2016-5-4 14:42:16
帮顶      
sfee2002 回答时间:2016-5-4 15:52:50
程序中。先拉低,然后将IO设成输入,用示波器看是否有复位脉冲。这样可以确保硬件没问题

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

荣丰宇 回答时间:2016-5-4 16:05:27
1.时序是否正确
2.管脚是否有上拉电阻

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

愚民点子 回答时间:2016-5-4 16:16:29
STM32的DS18B20的测温
设置成开漏输出,外接上拉电阻,
没有说明芯片类型,如是F103直接设成开漏输出。
                           如是L152直接设成开漏输出。最好用寄操作存器保证时序。

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

wtliu 回答时间:2016-5-4 16:19:04
有做上啦设置吗?

评分

参与人数 1ST金币 +2 收起 理由
沐紫 + 2

查看全部评分

1234下一页

所属标签

相似问题

关于意法半导体
我们是谁
投资者关系
意法半导体可持续发展举措
创新和工艺
招聘信息
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
关注我们
st-img 微信公众号
st-img 手机版