【CPKCOR-RA8D1】Home Assistant 物联网 ADC 电压温度计

【CPKCOR-RA8D1】Home Assistant 物联网ADC电压温度计

本文介绍了瑞萨 CPKCOR-RA8D1B 开发套件由 ADC 采集引脚电压、温度传感器数据,通过串口发送 JSON 消息至 ATK D20 WiFi 模块,ATK-D20 模块将 MQTT 消息透传至 Home Assistant 平台,实现 HA 物联网电压表的项目设计,包括项目介绍、工程创建、工程编译、效果演示等。

项目介绍

  • 硬件连接:RA8D1 和 ATK-D20 WiFi 模块的接线;
  • 流程图:代码和项目流程;
  • 工程代码:ADC 配置、双串口配置和主程序;
  • MQTT透传:包括 ATK-D20 模块 MQTT 透传配置、软件测试等;
  • 效果演示:包括接入 Home Assistant 平台、YAML 配置等。

项目结构

硬件连接

连接方案

  • 连接 ATK-D20 模块
RA8D1 ATK-D20 Note
RXD9 (P208) TX Receive data
TXD9 (P209) RX Transmit data
GND GND Ground
实物图

环境搭建

这里使用 Renesas 瑞萨 e2 studio 开发工具,

下载 FSP (flexible software package) 软件包 并安装。

  • FSP 安装程序内包含 e² studio 集成开发环境、工具链和 FSP 软件包。

流程图

透传 转发 开始 初始化ADC 初始化串口 主循环 读取ADC
电压&温度 构造MQTT报文 串口输出JSON ATK-D20模块 MQTT服务器 HA显示 延时1秒

工程创建

  • 打开 e2 studio 软件;

  • 依次点击 文件 - 新建 - 瑞萨 C/C++ 项目 - Renesas RA

  • 依次进行工程命名,路径设置,FSP版本,目标开发板选择,Device 选择 R7FA8D18HECBD ,工具链选择 GNU ARM Embedded ,调试器选择 J-Link ;

  • 完成工程创建 ;

工程配置

包括时钟、引脚和堆栈等工程配置流程。

时钟配置

由于调用了 SCI 的 UART 堆栈,需要使能相应的时钟,包括 CLKOUT 和 SCICLK;

引脚配置

根据核心板原理图可知,板载 JLINK 串口与 UART3 相连;

对应引脚为 P408 (RXD) 和 P409 (TXD);

  • 相应的引脚配置需定义为 异步串口模式

串口配置

  • 新建串口通信堆栈 New Stack - Connectivity - UART (r_sci_b_uart)

  • 串口属性配置,选中串口堆栈,属性 - General 、名称 g_uart3、通道为 3、Interrupts 设置

  • 回调函数名称设置为 user_uart_callback

  • 配置完成后,点击 Generate Project Content 生成工程;

  • 配置完成后,构建工程,确保无误。

串口通信

这里首先实现串口打印的功能及效果演示。

代码

打开项目工程目录 src 文件夹下的主函数文件 hal_entry.c ,并添加如下代码

c++ 复制代码
#include "hal_data.h"
#include <stdio.h>

fsp_err_t err = FSP_SUCCESS;
volatile bool uart_send_complete_flag = false;
void user_uart_callback (uart_callback_args_t * p_args)
{
    if(p_args->event == UART_EVENT_TX_COMPLETE)
    {
        uart_send_complete_flag = true;
    }
}

/*------------- 串口重定向 -------------*/
#ifdef __GNUC__
    #define PUTCHAR_PROTOTYPE int __io_putchar(int ch)
#else

#endif

PUTCHAR_PROTOTYPE
{
        err = R_SCI_B_UART_Write(&g_uart3_ctrl, (uint8_t *)&ch, 1);
        if(FSP_SUCCESS != err) __BKPT();
        while(uart_send_complete_flag == false){}
        uart_send_complete_flag = false;
        return ch;
}

int _write(int fd,char *pBuffer,int size)
{
    for(int i=0;i<size;i++)
    {
        __io_putchar(*pBuffer++);
    }
    return size;
}

void hal_entry(void)
{
    /* TODO: add your own code here */
    /* Open the transfer instance with initial configuration. */
    err = R_SCI_B_UART_Open(&g_uart3_ctrl, &g_uart3_cfg);
    assert(FSP_SUCCESS == err);

    while(1)
    {
        printf("hello world!\n");
        R_BSP_SoftwareDelay (1000, BSP_DELAY_UNITS_MILLISECONDS);
    }
#if BSP_TZ_SECURE_BUILD
    /* Enter non-secure code */
    R_BSP_NonSecureEnter();
#endif
}

保存代码并构建工程。

效果

  • 使用 Type-C 数据线连接开发板和电脑;

  • 点击菜单栏 Debug 按钮,进入调试功能界面,点击 Continue 按钮开始执行程序;

  • 打开串口调试助手工具,选择 JLINK 对应的串口设备,配置串口相关参数;

  • 点击打开串口按钮,即可接收到开发板发送的字符串,发送间隔为 1 秒;

ADC 电压温度

通过 ADC 功能实现引脚电压转换和数据测量,结合芯片内部的温度传感器实现 ADC 温度值计算。

ADC 配置

  • 新建ADC堆栈 New Stack - Analog - ADC (r_adc)

  • 属性配置 General 选项下设置 ADC 单次扫描

  • Input 选项下勾选 Channel0Temperature Sensor,配置中断与回调函数 adc_callback

    注意 RA8D1 使能芯片内部温度传感器需要开启时钟 PCLKC (默认开启).

  • ADC 及串口配置完成后,构建工程,确保无误。

ADC 电压

通过 ADC 获取引脚 P004 对应的电压值。

代码

在完成串口通信的基础上,打开 hal_entry.c ,添加如下代码

c++ 复制代码
/*********** ADC Callback**********/
volatile bool scan_complete_flag = false;
void adc_callback (adc_callback_args_t * p_args)
{
    FSP_PARAMETER_NOT_USED(p_args);
    scan_complete_flag = true;
}

/*******************
 * main
********************/
void hal_entry(void)
{
    /* TODO: add your own code here */
    /* Open the transfer instance with initial configuration. */
    err = R_SCI_B_UART_Open(&g_uart3_ctrl, &g_uart3_cfg);
    assert(FSP_SUCCESS == err);

    printf("RA8D1 ADC Sensor\n");

    /* Initializes the module. */
    err = R_ADC_Open(&g_adc0_ctrl, &g_adc0_cfg);
    /* Handle any errors. This function should be defined by the user. */
    assert(FSP_SUCCESS == err);
    /* Enable channels. */
    err = R_ADC_ScanCfg(&g_adc0_ctrl, &g_adc0_channel_cfg);
    assert(FSP_SUCCESS == err);

    while(1)
    {
        uint16_t adc_raw = 0;
        double volt;
        
        /* Enable scan triggering from ELC events. */
        (void) R_ADC_ScanStart(&g_adc0_ctrl);
        scan_complete_flag = false;
        while (!scan_complete_flag)
        {
            /* Wait for callback to set flag. */
        }

        err = R_ADC_Read(&g_adc0_ctrl, ADC_CHANNEL_0, &adc_raw);
        assert(FSP_SUCCESS == err);

        volt = (double)(adc_raw/4095.0)*3.3;
        printf("ADC = %d, Voltage = %fV\n",adc_raw,volt);

        R_BSP_SoftwareDelay (500, BSP_DELAY_UNITS_MILLISECONDS);
    }
#if BSP_TZ_SECURE_BUILD
    /* Enter non-secure code */
    R_BSP_NonSecureEnter();
#endif
}

保存代码并构建工程。

效果
  • 打开串口调试助手工具,选择 JLINK 对应的串口设备,配置串口相关参数;
  • 点击打开串口按钮,即可接收到开发板发送的 ADC 原始值和 P004 引脚的电压值;

ADC 温度

通过芯片内部的温度传感器获取 ADC 温度数据。

代码

在完成串口通信和 ADC 电压采集的基础上,打开 hal_entry.c ,添加如下代码

c++ 复制代码
/******************
 * ADC Temperature
 * (详见 https://renesas.github.io/fsp/group___a_d_c.html )
 *******************/
/* 官方例程常数 */
#define VCC_UV           (3300000UL)   /* 3.3 V → μV */
#define RES_SHIFT        (12U)         /* 12-bit ADC */
#define REF_TEMP         (127)         /* 校准点 127 ℃ */
#define SLOPE_UV_PER_C   (4000L)       /* 4 mV/℃ → 4000 μV/℃ */

/* 获取ADC通道温度 */
static int32_t get_temperature_c(void)
{
    /* 1. 启动 ADC 并等待完成 */
    R_ADC_ScanStart(&g_adc0_ctrl);
    adc_status_t status = { .state = ADC_STATE_SCAN_IN_PROGRESS };
    while (status.state == ADC_STATE_SCAN_IN_PROGRESS)
    {
        R_ADC_StatusGet(&g_adc0_ctrl, &status);
    }

    /* 2. 读温度通道原始码值 */
    uint16_t raw;
    R_ADC_Read(&g_adc0_ctrl, ADC_CHANNEL_TEMPERATURE, &raw);

    /* 3. 取 127 ℃ 校准码值(TSCDR) */
    adc_info_t info;
    R_ADC_InfoGet(&g_adc0_ctrl, &info);
    int32_t cal127 = (int32_t)info.calibration_data;

    /* 4. 官方公式(单位 μV) */
    int32_t v1_uv   = (VCC_UV >> RES_SHIFT) * cal127;   /* 127 ℃ 对应电压 */
    int32_t vs_uv   = (VCC_UV >> RES_SHIFT) * raw;      /* 当前电压 */
    int32_t temp_c  = (vs_uv - v1_uv) / SLOPE_UV_PER_C + REF_TEMP;
    //printf("raw=%u cal127=%ld v1=%ld vs=%ld temp=%ld\r\n",raw, cal127, v1_uv, vs_uv, temp_c);
    return temp_c;
}

/*******************
 * main
********************/
void hal_entry(void)
{
    /* TODO: add your own code here */
    //......
    //......

    while(1)
    {
        int32_t temp_c = get_temperature_c();
        printf("{\"temp\": %ld}\r\n",temp_c);
        R_BSP_SoftwareDelay (500, BSP_DELAY_UNITS_MILLISECONDS);
    }
}

保存代码并构建工程。

效果
  • 打开串口调试助手工具,选择 JLINK 对应的串口设备,配置串口相关参数;
  • 点击打开串口按钮,即可接收到开发板发送的 ADC 芯片内部温度传感器的数值;

Home Assistant

为了实现物联网 ADC 电压温度计,使用 ATK-D20 WiFi 模块,结合 MQTT 透传功能,实现 JSON 格式消息上传至 Home Assistant 智能家居平台。

ATK D20

这里使用 ATK-D20 WiFi DTU 模块实现串口 MQTT 透传。

ATK-D20 是由正点原子团队(ALIENTEK)自主研发的一款高性能 2.4GHz WiFi DTU 模块,主要用于实现串口设备通过 WiFi 无线方式接入网络。

  • 模块支持 TCP、UDP、HTTP、MQTT、原子云等多种通信协议,支持 AT 指令控制、注册包、心跳包、Modbus 采集等功能,极大地方便了二次开发与系统集成。

详见:D20 WiFi DTU | 文档 .

双串口输出

考虑到需要连接串口 MQTT 透传设备,根据扩展板原理图可知,JTAG 接口包含一对串口 UART9,引脚对应 P208和 P209,因此需要使能双串口输出 ADC 电压和温度数据。

工程配置
  • 在工程配置中新增串口 Stacks 堆栈,选择通道 9,波特率设置为 9600,回调函数命名为 user_uart9_callback
  • 串口 9 对应引脚设置为 P208 (RXD) 和 P209 (TXD);
  • 点击 Generate Project Content 生成工程;
代码

在完成之前工作的基础上,打开 hal_entry.c ,添加如下代码

c++ 复制代码
/* 串口 9 回调 */
volatile bool uart9_send_complete_flag = false;
void user_uart9_callback(uart_callback_args_t *p_args)
{
    if (p_args->event == UART_EVENT_TX_COMPLETE)
        uart9_send_complete_flag = true;
}

/**************************
 * main
****************************/
void hal_entry(void)
{
    /* TODO: add your own code here */
    //......
    //......
    /* Open the transfer instance with initial configuration. */
    err = R_SCI_B_UART_Open(&g_uart9_ctrl, &g_uart9_cfg);
    assert(FSP_SUCCESS == err);

    while(1)
    {
    	//......
    	//......
        printf("{\"adc\": %u, \"volt\": %.3f, \"temp\": %ld}\r\n", adc_raw, volt, temp_c); // uart3 print
        /* *********** UART9 print ************/
        char buf[64];
        int  len = snprintf(buf, sizeof(buf), "{\"adc\": %u, \"volt\": %.3f, \"temp\": %ld}\r\n", adc_raw, volt, temp_c);
        uart9_send_complete_flag = false;
        R_SCI_B_UART_Write(&g_uart9_ctrl, (uint8_t *)buf, len);
        while (!uart9_send_complete_flag) ;          // 等待发完

        R_BSP_SoftwareDelay (1000, BSP_DELAY_UNITS_MILLISECONDS);
    }
}

保存代码并构建工程。

效果
  • 打开串口调试助手工具,选择 JLINK 对应的串口设备,配置串口相关参数;
  • 点击打开串口按钮,即可接收到 ADC 对应的 JSON 消息;
  • 使用 USB 转 TTL 模块连接 UART9(P208/P209)可获取其输出字符串

MQTT 配置

  • 检查硬件连接,打开 ATK-D2x 配置软件,打开串口;

  • 进入左侧 模式配置 界面,工作模式选择 MQTT;

  • 填写 MQTT 服务器用户名、密码、ip地址、订阅主题、发送主题等信息;

  • 点击上方 保存所有参数 按钮,此时上位机自动发送 AT 指令,完成 MQTT 配置并自动重启;

详见:正点原子 D20 WiFi 模块 .

MQTTX

使用 MQTTX 软件测试串口透传与服务器转发。

  • 打开 MQTTX 软件,新建连接;

  • 填写 MQTT 服务器地址、用户名信息等,点击 Connect 按钮;

  • 新建订阅主题,输入 ATK-D20 上位机对应的发布主题信息,如 homeassistant/sensor/adc/state

  • 窗口不断弹出接收到的 MQTT 服务器转发的电压等信息;

YAML 配置

配置 HA 平台的 YAML 文件,根据主题添加相关参数;

YAML 文件代码

yaml 复制代码
mqtt:
  sensor:
    - name: "ADC 数值"
      state_topic: "homeassistant/sensor/adc/state"
      unit_of_measurement: "%"
      value_template: "{{ value_json.adc }}"
    - name: "ADC 电压"
      state_topic: "homeassistant/sensor/adc/state"
      unit_of_measurement: "%"
      value_template: "{{ value_json.volt }}"
    - name: "ADC 温度"
      state_topic: "homeassistant/sensor/adc/state"
      unit_of_measurement: "°C"
      value_template: "{{ value_json.temp }}"
  • 进入 HA 概览页面,编辑仪表盘,添加对应的卡片即可;
  • 卡片的 ADC 数值每秒更新

总结

本文介绍了瑞萨 CPKCOR-RA8D1B 开发套件由 ADC 采集引脚电压、温度传感器数据,通过串口发送 JSON 消息至 ATK D20 WiFi 模块,ATK-D20 模块将 MQTT 消息透传至 Home Assistant 平台,实现 HA 物联网电压表的项目设计,为该产品在物联网领域的开发设计和快速应用提供了参考。

相关推荐
诸葛务农2 小时前
光电对抗分类及外场静爆试验操作规程
人工智能·嵌入式硬件·分类·数据挖掘
点灯小铭6 小时前
基于单片机的多波形信号发生器设计
单片机·嵌入式硬件·毕业设计·课程设计·期末大作业
gfanbei12 小时前
ARM V8 Cortex R52 上电运行在什么状态?— Deepseek 解答
linux·arm开发·嵌入式硬件
小刘爱玩单片机13 小时前
【stm32协议外设篇】- PAJ7620手势识别传感器
c语言·stm32·单片机·嵌入式硬件
Jerry丶Li15 小时前
二十七、通信接口
c语言·stm32·单片机·嵌入式硬件
沸速存储15 小时前
DDR5引领变革:内存条行业的技术迭代与市场重构
嵌入式硬件·电脑
飞睿科技16 小时前
【IoT开发选型】乐鑫ESP32-C6核心优势解析:为何它在无线连接中表现如此全面?
嵌入式硬件·物联网
heisd_116 小时前
STM32时钟系统对于STM32F1系列(详解)
stm32·单片机·嵌入式硬件
应用市场16 小时前
STM32 ADC底层原理与寄存器配置详解
stm32·单片机·嵌入式硬件