野火电子论坛

 找回密码
 注册

QQ登录

只需一步,快速开始

查看: 16021|回复: 2

关于STM32结构体指针的问题,视频第9讲第1节

[复制链接]
发表于 2020-5-23 23:29:53 | 显示全部楼层 |阅读模式
本帖最后由 浮云来客 于 2020-5-23 23:36 编辑

视频中有讲到,将GPIO的寄存器定义成结构体。代码如下:
#define PERIPH_BASE                   ((unsigned int ) 0x40000000)         //声明外设基地址为0x4000 0000
#define APB2PERIPH_BASE                (PERIPH_BASE + 0x10000)                        //声明APB2基地址0x4001 0000
#define GPIOA_PERIPH_BASE                (APB2PERIPH_BASE + 0x0800)                        //声明GPIOA基地址0x4001 0800

typedef struct   
{
        uint32_t CRL;        //0x00
        uint32_t CRH;        //0x04        
        uint32_t IDR;        //0x08
        uint32_t ODR;        //0x0c
        uint32_t BSRR;        //0x10
        uint32_t BRR;        //0x14
        uint32_t LCKR;        //0x18
        

}GPIO_TypeDef;

#define GPIOA  ((GPIO_TypeDef *) GPIOA_PERIPH_BASE )
//而这个在主函数中是直接访问的结构体成员变量的,缺少取指符,之前讲的都有取指符的
RCC_APB2ENR |= (1<<2);                             //打开GPIOA的时钟
GPIOA->CRH &=~((0x0f)<<(4*0)) ;                //将GPIOA的CRH寄存器清零 即GPIOA_8
GPIOA->CRH |= (1<<(4*0));                        //将GPIOA的CRH寄存器配置为0x0001
//之前的讲解的程序是这样的;指针前面都有取指符的
*( unsigned int * )(0x40021000 + 0x18) |= (1<<2); //打开GPIOA的时钟
*( unsigned int * )(0x40010800 + 0x04) &=~((0x0f)<<(4*0)); //先要将CRH寄存器清零
*( unsigned int * )(0x40010800 + 0x04) |= (1<<(4*0));

//我理解的 GPIOA->CRH 等于(GPIO_TypeDef *) (GPIOA_PERIPH_BASE+CRH的偏移地址) 即为 (GPIO_TypeDef *)(0x40010800 + 0x04)
//这样是没有取指符的

是我理解有问题吗,请大神帮忙解释一下,谢谢!






回复

使用道具 举报

发表于 2020-7-16 11:56:08 | 显示全部楼层
帮顶一下,遇到同样的疑惑!
回复 支持 反对

使用道具 举报

发表于 2020-7-16 12:11:21 | 显示全部楼层
我建议去翻阅一下C语言中结构体访问成员变量的两种方法,就能理解了。 ((GPIO_TypeDef *) GPIOA_PERIPH_BASE )已经被强制转换成了一个结构体指针,而结构体指针访问成员的时候直接是使用->,也就是GPIOA->CRL就达到了访问成员的目的。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

联系站长|手机版|野火电子官网|野火淘宝店铺|野火电子论坛 ( 粤ICP备14069197号 ) 大学生ARM嵌入式2群

GMT+8, 2024-11-25 14:30 , Processed in 0.027369 second(s), 24 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表