使用STM32CubeMX生成项目
首先我们点击CubeMX,进入芯片选择页面,这里根据自己的开发板的芯片型号,自行选择。
这里选择自己的芯片双击即可
这里我们首先配置系统时钟RCC,时钟是单片机运行的基础,时钟信号推动单片机内各个部分执行相应的指令。时钟系统就是CPU的脉搏,决定cpu速率,像人的心跳一样 只有有了心跳,人才能做其他的事情,而单片机有了时钟,才能够运行执行指令,才能够做其他的处理 (点灯,串口,ADC),时钟的重要性不言而喻。
晶振选择为3种:
Disable 这个是不用外部晶振
Crystal/Ceramic Resontor 这个是用无源外部晶振
BYPASS Clock Source 这个是有源外部晶振
这里我高速时钟和低速时钟都配置成无源外部晶振,读者可以自行根据项目配置。
这里SYS,Debug配置成Serial Wire,时钟源选择定时器4(我这是为后续移植FreeRTOS准备,所以没有选择第一个系统的)
因为这是一个简单的串口数据显示项目,所以我没有配置其他的,单独配置一个串口1,串口中断不开,因为后续BSP移植里面会有串口中断的配置。
然后配置时钟,只需配置HCLK,配置成72MHz即可。
这里将自己的项目名,项目存放路径,自己选择好,然后在Toolchain/IDE选择MDK-ARM。
这里勾选将.h和.c分开查看的按键。
然后点击右上角生成代码,我们用CubeMX生成的项目最开始就生成了。
修改生成的工程项目
然后打开工程。
这便是我们生成的项目,但是还有很多冗杂的东西,我们首先把gpio.c、usart.c这两个.c文件删除。
我们在项目的目录下新建一个文件夹,改名为BSP。
再将我们写好的串口配置函数直接调用。
需要的可以自行在资源里面下载
我们点击一个长得像品字的按钮,然后添加组BSP,再加进去bsp_usart.c文件。(这里.h文件都是看不见的,但是是存在的),然后点击ok。
再点击魔法棒,按图中点击,更新路径
找到路径中的BSP并加入进去。
然后打开main.c文件,我们进行适当修改。
我们删除usart.h,gpio.h这两个头文件,并引入bsp_usart.h这个头文件,然后删除 MX_GPIO_Init();
MX_USART1_UART_Init(); 这两个hal库配置的串口。
可以看见现在是0 ERROR,0 Warning。我们再来配置串口,我们在bsp_usart.c文件中可以看见,我们配置串口1是
void USART1_Init(unsigned int BPS, void Tx_Over(void), void (*RxFunction)(unsigned char RX_Data))
{
GPIO_InitTypeDef GPIO_InitStruct = {0};
//´®¿Ú1³õʼ»¯
__HAL_RCC_USART1_CLK_ENABLE();
__HAL_RCC_GPIOA_CLK_ENABLE();
Usart_ISR.U1TXOver = Tx_Over; //·¢ËÍÍê³É»Øµ÷
Usart_ISR.U1RXOperation = RxFunction; //½ÓÊÕÊý¾Ýº¯Êý
GPIO_InitStruct.Pin = GPIO_PIN_9;
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = GPIO_PIN_10;
GPIO_InitStruct.Mode = GPIO_MODE_INPUT;
GPIO_InitStruct.Pull = GPIO_NOPULL;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
huart1.Instance = USART1;
huart1.Init.BaudRate = BPS;
huart1.Init.WordLength = UART_WORDLENGTH_8B;
huart1.Init.StopBits = UART_STOPBITS_1;
huart1.Init.Parity = UART_PARITY_NONE;
huart1.Init.Mode = UART_MODE_TX_RX;
huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
huart1.Init.OverSampling = UART_OVERSAMPLING_16;
if (HAL_UART_Init(&huart1) != HAL_OK)
{
Error_Handler();
}
__HAL_UART_ENABLE_IT(&huart1, UART_IT_RXNE); //ʹÄܽÓÊÕÖжÏ
//USART3 NVIC ÅäÖÃ
HAL_NVIC_SetPriority(USART1_IRQn, 0, 1);
HAL_NVIC_EnableIRQ(USART1_IRQn);
}
这是串口一的初始化
但这样就好了吗,其实还没有,我们在stm32中使用printf这个函数,我们都需要对fputc这个函数进行重定义。
int fputc( int ch, FILE *f )
{
USART_TypeDef* USARTx = USART1;
while((USARTx->SR & (1<<7))==0);
USARTx->DR=ch;
return ch;
}
这是重定义的函数,原理是我们查看stm32f103系列的芯片手册时,可以看见数据是存入stm32的DR寄存器的,当bit=7时,我们的数据便全部发送出去了,然后我们SR寄存器是状态寄存器,我们可以判断是否有数据存入。
我们要点击魔法棒,勾选使用MicroLIB,然后自己用的什么下载工具自行配置,不然我们的printf打印的内容还是无法在串口助手上查看。
像这样,我们便可以下载到开发板上进行调试了,但注意不能在keil5里面在线模拟调试,因为hal库使用模拟调试会出现什么都打印不了的情况。
下载到开发板,我们打开串口助手,就能看见我们打印的数据在串口助手上一秒一次的发送。
到此本文结束。