【GD32F427开发板试用】UART1读取ds18b20温度传感器

本篇文章来自极术社区与兆易创新组织的GD32F427开发板评测活动,更多开发板试用活动请关注极术社区网站。作者:Smile°

硬件部分

1.GD32F427R开发板

2.ds18b20温度传感器

详细原理及时序可参考CSDN论坛大佬博客
3.USB转TTL模块

软件部分

参考官方systick库实现delay毫秒函数

#include "gd32f4xx.h"
    #include "systick.h"
    
    volatile static uint32_t delay;
    
    /*!
        \brief      configure systick
        \param[in]  none
        \param[out] none
        \retval     none
    */
    void systick_config(void)
    {
        /* setup systick timer for 1000Hz interrupts */
        if(SysTick_Config(SystemCoreClock / 1000000U)) {
            /* capture error */
            while(1) {
            }
        }
        /* configure the systick handler priority */
        NVIC_SetPriority(SysTick_IRQn, 0x00U);
    }
    
    /*!
        \brief      delay a time in milliseconds
        \param[in]  count: count in milliseconds
        \param[out] none
        \retval     none
    */
    void delay_1ms(uint32_t count)
    {
        delay = 1000*count;
    
        while(0U != delay) {
        }
    }
    /*!
        \brief      delay a time in microseconds
        \param[in]  count: count in microseconds
        \param[out] none
        \retval     none
    */
    void delay_1us(uint32_t count)
    {
        delay = count;
    
        while(0U != delay) {
        }
    }

ds18b20.c代码

#include "ds18b20.h"
    
    int DS18B20_Init(void)
    {
      int i=0;
      DS_DIO(1);  //GPIOA->ODR |= 1;  //GPIOA-0输出高电平
      DS18B20_Mode_OutPut();//令DQ口为输出模式
      DS_DIO(0);   //PAout(0)=0;
      delay_1us(720);//延时480-960us
      DS_DIO(0);   //PAout(0)=1;
      delay_1us(30);//等待15-60us 
      DS18B20_Mode_InPut();//改为输入模式
      while(READ_DIO == 1)  //   //while(PAin(0)==1)    //若DS18B20存在则会将总线拉低60-240us
      {   
         delay_1us(1);
         i++;
         if(i>240)  return 0;     //时间大于240us总线仍为高电平则DS18B20不存在
      }
      return 1;
    }
    
    void DS18B20_WriteByte(uint8_t dat)
    {
     int i;
     DS18B20_Mode_OutPut();
     for(i=0;i<8;i++)
     {
      DS_DIO(0); //   PAout(0)=0;        //先拉低引脚
      delay_1us(15);      //等待15us,在第15-60us内DS18B20会获取总线电平
      if(dat&0x01)  DS_DIO(1);  //PAout(0)=dat&0x01;
        else DS_DIO(0); 
      delay_1us(60);      //延时,使时序图完整
      DS_DIO(1);  //    PAout(0)=1;
      dat>>=1;
     }
    }
    
    uint8_t DS18b20_ReadByte(void)
    {
     int j;
     uint8_t dat,byte;
     for(j=8;j>0;j--)
     {
      DS18B20_Mode_OutPut();   
      DS_DIO(0);   //PAout(0)=0;          //先拉低引脚
      delay_1us(1);         //延时至少大于1us
      DS_DIO(1); //PAout(0)=1;          //释放总线
      delay_1us(10);        //DS18B20会在15us发送数据
      DS18B20_Mode_InPut();
      dat=READ_DIO;   //PAin(0);
      byte=(byte>>1)|(dat<<7);
      delay_1us(45);        //使时序完整
      DS18B20_Mode_OutPut();
      DS_DIO(1);   //PAout(0)=1;
     }
     return byte;
    }
    
    /*改变DS18B20的高温报警和低温报警以及分辨率*/
    void DS18B20_Resolving_Temp(void)
    {
     DS18B20_Init();//单片机每次向DS18B20发送功能指令前都需要重新初始化DS18B20和写ROM指令
     delay_1ms(1);
     DS18B20_WriteByte(0xcc);
     DS18B20_WriteByte(0xbe);//高温报警的上限
     DS18B20_WriteByte(0x00);//低温报警的下限
     DS18B20_WriteByte(0x7f);//改变温度分辨率
    }
    
    /*进行温度转化*/
    void Ds18b20ChangeTemp(void)
    {
     DS18B20_Init();
     delay_1ms(1);
     DS18B20_WriteByte(0xcc);//跳过ROM
     DS18B20_WriteByte(0x44);//发送指令RAM温度变换
    }
    
    /*读取温度*/
    void Ds18b20ReadTempCom(void)
    {
     DS18B20_Init();
     delay_1ms(1);
     DS18B20_WriteByte(0xcc);//跳过ROM
     DS18B20_WriteByte(0xbe);//发送指令RAM读暂时寄存器
    }
    
    int Ds18b20ReadTemp(void)
    {
     int temp;
     float fp;
     uint8_t tml,tmh; 
     DS18B20_Resolving_Temp();//改变高温报警和低温报警以及温度的分辨率
     Ds18b20ChangeTemp();//进行温度转换
     Ds18b20ReadTempCom();//读取温度
     tml=DS18b20_ReadByte();//读低8位数据
     tmh=DS18b20_ReadByte();//读高8位数据
     temp=tmh;
     temp<<=8;
     temp|=tml;//拼接为16位数据
     fp = temp;
     if(temp < 0)//DS18B20存储数据为补码形式,当temp<0时需要转为原码
     {
      temp = ~temp;
      temp += 1;
     }
     temp = fp*0.0625*10+0.5;//根据获得的温度所需的小数而改变,如果保留2位小数则乘100,+0.5是为了四舍五入
     return temp;//返回数据
    }

主函数

#include "gd32f4xx.h"
    #include "gd32f427r_start.h"
    #include "systick.h"
    #include <stdio.h>
    #include "ds18b20.h"
    
    /*!
        \brief      main function
        \param[in]  none
        \param[out] none
        \retval     none
    */
    int main(void)
    {
        /* configure systick */
        systick_config();
            /* enable GPIO clock */
        rcu_periph_clock_enable(RCU_GPIOA);
    
        /* enable USART clock */
        rcu_periph_clock_enable(RCU_USART1);
    
        /* configure the USART0 TX pin and USART0 RX pin */
        gpio_af_set(GPIOA, GPIO_AF_7, GPIO_PIN_2);
        gpio_af_set(GPIOA, GPIO_AF_7, GPIO_PIN_3);
    
        /* configure USART0 TX as alternate function push-pull */
        gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_2);
        gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_2);
    
        /* configure USART0 RX as alternate function push-pull */
        gpio_mode_set(GPIOA, GPIO_MODE_AF, GPIO_PUPD_PULLUP, GPIO_PIN_3);
        gpio_output_options_set(GPIOA, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_3);
    
        /* USART configure */
        usart_deinit(USART1);
        usart_baudrate_set(USART1, 115200U);
        usart_receive_config(USART1, USART_RECEIVE_ENABLE);
        usart_transmit_config(USART1, USART_TRANSMIT_ENABLE);
        usart_enable(USART1);
    
    
        /* enable the LEDs GPIO clock */
        rcu_periph_clock_enable(RCU_GPIOC);
    
        /* configure LED1 GPIO port */
        gpio_mode_set(GPIOC, GPIO_MODE_OUTPUT, GPIO_PUPD_NONE, GPIO_PIN_6);
        gpio_output_options_set(GPIOC, GPIO_OTYPE_PP, GPIO_OSPEED_50MHZ, GPIO_PIN_6);
        /* reset LED1 GPIO pin */
        gpio_bit_set(GPIOC, GPIO_PIN_6);
            DS18B20_Init();
        
        while(1) {
            
            
                float  value = (float)Ds18b20ReadTemp()/10;
                 printf("\n\r%.1f\n\r", value);
                
        }
    }
    int fputc(int ch, FILE *f)
    {
        usart_data_transmit(USART1, (uint8_t)ch);
        while(RESET == usart_flag_get(USART1, USART_FLAG_TBE));
        return ch;
    }

结果

用手握住DS18B20探头

温度数值上升

  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值