跳转至

STM32CubeMX生成Keil工程并实现闪灯与串口输出

STM32CubeMX生成Keil工程并实现闪灯与串口输出

环境搭建

STM32CubeMX 下载链接:https://www.st.com/stm32cubemx

Keil 下载链接:https://www.keil.com/download/product/

1728704546211-4e95e0a2-86c3-429a-85f1-56543ec7654c.png

Keil 为付费软件,可以在网上寻找注册机激活使用

1728704881460-facd9a5d-b33a-424d-a3ae-81f8462b8a4b.png

另外 Keil 需要安装一下 STM32 的 pack 包可以直接在 Keil 的 Pack Installer 中下载

1728707374314-fda48a3b-3b24-4844-b0a8-0f19e99387bb.png

1728707336389-f9e1097d-f2c8-4fb1-9476-a95eafebfafe.png

也可以从官网下载:https://www.keil.arm.com/packs 然后双击安装

1728705448258-fd00c82a-8c0a-4953-a877-29cad294c5aa.png

1728707481949-f9352ef9-6504-4915-beb4-851cb9cb8aa0.png

工程配置

打开 STM32CubeMX 点击新建工程

1728698279943-0f314161-966e-4b1b-a070-aad363dd2c53.png

在打开的窗口中选择选择一下芯片型号,然后在右边选择对应的封装,点击 Start Project

1728698420525-63c1ca7d-579f-4997-89f6-0703fb26245e.png

接下来配置始时钟

选择 System Core -> RCC 将 High Speed Clock(HSE)修改为 Crystal/Ceramic Resonator

1728699695091-e07d14d9-8db9-4149-8d61-a577956f480f.png

这里有必要多介绍一下,首先有两个不同的选项 HSE 和 LSE,这两都是配置外部时钟的选项,区别是:
HSE 是高速外部时钟,可接石英/陶瓷谐振器(晶振),或者接外部时钟源,频率范围为4MHz~16MHz

LSE 是低速外部时钟,接频率为32.768kHz的石英晶体

一般开发板上会有外部晶振,所以选择 HSE,其中又有三个选项:Disable 、 BYPASS Clock Source(旁路时钟源) 、Crystal/Ceramic Resonator(石英/陶瓷 晶振)

Disable 就不用多说了,禁用外部时钟,BYPASS Clock Source 意思是接直接从旁路导入时钟信号主要是给有源晶振用的,只需要接入 OSC_IN 引脚即可;Crystal/Ceramic Resonator 意思是需要 STM32 内部的时钟驱动电路配合外部无源晶振需要接 OSC_IN 和 OSC_OUT

然后来到 Clock Configuration 将 HCLK 修改为最大的 72,然后回车,会自动配置其他的参数

1728700533914-1e414147-0743-48df-b0e4-8f02f2db62e6.png

然后配置调试模式为 Serial Wire 即 SWD 调试,否则调试引脚可能被复用为其他功能导致无法调试

1728700727411-d04bb239-2c47-4063-9689-b62435a8fc06.png

如果想要点亮一个 LED 灯的话,需要知道 LED 灯在开发板上连接到了哪个引脚,例如我这块板子上是 PC13,那么就需要配置 PC13 引脚为 GPIO_Output,配置时只需要点击右侧芯片上的对应引脚即可

1728701207315-1590f557-fe8b-4424-aaf6-831f8d409469.png

然后如果想要使用 printf 打印什么的话,可以在 Connectivity 选择 USART1/2/3 ,设置 Mode 为 Asynchronous(异步通信),可以在下方的 Configuration -> GPIO Settings 配置使用哪个引脚来进行 USART 通信,也可以在 Configuration -> Parameter Settings 选择波特率等参数(默认 115200 可以不配置)

需要注意的在 Configuration -> NVIC Settings 中使能串口中断

1728701442580-674759b3-75a9-476e-94bb-56eb9a13ce44.png

之后就可以来到 Project Manager 页面填写好项目名称及 IDE和版本

1728701815905-c0605fa6-acb4-4250-866a-a7f50e1dccae.png

然后来到 Code Generator 勾选生成独立的外设文件,最后点击右上角的 GENERATE CODE 即可,生成过程中遇到啥让下载的让他下载即可

1728701975789-a1ffab37-88a5-49d4-aa2c-3b09c5190563.png

来到对应的文件夹,找到 MDK-ARM 双击 .uvprojx 结尾的 keil 工程即可打开

1728702343715-06a84458-9214-4b40-95b2-31331e5e9fa5.png

代码编写

点击 Options for Target 勾选上 Usb MicroLIB

1728703748380-11373f9c-a1ae-4595-9dcc-43f2e3231c04.png

在 stm32f1xx_it.c 最后面添加这段代码

void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
    if(huart->Instance == USART1)
    {
        HAL_UART_Transmit(&huart1, (uint8_t *)Buffer, 1, 0xffff);
        HAL_UART_Receive_IT(&huart1, (uint8_t *)Buffer, 1);
    }
}

1728702710685-c104506d-1112-49be-8ecd-ed930c31210e.png

在 main.c 中添加包含 stdio.h 头文件和这俩函数

int fputc(int ch, FILE *f)
{
    HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xffff);
    return ch;
}

int fgetc(FILE *f)
{
    uint8_t ch = 0;
    HAL_UART_Receive(&huart1, &ch, 1, 0xffff);
    return ch;
}

1728702935064-c783cdb3-0001-4493-8e2f-f69d47ef9612.png

在 main.c 中添加全局变量:uint8_t Buffer[1];

在 stm32f1xx_it.c 头部声明全局变量 Buffer:extern uint8_t Buffer[1];

1728703143555-25ed40f8-b876-45b0-8684-6e70024522b7.png

在串口初始化后,while 循环前添加接收中断开启函数

HAL_UART_Receive_IT(&huart1, (uint8_t *)Buffer, 1);

1728703250731-6266cf47-0f2a-44f9-a514-b598d1be8241.png

接下来就可以正常在 while 里面写代码,正常使用 printf 格式化字符串输出了

  while (1)
  {
      HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13,GPIO_PIN_SET);//灯亮 
      HAL_Delay(500); 
      HAL_GPIO_WritePin(GPIOC,GPIO_PIN_13,GPIO_PIN_RESET);//灯灭 
      HAL_Delay(500);
      printf("Hello World!\n\n");
  }

原文: https://www.yuque.com/hxfqg9/iot/fgy6mzhhg0vgx4p4