【STM32F407 开发板】实验一(PLUS):跑马灯实验

前言:

好长时间没有写过专业性的博客了,一直在看书,书也由于太深奥看不太懂,近来由于追喜欢的女孩子失败了,唉,伤心欲绝,肝肠寸断,痛哭流涕,泣不成声啊,最终彻悟,女孩子只会影响我拔刀的速度,便下定决心投入学习,此时回首才猛然想起研二快要开题了,不能连板子都不会用,所以开始做起了嵌入式实验,重操旧业。


一、连接板子

连接板子使用的是还是老工具,如下图所示:
在这里插入图片描述
将板子连接好之后,双击打开软件:

在这里插入图片描述
点击Connect连接开发板。
在这里插入图片描述
此时就可以关闭软件了。

二、新建工程

由于我也是新手,能按照满是错误的实验指导书来,并且做出正确的实验,就已经很不错了。

新建工程使用的是:
在这里插入图片描述
打开软件:
在这里插入图片描述
新建工程:
在这里插入图片描述
选择自己开发板的板子,由于我们的板子是F407的,我就选的这个型号。其中的MCU的意思是:微型控制器单元。选择完成后点击OK

在这里插入图片描述

三、设置管脚

进入如下界面,接下来的操作,我也不是很理解,单能说出个大概:

这是一个芯片,就是F407,做这个实验,就是要看电路,这个芯片的正确的电路图如下图所示:

在这里插入图片描述
这就是贼坑人的一点了,实验指导书,妈的,它的电路图是错误的,如果按照之前的电路图来说,只亮三个灯,恶心,PE2管脚的灯不亮,因为错误的电路图上,这个管脚是PF7,亮个屁啊,连电路都不对。

有了电路图,可以看出是低压亮灯。并且在芯片上找到对应的管脚,并设为OUTPUT模式。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

四、时钟树配置,配置外部时钟

在左侧外设一栏中选择RCC:
在这里插入图片描述
这个RCC是一个系统时钟,其中选用了HSE高速外部时钟,具体的指望我短时间了解,怕是不太行了,我贴上一个很详细的博客吧!【STM32】系统时钟RCC详解(超详细,超全面)

选完之后,可以看到芯片上这俩个管脚亮了:
在这里插入图片描述
我觉得意思应该是OS_CLOCK_IN和OS_CLOCK_OUT,因为这是一个高速外部时钟,应该是要有进有出的吧,,,

接下来就是我的个人理解了,因为是自学,我感觉我理解的是对的,哈哈哈

首先看F407的外设图:

在这里插入图片描述
额,浅要理解吧,我们需要的是GPIO外设,GPIO外设是在AHB总线上,并且要求168MHZ,所以时钟配置图来了

点击配置时钟标签,进入配置时钟界面:
在这里插入图片描述

在这里插入图片描述
说一下下吧,首先左侧输入的频率是25MHZ,是HSE高速外部时钟,所以后面那个PLL Source当然要选择HSE,之后的一顿乘除,我感觉写啥都可以,只要凑够168MHZ的时钟就行,之后作为PLLCLK时钟进行输入,产生了系统时钟168MHZ,然后AHB的预定为168MHZ,之后的那个红框框里面的/4 /2,我个人觉得只是为了凑后面的MAX MHZ而已,我们真正的目的只是AHB就可。

五、外设详细参数设置

点击菜单栏上的Configuration
在这里插入图片描述
显示如下,说实话,我也不知道咋用,感觉就是简简单单的配置一下外设就可以了
在这里插入图片描述

点击GPIO可以查看我们选定的,指定功能要用的管脚:
在这里插入图片描述
可以看到用到了4个管脚,对于每个管脚,我们都可以进行管脚的模式、速度、上拉下拉之类的进行配置,现在这个工程实验里面不需要配置。

这时候就可以点击Generate生成工程代码了,其实说实话,我感觉Cube就是一个图形化编程软件,他把整个工程的大概框架以图形化的形式展现出来,这样生成的代码,最后只需要添加业务逻辑代码就可以了,其他的配置都在Cube中配置完了。

点击在这里插入图片描述生成工程文件。
在这里插入图片描述

在这里插入图片描述

点击OK,生成文件。

六、添加业务逻辑代码,编译工程

在这里插入图片描述
选择Open Project,进入Keil5的工程界面:
在这里插入图片描述
然后其实我们主要写的就是main.c文件里面的业务逻辑了

点开main.c
在这里插入图片描述
在这里插入图片描述

HAL_GPIO_WritePin(GPIOF, GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10, GPIO_PIN_SET);
HAL_GPIO_WritePin(GPIOE, GPIO_PIN_2, GPIO_PIN_SET);
Turn_On_LED(count % 4);
count++;
HAL_Delay(500);

编写 Turn_On_LED(uint8_t LED_NUM)
在这里插入图片描述

void Turn_On_LED(uint8_t LED_NUM)
{
	switch(LED_NUM)
	{
		case 0:
			HAL_GPIO_WritePin(GPIOE, GPIO_PIN_2, GPIO_PIN_RESET); 
			break;
		case 1:
			HAL_GPIO_WritePin(GPIOF, GPIO_PIN_8, GPIO_PIN_RESET); 
			break;
		case 2:
			HAL_GPIO_WritePin(GPIOF, GPIO_PIN_9, GPIO_PIN_RESET); 
			break;
		case 3:
			HAL_GPIO_WritePin(GPIOF, GPIO_PIN_10, GPIO_PIN_RESET); 
			break;
		default:
			break;
	}
}

编写完成后,点击编译在这里插入图片描述
在这里插入图片描述
编译完成后,点击LOAD到板子上:
在这里插入图片描述
在这里插入图片描述

七、运行

下载到板子上之后,需要点击一下reset复位键(其实也可以不点,只需要在下面的图标里面设置一下就可以了)
在这里插入图片描述
点击复位键后,板子开始运行代码,如图:

在这里插入图片描述

八、详细分析源代码(重点)

说是详细分析,其实我也是个大菜逼,只是分析一下main.c中的函数叭

  1. HAL_Init();
    右击函数名,点击进入函数具体定义页面,这里的HAL,是Hardware Abstraction Layer(硬件抽象层):

    HAL_StatusTypeDef HAL_Init(void)
    {
      /* Configure Flash prefetch, Instruction cache, Data cache */ 
    #if (INSTRUCTION_CACHE_ENABLE != 0U)
       __HAL_FLASH_INSTRUCTION_CACHE_ENABLE();
    #endif /* INSTRUCTION_CACHE_ENABLE */
    
    #if (DATA_CACHE_ENABLE != 0U)
       __HAL_FLASH_DATA_CACHE_ENABLE();
    #endif /* DATA_CACHE_ENABLE */
    
    #if (PREFETCH_ENABLE != 0U)
      __HAL_FLASH_PREFETCH_BUFFER_ENABLE();
    #endif /* PREFETCH_ENABLE */
    
      /* Set Interrupt Group Priority */
      HAL_NVIC_SetPriorityGrouping(NVIC_PRIORITYGROUP_4);
    
      /* Use systick as time base source and configure 1ms tick (default clock after Reset is HSI) */
      HAL_InitTick(TICK_INT_PRIORITY);
      
      /* Init the low level hardware */
      HAL_MspInit();
      
      /* Return function status */
      return HAL_OK;
    }
    

    这个函数说实话,我看不懂,我只知道那个NVIC是嵌套中断控制器,详情见这篇博客:STM32中的NVIC详解 至于其他的函数逻辑,目前确实不太懂

  2. void MX_GPIO_Init(void)
    这个函数是GPIO的初始化函数,当初GPIO的初始化,通过Cube来设置的,就是查看详细外设参数那里,这里是,生成的代码层次的实现:

    void MX_GPIO_Init(void)
    {
    
      GPIO_InitTypeDef GPIO_InitStruct;
    
      /* GPIO Ports Clock Enable */
      __HAL_RCC_GPIOE_CLK_ENABLE();/*使 能 管 脚 E F H 的 时 钟*/
      __HAL_RCC_GPIOF_CLK_ENABLE();
      __HAL_RCC_GPIOH_CLK_ENABLE();
    
      /*Configure GPIO pin Output Level */
      HAL_GPIO_WritePin(GPIOE, GPIO_PIN_2, GPIO_PIN_RESET);
    
      /*Configure GPIO pin Output Level */
      HAL_GPIO_WritePin(GPIOF, GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10, GPIO_PIN_RESET);
    
      /*Configure GPIO pin : PE2 */
      GPIO_InitStruct.Pin = GPIO_PIN_2;
      GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
      GPIO_InitStruct.Pull = GPIO_NOPULL;
      GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
      HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);
    
      /*Configure GPIO pins : PF8 PF9 PF10 */
      GPIO_InitStruct.Pin = GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10;
      GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
      GPIO_InitStruct.Pull = GPIO_NOPULL;
      GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
      HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
    
    }
    

    __HAL_RCC_GPIOE_CLK_ENABLE();这个宏定义的含义就是使能GPIO的时钟。至于详细的操作了哪个寄存器,我目前还没分析过。

    HAL_GPIO_WritePin(GPIOE, GPIO_PIN_2, GPIO_PIN_RESET);GPIO管脚的输出值的设置,其函数具体内容如下:
    在这里插入图片描述
    在这里插入图片描述
    由简介看到这个函数操作的是BSRR寄存器,在板子的参考手册中有:
    在这里插入图片描述
    可以看到高位是用来复位的,低位是用来置位的,有上面函数代码逻辑可知,如果函数传入的不是RESET(复位)的话,就认为是置位,由上图可知,对应位为1的话,则对ODRx寄存器进行置位操作,所以这个寄存器相当于一个标志数组的概念,用来进行标志。在进行复位的时候,是将传入的uint16数值强转为32位的,然后左移16位,进行寄存器复位部位的赋值操作。

    ODRx寄存器的说明如下:
    在这里插入图片描述
    ODR寄存器是端口的输出数据,因为端口都是电路,其实就是输出电压而已,举个例子,在Turn_On_LED函数中,点亮一个LED需要使用RESET复位操作,也就是需要将ODR中的某一位复位,那么复位就会时灯亮,而灯亮是低电压才亮,所以复位的话,就是如上的0x0000 0000就是在对应端口输出低电压。

    最上面代码的这个部分:

      /*Configure GPIO pin : PE2 */
      GPIO_InitStruct.Pin = GPIO_PIN_2;
      GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
      GPIO_InitStruct.Pull = GPIO_NOPULL;
      GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
      HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);
    
    

    就是对管脚的配置初始化信息,如上,初始化管脚位PIN2,模式位PULL/PUSH,然后NO PULL & NO PUSH,速度为LOW,都是当初在Cube中设置过的。至于 HAL_GPIO_Init(GPIOE, &GPIO_InitStruct); 这个函数,目前功力尚浅,看的我眼花缭乱。

  3. 接下来就是最简单的while部分
    在这里插入图片描述
    可以明显的看到,一开始是将所有管脚设为SET,高电压模式,所有灯都不亮,然后点亮一个灯,如此循环。

  4. void Turn_On_LED(uint8_t LED_NUM)
    在这里插入图片描述
    这个目前来说就非常简单了叭,就是一个switch/case语句加上一个RESET输出低电压点亮灯的过程。

九、总结

行了,说了这么多,终于说完了,总结一下吧,主要还是对于硬件的理解太少,因为之前我一直致力于软件工程,看我以前的博客就知道,我是纯软件,没想到硕士变成了嵌入式,害,重新来过吧,一点点的开始学习叭,加油!!!

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值