实现vscode上用gdb调试stm32

2024-02-11 23:20

本文主要是介绍实现vscode上用gdb调试stm32,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

实现vscode上用gdb调试stm32

这周负责编写设备的某个模块,其中遇到了一些变量地址不正确的错误,按理这种底层变量错误用gdb一类的调试器就能很快查到,可是初入嵌入式一行,此C语言非彼C语言,对于gdb怎么对接到项目上根本一无所知,问了下周边同事,发现他们居然都是直接打串口日志来调试的,那岂不是每次遇到问题都得在代码上留一堆丑陋的printf? 我对如此原始的调试方式实在不服气,便想找到相关的对接工具,我的开发习惯是在vscode上写好代码后再在keil上编译烧录,由于keil的界面和操作实在令我难以接受,因此我的需求就是找到在vscode上找到调试单片机的方法,一开始我以为占工作时间一两小时就调通了,结果发现课题复杂度远超出自己的预期,只好乖乖放弃,在代码上不断加入丑陋的printf。。。。。。

等到周末,终于有时间研究了,总之就是不断搜索踩坑,整了两天,总算完事,现作记录。

我使用的是江科大的stm32c8t6开发板,仿真器用的st-link-v2。

1.下载openocd

gdb对于stm32的调试需要借助一个gdb server, st-link和Jlink都有自带的gdbserver, 我这里选择用openocd作为板子的gdbserver,实际上openocd除了调试还可以烧录,感兴趣的可以自己深入研究下,附一张板子,openocd,pc机之间的关系:

v2-aac3a16fbd3a81fc5de0a1e76d9ae483_1440w

openocd尽量选新的,我这里是windows平台,用的xpack-0.11.0版本,之前用的0.10.0版本跟cotrexDebug扩展组合莫名会出行gdb server超时的错误。

这里附openocd的下载地址:https://github.com/xpack-dev-tools/openocd-xpack/releases

后面关于如何烧录及开gdb server可自行查找。

2.下载arm-gnu-toolchains

arm平台有专属的gcc,gdb,make等工具用于arm系列开发板的开发,stm32的开发和调试工具就靠这些,下载:https://developer.arm.com/downloads/-/arm-gnu-toolchain-downloads

windows平台用户可选择:

image-20230806164552347

3.MinGW

在windows下作C/C++开发的同学应该很熟,不作赘述,这里记个坑,官方下载的时候总是遇到The file has been downloaded incorrectly,据说是网络问题导致,直接下官网的压缩包又太慢,真的无力。好在已经有好心人贴了百度链接,如下:https://pan.baidu.com/s/1mIq_Vbn2w45L_B-AGJk0ww?pwd=gv1s

参考:

Mingw快捷安装教程 并完美解决出现的下载错误:The file has been downloaded incorrectly

4.Cotrex-Debug下载及配置

参考:https://blog.csdn.net/qq_40833810/article/details/106713462

注意那个configFile可根据相对路径来填,另外别把单词写错了,当时由于把interface写成interfaces卡了一整晚。。。。

executable部分写keil的axf文件或者bin文件都可以,前者确保output选项打勾了Debug Information!

5.STM32CubeMX

对于STM32,Cotrex-Debug只支持调试其HAL库的代码,对于板子相关的库函数的代码貌似不支持,我试过,拿江科大的库代码版本烧进板子后vscode F5调试,gdb没响应,显然是不兼容。目前stm32开发已经是HAL库的天下了,一个HAL库兼容st下所有型号的板子,这么高效的开发,怎么能不学呢?看来当时应该买正点的板子的,然而太贵了。。。。

STM32CubeMX是ST公司为其开发板做的专属项目生成工具,支持MDK-ARM和makefile两种编译方法,各位同学可根据自身需求选择自己的编译方式, 它就是用的HAL库,而且似乎只能用HAL库,如果学的板子相关标准库的同学(江科大就是stm32f103的标准库)得多做点功课。。。。

另外这东西可以图形化配置芯片的IO口和时钟,最后生成相关的配置代码,还挺方便的。。。

拿江科大的LED闪烁实验来说,原代码是这样:

#include "stm32f10x.h"                  // Device header
#include "Delay.h"int main(void)
{RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);GPIO_InitTypeDef GPIO_InitStructure;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_Init(GPIOA, &GPIO_InitStructure);while (1){GPIO_ResetBits(GPIOA, GPIO_Pin_0);Delay_ms(500);GPIO_SetBits(GPIOA, GPIO_Pin_0);Delay_ms(500);GPIO_WriteBit(GPIOA, GPIO_Pin_0, Bit_RESET);Delay_ms(500);GPIO_WriteBit(GPIOA, GPIO_Pin_0, Bit_SET);Delay_ms(500);GPIO_WriteBit(GPIOA, GPIO_Pin_0, (BitAction)0);Delay_ms(500);GPIO_WriteBit(GPIOA, GPIO_Pin_0, (BitAction)1);Delay_ms(500);}
}

在STM32CubeMX里面可以预先把IO口设置好,我这里由于PA0和System-WKUP冲突改选了PA1,将PA1设置为推挽输出的操作如图:

image-20230806170425314

最后generate code可在MX_GPIO_Init()一行看到, 自己的配置已经被落实了:

static void MX_GPIO_Init(void)
{GPIO_InitTypeDef GPIO_InitStruct = {0};
/* USER CODE BEGIN MX_GPIO_Init_1 */
/* USER CODE END MX_GPIO_Init_1 *//* GPIO Ports Clock Enable */__HAL_RCC_GPIOD_CLK_ENABLE();__HAL_RCC_GPIOA_CLK_ENABLE();/*Configure GPIO pin Output Level */HAL_GPIO_WritePin(GPIOA, GPIO_PIN_1, GPIO_PIN_RESET);/*Configure GPIO pin : PA1 */GPIO_InitStruct.Pin = GPIO_PIN_1;GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;GPIO_InitStruct.Pull = GPIO_NOPULL;GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;	//HAL库中LOW,MEDIUM,HIGH三档分别对应库函数的2MHZ,10MHZ,50MHZHAL_GPIO_Init(GPIOA, &GPIO_InitStruct);/* USER CODE BEGIN MX_GPIO_Init_2 */
/* USER CODE END MX_GPIO_Init_2 */
}

闪烁灯代码如下:

int main(void)
{/* USER CODE BEGIN 1 *//* USER CODE END 1 *//* MCU Configuration--------------------------------------------------------*//* Reset of all peripherals, Initializes the Flash interface and the Systick. */HAL_Init();/* USER CODE BEGIN Init *//* USER CODE END Init *//* Configure the system clock */SystemClock_Config();/* USER CODE BEGIN SysInit *//* USER CODE END SysInit *//* Initialize all configured peripherals */MX_GPIO_Init();/* USER CODE BEGIN 2 *//* USER CODE END 2 *//* Infinite loop *//* USER CODE BEGIN WHILE */while (1){/* USER CODE END WHILE */HAL_GPIO_WritePin(GPIOA,GPIO_PIN_1,GPIO_PIN_SET);HAL_Delay(500);HAL_GPIO_WritePin(GPIOA,GPIO_PIN_1,GPIO_PIN_RESET);HAL_Delay(500);/* USER CODE BEGIN 3 */}/* USER CODE END 3 */
}

6.最终效果

在vscode的launch.json上配置好:

{// Use IntelliSense to learn about possible attributes.// Hover to view descriptions of existing attributes.// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387"version": "0.2.0","configurations": [{"name": "Cortex Debug","cwd": "${workspaceFolder}","request": "launch","type": "cortex-debug","runToEntryPoint": "main","servertype": "openocd","configFiles": ["interface/stlink.cfg","target/stm32f1x.cfg"],"executable":"build/mdk_arm_test.axf","svdFile": "D:/Arm/Packs/Keil/STM32F1xx_DFP/2.2.0/SVD/STM32F103xx.svd",}]
}

用之前STM32CubeMX生成的HAL库的代码直接在keil上面编译烧录。

image-20230806172855964

然后上vscode, F5开启调试,成功!尽情享受吧!

image-20230806171846136

这篇关于实现vscode上用gdb调试stm32的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/701092

相关文章

pytorch自动求梯度autograd的实现

《pytorch自动求梯度autograd的实现》autograd是一个自动微分引擎,它可以自动计算张量的梯度,本文主要介绍了pytorch自动求梯度autograd的实现,具有一定的参考价值,感兴趣... autograd是pytorch构建神经网络的核心。在 PyTorch 中,结合以下代码例子,当你

SpringBoot集成Milvus实现数据增删改查功能

《SpringBoot集成Milvus实现数据增删改查功能》milvus支持的语言比较多,支持python,Java,Go,node等开发语言,本文主要介绍如何使用Java语言,采用springboo... 目录1、Milvus基本概念2、添加maven依赖3、配置yml文件4、创建MilvusClient

JS+HTML实现在线图片水印添加工具

《JS+HTML实现在线图片水印添加工具》在社交媒体和内容创作日益频繁的今天,如何保护原创内容、展示品牌身份成了一个不得不面对的问题,本文将实现一个完全基于HTML+CSS构建的现代化图片水印在线工具... 目录概述功能亮点使用方法技术解析延伸思考运行效果项目源码下载总结概述在社交媒体和内容创作日益频繁的

openCV中KNN算法的实现

《openCV中KNN算法的实现》KNN算法是一种简单且常用的分类算法,本文主要介绍了openCV中KNN算法的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的... 目录KNN算法流程使用OpenCV实现KNNOpenCV 是一个开源的跨平台计算机视觉库,它提供了各

OpenCV图像形态学的实现

《OpenCV图像形态学的实现》本文主要介绍了OpenCV图像形态学的实现,包括腐蚀、膨胀、开运算、闭运算、梯度运算、顶帽运算和黑帽运算,文中通过示例代码介绍的非常详细,需要的朋友们下面随着小编来一起... 目录一、图像形态学简介二、腐蚀(Erosion)1. 原理2. OpenCV 实现三、膨胀China编程(

通过Spring层面进行事务回滚的实现

《通过Spring层面进行事务回滚的实现》本文主要介绍了通过Spring层面进行事务回滚的实现,包括声明式事务和编程式事务,具有一定的参考价值,感兴趣的可以了解一下... 目录声明式事务回滚:1. 基础注解配置2. 指定回滚异常类型3. ​不回滚特殊场景编程式事务回滚:1. ​使用 TransactionT

Android实现打开本地pdf文件的两种方式

《Android实现打开本地pdf文件的两种方式》在现代应用中,PDF格式因其跨平台、稳定性好、展示内容一致等特点,在Android平台上,如何高效地打开本地PDF文件,不仅关系到用户体验,也直接影响... 目录一、项目概述二、相关知识2.1 PDF文件基本概述2.2 android 文件访问与存储权限2.

使用Python实现全能手机虚拟键盘的示例代码

《使用Python实现全能手机虚拟键盘的示例代码》在数字化办公时代,你是否遇到过这样的场景:会议室投影电脑突然键盘失灵、躺在沙发上想远程控制书房电脑、或者需要给长辈远程协助操作?今天我要分享的Pyth... 目录一、项目概述:不止于键盘的远程控制方案1.1 创新价值1.2 技术栈全景二、需求实现步骤一、需求

Spring Shell 命令行实现交互式Shell应用开发

《SpringShell命令行实现交互式Shell应用开发》本文主要介绍了SpringShell命令行实现交互式Shell应用开发,能够帮助开发者快速构建功能丰富的命令行应用程序,具有一定的参考价... 目录引言一、Spring Shell概述二、创建命令类三、命令参数处理四、命令分组与帮助系统五、自定义S

SpringBatch数据写入实现

《SpringBatch数据写入实现》SpringBatch通过ItemWriter接口及其丰富的实现,提供了强大的数据写入能力,本文主要介绍了SpringBatch数据写入实现,具有一定的参考价值,... 目录python引言一、ItemWriter核心概念二、数据库写入实现三、文件写入实现四、多目标写入