睿云联嵌入式一面:RTOS 调度与 bootloader 升级
- 轮次
- 一面
- 时间
- 2026-09
- 来源
- 牛客网
《面试题目》
- 自我介绍。
- 详细介绍一下项目。
- 接触过 Web 吗?
- 讲一下上下文切换。
- 抢占式调度是怎么做的?
- 指针有几种类型?
- 指针异常有哪些?怎么避免、怎么解决?
- 互斥锁是怎么实现的?
- 做过应用层开发吗?具体讲讲。
- 项目中实现的算法讲一下。
- bootloader 是怎么设计的?
- flash 有限的情况下怎么保证升级成功?
- 那跟重新刷写程序有什么区别?
- 竞赛几个人参加,你主要负责什么?
- 任务怎么划分,依据是什么?
- 项目中云端通信是怎么设计的?
- 通信协议用了什么?
- 模型是专门部署到嵌入式设备上的吗?识别精度如何?
《参考解析》
上下文切换与抢占式调度:一次切换要做的事包括保存当前任务的寄存器组与程序计数器、切换栈指针与任务控制块状态、选出下一个就绪任务并恢复它的现场,可能还要处理浮点/SIMD 上下文与缓存、TLB 的影响。RTOS 通常把切换放在 PendSV 这类低优先级异常里执行,保证不打断正在处理的中断。开销不只在压栈出栈,调度器本身、缓存抖动、以及切换频率过高带来的吞吐损失都要算进去。抢占式调度指高优先级任务一就绪就能打断低优先级任务,配合时间片轮转让同级轮转;要能对比协作式调度(靠任务主动让出)在响应实时性上的短板,并延伸到优先级反转与优先级继承、临界区关中断时长过长会推高最坏响应时间。
指针的类型与指针异常:指针按指向对象分对象指针、函数指针、void *、空指针;类型不只是「地址」,它决定解引用时读几个字节、自增时的步长,以及编译器怎么做别名分析。常见异常:未初始化就使用(野指针)、数组越界、释放后继续使用(悬垂指针)、返回栈上局部变量的地址、对齐不满足、栈溢出踩到别的数据。防护手段是工程习惯加机制:定义即初始化、释放后置空、边界检查、打开编译告警并当错误处理、上静态分析、用 MPU/MMU 或断言保护关键区域,配合看门狗兜住跑飞。
互斥锁的实现:单核 RTOS 里常见做法是关中断或挂起调度器保护极短临界区,配合「拿不到锁就挂起当前任务、由释放者唤醒」的睡眠式等待;多核则必须靠原子指令(CAS、TAS、LL/SC)实现自旋锁,并配内存屏障保证可见性。RTOS 的互斥锁与二值信号量的差别在所有权、优先级继承和可递归加锁,优先级继承正是用来缓解优先级反转。实践要点:中断服务程序里不能使用会睡眠的锁,只能用自旋或短临界区;临界区越短越好,嵌套加锁要有统一的顺序。
bootloader 与 flash 受限时的升级可靠性:典型结构是 Boot + App(条件允许再加备份区或参数区)。上电后 Boot 先校验 App 的有效标志、CRC 与签名,通过才跳转,不通过就停在恢复模式等待串口/网络重传。flash 装不下双区时,可用外部 flash 暂存新固件、做差分/增量升级把包体压小、或分块接收并分块写入。核心不是省空间而是断电安全:任何时刻掉电都要能恢复,所以「升级完成」的标志必须最后写、写完先校验再切换,切换失败要能回滚。至于「跟重新刷写程序有什么区别」——烧录器重刷是产线或维修场景,要停机、接线、人工介入;bootloader 升级是设备在现场自己更新,要求远程下发、可校验、可回滚、掉电不砖。
云端通信协议与设计:上报型设备多用 MQTT(长连接、QoS 分级、遗嘱消息、主题分层),资源与带宽特别紧张时看 CoAP/LwM2M,低频配置同步走 HTTP 也够。要讲清的部分包括:一机一密的鉴权与 TLS、心跳保活与断线重连(指数退避加抖动)、离线期间的数据缓存与补传、上报频率与功耗/流量预算的权衡、数据格式(JSON 便于调试、protobuf 省流量)、以及下行命令的幂等与超时。面试官问「通信协议用了什么」,想听的不只是协议名,而是为什么在带宽、功耗、可靠性之间选它。
端侧模型部署与精度:模型要按 MCU/NPU 的算力与内存裁剪:换更小的骨干网络、剪枝、蒸馏、INT8 量化;量化后精度通常会掉,要靠有代表性的校准集和量化感知训练补回来,并用业务指标而不是单纯的准确率验收。推理侧注意算子支持与内存峰值,必要时做算子替换或分片推理。回答「精度如何」时给出的是在真实采集数据上的指标和误判代价,而不是一个孤立数字。
项目与竞赛怎么讲:面试官问「你负责什么」「任务怎么划分」,是在确认你的贡献边界和协作方式。划分依据可以按模块边界、依赖关系、风险高低、成员技能来谈,重点讲清接口怎么定、进度怎么同步、出问题怎么定位、有没有返工。别只讲团队成果的宏观描述,落到具体到你写的那部分和当时的取舍上。