0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

定义IO初始化结构体

瑞萨MCU小百科 ? 来源:野火电子 ? 2025-07-16 16:26 ? 次阅读
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

欢迎回到我们的RA系列FSP库开发实战指南频道,下面我们将继续讲解“自己写库——构建库函数雏形”部分:

8.2.5定义IO初始化结构体

由上述IOPORT相关功能的枚举类型我们可以知道,在对IOPORT模块进行初始化时需要根据情况配置它们。因此我们定义一个IOPORT初始化的结构体类型IOPORT_Init_t,它的成员包括了由上述所有枚举类型所声明的变量,因此该结构体类型的变量可以包含IOPORT的相关功能配置。

列表5:代码清单8-4:ra_ioport.h文件

左右滑动查看完整内容

/* IOPORT 初始化结构体类型定义 */


typedefstruct
{
IO_Port_tPort;
IO_Pin_tPin;
IO_Mode_tMode;
IO_Dir_tDir;
IO_OType_tOType;
IO_DriveCapability_tDrive;
IO_Level_tLevel;
IO_Pull_tPull;
} IOPORT_Init_t;

8.2.6编写IO操作函数

我们把IO操作函数的声明和IO初始化函数的声明都放在ra_ioport.h头文件。

列表6:代码清单8-5:ra_ioport.h文件

左右滑动查看完整内容

/* IO 操作函数(调用一次只能操作一个 IO 引脚) */
uint32_tIOPORT_PinRead(IO_Port_t port, IO_Pin_t pin);
voidIOPORT_PinWrite(IO_Port_t port, IO_Pin_t pin, IO_Level_t?
→level);
voidIOPORT_PinToggle(IO_Port_t port, IO_Pin_t pin);
voidIOPORT_PinAccessEnable(void);
voidIOPORT_PinAccessDisable(void);


/* IO 初始化函数(调用一次只能初始化一个 IO 引脚) */
voidIOPORT_Init(IOPORT_Init_t *ioport_init);

然后在ra_ioport.c源文件里面实现这些IO操作函数。

列表7:代码清单8-6:ra6m5_ioport.c文件

左右滑动查看完整内容

/* 读引脚电平 */


uint32_tIOPORT_PinRead(IO_Port_t port, IO_Pin_t pin)
{
/* Read pin level. */
returnR_PFS->PORT[port >>8].PIN[pin].PmnPFS_b.PIDR;
}


/* 写引脚电平 */
voidIOPORT_PinWrite(IO_Port_t port, IO_Pin_t pin, IO_Level_t level)
{
uint32_t pfs_bits =R_PFS->PORT[port >>8].PIN[pin].PmnPFS;//读寄存器?
→PmnPFS


pfs_bits &= ~(uint32_t)0x1;//清零 PODR 位
R_PFS->PORT[port >>8].PIN[pin].PmnPFS= (pfs_bits | level);
}


/* 翻转引脚电平 */
voidIOPORT_PinToggle(IO_Port_t port, IO_Pin_t pin)
{
uint32_t pfs_bits =R_PFS->PORT[port >>8].PIN[pin].PmnPFS;//读寄存器?
→PmnPFS
pfs_bits ^= (uint32_t)0x1;//取反 PODR 位
R_PFS->PORT[port >>8].PIN[pin].PmnPFS= pfs_bits;
}


/* 引脚访问使能 */
voidIOPORT_PinAccessEnable(void)
{
R_PMISC->PWPR=0;///< Clear BOWI bit - writing to PFSWE bit?
→enabled
R_PMISC->PWPR= 1U << 6U;?///< Set PFSWE bit - writing to PFS register?
→enabled
}


/* 引脚访问禁止 */
voidIOPORT_PinAccessDisable(void)
{
R_PMISC->PWPR=0;///< Clear PFSWE bit - writing to PFS register?
→disabled
R_PMISC->PWPR= 1U << 7U;?///< Set BOWI bit - writing to PFSWE bit?
→disabled
}

8.2.7编写IO初始化函数

最后编写IOPORT初始化函数。

列表8:代码清单8-7:ra_ioport.c文件

左右滑动查看完整内容

/* IOPORT 初始化函数 */


voidIOPORT_Init(IOPORT_Init_t *ioport_init)
{
uint32_t pfs_bits =0;//不读取寄存器 PmnPFS
if(ioport_init->Mode==IO_MODE_GPIO)//如果引脚用作普通 GPIO 功能
{
if(ioport_init->Dir==IO_DIR_INPUT)/* 用作输入模式 */
{
pfs_bits |= (ioport_init->Pull) <Dir==IO_DIR_OUTPUT)/* 用作输出模式 */
{
pfs_bits |= (ioport_init->Dir) <Level) <Mode) <Drive) <PORT[ioport_init->Port>>8].PIN[ioport_init->Pin].PmnPFS= pfs_
→bits;
}

8.2.8hal_entry入口函数

前一章节实验里有讲过,当使用RTOS时,程序从main函数开始进行线程调度;当没有使用RTOS时,C语言程序的入口函数main函数调用了hal_entry函数。本章节实验的工程也是没有选用RTOS的,因此,用户程序是从hal_entry函数开始执行。

打开“srchal_entry.c”文件,我们在“hal_entry.c”文件中添加对头文件“ra_ioport.h”的包含,然后在hal_entry函数里面编写我们的代码。

以启明6M5开发板为例,RA6M5工程的hal_entry数代码如下所示。

注解

启明4M2开发板和启明2L1开发板的用户可直接打开配套的“09_Register_MyLib”例程查看该代码,限于篇幅,不在本章中贴出。

列表9:代码清单8-8:hal_entry.c文件

左右滑动查看完整内容

/* IOPORT 模块头文件 (自己写库——构建库函数雏形) */
#include"ioport/ra_ioport.h"


voidhal_entry(void)
{
/*TODO:add your own code here */


/* 调用取消写保护函数 */
IOPORT_PinAccessEnable();


/* 使用 IOPORT 初始化结构体和调用初始化函数来配置 PFS 寄存器 */
IOPORT_Init_t led_io_init;
led_io_init.Port = IO_PORT_04;
led_io_init.Pin = IO_PIN_00;
led_io_init.Mode = IO_MODE_GPIO;//普通 GPIO 模式,而不是复用功能模式或其他
的
led_io_init.Dir = IO_DIR_OUTPUT;
led_io_init.OType = IO_OTYPE_PP;
led_io_init.Drive = IO_DRIVE_LOW;
led_io_init.Level = IO_LEVEL_HIGH;//输出高电平(LED 熄灭)
//LED_IO_Init.Pull = IO_NO_PULL; //端口方向处于输出模式下是用不了上拉的,所以这
个属性没意义
IOPORT_Init(&led_io_init);//调用初始化函数,进行 LED1 引脚初始化
led_io_init.Pin = IO_PIN_03;//更换引脚号
IOPORT_Init(&led_io_init);//结构体其他属性不变,再次调用初始化函数,进行 LED2 引
脚初始化
led_io_init.Pin = IO_PIN_04;//更换引脚号
IOPORT_Init(&led_io_init);//结构体其他属性不变,再次调用初始化函数,进行 LED3 引
脚初始化


/** 此时 3 个 LED 灯的引脚默认输出的是高电平,所以 3 个 LED 灯都会默认不亮
* 我们先打开所有 LED 灯,然后在 while 循环里让 LED1 闪烁:每秒钟翻转一次状态
*/
IOPORT_PinWrite(IO_PORT_04, IO_PIN_00, IO_LEVEL_LOW);//点亮 LED1
IOPORT_PinWrite(IO_PORT_04, IO_PIN_03, IO_LEVEL_LOW);//点亮 LED2
IOPORT_PinWrite(IO_PORT_04, IO_PIN_04, IO_LEVEL_LOW);//点亮 LED3


while(1)
{
/* 使用函数 IOPORT_PinToggle 翻转 LED1 引脚电平 */
IOPORT_PinToggle(IO_PORT_04, IO_PIN_00);
R_BSP_SoftwareDelay(1000, BSP_DELAY_UNITS_MILLISECONDS);
}


#ifBSP_TZ_SECURE_BUILD
/* Enter non-secure code */
R_BSP_NonSecureEnter();
#endif
}

8.3下载验证

编写好上述代码,然后将程序编译并下载到开发板之后,按下复位按键来复位开发板,可以观察到实验现象与上一章的实验现象相同:开发板上面除了电源指示灯之外的3个LED灯当中有两个灯常亮,还有一个灯在缓慢闪烁。闪烁着的LED灯为LED1,它每秒钟(1000毫秒)便改变一次亮灭的状态。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • 函数
    +关注

    关注

    3

    文章

    4383

    浏览量

    65020
  • 开发板
    +关注

    关注

    25

    文章

    5707

    浏览量

    105204
  • 结构体
    +关注

    关注

    1

    文章

    131

    浏览量

    11128
  • FSP
    FSP
    +关注

    关注

    0

    文章

    45

    浏览量

    7445

原文标题:定义IO初始化结构体——瑞萨RA系列FSP库开发实战指南(21)

文章出处:【微信号:瑞萨MCU小百科,微信公众号:瑞萨MCU小百科】欢迎添加关注!文章转载请注明出处。

收藏 人收藏
加入交流群
微信小助手二维码

扫码添加小助手

加入工程师交流群

    评论

    相关推荐
    热点推荐

    RT-Thread自动初始化详解

    初始化函数不需要被显式调用,只需要在函数定义处通过宏定义的方式进行申明,就会在系统启动过程中被执行,非常的方便。 1 普通初始化 前面也讲了,我们在写单片机的程序时,需要对硬件进行
    的头像 发表于 06-25 21:38 ?1.2w次阅读
    RT-Thread自动<b class='flag-5'>初始化</b>详解

    自动初始化机制原理详解

    自动初始化机制是指初始化函数不需要被显式调用,只需要在函数定义处通过宏定义的方式进行申明,就会在系统启动过程中被执行。这篇文章就来探索一下其中的奥秘, 简单理解其原理!
    的头像 发表于 12-16 09:33 ?1441次阅读
    自动<b class='flag-5'>初始化</b>机制原理详解

    LED实验中把结构定义放在时钟初始化后出现报错

    有人知道LED实验中,led.c文件中把结构定义放在时钟初始化后面,会报错,这是什么原因呢?正常程序如下:GPIO_InitTypeDef GPIO_InitStructure
    发表于 03-23 04:37

    C51的结构初始化编译错误

    8051的结构初始化错误,我查了下这种初始化是C99可以支持的,但在option中设置没有C99模式选项,怎么破?
    发表于 03-25 02:37

    定时器初始化结构定义

    定时器初始化结构定义为typedef struct{uint16_t TIM_Prescaler; uint16_t TIM_CounterMode; uint16_t TIM_Pe
    发表于 08-18 07:12

    【原创分享】变量的初始化技巧

    由于在嵌入式系统中必须考虑程序规模的问题,因此,对程序中的变量的初始化也需要进行慎重的考虑。在C语言中,基本数据结构(字符型、整型)的初始化相对简单;数组、结构
    发表于 09-08 15:28

    STM32f1单片机的HAL库是如何去定义定时器相关的初始化结构

    STM32F1定时器可分为哪几类呢?STM32f1单片机的HAL库是如何去定义定时器相关的初始化结构的?
    发表于 11-23 07:39

    请问STM32通用定时器初始化结构定义是什么

    请问STM32通用定时器初始化结构定义是什么?
    发表于 11-23 06:56

    结构初始化怎么才能在keil4中编译通过呢

    结构初始化怎么才能在keil4中编译通过呢?有何解决办法?
    发表于 12-20 07:58

    利用结构数组方便地控制单片机IO相关资料推荐

    定义结构typedef struct {GPIO_TypeDef *GPIOx;u8Pinx;} relay_io;初始化
    发表于 01-18 09:10

    USART初始化结构详解

    USART 初始化结构详解标准库函数对每个外设都建立了一个初始化结构,比如USART_Ini
    发表于 02-22 06:08

    结构数组的初始化

    ] = {3,4},[4] = {5,6},[2] = {7,8}, [0] = {9,10}};//首次见到的初始化方法,这样赋值顺序可自定义。但有什么用呢? for(i = 0 ; i
    发表于 05-21 15:24

    结构定义初始化和赋值

    type)的一类。结构可以被声明为变量、指针或数组等,用以实现较复杂的数据结构结构同时也是一些元素的集合,这些元素称为
    发表于 11-20 09:29 ?5.6w次阅读

    STM32的IO口基本操作:初始化结构,设置系统时钟,开启外设时钟资料下载

    电子发烧友网为你提供STM32的IO口基本操作:初始化结构,设置系统时钟,开启外设时钟资料下载的电子资料下载,更有其他相关的电路图、源代码、课件教程、中文资料、英文资料、参考设计、用
    发表于 03-29 16:49 ?17次下载
    STM32的<b class='flag-5'>IO</b>口基本操作:<b class='flag-5'>初始化</b><b class='flag-5'>结构</b><b class='flag-5'>体</b>,设置系统时钟,开启外设时钟资料下载

    C语言指定初始化器解析及其应用

    C90 标准要求初始化程序中的元素以固定的顺序出现,与要初始化的数组或结构中的元素顺序相同。但是在新标准 C99 中,增加了一个新的特...
    发表于 02-07 11:28 ?2次下载
    C语言指定<b class='flag-5'>初始化</b>器解析及其应用