ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

STM32F103开发板入门指南:从开箱到进阶的完整学习路线

STM32F103开发板入门指南:从开箱到进阶的完整学习路线 开发板到手的那一刻确实挺兴奋的。STM32-103的开发板也就是基于STM32F103芯片的那些板子可能是国内学习嵌入式接触最多的一类硬件了。不管你是电子相关专业的学生还是工作后转行想搞单片机这个板子基本是绕不过去的一站。这篇文章就针对刚把板子买回来、还没想好怎么下手的朋友把开箱确认、环境搭建、第一个程序到进阶模块的路线完整捋一遍顺便把那些容易踩的坑提前给你标出来。先说清楚这块板子能干什么。STM32F103是意法半导体推出的一款基于ARM Cortex-M3内核的32位单片机主频最高72MHz片上资源包括Flash存储、SRAM、ADC、定时器、USART串口、I2C、SPI、CAN、USB等常见外设。你手头这块板子一般就是把最小系统、USB转串口、LED、按键、TFTLCD接口、Flash芯片等外设集成在一起的开发板。它能做的事情非常多从简单的跑马灯、按键检测到超声波测距、控制伺服电机、驱动打印机再到读取显示屏、做USB设备、跑CAN通信全都能覆盖。适合零基础的初学者也适合做毕业设计或者产品原型验证。买回来之后很多人第一件事是迷茫不知道从哪里开始。别急我按自己的实操经验把整个流程拆成几个阶段一步一步来说。1. 开箱之后先别急着上电把板子认清楚再说1.1 先确认主控芯片型号和封装STM32F103这个系列有很多型号常见的有STM32F103C8T6、STM32F103RCT6、STM32F103ZET6等。后缀里的字母和数字代表封装和Flash容量。C8T6是48引脚Flash 64KB常用的“蓝板”就是这颗RCT6是64引脚Flash 256KB很多入门开发板用的也是它ZET6是144引脚Flash 512KB属于大容量型号。拿到板子后先找到主控芯片看丝印上的型号。这个动作很重要因为后续建工程选芯片型号、配置启动文件、选择Flash容量都要用它。千万别凭感觉选错型号否则程序烧进去可能跑不起来或者下载器报错说识别不到芯片。我第一次就因为这个折腾了大半天板子是RCT6工程里选的C8T6编译下载都正常但一跑就死机。1.2 确认第一脚养成看原理图的习惯很多新手拿到板子会问芯片第一脚怎么确认。方法很简单芯片上有圆形或斜切的标记从标记处开始逆时针数就是第1脚。开发板出厂一般会在PCB上印上芯片的方向和1脚位置不会太明显但放大看能找到。这个细节千万不要忽视因为后面你接外设、量信号、接示波器探头都要从原理图出发原理图里芯片引脚编号就是按第一脚顺序排的。顺便说一句开发板的原理图一定要从卖家页面或者配套资料里下载保存好后面查问题全靠它。1.3 上电前的检查清单上电前最好做三件事一是看板子供电方式大多数开发板通过USB供电也有支持DC电源座或外部电源输入的二是确认板子上的电源开关是否拨到ON三是检查有没有明显焊锡短路或者元器件脱落尤其是USB接口附近的保护元件。确认没问题后插上USB线。正常情况下板子上的电源指示灯会亮如果是带USB转串口的板子电脑上会识别到一个串口设备。如果你的电脑识别不了先检查驱动。很多板子用的USB转串口芯片是CH340在Windows 10/11下一般会自动装驱动但偶尔需要手动安装。如果连的是什么CP2102或者FT232也都有对应驱动去官网下载安装就行。1.4 确认串口芯片和板子版本有个经验买开发板一定要看清串口芯片型号。CH340的兼容性最好驱动好装烧录也方便。部分老板子用的CP2102在某些系统上会抽风FT232虽然稳定但假货多。板子到手后打开设备管理器看端口那一栏确认识别到一个COM口并且记下COM几后面下载程序要用。2. 开发环境搭建Keil和VSCode两条路都要会2.1 Keil MDK的安装和芯片包STM32开发最主流的IDE是Keil MDK也就是Keil uVision。去官网下载MDK安装包建议用5.x版本。装完之后必须装芯片包否则Device里找不到STM32F103。芯片包在Keil官网的Pack Installer里在线安装或者下载离线pack包手动装。打开Pack Installer搜索STM32F1找到STM32F1xx系列的支持包点击Install。这一步很关键很多人装完MDK发现没有STM32选项就是漏了芯片包。装完后新建工程在弹出的Device选择界面搜索STM32F103根据你的型号选择对应的具体芯片比如STM32F103RCTx。启动文件也要选对。在Manage Run-Time Environment里Device下的Startup勾选。MDK会自动帮你选择对应容量型号的启动文件大容量和小容量启动文件不一样不要自己乱改。2.2 标准库还是HAL库选型背后的逻辑STM32开发有两条主流路线标准外设库Standard Peripheral Library简称标准库和HAL库。标准库是意法半导体早期的封装库代码直观一个外设对应一组API比如GPIO_Init、USART_SendData适合理解寄存器操作逻辑。HAL库是后来的抽象库代码更臃肿但跨平台迁移好配合STM32CubeMX图形化配置工具非常方便。我的建议是如果是学生做毕设、比赛或者产品要用STM32CubeMX生成工程直接用HAL库如果想把单片机底层搞透、希望代码精简可控标准库更适合练手。现在的开发板资料里F103的标准库资料非常多绝大多数入门教程都是标准库写的所以新手用标准库跟着教程走最顺畅。但也要提醒一句能读懂HAL库也总要会的因为现在的芯片型号和第三方SDK越来越多地默认用HAL。2.3 VSCode搭建STM32开发环境的补充方案除了Keil也可以用VSCode搭配EIDEEmbedded IDE插件或者PlatformIO来开发STM32。热词里也有不少人搜“VSCode配置STM32开发环境”说明这个需求确实在增长。EIDE插件的思路是在VSCode里管理工程、编译然后配合OpenOCD或者pyOCD下载调试。这个方案的好处是编辑器体验好代码补全比Keil舒服太多而且工程可以方便地放进Git管理。缺点是要自己折腾配置编译链要用arm-none-eabi-gcc调试配置文件要自己写launch.json。如果你只是入门阶段建议先用Keil把流程跑通等代码量上来了再考虑切VSCode否则环境问题会把你劝退。2.4 下载调试工具的选择开发板通常板载ST-Link或者用DAP-Link也有的是用USB转串口ISP下载。ST-Link是意法半导体官方的调试器支持SWD模式接线只有SWDIO、SWCLK、GND三根非常省事。如果你的板子没有板载ST-Link外接一个ST-Link V2也很便宜几块钱到十几块不等能用就行。注意一点很多板载ST-Link和板载串口是分开的两个USB口上电的时候两个口都插上调试和串口监视才能同时工作。有些初学者只插了串口口结果Keil里怎么都识别不到ST-Link就是这个原因。3. 第一个程序跑马灯和按键GPIO的核心你要吃透3.1 跑马灯背后的原理很多人的第一个STM32程序就是点亮LED。看似简单但里面的知识点一点也不简单。LED的引脚一般接在芯片的某个GPIO上你要做的就是把这个GPIO配置成推挽输出模式然后写高电平或低电平控制LED亮灭。GPIO配置在标准库里就是几行代码GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); GPIO_InitStructure.GPIO_Pin GPIO_Pin_0; GPIO_InitStructure.GPIO_Mode GPIO_Mode_Out_PP; GPIO_InitStructure.GPIO_Speed GPIO_Speed_50MHz; GPIO_Init(GPIOB, GPIO_InitStructure);这段代码干的事情是打开GPIOB的时钟、把Pin0设置为推挽输出、速度50MHz。STM32的每一个外设在使用前都要先打开对应的时钟这一点和51单片机非常不一样也是新手最容易忘的。忘了使能时钟代码看起来全对但外设就是不工作。推挽输出是什么意思简单说就是引脚既能输出高电平、也能输出低电平而且驱动能力比较强适合驱动LED这种负载。对应的还有开漏输出开漏模式不能主动输出高电平必须接上拉电阻才能输出高一般用于I2C这类总线或者需要在外部接不同电压电平的场合。跑马灯就是多个LED依次亮灭本质上就是循环控制几个引脚的电平变化。用延时函数控制节奏比如每点亮一个灯延时500ms再切换。这是练习GPIO输出和延时函数的好项目。3.2 按键输入的上拉下拉和消抖按键输入和LED相反要配置成输入模式。这里有两个关键点上拉/下拉电阻的选择和消抖处理。按键的一端接GPIO另一端接GND或者VCC。如果按键一端接地那么GPIO需要配置成上拉输入平时读到高电平按下时读到低电平。反过来如果按键接VCC就要用下拉输入。标准库配置里对应的是GPIO_Mode_IPU和GPIO_Mode_IPD。消抖的问题是机械按键固有的。按下和松开的瞬间机械触点会抖动单片机读到的电平在几毫秒里会跳变多次。如果不对这个跳变做处理一次按键可能会被识别成好几次。最简单的消抖方法就是软件延时检测到电平变化后延时10到20毫秒再读一次确认电平真的变化了再执行操作。这个延时消抖是嵌入式里非常基础的手法后面做矩阵键盘、旋转编码器都要用到。3.3 启动配置BOOT0和BOOT1板子上一般有两个跳线或者拨码开关标注BOOT0和BOOT1。这两个引脚决定芯片从哪个地址启动。BOOT0拉低时从Flash启动正常运行你的程序BOOT0拉高、BOOT1拉低时从系统存储器启动此时可以通过串口ISP烧录固件BOOT0和BOOT1都拉高时从SRAM启动一般调试用。新手经常犯的问题是程序下载进去没反应或者下载的时候出现“Cannot access target”结果发现BOOT0跳线插错了位置。记住一个规律正常运行时BOOT0接GND如果需要用串口ISP下载把BOOT0接到3V3下载完再拨回去。3.4 下载程序时JTAG和SWD的坑热词里有“STM32禁用JTAG”这个是很经典的一个坑。STM32默认的调试接口是JTAG占用了PA13、PA14、PA15、PB3、PB4这几个引脚。如果你的程序初始化里复用或者重映射了这些引脚那么调试器可能就接不上了表现为下载失败、芯片锁死。解决办法有两种一种是在程序里保持默认的SWD引脚配置也就是说你即便不用调试接口也别动PA13和PA14这两个是SWDIO和SWCLK另一种是你真的要用这些引脚做其他功能那就得在程序里禁用JTAG功能比如标准库里写GPIO_PinRemapConfig(GPIO_Remap_SWJ_Disable, ENABLE);但禁用之后再用调试器就识别不到芯片了需要先设置BOOT0为系统存储器模式、通过串口擦除或者用ST-Link的Connect under reset方式恢复。所以建议新板子刚开始玩PA13和PA14别离它们。调试接口比多两个GPIO重要得多。4. 进阶模块的学习路线定时器、中断、串口、显示和总线4.1 中断系统让CPU学会响应事件中断是STM32里最核心的机制。没有中断的话CPU只能不停地轮询外设状态效率低实时性也差。STM32F103的NVIC嵌套向量中断控制器支持多个中断优先级分组每个外设都可以产生中断请求。学习中断建议从外部中断入手也就是EXTI。配置步骤是初始化GPIO为输入、把引脚连接到EXTI线、配置EXTI触发方式上升沿、下降沿或双沿、配置NVIC优先级、编写中断服务函数。中断服务函数执行时间要短不要在中断里做耗时的事情比如延时、打印、浮点运算。原因很简单中断期间主程序是被打断的你在中断里磨蹭太久后面的中断就会排队实时性就崩了。我自己踩过的一个坑是中断服务函数里调用了printf结果波特率又没配好程序一进中断就卡死。后来查了几天才发现是printf重定向的问题。现在我的习惯是中断里只置标记位主循环里查标记位处理业务。4.2 定时器不仅会数数还能捕获、比较、产生PWM定时器是STM32里水最深的一个外设。F103有高级定时器TIM1和TIM8、通用定时器TIM2到TIM5、基本定时器TIM6和TIM7。学习定时器可以从最基本的定时中断开始配置定时器时钟分频、计数周期、使能更新中断然后在中断服务函数里累加一个标志变量就能实现非阻塞的时间片轮询比裸奔的delay好用得多。进阶的操作是输入捕获热词里有“STM32定时器捕获测频率”这个功能非常实用。输入捕获的原理是定时器计数器不断自增当检测到引脚上的边沿信号时把当前的计数值捕获到寄存器里。两次捕获的计数值之差乘以定时器时钟周期就是信号周期一算就是频率。用这个功能不需要额外外部电路就能测量PWM频率和脉宽。还有一个非常常用的功能是PWM输出也就是定时器比较输出。通过调节比较值可以改变占空比占空比不同LED亮度不同舵机角度不同电机转速也不同。这是后面做控制和驱动的基础。4.3 串口通信和printf重定向USART串口是调试和通信的必备外设。STM32F103一般有多个USART其中USART1的引脚是PA9(TX)和PA10(RX)。配置串口要注意的引脚复用PA9和PA10默认就是USART1的功能但要确保没有其他代码把这两个引脚配置成了普通GPIO。串口调试的一个利器是printf重定向。标准库里通过重写fputc函数让printf输出到USART这样在代码里写printf电脑串口助手就能看到格式化输出。重定向代码大致是这样int fputc(int ch, FILE *f) { USART_SendData(USART1, (uint8_t)ch); while (USART_GetFlagStatus(USART1, USART_FLAG_TXE) RESET); return ch; }这里要注意发送完数据要等待发送数据寄存器空否则数据会丢。还有用MDK标准库时记得在配置里勾选Use MicroLIB否则printf会占用大量Flash和RAM还有可能因为堆栈问题死机。4.4 显示模块的坑ILI9341读ID是0xA1A1是怎么回事热词里有“STM32使用ILI9341读ID是A1A1”这个问题也很有意思。ILI9341是常见的TFTLCD驱动芯片读ID的时候正常应该返回0x9341但很多人读到0xA1A1。这说明通信时序上有点问题大概率是数据线没接对或者是在读ID前没正常初始化甚至可能是你手里的屏幕根本不是ILI9341而是国产的兼容主控。排查思路一般是先检查接线尤其是DB0到DB15的数据线有没有次序错位然后检查复位时序屏幕的复位引脚要先拉低再拉高延时足够再检查初始化序列是不是对应你屏幕型号的厂商校准版本。这类问题不是代码逻辑错误是硬件时序和器件差异导致的调试起来要有耐心用示波器或者逻辑分析仪看一遍波形就能定位。4.5 I2C和SPI总线理解总线的握手规则F103的I2C外设口碑一般硬件I2C的时序要求苛刻很多老手宁可用GPIO模拟I2C。模拟I2C其实就是用代码控制时钟线SCL和数据线SDA的电平变化按I2C协议时序把数据发出去注意开始信号、停止信号、应答位这些细节。模拟的好处是引脚随便选调试直观也不会有硬件I2C那些怪问题。SPI总线的学习可以配合Flash芯片或者屏幕驱动来做。SPI有四种模式区别在于时钟极性和相位主设备和从设备不匹配就会读到全0或者乱码。你需要看好从设备数据手册里要求的CPOL和CPHA取值。比如某些Flash芯片要求模式0或模式3配置错了通信就是废的。4.6 CAN通信和USB设备打开更广的应用空间CAN通信在工业控制、汽车电子领域用得非常广泛。STM32F103的bxCAN外设支持标准帧和扩展帧波特率靠分频和位时间配置。很多人搜“STM32 CAN通信突然连不上”这个问题的排查技巧是先看CAN收发器比如TJA1050的供电和接线再看波特率是否一致三看有没有给总线接上终端电阻120欧姆最后看硬件滤波和软件滤波配置。CAN总线上如果只有两个节点至少一端要接终端电阻否则信号反射会导致通信不稳定。USB设备方面F103的USB是符合USB 2.0全速规范的设备控制器可以做键盘、鼠标、虚拟串口这些设备。做USB设备的一个坑是F103的USB需要外接晶振而且很多开发板上的晶振可能是8MHz或者12MHz直接影响USB的时钟配置不一致时USB枚举不成功。起步阶段建议先跑官方的虚拟串口例程把USB枚举流程跑通再改造成自己的设备。4.7 综合实战项目超声波测距和步进电机学完上面这些外设就可以做点综合性的项目了。超声波测距是一个很典型的练习用定时器的输入捕获测超声波模块ECHO引脚的高电平时间再乘以声速除以2得到距离然后把结果显示在OLED或者串口上。这个项目串起了定时器捕获、GPIO、显示、串口等多个模块做完一次整块知识的连接感就建立起来了。步进电机控制也是非常合适的练手项目热词里的“五线四相步进电机STM32”就是这个。五线四相步进电机内部有四个线圈用双极性或者单极性驱动控制方式是给四相线圈按顺序通电每换一次相电机轴就转一步。用GPIO输出脉冲时序表或者用定时器产生精确脉冲配合ULN2003驱动模块就能做匀速转动和定位控制。做这个项目可以顺便理解PWM输出、延时精度和机械传动的基本概念。5. 常见问题速查表这些坑我替你踩过了问题原因排查方法识别不到芯片/下载失败BOOT0配置不对驱动没装ST-Link接线错误芯片锁死检查BOOT0跳线重新装驱动检查SWD三根线进入系统存储器模式后擦除打开时钟仍然外设不工作引脚复用冲突误配置了JTAG占用引脚看原理图和引脚复用表检查PA13/PA14/PA15/PB3/PB4是否被占延时函数卡死延时函数用了SysTick且中断冲突HAL库和标准库混用确认系统时钟配置检查是否在中断里调用延时统一库版本printf没有任何输出串口引脚配错没有重定向fputc未勾选MicroLIB波特率不匹配检查USART引脚对比重定向代码打开MicroLIB核对波特率屏幕读ID异常时序问题复位异常数据线错位主控不兼容检查接线逐行比对初始化序列用逻辑分析仪看波形CAN通信突然连不上收发器问题波特率不一致缺少终端电阻检查CAN收发器供电确认波特率总线两端接120欧姆USB设备枚举失败晶振频率不对VBUS连接问题USB拉电流不足确认晶振核查USB D/D-走线检查电源供应PB3/PB4做不了普通IOJTAG默认占用禁用JTAG功能或者仅保留SWD这些坑非常典型我基本都碰到过一遍。很多问题并不是代码逻辑有多难而是你还没建立起硬件和软件一一对应的那种感觉。遇到问题先别急着怀疑代码先拿万用表测电平拿示波器看波形再回头看代码定位效率会高很多。6. 顺着这个方向继续深入你还能走多远很多新手学了GPIO和串口之后就不知道该学什么了。实际上STM32F103只是整个嵌入式世界的一个起点这个板子带给你的能力是可以直接迁移到更高阶平台的。F103上学会的GPIO、中断、定时器、串口、I2C、SPI在STM32F4/H7上一样适用在国产的GD32、AT32、APM32上也是同一套思路只不过寄存器地址和库接口略有差异。我自己用过很多芯片之后回头想F103最好的一点并不是性能有多强而是资料足够多、生态足够成熟、踩坑成本足够低。一个F103工程能把中断优先级、时钟树、启动文件、链接脚本这些东西全部过一遍这些底层知识到哪都值钱。6.1 从裸机到操作系统进阶的几条路如果想把F103玩得更深入可以考虑往这几个方向走。一个是学习使用RTOS比如FreeRTOSF103跑FreeRTOS完全没有问题任务调度、信号量、队列、互斥锁这些概念通过实操理解最深。另一个是引入上位机通信比如用串口或者WiFi模块把板子采集的数据传到电脑上再用Python写个显示界面这就是一个很完整的物联网小项目了。还有一条路是做电机控制和工业控制方向。F103在伺服电机、步进电机、无刷电机驱动上非常常见热词里的“STM32控制伺服电机485”就是这种场景。伺服驱动器一般支持RS485总线用MODBUS协议进行位置、速度、扭矩控制STM32只需要作为主站发指令通过AGILE_MODBUS这类开源协议栈就能实现。工程应用价值非常高也是很多自动化岗位面试会问的内容。6.2 代码规范和调试习惯越早养成越好学到后面你会发现真正限制你的已经不是语法和技术点而是开发习惯。我从一开始就吃了不少亏代码文件命名乱七八糟、全局变量满天飞、修改了程序不写注释结果过两周回来看完全不知道当时在干什么。建议从一开始就养成几个习惯一是每个外设的功能单独放在一个.c和.h文件里接口函数命名清晰二是全局变量尽量少用能用传参和返回值解决的就不要用全局变量三是程序里保留版本号注释和修改记录哪怕简单到只是加一行说明四是每次改动前先备份一个能编译通过的版本防止改坏了回不去。调试习惯方面有一个很实用的技巧把调试打印信息分级比如ERROR、WARN、INFO并且在串口输出里带上时间戳。这个习惯在系统比较复杂的时候能救命否则你面对一堆printf根本不知道哪条和哪条是对应关系。另外能用调试器单步就不加printf能用示波器就不瞎猜工具越熟练排查问题越快。6.3 学习资源的取舍现在的学习资源比十年前好太多了。买开发板附带的视频和资料一般是最贴合你板子的建议先跟着配套视频过一遍按部就班地把点亮LED、按键检测、串口打印、定时器中断、外部中断这几个例程全部自己敲一遍。注意是自己敲不是复制粘贴很多细节只有自己敲一遍才会暴露出来。然后再去看芯片参考手册和数据手册。ST官方的手册写得其实很清晰比如《STM32F10xxx参考手册》里的GPIO章节会详细列出每个寄存器的位定义和配置模式。刚开始看可能看不懂但每做完一个例程就回去翻对应章节你会发现手册越来越看得懂这是一个螺旋上升的过程。最后尽量加入一个技术社区有问题先搜索再提问。提问的时候把芯片型号、开发环境版本、代码片段、问题现象发全这样别人才能真正帮你定位问题。不要一上来就问“为什么我的程序不跑”没有人能凭空知道答案。7. 写在最后的一些体会板子买回来只是第一步后面能学到什么程度取决于你动手的频率和遇到问题时查资料的耐心。ST的开发板资料已经非常齐全只要你能耐着性子把每一个例程不看教程就手动敲一遍遇到报错先自己分析再查答案基本四到八周就能把GPIO、串口、定时器、中断这些核心内容吃透。我个人实际玩下来有个体会嵌入式这行台上一分钟台下十年功。芯片型号会更新库版本会迭代但底层的那套逻辑——时钟、引脚、寄存器、总线协议、中断优先级——几十年来没有变过。你现在在F103上花的时间并不会白费迟早会在别的芯片上兑现成更高的效率和更短的调试时间。最后再分享一个小技巧学STM32不要贪多不要今天看USB明天看CAN后天玩屏幕没有连成体系的知识很快就忘光了。你可以按照“点灯→按键→中断→定时器→串口→I2C/SPI→项目实战”的路线每一步花三到五天做完了再做下一个。只要按这个节奏坚持下来单片机开发的基本功就算打牢了。后面无论去搞家电控制、智能硬件还是工业设备你都会感谢当初认真折腾F103的自己。
返回列表