STM32F103C8T6 点亮 LED —— 小白零基础完整教程

开发环境:Keil MDK v5.34(µVision 5.34,2021-03-12 发布) | 开发方式:ST 标准外设库 V3.5.0(库函数版)

目标芯片:STM32F103C8T6(Cortex-M3,72MHz,64KB Flash,20KB SRAM,LQFP-48,中容量 MD)

最终效果:下载程序后,开发板上的蓝色 LED 每 500ms 闪烁一次

难度:★☆☆☆☆ 时长:约 1~2 小时 成本:几十元(开发板 + 下载器) 适用:纯新手 / 首次接触 STM32

📑 目录

  1. 写在前面:我们要做什么
  2. 原理速览:LED 为什么会亮
  3. 硬件准备与接线
  4. 软件安装(Keil / 器件包 / 驱动 / 标准库)
  5. 搭建工程(每一步都详细)
  6. 编写代码(含逐行讲解)
  7. 编译与错误处理
  8. 下载程序到开发板
  9. 常见问题 FAQ
  10. 进阶方向
  11. 参考资料

一、写在前面:我们要做什么

单片机(微控制器)的"Hello World"就是点亮一颗 LED 灯。它虽然简单,却能让你完整走一遍嵌入式开发的全部流程:

本教程使用 Keil v5.34ST 标准外设库(Standard Peripheral Library)V3.5.0,这是 STM32 入门最经典、教程资料最多的一套组合(相比后来主推的 HAL 库,标准库代码直接、易学,国内大量教材都在用它)。

什么是"标准库"?ST 公司把操作芯片底层寄存器的代码封装成一个个函数(比如 GPIO_InitRCC_APB2PeriphClockCmd),你只需要调用这些函数,而不用自己计算寄存器每一位的值。学标准库 = 学"调函数",比直接操作寄存器容易得多,又能理解底层原理。
注意:教程以最常见的"STM32F103C8T6 最小系统板"(淘宝俗称蓝板 / Blue Pill)为例,板上自带一颗蓝色 LED 接在 PC13 引脚,无需额外焊接任何元件,最适合新手。如果你用的是其他开发板,LED 引脚可能不同(如 PB12、PB1、PA8),只需修改代码里的引脚宏即可,原理完全一样。

二、原理速览:LED 为什么会亮

只用理解 3 个概念,足够完成本教程:

2.1 GPIO 引脚 = 芯片伸出来的"手"

STM32F103C8T6 有 37 个 GPIO 引脚(PA0~PA15、PB0~PB15、PC13~PC15 等)。每个引脚都可以配置成输入(读外面信号)或输出(向外发信号)。我们要做的,就是把 PC13 配置成输出模式,然后让它在高电平(3.3V)低电平(0V)之间切换。

2.2 推挽输出:拉高拉低都靠芯片

GPIO 输出有 8 种模式,点亮 LED 用推挽输出(GPIO_Mode_Out_PP):芯片内部像一个"推"和"挽"两个开关,要么把引脚接到 3.3V(输出高电平),要么把引脚接到 GND(输出低电平),驱动能力最强,最常用。

2.3 时钟:芯片的"心跳"要逐个外设打开

STM32 为了省电,所有外设(包括 GPIO 端口)默认关着电。用哪个外设,必须先打开它的时钟(想象成"给这个外设通电")。GPIO 挂在 APB2 总线上,所以第一步永远是调用 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE) 给 GPIOC 通电。

2.4 蓝板上的 LED 为什么"低电平点亮"

蓝板原理图:LED 的阳极(+)接 3.3V,阴极(-)经一个限流电阻接 PC13。因此:

这正是新手最容易踩的坑:PC13 是"输出 0 点亮",和直觉相反。代码里我们约定 LED_ON() = 输出低电平(GPIO_ResetBits)。

一个比喻:把单片机想成"水龙头",引脚就是出水口,高电平=出 3.3V 的水,低电平=出 0V 的水;LED 是"落差瀑布",两端水压差越大越亮。PC13 的 LED 一头固定在 3.3V,所以 PC13 给 0V 时"落差"最大,灯最亮。

三、硬件准备与接线

3.1 需要购买的硬件(总价约 30~60 元)

物品说明价格参考
STM32F103C8T6 最小系统板(蓝板)板载 8MHz 晶振、复位按键、USB 供电接口、蓝色 LED(PC13)约 8~15 元
ST-Link V2 下载器用于把程序烧进芯片,选 SWD 4 针(3.3V/SWDIO/SWCLK/GND)的即可约 10~20 元
USB 线 × 2Micro-USB:一根给开发板供电,一根给 ST-Link几元
杜邦线(公对母)× 4连接 ST-Link 与开发板1~3 元
(可选)面包板 + LED + 330Ω 电阻如果想外接 LED 练习,见第 6.5 节几元
关于下载器:STM32 也可以用"USB 转 TTL 串口"下载(通过 BOOT0 引脚进系统引导程序),但操作繁琐、速度慢;强烈建议用 ST-Link V2,即插即用、支持在线调试,几十块钱就能买到,新手首选。

3.2 ST-Link 与开发板接线(SWD 方式,只需 4 根线)

ST-Link V2 引脚接到开发板引脚说明
3.3V3.3V给板子供电(可选,见下方提示)
SWDIODIO(即 PA13)数据线
SWCLKCLK(即 PA14)时钟线
GNDGND共地,必须连接

蓝板上的丝印一般标着 DIO(PA13)和 CLK(PA14),紧挨着 3.3V 和 GND,对照上图用杜邦线连好即可。有条件可以把 ST-Link 的 RST 也接到板子的 RESET 脚,能提高下载成功率,但不是必须。

供电建议(新手常见错误):很多便宜 ST-Link 的 3.3V 输出电流很小,带不动整块板子。稳妥做法是开发板用 USB 线单独供电,ST-Link 只接 SWDIO、SWCLK、GND 三根线(共地即可);ST-Link 自己用另一根 USB 线插电脑。这样供电最稳,下载也不受干扰。
千万不要:把板子的 5V 脚接进 ST-Link 的 3.3V,或电源正负极接反,会烧芯片。

四、软件安装(四步,顺序不能乱)

4.1 安装 Keil MDK v5.34

1下载:打开 https://www.keil.com/download/product/,找到 MDK-ARM(即 MDK v5),下载 v5.34 安装包(文件名形如 MDK534.exe,约 1GB)。下载前需要免费注册一个 ARM 账号并登录,用邮箱即可。

2运行安装:双击安装包,一路 Next。安装路径建议保持默认 C:\Keil_v5不要用中文或带空格的路径,否则编译器会出怪问题)。

3注册 License:安装完成后首次打开 µVision,会提示 License。个人学习直接用评估版(Evaluation)即可:编译代码大小限制 32KB,而我们的 LED 程序只有 1~2KB,完全够用,且功能无任何阉割(不弹窗、能下载能调试)。若公司商用,请购买正版 License(软件里 File → License Management → 添加许可证)。

为什么是 v5.34?v5.34 是 ARM 官方 2021 年 3 月 12 日发布的版本,它同时自带 Arm Compiler 5(AC5) 编译器——标准外设库用 AC5 编译最稳、报错最少。而 v5.36 之后的版本默认不带 AC5,标准库编译容易踩坑。所以你的 v5.34 选得非常合适。

4.2 安装 STM32F1 系列器件包(Device Family Pack,DFP)

MDK v5 的器件支持靠"器件包"管理。没有 STM32F1 的器件包,新建工程时就选不到 STM32F103C8 这颗芯片。安装方法二选一:

4.3 安装 ST-Link 驱动

4.4 下载 ST 标准外设库 V3.5.0

这是本教程的"弹药库"——ST 官方写的芯片驱动函数源码。下载方式:

解压后你会看到如下结构(记住它,下一节要用):

STM32F10x_StdPeriph_Lib_V3.5.0/
├── Libraries/                          ← 我们要用的核心库
│   ├── CMSIS/
│   │   └── CM3/
│   │       ├── CoreSupport/            ← core_cm3.c / core_cm3.h(内核支持)
│   │       └── DeviceSupport/ST/STM32F10x/
│   │           ├── stm32f10x.h         ← 芯片总头文件
│   │           ├── system_stm32f10x.c  ← 系统时钟初始化(默认72MHz)
│   │           ├── system_stm32f10x.h
│   │           └── startup/arm/
│   │               └── startup_stm32f10x_md.s  ← 启动文件(中容量MD!)
│   └── STM32F10x_StdPeriph_Driver/
│       ├── inc/                        ← 外设头文件(stm32f10x_gpio.h 等)
│       └── src/                        ← 外设源文件(stm32f10x_gpio.c 等)
├── Project/                            ← 官方示例工程(可参考,不直接用)
├── Utilities/                          ← 评估板代码(本教程不需要)
└── _htmresc/                           ← 图片素材(不需要)
关于启动文件:STM32F103 按 Flash 容量分小/中/大容量,选错启动文件会编译报错或无法启动。启动文件有 3 个:startup_stm32f10x_ld.s(低容量,16/32KB)、startup_stm32f10x_md.s(中容量,64/128KB)、startup_stm32f10x_hd.s(大容量,256KB+)。C8T6 = 64KB Flash = 中容量(Medium Density)→ 必须用 startup_stm32f10x_md.s,对应预定义宏 STM32F10X_MD(后面配置工程要用)。

五、搭建工程(照做即可,每一步都详细)

5.1 建文件夹,从标准库中"提取"需要的文件

在自己电脑上新建一个工程总文件夹(路径不要含中文,例如 D:\STM32_LED_Demo),然后按下面的结构建子文件夹:

STM32_LED_Demo/
├── Libraries/          ← 从标准库复制(下面细说)
│   ├── CMSIS/
│   └── STM32F10x_StdPeriph_Driver/
├── User/               ← 我们自己写的代码(main.c / led.c / led.h / delay.c / delay.h)
├── Project/            ← 存放 Keil 工程文件(.uvprojx 等)
└── Doc/                ← 放资料文档(可选)

从刚才解压的标准库里复制这些文件(只复制需要的,不要整个文件夹复制):

目标位置从标准库哪里复制复制什么
Libraries\CMSIS\Libraries\CMSIS\CM3\CoreSupport\core_cm3.c、core_cm3.h
Libraries\CMSIS\Libraries\CMSIS\CM3\DeviceSupport\ST\STM32F10x\stm32f10x.h、system_stm32f10x.c、system_stm32f10x.h
Libraries\CMSIS\...\STM32F10x\startup\arm\startup_stm32f10x_md.s(中容量启动文件)
Libraries\STM32F10x_StdPeriph_Driver\inc\Libraries\STM32F10x_StdPeriph_Driver\inc\stm32f10x_gpio.h、stm32f10x_rcc.h、stm32f10x_misc.h(可先全拷,后续用到不折腾)
Libraries\STM32F10x_StdPeriph_Driver\src\Libraries\STM32F10x_StdPeriph_Driver\src\stm32f10x_gpio.c、stm32f10x_rcc.c、stm32f10x_misc.c

说明:标准库外设文件很多(USART、TIM、ADC……),本工程只用到 GPIO 和 RCC,所以只需 gpio、rcc、misc 三个外设源文件;misc.c 是 NVIC 内核中断相关,加进去备用。头文件建议把 inc 整个文件夹复制,省得以后缺头文件。

偷懒技巧:网上很多"标准库工程模板"压缩包,直接下载解压就能用。但自己亲手搭一遍才能理解每个文件的用途,强烈建议先照本教程搭一次。

5.2 在 Keil 中新建工程、选择芯片

1打开 Keil µVision 5,菜单 Project → New uVision Project...

2在弹出的保存窗口中,进入刚才建的 STM32_LED_Demo\Project 文件夹,工程名输入 LED_Blink,点保存(会自动生成 LED_Blink.uvprojx)。

3弹出 Select Device for Target 窗口:左侧输入框搜索 STM32F103C8,在结果里选择 STMicroelectronics → STM32F1 Series → STM32F103 → STM32F103C8(注意看清是 C8 不是 C6/CB),点 OK。能看到右侧显示芯片信息:Cortex-M3、72MHz、64KB Flash、20KB SRAM。

4随后会弹出 Manage Run-Time Environment(软件包组件勾选窗口)——标准库开发直接点右上角红色 X 关闭它,不要勾任何组件(那些组件是给 CMSIS-Pack 方式用的,我们用标准库自带文件,避免重复定义)。

5如果弹窗问 "Copy STM32 Startup Code to project folder?",选择 (我们自己用标准库的 startup_stm32f10x_md.s)。

现在左侧 Project 窗口里出现 Target 1,里面只有一个空的 Source Group 1。接下来把它改造成规范的分组结构。

5.3 分组(Group)并添加文件

1右键 Target 1Manage Project Items...(或点工具栏第二个图标"项目窗口"),打开项目管理窗口。

2Project Targets 里把 Target 1 改名 LED_Blink

3Groups 里删掉 Source Group 1,然后依次点 Add 新建 4 个组,命名为:StartupCMSISFWLIBUser

4选中某个组,点 Add Files,把对应文件加进去(在文件类型下拉框选"All files"以便能看到 .s 文件):

组名添加的文件(路径相对工程根目录)
StartupLibraries\CMSIS\startup_stm32f10x_md.s
CMSISLibraries\CMSIS\core_cm3.c、Libraries\CMSIS\system_stm32f10x.c
FWLIBLibraries\STM32F10x_StdPeriph_Driver\src\stm32f10x_gpio.c、stm32f10x_rcc.c、stm32f10x_misc.c
UserUser\main.c、User\led.c、User\led.h、User\delay.c、User\delay.h(文件还没写,先建空的占位,下一节再写内容)
文件类型提醒:在 Add Files 对话框右下角把文件类型从默认的 C Source 改成 All files,否则看不到 .s 汇编启动文件和 .h 头文件。

5.4 工程配置("魔术棒"Options for Target)——最关键的一步

点击工具栏魔术棒图标(或菜单 Project → Options for Target,快捷键 Alt+F7),逐页配置:

① Target 页

AC5 还是 AC6?v5.34 同时装了 AC5 和 AC6 两套编译器。AC6(armclang)编译标准库会冒出几十个警告(C99 语法兼容问题),虽然也能过,但对新手不友好。选 AC5 一劳永逸

② Output 页

③ C/C++ 页(两个必填项)

.\Libraries\CMSIS
.\Libraries\STM32F10x_StdPeriph_Driver\inc
.\User

这 4 个路径让编译器能找到 stm32f10x.h、stm32f10x_gpio.h、stm32f10x_rcc.h、led.h 等头文件。漏掉任何一个,编译都会报 "cannot open source file" 错误。

④ Debug 页(选下载器)

为什么选"Med-density 128K"?这是 Keil 为 F103 中容量芯片提供的统一烧录算法(.FLM)。C8T6 实际 Flash 只有 64KB,但程序会写入 0x08000000 起始的低地址区,远小于芯片容量,完全兼容。选择该算法即可正常烧录。

⑤ Utilities 页

配置完成,点 OK 关闭。至此工程搭建完毕。先别急着编译——我们的 User 文件夹里还没有真正的代码。

六、编写代码(复制粘贴 + 逐行讲解)

User 文件夹里新建 5 个文件,把下面的代码完整复制进去。文件较多,我们用"分层"方式组织:led(硬件驱动)delay(延时)main(主程序),这也是以后写复杂工程的标准结构。

6.1 led.h —— LED 的"说明书"(头文件)

把所有与硬件相关的定义集中在这里:以后换板子、换引脚,只改这一个文件。

#ifndef __LED_H
#define __LED_H

#include "stm32f10x.h"          // 标准库总头文件:包含 GPIO、RCC 等所有外设定义

/*---------------- 硬件配置区:换开发板只改这里 ----------------*/
// 板载LED:蓝板 LED 接在 PC13,阴极接PC13、阳极接3.3V,所以"低电平点亮"
#define LED_GPIO_PORT   GPIOC                       // LED 所在端口
#define LED_GPIO_PIN    GPIO_Pin_13                 // LED 所在引脚
#define LED_GPIO_CLK    RCC_APB2Periph_GPIOC        // 对应端口的时钟(GPIO挂在APB2总线)

/*---------------- 操作宏:语义化,主程序里好读 ----------------*/
#define LED_ON()    GPIO_ResetBits(LED_GPIO_PORT, LED_GPIO_PIN)   // PC13输出低电平 → 灯亮
#define LED_OFF()   GPIO_SetBits(LED_GPIO_PORT, LED_GPIO_PIN)     // PC13输出高电平 → 灯灭

/* 函数声明 */
void LED_Init(void);

#endif  // __LED_H

#ifndef / #define / #endif 是"防止头文件重复包含"的经典写法,编译原理是:第一次包含时定义 __LED_H 宏,第二次再包含时直接被跳过,避免重复定义错误。每个头文件都要这样写。

6.2 led.c —— LED 的"具体实现"(源文件)

#include "led.h"        // 先包含自己的头文件

/**
 * @brief  初始化 LED 引脚
 * @note   三步走:开时钟 → 配结构体 → 调用库函数
 */
void LED_Init(void)
{
    GPIO_InitTypeDef GPIO_InitStructure;   // 定义"配置结构体"变量

    // 第1步:打开 GPIOC 端口的时钟(不打开,寄存器写了也白写)
    RCC_APB2PeriphClockCmd(LED_GPIO_CLK, ENABLE);

    // 第2步:往结构体里填配置参数
    GPIO_InitStructure.GPIO_Pin  = LED_GPIO_PIN;      // 选中引脚:PC13
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;  // 输出模式:通用推挽输出
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; // 输出速度:50MHz(LED够用,选最低的2MHz也行)

    // 第3步:把结构体配置真正写入寄存器(初始化完成)
    GPIO_Init(LED_GPIO_PORT, &GPIO_InitStructure);

    // 初始状态:灯灭(PC13 输出高电平)
    LED_OFF();
}

逐句讲解

6.3 delay.c / delay.h —— 简单延时(软件延时,教学够用)

// delay.h
#ifndef __DELAY_H
#define __DELAY_H

#include "stm32f10x.h"

void Delay_ms(uint32_t ms);

#endif  // __DELAY_H
// delay.c —— 注意:这是"空循环"软件延时,精度不高但简单直观
#include "delay.h"

/**
 * @brief  毫秒级软件延时(近似值)
 * @note   72MHz主频下,内层循环7200次约耗时1ms(会随编译优化等级略有变化)
 */
void Delay_ms(uint32_t ms)
{
    uint32_t i, j;
    for (i = 0; i < ms; i++)
    {
        for (j = 0; j < 7200; j++);   // 空循环消磨时间
    }
}
为什么先学"笨办法"?真正的工业级延时用 SysTick 定时器(硬件计时,精确且不占用 CPU 空转),教程附录 A 给了 SysTick 精确延时版本。但新手先用空循环延时能少接触一个概念、更快看到现象。等学会定时器中断再升级不迟。

6.4 main.c —— 主程序(程序入口)

/**
 * 工程名:LED_Blink
 * 芯片  :STM32F103C8T6
 * 效果  :板载蓝色LED每500ms闪烁一次
 */
#include "stm32f10x.h"   // 标准库总头文件
#include "led.h"         // LED驱动
#include "delay.h"       // 延时

int main(void)
{
    LED_Init();              // 第1步:初始化LED引脚(配置成推挽输出)

    while (1)                // 第2步:死循环,程序永远在这里转
    {
        LED_ON();            // 点亮:PC13输出低电平
        Delay_ms(500);       // 保持500ms

        LED_OFF();           // 熄灭:PC13输出高电平
        Delay_ms(500);       // 保持500ms
    }
}

几个关键点

6.5 (可选)外接 LED 怎么接、代码怎么改

如果手痒想用面包板外接一颗 LED(以 PA0 为例):

  1. 接线:PA0 → 330Ω 电阻 → LED 阳极 → LED 阴极 → GND。此时 PA0 输出高电平点亮(和板载相反)。
  2. led.h 的硬件配置区即可,主程序一行不用动:
// 外接LED接 PA0(阳极接PA0、阴极经电阻接地 → 高电平点亮)
#define LED_GPIO_PORT   GPIOA
#define LED_GPIO_PIN    GPIO_Pin_0
#define LED_GPIO_CLK    RCC_APB2Periph_GPIOA

// 因为极性反了,亮/灭宏也要对调:
#define LED_ON()    GPIO_SetBits(LED_GPIO_PORT, LED_GPIO_PIN)    // 输出高 → 亮
#define LED_OFF()   GPIO_ResetBits(LED_GPIO_PORT, LED_GPIO_PIN)  // 输出低 → 灭
必须串限流电阻:LED 直接接 GPIO 会把 20mA 左右的电流全灌进引脚,时间长了可能损伤芯片。串一个 330Ω~1kΩ 电阻最保险。

七、编译与错误处理

1点击工具栏 Build 图标(或按 F7,或菜单 Project → Build Target)编译。

2看底部 Build Output 窗口。成功标志:最后一行出现 "LED_Blink.axf" - 0 Error(s), 0 Warning(s)(或 0 Error、少量 Warning 也正常)。同时会在 Project 文件夹下生成 LED_Blink.hex

3如果报错:双击 Build Output 里的红色错误行,光标会自动跳到出错位置,对照下表排查。

报错信息原因解决方法
fatal error: stm32f10x.h: No such file or directory头文件搜索路径没配Options → C/C++ → Include Paths 添加 5.4 节的 4 个路径
undefined symbol: GPIO_Init 等库源文件没加入工程确认 FWLIB 组里加了 stm32f10x_gpio.c、stm32f10x_rcc.c、stm32f10x_misc.c
startup_stm32f10x_md.s: error A1163E: Unknown opcode启动文件格式/版本不对确认用的是标准库自带的 startup_stm32f10x_md.s,而不是从别处复制的
multiple definition / redefinition文件重复添加或宏重复定义检查各组里文件是否有重复;头文件用 #ifndef 保护
#error "Please select first the target STM32F10x device..."宏定义少了 STM32F10X_MDC/C++ → Define 填 STM32F10X_MD, USE_STDPERIPH_DRIVER
Warning: #1-D: last line of file ends without a newline警告,无害在文件末尾补一个空行即可消除
编译不等于成功下载:0 Error 只代表代码语法正确,程序能不能跑、灯亮不亮,还要靠下载到板子上验证。新手第一个程序报几次错太正常了,按错误提示逐条改即可。

八、下载程序到开发板(点亮时刻!)

1接线:按第 3.2 节把 ST-Link 与开发板用杜邦线连好(SWDIO→DIO、SWCLK→CLK、GND→GND,3.3V 可选),开发板插 USB 供电,ST-Link 插电脑 USB。

2确认芯片可识别:Options → Debug → Settings,右侧 SW Device 里应显示芯片 IDCODE,说明 ST-Link 和芯片握手成功。

3点击工具栏 LOAD 按钮(Download,图标是一个芯片带向下箭头;也可按 F8 不保证,以点按钮为准)。

4Build Output 窗口滚动输出下载进度,最后出现 Application running ...(因为我们勾了 Reset and Run,下载完自动复位运行)。

5看效果:开发板上 PC13 的蓝色 LED 开始以 500ms 间隔闪烁!🎉

如果灯没亮,按第 9 节 FAQ 排查。下载成功后,把板子拔电再上电,程序依然会运行——因为程序已经烧进了芯片内部的 Flash,断电不丢失。这就是"单片机"和"电脑程序"的本质区别。

九、常见问题 FAQ

现象可能原因 / 解决办法
下载时报 "No target connected" 或 "Cannot connect to target"① ST-Link 驱动没装好(重装第 4.3 步驱动);② 接线错了(SWDIO/SWCLK 接反);③ 板子没供电(单独用 USB 给板子供电);④ 杜邦线接触不良(重新插紧)。
下载后灯不亮,但下载成功① 没勾 Reset and Run,按一下板子 RESET 键;② 检查代码里 LED 引脚是否和你的板子一致(蓝板是 PC13);③ 确认宏定义 STM32F10X_MD 没写错成 HD(HD 会编译过但外设基址可能错乱,极端情况程序跑飞)。
程序下载过一次后,第二次连不上 ST-Link上次程序可能把 SWD 引脚(PA13/PA14)配置成了普通 IO 并锁死。解决:按住板子 RESET 键不放 → 点 Keil LOAD → 松开 RESET,趁"复位窗口期"擦除重烧;或用 ST-Link Utility / STM32CubeProgrammer 做全片擦除(Erase)。
编译报 "cannot open source file xxx.h"Include Paths 没配全(第 5.4 节③),把 4 个路径都加上。
中文注释在 Keil 里显示乱码文件编码问题。菜单 Edit → Configuration → Editor → Encoding 选 Chinese GB2312 (Simplified);或把源码文件另存为 GB2312/ANSI 编码(Notepad++ 可转)。
灯亮度很低 / 闪烁规律怪异可能程序里用了 SystemInit 后主频不是 72MHz(蓝板晶振虚焊/损坏),先检查板子 8MHz 晶振是否焊好;软件延时随主频变化属正常。
想删掉整个工程重来直接删除工程文件夹即可。Keil 不写注册表、不残留服务,删文件夹就是卸载工程。
评估版提示 32KB 限制不够用LED 程序编译后仅 1~2KB,远没到限制。以后做大型项目(FreeRTOS 等)超出限制时再考虑购买 License。

十、进阶方向(点亮之后学什么)

  1. 寄存器版点亮 LED:不调库函数,直接操作 RCC->APB2ENRGPIOC->CRHGPIOC->ODR 寄存器——彻底搞懂库函数背后发生了什么。
  2. SysTick 精确延时 + 定时器中断:用硬件定时器代替空循环,学中断(NVIC)。
  3. 按键输入:GPIO 输入模式(上拉/下拉),用按键控制 LED。这是"输入"概念的入门。
  4. 串口 USART:printf 打印调试信息,与电脑通信——嵌入式开发最重要的调试手段。
  5. PWM 呼吸灯:定时器 PWM 输出,LED 渐亮渐暗。
  6. ADC 采集:读电位器电压,串口发出来。
  7. 之后可以学 HAL 库 + STM32CubeMX 图形化配置,或用 FreeRTOS 做多任务。

十一、参考资料


本教程由 Hermes Agent 依据公开资料整理生成 · 内容核实日期:2026-08-06 · 版权归原作者各自所有,仅供学习使用