CubeMX v6.1.0、RT-Thread Nano v3.1.3、Keil v5.33

第一步 配置并生成代码

官方指南假设你已了解关于CubeMX 的中级知识。如果你刚开始学习单片机,将此文档作为你的第一步可能不是最好的主意——掌握好基础知识再来吧!之前有其它框架的使用经验会有帮助,但这不是必需的。
配置好我们所需的外设后,添加CJSON、RTT支持包,如下图所示:
image.png
一定要去掉下面4项:
image.png
进行上一步操作之后,生成代码【GENERATE CODE】,此时用keil打开工程并进行相关设置,如下图:
image.png


第二步 安装nodejs、并添加相应支持

nodejs v14.15.1 LTS
添加脚本【${project}/MDK-ARM/RttSrcModify.js】

  1. var fs = require('fs');
  2. var path = require('path');
  3. let log = console.log
  4. const dir = fs.readdirSync('.');
  5. let projectName = dir.filter(e=>e.includes('.uvprojx'))[0];
  6. // log(projectName)
  7. // return;
  8. let ModifyKeilFilesConfigFilePath = path.join(__dirname, "RttSrcModify.json")
  9. let defaultPath = '../Middlewares/Third_Party/RealThread_RTOS_RT-Thread'
  10. let config = fs.readFileSync(ModifyKeilFilesConfigFilePath);
  11. config = config.toString();
  12. config = config.replace(/_myProject.uvprojx/g, projectName)
  13. config = JSON.parse(config)
  14. config?.modifyFiles?.forEach(e => {
  15. let fPath = e.filePath.includes('./') ? path.join(__dirname, e.filePath) : path.join(__dirname, defaultPath, e.filePath)
  16. let fileContent = fs.readFileSync(fPath)
  17. fileContent = fileContent.toString().split('\n');
  18. let isModify = false
  19. fileContent.forEach((ee, i) => {
  20. if (ee.includes(e.findStr)) {
  21. if(fileContent[i + e.dstOffset].includes(e.src)) {
  22. isModify = true;
  23. fileContent[i + e.dstOffset] = fileContent[i + e.dstOffset].replace(e.src, e.dst)
  24. }
  25. }
  26. })
  27. //log(fileContent)
  28. if(isModify) fs.writeFileSync(fPath, fileContent.join('\n'))
  29. });

添加修改json文件【${project}/MDK-ARM/RttSrcModify.json】

  1. {
  2. "modifyFiles":[
  3. {
  4. "filePath": "./_myProject.uvprojx",
  5. "findStr":"<FileName>main.c</FileName>",
  6. "dstOffset": 1,
  7. "src":"<FileType>1</FileType>",
  8. "dst":"<FileType>8</FileType>"
  9. },
  10. {
  11. "filePath": "./_myProject.uvprojx",
  12. "findStr":"<FileName>context_rvds.S</FileName>",
  13. "dstOffset": 1,
  14. "src":"<FileType>1</FileType>",
  15. "dst":"<FileType>2</FileType>"
  16. },
  17. {
  18. "filePath": "src/ipc.c",
  19. "findStr":"mb->msg_pool = msgpool;\n",
  20. "dstOffset": 0,
  21. "src":"mb->msg_pool = msgpool;\n",
  22. "dst":"mb->msg_pool = (rt_uint32_t *)RT_KERNEL_MALLOC(mb->size * sizeof(rt_uint32_t));\n"
  23. },
  24. {
  25. "filePath": "src/ipc.c",
  26. "findStr":"mb->msg_pool = RT_KERNEL_MALLOC(mb->size * sizeof(rt_uint32_t));\n",
  27. "dstOffset": 0,
  28. "src":"mb->msg_pool = RT_KERNEL_MALLOC(mb->size * sizeof(rt_uint32_t));\n",
  29. "dst":"mb->msg_pool = (rt_uint32_t *)RT_KERNEL_MALLOC(mb->size * sizeof(rt_uint32_t));\n"
  30. },
  31. {
  32. "filePath": "src/kservice.c",
  33. "findStr":"for (su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)\n",
  34. "dstOffset": 0,
  35. "src":"for (su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)\n",
  36. "dst":"for (su1 = (const unsigned char *)cs, su2 = (const unsigned char *)ct; 0 < count; ++su1, ++su2, count--)\n"
  37. },
  38. {
  39. "filePath": "src/thread.c",
  40. "findStr":"(void *)((char *)thread->stack_addr + thread->stack_size - 4),\n",
  41. "dstOffset": 0,
  42. "src":"(void *)((char *)thread->stack_addr + thread->stack_size - 4),\n",
  43. "dst":"(rt_uint8_t *)((char *)thread->stack_addr + thread->stack_size - 4),\n"
  44. },
  45. {
  46. "filePath": "include/rtdef.h",
  47. "findStr": "RT_USED const init_fn_t __rt_init_##fn SECTION(\".rti_fn.\"level) = fn\r",
  48. "dstOffset": 0,
  49. "src":"RT_USED const init_fn_t __rt_init_##fn SECTION(\".rti_fn.\"level) = fn\r",
  50. "dst":"RT_USED const init_fn_t __rt_init_##fn SECTION(\".rti_fn.\" level) = fn\r"
  51. },
  52. {
  53. "filePath": "bsp/rtconfig.h",
  54. "findStr": "#define RT_MAIN_THREAD_STACK_SIZE 256",
  55. "dstOffset": 0,
  56. "src":"#define RT_MAIN_THREAD_STACK_SIZE 256",
  57. "dst":"#define RT_MAIN_THREAD_STACK_SIZE 2048"
  58. },
  59. {
  60. "filePath": "bsp/rtconfig.h",
  61. "findStr": "//#define RT_USING_HEAP\r",
  62. "dstOffset": 0,
  63. "src":"//#define RT_USING_HEAP\r",
  64. "dst":"#define RT_USING_HEAP\r"
  65. },
  66. {
  67. "filePath": "bsp/board.c",
  68. "findStr": "#define RT_HEAP_SIZE 1024\r",
  69. "dstOffset": 0,
  70. "src":"#define RT_HEAP_SIZE 1024\r",
  71. "dst":"#define RT_HEAP_SIZE 1024 * 20"
  72. }
  73. ]
  74. }

第三步 添加快捷菜单项

image.png
完成后,即可进行点灯啦!

当日总结

主线程栈默认值点灯都跑不起来【#define RT_MAIN_THREAD_STACK_SIZE 256】。
启用动态堆【#define RT_USING_HEAP】之后可以动态创建线程,但是线程栈总大小被【#define RT_HEAP_SIZE 1024】限制了,所以简单调节一下即可。