尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

STM32CubeMX生成IAR工程实战指南:配置、编译与常见坑

STM32CubeMX生成IAR工程实战指南:配置、编译与常见坑 今天聊聊嵌入式开发里一个挺常见的需求用STM32CubeMX生成IAR工程。网上有个词叫“STM32CubeMX2”其实就是我们平时说的STM32CubeMX可能版本号写顺了多打了个2。最近在一个老项目里接手了一批IAR工程代码维护全靠CubeMX重新生成不少同事卡在“生成的工程用IAR打不开”“编译全是头文件漂红”这类问题上。这篇文章我会把这套流程从头到尾捋一遍重点讲CubeMX导出IAR工程的设置、IAR首次编译的配置以及我实际踩过的几个坑。适合刚开始用IAR做STM32开发、或者一直习惯Keil但被项目推着换IAR的朋友。1. 为什么我建议STM32CubeMX配IAR用1.1 我最初也以为只能生成Keil工程早几年我第一次接触STM32CubeMX当时网上教程清一色是“生成MDK-ARM工程”默认的Toolchain/IDE下拉框我也基本没动过因为MDK-ARM能打开就把CubeMX当成“Keil专属代码生成器”。直到后来接手一个工业控制项目客户指定要IAR环境我整个人是懵的第一反应是想把HAL初始化的代码手动复制到IAR里重建工程光处理启动文件和外设时钟就折腾了大半天。后来才发现CubeMX其实一直支持生成IAR工程入口就在Project Manager - Project Settings - Toolchain/IDE下拉框里有“IAR Embedded Workbench for ARM”选项。换句话说CubeMX不仅能生成初始化代码还能把整个IAR的工程骨架、启动文件、链接脚本、中间件文件全部编排好不需要你手动去添加那些源文件路径。这个功能不是冷门功能只是因为教程惯性导致很多用Keil的人根本不知道。我这里多说一句如果你只在KEIL环境下做过开发上手IAR时最容易踩的坑就是“拿Keil的思维套IAR”。两个工具链的工程文件、链接脚本、编译器语法都不一样但如果从一开始就让CubeMX按IAR的方式生成你其实不需要关心大部分底层差异。CubeMX在你选择IAR的那一刻就已经把对应的启动文件、ICF链接脚本和预定义宏都安排好了。1.2 IAR到底好在哪为什么大厂喜欢很多做消费电子、小家电的朋友会觉得IAR就是个收费IDE不如Keil上手简单。确实IAR的界面不如Keil友好尤其旧版本看起来非常“工程师脾气”。但IAR在一些细分领域地位非常高最典型的是ARM Cortex-M开发它有几个明显优势编译代码密度好优化效果在同等级别下往往比MDK更激进调试稳定性不错对低功耗、Bootloader、汽车电子、工业控制等场景支持很成熟。我自己感受最明显的是一个运行在STM32F103C8T6上的项目同样功能逻辑用Keil默认优化和IAR高优化编译出来IAR的固件大小能小不少。对几十KB Flash的芯片来说小几百字节可能就意味着功能能不能塞进去。这不见得是Keil不行但不同编译器对同一个C代码的解释和优化路径确实不一样IAR在代码大小优化上确实有独到之处。当然IAR不是神它也有学习成本、许可证成本以及一些独有的“小脾气”。但如果你和我一样需要在不同IDE之间切换最好的办法就是用STM32CubeMX把“生成工程”这件事统一起来。不要自己手工去搭IAR工程让工具自动生成省心得多。2. 环境准备IAR安装与版本匹配的坑2.1 先分清EWARM和IAR for 8051准备环境的第一件事不是下载而是搞清楚IAR的版本体系。网上搜“IAR”经常出来一堆“IAR for 8051”“IAR for STM8”“IAR 6.3 8051开发环境”这类内容很多人下错了装了半天发现没有ARM选项。IAR Embedded Workbench有两个大分支一种是IAR for ARM简称EWARM专门支持Cortex-M、Cortex-A/R等ARM内核另一种是IAR for 8051支持CC2530等增强型8051内核。这两个IDE完全不通用装哪个取决于你的目标芯片。STM32全部是ARM内核所以要装的是“IAR Embedded Workbench for ARM”而不是“IAR for 8051”。搜索时可以带上“EWARM”关键词避免下载到错误版本。安装过程建议保持默认路径一路Next就可以安装完成后打开一次IAR确认能正常进入界面。刚装完IAR时有些版本许可证服务不会立即生效我遇到过装完直接编译报许可证错误的情况重启一次电脑或从开始菜单把IAR License Manager打开看一眼通常能解决。许可证这块我多说一句IAR是商业软件但很多芯片原厂和开发板厂商会提供评估版学校实验室也可能有正版授权。我之前遇到一些朋友从网上下载所谓“绿色版”编译时会卡在各种奇奇怪怪的验证错误上最后又绕回来问为什么工程打不开。与其浪费时间折腾不如先确认许可证是否正常。2.2 CubeMX中Toolchain版本怎么选CubeMX在生成IAR工程时会让你选一个具体的IAR版本比如IAR Embedded Workbench for ARM 8.40、8.50、9.30等。很多人这里会纠结但其实没那么复杂核心原则是选一个不高于你本机安装版本的选项或者直接选一个你安装版本附近的大版本。我举个例子你电脑里装的是IAR for ARM 8.32但CubeMX下拉框里你选了IAR 9.30生成的EWP工程文件可能是新版本格式8.32根本打不开这时候你大概率会以为是CubeMX坏了。反过来你选了7.80你的9.30能打开老格式工程但可能出现一些新芯片支持不完整的提示。所以稳妥办法是在下拉框里找一个和你安装版本最接近的如果没有完全一致的就选一个低一点的大版本。CubeMX对工程文件的向后兼容做得可以但向前兼容很差。还有一种方法如果你手头IAR版本太老比如还是6.x、7.x建议直接升级IAR版本。很多老教程里写“IAR 6.3 8051开发环境”是针对CC2530等8051芯片的和STM32无关不要混为一谈。当前阶段的EWARM8.50或9.x是主流CubeMX生成后打开的成功率最高。2.3 常见许可证错误别急着重装IAR有一个非常经典的编译错误错误码是“fatal error[Lms001]: license check failed. use the iar license manager to re...”字面意思就是许可证检查失败让你用IAR License Manager重新注册。这个问题我见过不下五次一大半人选择重装IAR其实没必要。正确做法打开Windows开始菜单找到IAR License Manager启动后看许可证状态。如果是试用许可证过期需要重新申请试用如果是节点锁许可注意许可证绑定的电脑标识变了没有如果是网络浮动许可检查服务器地址能不能ping通。重装IAR并不能绕开许可证验证反而会浪费你一下午。这个问题我在后面常见问题里还会再展开。3. CubeMX导出IAR工程的实操演示3.1 新建工程时先把IDE定下来实操部分我以常见的STM32F103C8T6为例一步步演示。打开STM32CubeMX点击New Project在芯片搜索框输入STM32F103C8T6双击选中该型号进入主界面以后先不要急着配引脚先把几个关键项设置好不然后面容易反复。在左侧Categories列表里找到System Core中的SYS把Debug设置为Serial Wire。这个动作很关键如果不设置默认情况下SWD调试口可能被配置成普通IO第一次下载完程序之后第二次再想下载就困难了。建议所有人新建工程的第一时间都做这个设置无论你是下载调试还是出厂烧录调试口都建议保留。然后打开Clock Configuration配置系统时钟。STM32F103C8T6最大主频72MHz一般用HSE外部晶振或内部HSI我习惯用HSE 8MHz经过PLL倍频到72MHz。你可以直接在图里输入72CubeMX会自动帮我计算分频倍频系数。时钟树配置正确与否直接影响串口波特率、定时器定时时间等后面如果发现外设频率不对先回来看时钟配置。接着进入Project Manager - Project Settings在Project Name里填工程名比如demo_iar。Location是工程存放路径这里我要强调路径内不要出现中文、不要出现空格、不要放在需要管理员权限的目录比如C盘Program Files下。IAR对路径中的空格还算宽容但CubeMX生成的Makefile、链接脚本以及后续的Git版本管理都会因为空格和中文产生莫名其妙的问题最佳实践是纯英文字符路径。往下看就是核心选项Toolchain/IDE默认可能是STM32CubeIDE或MDK-ARM把它改成IAR Embedded Workbench for ARM。旁边的Toolchain Version下拉框就按前面讲的版本匹配原则选一个。再往下有Minimum Heap Size和Minimum Stack Size默认值一般是0x200和0x400这表示编译器堆区和栈区大小。实际开发中如果你用了很多局部变量、递归或者malloc可能需要调大栈如果主要跑RTOS任务栈是从FreeRTOS自己的堆里分配和这里的CSTACK不一样。这个值尽量不要给太小宁可编译多占一点RAM也别让程序跑着跑着栈溢出。设置完成后点击右上角GENERATE CODE。如果你的工程配置了中间件比如FreeRTOSCubeMX会弹出提示询问你“是否初始化所有外设”选择Yes即可。生成过程很快看到提示框说明生成成功。3.2 中间件和底层代码配置的注意点很多人拿CubeMX生成IAR工程是为了跑FreeRTOS这也是我最近收到最多的咨询。网上有个热词叫“freertos学习篇一:stm32f103c8t6下的移植”通常是在讲手动移植FreeRTOS。但如果你用CubeMX根本不需要手动移植在左侧Middleware and Software Packs里勾选FreeRTOS选择CMSIS_V1或CMSIS_V2即可。CMSIS_V2对应的是较新的RTOS接口代码规范和老的CMSIS_V1有差异如果后续代码大量参考老教程选V1可能更顺手如果是从零开始新项目建议直接选V2。勾完FreeRTOS之后CubeMX会询问你使用哪个时基源。因为STM32的HAL库默认把Systick作为HAL时基但FreeRTOS也需要一个系统时钟节拍如果用同一个Systick两者会冲突。CubeMX通常在配置FreeRTOS时会提示你把Timebase Source改成一个基本定时器比如TIM1或TIM6具体看芯片资源。这一步不能忽略否则你的FreeRTOS任务调度和HAL_Delay会互相打架程序卡死都不知道为什么。在IAR环境里跑FreeRTOS还要注意一个概念FreeRTOS的任务堆和IAR链接脚本中的堆区不是一回事。IAR工程里的HEAP区是C标准库malloc使用的那块内存FreeRTOS的configTOTAL_HEAP_SIZE是FreeRTOS内核用来创建任务、队列、信号量的内存池。CubeMX生成的默认FreeRTOS配置通常使用heap_4.c内存池就是一个大数组不需要你去动IAR的Heap Size。如果你在网上的移植教程里看到类似uint8_t ucheap[ ] __section(.heap) {0};这样的代码这是IAR编译器里把数组放到.heap段的一种写法一般是用来手动扩展堆区不是在FreeRTOS里面放任务堆。这块语法很IAR风格等会第4节我会再细说。3.3 生成后的目录里到底多了什么生成完成后打开工程存放目录你会看到下面这样的结构demo_iar/ ├─ Core/ │ ├─ Inc/ │ └─ Src/ │ ├─ main.c │ ├─ gpio.c │ ├─ freertos.c │ └─ stm32f1xx_it.c ├─ Drivers/ │ ├─ CMSIS/ │ └─ STM32F1xx_HAL_Driver/ ├─ EWARM/ │ ├─ demo_iar.eww │ ├─ demo_iar.ewp │ ├─ demo_iar.icf │ ├─ startup_stm32f103c8tx.s │ └─ ... ├─ Middlewares/如果启用FreeRTOS等 └─ .mxprojectCore目录存放的是用户代码包括main.c、中断处理文件和外设初始化文件Drivers目录是HAL库和CMSISEWARM目录则是IAR需要的一切工程文件。这里最关键的是三个东西.eww是IAR工作区文件相当于“一个浏览器窗口”.ewp是IAR工程文件里面配置了源文件列表和编译选项.icf是IAR的链接脚本文件决定了代码段、数据段、堆栈段放在Flash和RAM的什么位置。很多初学者双击.eww后找不到工程以为是CubeMX没生成成功。其实你只要知道在EWARM目录下demo_iar.eww就是我们应该打开的文件。从Git版本管理的角度大家提交代码时别漏了EWARM目录最好整个目录提交。CubeMX的.mxproject文件是给CubeMX识别工程用的建议也保留。3.4 在IAR里完成首次编译双击EWARM目录下的.eww文件IAR Workbench会打开。如果界面左侧的Workspace窗口没有显示工程可能是IAR打开的窗口不对可以再次双击.eww或者从IAR菜单File - Open Workspace选择文件。正常情况下左侧出现工程树里面包含main.c、stm32f1xx_hal_msp.c等源文件。第一次编译之前建议确认一下芯片型号。在IAR菜单栏选择Project - Options进入General Options - Target在Device下拉框中选择实际芯片。CubeMX生成时通常会自动设置好但如果你拷贝过他人工程或者IAR升级过这个选项可能会变成Generic设备导致调试器和启动文件不匹配。对STM32F103C8T6Device下拉框里找到ST - STM32F1xx - STM32F103C8Tx即可。接着可以直接按F7编译也可以点击工具栏的Make按钮。第一次编译会比较慢因为HAL库文件全部要编译一遍。等待下方Build窗口输出最后看到0 errors, 0 warnings即便有warning也不是大问题就说明工程本身没问题。如果出现Error[Pe169]: cannot open source file xxx.h别急着搜代码多半是头文件路径没配置或者是工程目录移动过具体排查见第5节。3.5 烧录和调试配置编译通过只是第一步真正调试前还要设置下载器。IAR默认的Debugger可能不是你的ST-Link或J-Link所以打开Project - Options - Debugger在Setup页里把Driver改为ST-LINK如果用的是J-Link就选J-LINK。然后在Debugger日志窗口里能看到下载时的调试信息。使用ST-Link时再进入Debugger - ST-LINK把Interface改成SWD。STM32几乎都可以用SWD两线调试只占SWDIO和SWCLK两根线比JTAG省引脚。把Reset选项设成“Normal”或者“Software Reset”一般默认就可以。设置完成后接好ST-Link和板子点击Project - Download and Debug或者快捷键CtrlDIAR会编译后下载并进入调试界面。我第一次用IAR下载的时候被界面搞得有点懵IAR的调试布局和Keil不太一样watch窗口、寄存器窗口默认比较分散。你可以在View菜单里把Watch、Register、Disassembly找出来按自己习惯排布。如果下载后能停在main函数说明整个CubeMX导出IAR工程的流程已经跑通了。4. IAR工程与Keil工程之间的关键差异4.1 文件扩展名和工程组织方式从一个用惯Keil的人的角度看IAR工程的组织方式确实需要适应。Keil的工程文件后缀是.uvprojx双击就能打开IAR是.ewp和.eww其中.eww是工作区可以包含多个.ewp工程。CubeMX每次生成IAR工程时通常生成一个.eww和一个.ewp只包含一个工程。因为工程文件格式完全不同不要想着用Keil直接打开IAR工程或者用IAR打开Keil的uvprojx。如果你用CubeMX管理工程想换IDE也不需要手动改工程文件只需要回到CubeMX把Toolchain/IDE改成MDK-ARM或者IAR重新生成即可。当然强烈建议不要在同一个目录里混着生成两种工具链的工程最好单独建一个生成目录或者分开两个目录不然很容易把源文件、工程文件弄混。4.2 启动文件、链接脚本、堆栈定义STM32工程里启动文件是芯片进入C世界的入口。Keil的启动文件是startup_stm32f103c8tx.sIAR也有同名文件但细节不一样用的伪指令和段名不同。CubeMX在生成IAR工程时已经把IAR版本的启动文件放在了EWARM目录下你不用管它但不要去手动替换成Keil版本。链接脚本方面Keil用的是分散加载文件通常是.sct后缀IAR用的是.icf后缀。两者都负责告诉链接器“哪个段放Flash、哪个段放RAM、堆栈多大”语法差异很大。CubeMX生成IAR工程时会根据你Project Manager里填写的Heap/Stack Size自动生成对应配置的icf文件。如果你用Keil工程里积累的地址分配经验去IAR里找.sct文件是找不到的要找的是.icf。4.3 __section(.heap)这段代码到底是什么意思热词里有一条很典型的IAR代码uint8_t ucheap[ ] __section(.heap) {0};。这行代码在IAR里会把一个数组放到名为.heap的段中。在IAR的链接脚本里.heap段是一个专门给C库分配动态内存的区域。如果你自己定义一个数组然后强制放到.heap段就相当于你手动扩充了堆区的大小。这种写法常见于一些从GCC或Keil移植过来的代码。在Keil里你可能会看到类似__attribute__((section(.bss.heap)))的写法在GCC里则可能是__attribute__((section(.heap)))在IAR里则使用__section(.heap)。所以如果你在网上看到一个堆区数组的移植代码先确认编译器是不是IAR如果是其他编译器的语法直接复制到IAR里大概率编译不过。大多数情况下你不需要在IAR工程里手动定义堆区CubeMX生成的icf文件已经定义了HEAP和CSTACK大小。但当你使用FreeRTOS时它会自己管理内存这时候IAR的HEAP大小影响不大你反而需要关心FreeRTOSConfig.h里的configTOTAL_HEAP_SIZE这个值才是给任务、队列分配内存的“总池子”。这块知识非常容易混淆建议记下来。4.4 编译器关键词和预定义宏的差异IAR的C语言语法和Keil有一定差异最典型的是内存对齐、结构体压缩、位域等属性的写法。比如Keil里常用__attribute__((packed))定义紧凑结构体IAR里则用__packed。CMSIS头文件做了一层封装所以你在STM32库里直接用__PACKED宏就可以了但如果是从网上找的驱动代码可能还会看到形形色色的编译器特定写法。预定义宏也需要留意。Keil编译器会预定义__CC_ARMIAR会预定义__ICCARM__很多库会通过这两个宏选择不同的实现。CubeMX在生成IAR工程时会自动在编译选项里加上USE_HAL_DRIVER和STM32F103xE之类的宏所以你不必自己去Project - Options - C/C Compiler - Preprocessor里手动添加但要知道去哪里看。如果从别的工程复制了头文件路径这里就是需要调整的位置。5. 常见问题与排查技巧实录5.1 双击生成的.eww没反应或提示工程版本过新这种情况绝大多数是IAR版本和生成工程时选的版本不匹配。CubeMX生成的EWP工程版本如果高于你安装的IAR所能识别的最高版本IAR会直接拒绝打开或者打开之后工程结构空白。解决办法是回到CubeMX把Toolchain Version改成低一点的版本再重新生成。这个思路比在IAR里折腾“Open Workspace”更高效。还有一种情况是你的IAR打开方式不对。有人下载并安装IAR后没有通过IAR的File - Open Workspace打开而是直接在Windows里双击.eww如果文件关联没有设置好系统可能用记事本打开或者提示找不到程序。建议先手动打开IAR再通过菜单打开工程文件。5.2 编译报错找不到文件、头文件编译时常见的错误是Error[Pe169]: cannot open source file stm32f1xx_hal_conf.h或者找不到某个.c文件。这通常不是代码问题而是IAR的头文件搜索路径不对。CubeMX生成时默认在EWP里配置了相对路径但如果你把整个工程目录移动过位置或者只复制了一部分源文件相对路径就失效了。排查思路很简单打开Project - Options - C/C Compiler - Preprocessor看Additional include directories里的路径是否存在。正常CubeMX生成的IAR工程会包含类似$PROJ_DIR$\..\Core\Inc、$PROJ_DIR$\..\Drivers\STM32F1xx_HAL_Driver\Inc、$PROJ_DIR$\..\Drivers\CMSIS\Device\ST\STM32F1xx\Include等路径。$PROJ_DIR$是一个变量表示EWP文件所在的目录。只要相对路径还在前面加的两个点就是向上跳一级目录对应的文件夹必须存在。如果缺失手动补上这些路径或者检查你的源文件目录是不是被重命名了。5.3 链接时报错section placement failedRAM不够怎么办当全局变量定义太多、堆栈设置太大或者FreeRTOS任务栈分配过多时IAR链接器可能报Error[Lp011]: section placement failed。它的意思是想放的数据段太大RAM里放不下了。这种情况下先看Build日志里给的地址范围然后逐个排查。一个常见做法是调小CubeMX里的Minimum Heap Size和Minimum Stack Size但调小之前要想清楚是不是真的需要那么大。如果只是全局变量多导致RAM溢出调小堆栈只是暂时挤出了空间程序深层调用还得小心。另一种办法是在IAR的icf文件里适当调整RAM区域但那是高级玩法不建议新手改。最稳的方案还是先清理不必要的全局数组或者换一个RAM更大的芯片。如果你用了FreeRTOS还要检查它的configTOTAL_HEAP_SIZE是否设置得过大。在STM32F103C8T6这种只有20KB RAM的芯片上一个任务栈给个4KB就很夸张了多个任务加起来很容易超过RAM。FreeRTOS任务栈常用xTaskCreate里的栈深度参数单位是字而不是字节很多人在这里算错导致实际分配的RAM比预想大一倍直接把内存挤爆。5.4 IAR编译时出现License check failed前面提过的fatal error[Lms001]: license check failed. use the iar license manager to re...值得单独拿出来说。这个报错一般出现在新建工程或第一次编译时IAR许可证验证失败不会生成任何代码。我见过有人急着重装IAR结果装完问题依旧原因是没有从根上解决许可证绑定问题。正确步骤是关闭IAR打开开始菜单里的IAR License Manager查看当前许可证状态。如果显示“No license”或者“License expired”需要重新导入许可证文件或者激活码。如果是从公司服务器获取浮动许可证检查主机网络和服务器地址是否能够访问。这里的核心逻辑是让IAR的许可证工具自己告诉你问题出在哪而不是靠重装去撞大运。5.5 下载程序失败No target connected编译通过、但下载时报No target connected大部分情况下不是IAR配置问题而是硬件连接或者调试口被占用。先检查Debugger选项里是不是选了ST-LINK/J-LINK以及SWD接口是否选对。然后再看板子的ST-Link接线SWDIO、SWCLK、GND三根线是必须的VCC最好也接上否则电平不稳。最让人头疼的情况是之前往板子里下载过一段代码里面把SWD引脚复用成普通IO导致调试器连不上。这种情况可以在STM32的BOOT0引脚上做文章把BOOT0拉高复位后芯片从系统存储器启动不会执行用户代码再用ST-Link连接并擦除Flash最后把BOOT0拉回低电平。有些开发板自带复位键还有一个技巧是按住复位键不放点IAR的Download按钮然后在开始下载瞬间松开复位键也能救回来一部分板子。5.6 CubeMX重新生成代码工作丢失了用CubeMX最需要养成的习惯就是你手写的代码必须放在USER CODE BEGIN和USER CODE END注释之间。CubeMX重新生成时会完整保留这两个注释之间的内容但如果写在外部生成一次可能就没了。这个规则对所有IDE生成方式都一样IAR工程也不例外。很多人在IAR工程里改了main.c重新生成后编译报错一大堆才发现自己写在保护区域外的代码被覆盖。如果你真的忘了备份也有补救办法CubeMX生成前会在工程目录里生成一个Backup文件夹吗不同版本行为不完全一样有时候会有.mxproject文件用来恢复但不是万能。最靠谱还是使用版本管理工具Git能帮你找回历史版本。所以强烈建议在创建CubeMX工程的那一刻就用Git管理起来每次重新生成代码前后都提交一次。6. 几个让我少加班的小习惯写到最后分享几个我自己长期积累的习惯不一定都是大道理但确实让我少加过不少班。第一个是工程路径一定用纯英文一开始就杜绝中文和空格CubeMX生成、IAR编译、Git提交都会稳很多。第二个是调试口Serial Wire一定要在最开始配置别等程序烧进去之后才想起来。第三个是IAR工程版本和CubeMX选型匹配建议在电脑上固定一两个IAR主版本比如8.50和9.30都保留很多不兼容问题都能互相兜底。再就是尽量别手改CubeMX生成的EWP文件。IAR里有些配置可以在Options里微调但如果你改乱了重新生成一次CubeMX可能就会把变化覆盖掉。更好的做法是改配置时先截图记录下来再在CubeMX里找有没有对应选项实在没有的再考虑在IAR里改并在版本管理提交信息里写清楚。还有一个小技巧CubeMX生成IAR工程后EWARM目录里的.icf文件其实就是文本你可以用文本编辑器打开看看。里面会看到place in RAM with { readwrite };和place in ROM with { readonly };这样的语句理解了它你就大致明白IAR是怎么分配内存的。以后遇到RAM不足、堆栈溢出排查起来心里就有底。我个人在实际操作中的体会是IAR第一次用确实会觉得界面“老派”但只要你坚持用CubeMX来生成工程骨架不要自己手动搭工程后续的维护成本其实很低。记住那个Toolchain/IDE下拉框记住版本匹配记住路径别带中文后面基本顺风顺水。希望这篇文章能帮你少踩几个坑省出点时间多调一会儿程序。
返回列表