找回密码
立即注册
搜索
热搜: Java Python Linux Go
发回帖 发新帖

4709

积分

0

好友

611

主题
发表于 1 小时前 | 查看: 2| 回复: 0

本文聊聊 Yearnext Software Framework(以下简称 YSF),一个基于消息驱动的单片机软件框架。

https://gitee.com/accumulatedidea/Framework_Open

YSF 框架相关文档链接与版本信息

1. YSF 简介

YSF 全称 Yearnext Software Framework,定位是基于消息驱动的单片机软件框架,强调配置简便、跨平台、可裁剪。

如果你关心下面这几件事,值得翻一翻:

  • 想把「板级驱动」和「业务逻辑」拆开,换板时知道该动哪一层
  • 资源紧张的 MCU,想看协作式调度 + 消息队列,而不是一上来就上 FreeRTOS
  • 想对照一套现成的 fw_conf.h 裁剪思路

它不一定适合所有人。如果你已经在成熟 RTOS / 厂商中间件上跑产品,YSF 更像架构参考,而不是替代方案。

平台也不止 README 里写的 ARM。目录和配置里能看到 8051、STM8、STM32、新唐、HC32、i.MX RT,以及 MSVC 仿真等。换板之前先确认自己的编译器和 BOARD_PALTFORM 有没有现成包。

仓库顶层大致是:compilerhalkernelcomponent3rdpartybspprotocolutilitydocument

YSF 仓库顶层目录结构

仿真工程适合先在 PC 上摸清调度与消息路径,到真板再补 MSP 与引脚配置。

2. 五层怎么读

文档写的是「五层」,但很容易和「应用层」两个字拧在一起。按职责拆开看更清楚:

硬件层 → 硬件抽象层(HAL)→ 功能模块层 → 业务逻辑层 → 应用处理层

其中后两层合起来常被称为应用层:业务逻辑负责协议、状态、具体功能;应用处理层负责把产生的消息派发到对应模块。

YSF 五层软件架构分层图

换板时优先动 HAL/MSP,尽量别让业务代码直接绑死寄存器级类型。

2.1 硬件层

就是板载硬件:MCU、外设、引脚。框架不会「神奇地」代替你做原理图,只要求上层通过统一接口下去。

2.2 硬件抽象层

HAL 负责把底层驱动收成统一接口,方便上层调用。它大致分三块:

  • 编译器拓展包:框架专用宏、基础类型等,覆盖 Keil、IAR、SDCC、GCC、MSVC 等
  • MCU 支持包(MSP):把原厂驱动接到统一的 MSP API
  • 通用外设驱动包:复杂外设的工作机制

MSP 又拆成 LV0 / LV1,这是小容量平台上很实际的取舍:

  • LV0:贴近芯片,可以直接操作底层,常出现原厂类型(例如 GPIO_TypeDef*)。占用小,上层可移植性弱
  • LV1:标准抽象接口,把通用设备信息转成 LV0 专用信息再落硬件。可移植性更好,占用通常更大

YSF HAL 中 MSP 的 LV0/LV1 层级关系

先别急着全上 LV1。Flash/RAM 紧张、业务也不打算换平台时,LV0 往往更现实;真要跨芯片复用业务代码,再把调用面上抬到 LV1。

2.3 功能模块层

这一层是「框架能帮你省什么」的主体,分三块:

  • 框架内核:小型协作式任务调度,内建定时器、事件、消息队列、状态机等;还可选 Protothread。注意有 FullNano 两套实现,设计思路接近,但 API 互不兼容,需要在 fw_conf.h 里选版本
  • 功能组件(component):链表、环形缓冲区、CRC/校验和、查表、位操作等常用库
  • 开源组件(3rdparty):例如 SEGGER RTT、CmBacktrace、EasyLogger,以及 FatFs、SPIFFS、SimpleGUI、LVGL 等,按需编进工程即可

YSF 功能模块层组成与消息驱动路径

消息驱动的主路径可以粗略记成:硬件或定时产生事件 → 内核排队 → 应用处理层派发 → 业务模块处理。

协作式意味着任务要主动让出 CPU。长时间死循环占着资源,别的任务就会饿着——这和抢占式 RTOS 不是一回事,写简历或做技术对标时别混为一谈。

2.4 应用层怎么串起来

业务逻辑层:协议栈、设备状态、具体功能实现。仓库里 protocol 目前能看到如 xymodem 一类协议代码,文档里该目录仍标着待补充——实际使用时以源码为准。

应用处理层:把消息派到对应处理模块。

工程上常见的落点在 bsp/<平台>/application:框架初始化、配置裁剪、应用入口都在这一带。

对照例程里的写法,主函数往往很短:

Fw_Core_Init(),再 Fw_Core_Startup();真正的任务用 Fw_Task_Init / Fw_Task_Start 挂上去,Protothread 打开时可用 Fw_PT_Begin / Fw_PT_Delay 这类宏把「延时让出」写清楚。例程里的 LED 翻转,就是在验证调度和板级驱动是否走通。

YSF 例程中主函数与任务初始化代码截图

最小闭环可以这样走:

  1. 选一个接近你板子的 bsp 工程模版,例如仓库里有 STM32F1、STM32L4、simulator 等;文档里还提到过 HC32、N76E003 等模版,以你检出的目录为准
  2. 打开 application/fw_conf.h,选 Full/Nano、平台宏,关掉暂时用不到的组件
  3. 确认主流程能进内核启动;用 INIT_APP_EXPORT 一类机制注册应用初始化
  4. 先做一个 LED/定时任务或简单消息通路,确认调度和板级驱动通了,再叠加协议

bsp 里常见拆法:application 放应用与 fw_conf.hpaltform(仓库拼写如此)放 board、按键灯串口驱动、msp_conf.h

3. 注意事项

  • 别把协作式调度当成 RTOS:没有抢占优先级那一套预期时,任务写法要克制。中断里只做短处理,把重活投递成消息或事件,交给任务侧慢慢消化,通常更稳
  • Full / Nano 不要混用 API:换版本等于换一套接口,裁剪前先定版本再写业务
  • LV0 / LV1 别在业务里随意混调:抽象边界一旦糊掉,换板成本会重新回来
  • 文档有空链:例如「框架内核介绍」在 README 里尚未补全,以 document/dirkernel 源码和例程为准
  • 仓库年代较老:学习分层与裁剪很合适;选型前自己评估维护状态与芯片覆盖

和「自己从零搭分层」比,YSF 的价值主要在现成的配置入口和目录约定;和「直接上 RTOS」比,它更轻,但实时性和任务隔离也弱一截。选哪条路,先看产品要不要抢占、要不要多任务硬隔离,再看 Flash 还剩多少。

4. 总结

项目不是越大越好。YSF 分层把换板成本压在 HAL/MSP;消息驱动把业务拆成可派发的处理单元;能讲清五层职责、LV0/LV1 取舍、Full/Nano 差异,这套经验就比「把整个仓抄进工程」更有用。

如果对这类轻量级消息驱动的分层架构有想法,欢迎到 云栈社区 一起聊聊。




上一篇:AscendNPU IR 开源解析:昇腾 950 SIMT/SIMD 编译优化与 Triton 生态
下一篇:PCB铺铜后仍有孤铜:GND铜皮不接地就该删吗
您需要登录后才可以回帖 登录 | 立即注册

手机版|小黑屋|网站地图|云栈社区 ( 苏ICP备2022046150号-2 )

GMT+8, 2026-8-18 07:22 , Processed in 0.847110 second(s), 42 queries , Gzip On.

Powered by Discuz! X3.5

© 2025-2026 云栈社区.

快速回复 返回顶部 返回列表