本帖最后由 bigfanofloT 于 2023-9-1 20:43 编辑

感谢论坛和厂家,有机会学习瑞萨的MCU开发。
开发板型号是FPB-RA4E1
微信图片_20230901201132.jpg
RA4E1 快速原型板配备了 R7FA4E10D2CFM 微控制器,是一块专门用于各种应用原型开发的评估板。 板载 SEGGER J-Link™ 仿真器电路,无需额外工具即可以烧写/调试程序。 此外,标配 Arduino Uno 和 Pmod™ 接口,并可通过通孔连接微控制器的所有引脚,具有很高的可扩展性。
样例代码可用于演示 RA4E1 MCU 的功能以及连接 RA4E1 快速原型板和各种无线模块或传感器模块。
使用时,请根据各国家/地区的无线电法规使用 蓝牙™、LoRa® 和 Wi-Fi。

  • 配备 RA4E1 32 位微控制器(64 引脚,ROM:512KB,RAM:128KB)
  • 板载 SEGGER J-Link™ 仿真器电路,无需额外工具即可对程序进行烧写/调试
  • 可以通过通孔连接微控制器的所有引脚
  • 标配 Arduino Uno 和 Pmod™ 接口
  • 支持各种 RA4E1 软件和工具


微信图片_20230901201120.jpg
开发板主要特性:
屏幕截图 2023-09-01 201630.png
开发板官网链接如下:
https://www.renesas.cn/cn/zh/products/microcontrollers-microprocessors/ra-cortex-m-mcus/rtk7fpa4e1s00001be-ra4e1-fast-prototyping-board-fpb-ra4e1
提供了详细的开发资料和视频教程。
主控芯片是RA4E1,瑞萨电子 RA4E1 32 位微控制器 (MCU) 产品群使用支持 TrustZone 的高性能 Arm® Cortex®-M33 内核。 RA4E1 采用高效的 40nm 工艺,是 RA 产品家族微控制器的入门级产品,通过开放且灵活的生态系统(灵活配置软件包 (FSP))提供支持。 RA4E1 适用于入门级物联网应用的需求,这些应用通常需要优化的功能和集成的连接性、降低总体系统成本和平衡的功耗与性能。RA4E1提供 100 MHz 的Cortex-M33 内核和尽可能低的运行功耗(从闪存运行 CoreMark® 算法时功耗低至 81µA/MHz)的组合。
ra4e1-block-diagram_0.png


下面使用 RASC 软件新建一个工程, 直接借助 RASC 来自动生成一个 Keil 工程。
首先打开 RASC 软件,接着在菜单栏依次点击“File”→“New”→“FSP Project”,开始新建一个工程,然后会弹出如下的默认界面:
屏幕截图 2023-09-01 201748.png
接下来点击“Next”进入下一步,到工程选项界面,如下图所示。 与使用 e2s 新建工程时的一样,我们需要在这里选择 FSP 库版本、板子型号、设备(MCU)型号、编程语言、编译器等。 这里的不同之处主要在于需要额外选择 IDE 类型(Keil、IAR等),并且不需要选择调试器, 因为调试器是在 IDE 里面进行选择和配置的:
屏幕截图 2023-09-01 201838.png
选择IDE工具是KEIL:
屏幕截图 2023-09-01 201855.png
更改完成后的配置如下图所示。然后点击“Next”下一步:
屏幕截图 2023-09-01 201909.png
这里默认选择 “Flat (Non-TrustZone) Project” 即可。点击“下一步”:
屏幕截图 2023-09-01 201921.png
默认选择 “No RTOS” 即可,然后点“下一步”,最后进入主页了,图形化的配置方式,十分强大,不用去翻数据手册找寄存器了:
屏幕截图 2023-09-01 202028.png
接下来配置串口,根据原理图板卡的串口GPIO是:P109和P110
屏幕截图 2023-09-01 203239.png
SCI(Serial Communications Interface),意为串行通信接口, 是相对与并行通信的概念,是串行通信技术的一种总称,包括了UART,SPI等串行通信技术。
SCI 模块包含如下功能:
UART
8位时钟同步接口
简易IIC(只能用作主机)
简易SPI
智能卡接口(符合ISO/IEC 7816-3国际标准)
曼彻斯特接口
增强的串行接口
P109和P110管脚功能配置为串口:
屏幕截图 2023-09-01 203902.png
串口属性配置:注意通道和管脚的配置
屏幕截图 2023-09-01 204039.png

串口中断回调函数
在前面的 FSP 配置步骤的时候,设置了串口中断回调函数的名字为: debug_uart9_callback。 设置这么一个函数的原因是:每当串口发送或者接收完成一个字符时,都会默认触发串口的中断, 而在串口中断中会调用函数 debug_uart9_callback,在函数里我们需要根据不同的中断情况进行相应的处理。
因此,需要同时在我们的代码里面定义并实现这么函数 debug_uart9_callback。 我们把这个函数放到文件“bsp_debug_uart.c”中,该函数代码如下所示。
其中,需要定义一个额外的标志变量 uart_send_complete_flag 来表示串口发送数据已完成。 变量 uart_send_complete_flag 必须加上volatile,否则可能被编译器优化。
/* 发送完成标志 */
  • volatile bool uart_send_complete_flag = false;

  • /* 串口中断回调 */
  • void debug_uart9_callback (uart_callback_args_t * p_args)
  • {
  •    switch (p_args->event)
  •    {
  •       case UART_EVENT_RX_CHAR:
  •       {
  •             /* 把串口接收到的数据发送回去 */
  •             R_SCI_UART_Write(&g_uart9_ctrl, (uint8_t *)&(p_args->data), 1);
  •             break;
  •       }
  •       case UART_EVENT_TX_COMPLETE:
  •       {
  •             uart_send_complete_flag = true;
  •             break;
  •       }
  •       default:
  •             break;
  •    }
  • }
  • 复制代码
    重定向printf输出到串口
    虽然可以直接使用 R_SCI_UART_Write 函数来将字符串输出到串口, 但是这个函数在很多情况下没有 printf 函数那样方便。所以需要添加一段代码来将 printf 输出重定向到串口(UART9)。
    将以下的代码添加到源文件“bsp_debug_uart.c”里面。 由于不同C库的 printf 函数的底层实现不同,这里使用条件编译选择我们需要重写的函数。
    /* 重定向 printf 输出 */
  • #if defined __GNUC__ && !defined __clang__
  • int _write(int fd, char *pBuffer, int size); //防止编译警告
  • int _write(int fd, char *pBuffer, int size)
  • {
  •    (void)fd;
  •    R_SCI_UART_Write(&g_uart9_ctrl, (uint8_t *)pBuffer, (uint32_t)size);
  •    while(uart_send_complete_flag == false);
  •    uart_send_complete_flag = false;

  •    return size;
  • }
  • #else
  • int fputc(int ch, FILE *f)
  • {
  •    (void)f;
  •    R_SCI_UART_Write(&g_uart9_ctrl, (uint8_t *)&ch, 1);
  •    while(uart_send_complete_flag == false);
  •    uart_send_complete_flag = false;

  •    return ch;
  • }
  • #endif
  • 复制代码
    hal_entry入口函数
    C语言程序的入口函数 main 函数调用了 hal_entry 函数。 在 hal_entry 函数里面编写应用代码。
    void hal_entry(void)
  • {
  •    /* TODO: add your own code here */
  •    Debug_UART9_Init(); // SCI9 UART 调试串口初始化
  •    printf("mbb.eet-china.com,RA4E1 Test\r\n");
  •    while(1)
  •    {
  •       R_BSP_SoftwareDelay(1, BSP_DELAY_UNITS_SECONDS);
  •    }
  • #if BSP_TZ_SECURE_BUILD
  •    /* Enter non-secure code */
  •    R_BSP_NonSecureEnter();
  • #endif
  • }
  • 复制代码