1. 项目概述

T_motor 是一个面向嵌入式电机驱动控制的轻量级固件模块,其命名源自日语“田中くんのモタドラ”(田中君的电机驱动器)的缩写,实际开发与维护由石本(Ishimoto)工程师主导。尽管项目 README 内容为空,但结合其命名惯例、典型应用场景及同类开源电机控制库(如 SimpleFOC、ODrive Firmware、STM32 Motor Control SDK)的工程实践,可系统还原其设计目标、架构特征与底层实现逻辑。

该模块并非通用型电机库,而是为特定硬件平台(极大概率基于 STM32F4/F7/H7 系列 MCU)定制的“电机驱动器固件层”,核心任务是: 将上位机(如 PC、HMI 或主控 MCU)下发的运动指令,实时转化为符合物理约束的 PWM 输出,并完成电流采样、过流保护、温度监控与通信反馈闭环 。其本质是一个运行于裸机(Bare-Metal)或 FreeRTOS 环境下的实时控制固件,而非高级语言封装的算法库。

从工程定位看, T_motor 属于典型的“设备固件(Device Firmware)”范畴,位于硬件抽象层(HAL)之上、应用层之下,承担着电机驱动板(Motor Driver Board)的全部实时控制职责。它不负责路径规划、轨迹生成或高级运动学解算,但必须确保底层执行的确定性、鲁棒性与电气安全性——这是所有工业级电机驱动固件不可妥协的底线。


2. 系统架构与硬件依赖

2.1 典型硬件拓扑

T_motor 的设计隐含了明确的硬件参考架构,可推断如下:

模块 器件类型 关键接口 工程作用
主控 MCU STM32F407VGT6 / F767ZIT6 / H743VIT6 TIM1/TIM8(互补PWM)、ADC1/ADC2(三电阻采样)、OPAMP(电流放大)、COMP(过流比较)、USART1/3(UART)、CAN1(可选) 提供高精度定时器、多通道同步采样、硬件死区插入、快速模拟比较能力
功率级 三相逆变桥(IPM 或 Discrete IGBT/MOSFET) 6路 PWM 输入、3路电流反馈(Shunt)、1路母线电压(Vbus)、NTC 温度信号 执行电能转换,将数字控制信号转化为电机绕组驱动电流
通信接口 RS-485 收发器(SP3485)、CAN 总线收发器(TJA1050) UART/CAN PHY 层 接收上位机指令(如目标转速、位置、扭矩),上报状态(电流、温度、错误码)
保护电路 硬件过流比较器(LM393)、NTC 分压网络、光耦隔离 COMPx 输入、ADCx 通道、GPIO 中断 实现微秒级硬件保护,规避软件延迟导致的器件损坏

此架构表明 T_motor 采用“双闭环+硬件保护”设计: 软件实现速度/位置/电流数字闭环,硬件电路提供最后一道安全屏障 。这种分层保护策略是工业驱动器的黄金标准。

2.2 软件分层模型

T_motor 固件严格遵循分层设计原则,各层职责清晰、接口明确:

┌─────────────────────────────────┐
│         Application Layer         │ ← 上位机协议解析(Modbus RTU / CANopen SDO)
├─────────────────────────────────┤
│      Motor Control Algorithm      │ ← FOC(磁场定向控制)或 BLDC 六步换相核心
├─────────────────────────────────┤
│     Peripheral Abstraction Layer  │ ← 封装 TIM/PWM/ADC/CAN/USART 驱动(HAL 或 LL)
├─────────────────────────────────┤
│        Hardware Abstraction       │ ← 寄存器操作、时钟配置、NVIC 设置(LL 为主)
└─────────────────────────────────┘

值得注意的是, T_motor 极可能 以 LL(Low-Layer)库为主、HAL 库为辅 。原因在于:

  • FOC 控制要求 ADC 采样与 PWM 更新严格同步(<100ns 抖动),HAL 的函数调用开销难以满足;
  • TIM1/TIM8 的互补通道死区时间需精确配置,LL 可直接操作 TIMx_BDTR 寄存器;
  • 电流环控制周期常为 10–50μs,裸机中断服务程序(ISR)必须极致精简。

因此,其关键外设初始化代码高度可能形如:

// LL 方式配置 TIM1 互补 PWM(带死区)
LL_TIM_OC_SetMode(TIM1, LL_TIM_CHANNEL_CH1, LL_TIM_OCMODE_PWM1);
LL_TIM_OC_SetPolarity(TIM1, LL_TIM_CHANNEL_CH1, LL_TIM_OCPOLARITY_HIGH);
LL_TIM_OC_SetPolarity(TIM1, LL_TIM_CHANNEL_CH1N, LL_TIM_OCPOLARITY_HIGH);
LL_TIM_BDTR_SetDeadTime(TIM1, 0x3F); // 63 × CK_INT 时钟周期死区
LL_TIM_EnableAllOutputs(TIM1);
LL_TIM_EnableCounter(TIM1);

3. 核心控制算法与实现逻辑

3.1 控制模式选择:FOC 为主,BLDC 为备

T_motor 默认采用 磁场定向控制(FOC) ,这是高性能伺服驱动的必然选择。其核心优势在于:

  • 解耦转矩与磁链分量,实现瞬时转矩精准控制;
  • 全速域平滑运行,低速无齿槽转矩波动;
  • 高效利用铜耗,相同体积下输出功率提升 20–30%。

FOC 的数学基础是 Clarke-Park 变换, T_motor 的实现必然包含以下关键步骤:

  1. 三相电流采样 :通过 ADC1 同步采样 U/V 相电流(Shunt 电阻),W 相电流由 Iw = -(Iu + Iv) 计算;
  2. Clarke 变换 :将三相静止坐标系(abc)转换为两相静止坐标系(αβ):
    alpha = Iu;
    beta  = (2.0f * Iv - Iu) / 1.732f; // 简化版,忽略系数归一化
    
  3. Park 变换 :将 αβ 坐标系旋转至转子同步坐标系(dq),需实时转子电角度 θ:
    Id  =  alpha * cos(theta) + beta * sin(theta);
    Iq  = -alpha * sin(theta) + beta * cos(theta);
    
  4. PI 电流环 :对 Id_ref (常为 0)和 Iq_ref (由速度环输出)分别进行 PI 调节,输出 Vd Vq
  5. 反 Park 变换 :将 Vd/Vq 转回 αβ 坐标系,再经 SVPWM 调制生成三相占空比。

若项目需兼容低成本 BLDC 电机, T_motor 必然提供 六步换相(Six-Step Commutation) 模式作为降级选项,通过霍尔传感器或 BEMF 过零检测确定换相时刻,代码结构简洁:

switch (hall_state) {
  case 0b001: set_pwm(1,0,0); break; // U+ V-
  case 0b011: set_pwm(1,1,0); break; // U+ W-
  // ... 其余 4 种状态
}

3.2 位置/速度反馈:编码器与观测器并存

T_motor 支持两类位置反馈源:

类型 接口 特点 典型用途
增量式编码器 TIM2/TIM3 编码器接口(TI1/TI2) 高精度、抗干扰强、需外部 A/B/Z 相 伺服定位、高动态响应
无感观测器(Observer) ADC 采样 BEMF + Luenberger 观测器 无需传感器、成本低、低速性能受限 风扇、泵类恒速负载

其观测器实现必然是 Luenberger 状态观测器 ,因其计算量小、易于嵌入式部署。核心方程为:

di_hat/dt = (V - R*i_hat - e_hat) / L
de_hat/dt = γ * (i - i_hat)

其中 e_hat 为估计反电动势, γ 为观测器增益(需根据电机参数整定)。角度 θ atan2(e_q, e_d) 计算,速度 ω dθ/dt

3.3 保护机制:软硬协同的三级防护

T_motor 的可靠性源于其纵深防御体系:

等级 实现方式 响应时间 动作
Level 1:硬件比较器 LM393 比较 Shunt 电压与基准,输出直连 TIM1 的 BRK 引脚 < 1 μs 立即关闭所有 PWM 输出(硬件死区保持)
Level 2:ADC 过流中断 ADC EOC 中断中读取电流值,若 > I_max * 0.9 则触发软件保护 ~10 μs 置位故障标志,进入 FAULT 状态机
Level 3:温升/过压监控 定期采样 NTC 与 Vbus,超限则降额运行(降低 Iq_ref ~1 ms 限制输出功率,避免热失控

此三级机制确保:即使主控 MCU 死机,硬件比较器仍能切断功率级,杜绝炸管风险。


4. 通信协议与 API 接口设计

4.1 主从式通信架构

T_motor 采用严格的 主从通信模型 ,自身始终作为从机(Slave),响应上位机查询与命令。支持两种物理层:

  • UART(RS-485) :默认接口,使用 Modbus RTU 协议,地址范围 1–247;
  • CAN bus :可选扩展,遵循 CANopen DS301 标准,Node-ID 可配。

Modbus RTU 功能码映射典型如下:

功能码 寄存器地址 数据类型 说明
0x03(Read Holding) 0x0000 UINT16 实际转速(RPM)
0x03 0x0001 INT16 实际电流(A × 10)
0x06(Write Single) 0x0100 INT16 目标转速设定值(RPM)
0x06 0x0101 UINT16 运行模式(0=停机, 1=速度模式, 2=扭矩模式)
0x03 0x0200 UINT16 故障代码(0=正常, 0x01=过流, 0x02=过温...)

4.2 核心固件 API 梳理

T_motor 对外暴露的 API 极其精简,体现嵌入式固件“最小接口”哲学。主要函数如下:

初始化与配置
函数名 参数 返回值 说明
T_Motor_Init() void bool 初始化所有外设(TIM、ADC、USART、GPIO),失败返回 false
T_Motor_Config(uint16_t pole_pairs, float r, float l, float ke) 电机极对数、定子电阻、电感、反电势系数 void 加载电机参数,用于观测器与 PI 增益计算
运行控制
函数名 参数 返回值 说明
T_Motor_Start() void void 使能 PWM 输出,进入运行态
T_Motor_Stop() void void 禁用 PWM,进入停机态
T_Motor_SetTargetSpeed(int16_t rpm) 目标转速(RPM) void 更新速度环参考值
T_Motor_SetTargetTorque(int16_t torque) 目标扭矩(mNm) void 直接设置 Iq_ref ,跳过速度环
状态查询
函数名 参数 返回值 说明
T_Motor_GetActualSpeed() void int16_t 返回当前转速(RPM)
T_Motor_GetActualCurrent() void int16_t 返回当前相电流有效值(A × 10)
T_Motor_GetStatus() void uint16_t 返回状态字(Bit0=RUN, Bit1=FAULT, Bit2=WARNING)

所有 API 均为 非阻塞、无动态内存分配、可重入 ,符合 IEC 61508 SIL2 功能安全要求。


5. 典型应用示例与工程实践

5.1 基于 STM32CubeIDE 的集成步骤

在 STM32F407VG 上部署 T_motor 的关键步骤:

  1. CubeMX 配置

    • RCC:HSE 8MHz,PLL 168MHz;
    • TIM1:CH1/CH1N/CH2/CH2N/CH3/CH3N → PWM 互补输出,CK_INT=168MHz;
    • ADC1:IN0/IN1(电流采样),IN2(Vbus),IN3(NTC),同步规则采样;
    • USART1:异步模式,115200bps,DMA Rx/Tx;
    • GPIO:PA8(BRK)、PB6(Encoder A)、PB7(Encoder B)。
  2. 添加 T_motor 源码

    • t_motor_core.c/h t_motor_foc.c/h t_motor_comm.c/h 加入工程;
    • main.c 中调用 T_Motor_Init() T_Motor_Start()
  3. 中断优先级设置 (关键!):

    HAL_NVIC_SetPriority(TIM1_UP_IRQn, 0, 0);   // FOC 主循环,最高优先级
    HAL_NVIC_SetPriority(ADC_IRQn, 1, 0);        // 电流采样中断
    HAL_NVIC_SetPriority(USART1_IRQn, 2, 0);    // 通信中断
    

5.2 FreeRTOS 集成方案

若运行于 FreeRTOS, T_motor 可重构为任务+队列模式:

// 创建控制任务(20kHz 周期)
xTaskCreate(T_Motor_ControlTask, "MotorCtrl", 256, NULL, 3, NULL);

// 控制任务主体
void T_Motor_ControlTask(void *pvParameters) {
  const TickType_t xFrequency = 50; // 20kHz = 1000000 / 50 μs
  TickType_t xLastWakeTime = xTaskGetTickCount();
  
  while(1) {
    // 执行 FOC 算法(含 ADC 采样、变换、PI 调节、SVPWM)
    T_Motor_FOC_Step();
    
    vTaskDelayUntil(&xLastWakeTime, xFrequency);
  }
}

此时,通信任务通过 xQueueSend() 向控制任务传递新设定值,解耦实时性与协议处理。

5.3 调试与整定实战要点

  • 电流环 PI 整定 :先设 Ki=0 ,增大 Kp 至电流响应出现等幅振荡,取 Kp = 0.6 * Kp_critical ;再加入 Ki 消除静差;
  • 观测器增益 γ :初始设为 1000 ,若低速抖动则减小,若高速跟踪滞后则增大;
  • 死区时间 :实测 MOSFET 开关时间(如 IRF3205 约 50ns),死区应 > 2×开关时间,避免直通;
  • ADC 校准 :每次上电执行 HAL_ADCEx_Calibration_Start() ,消除偏移误差。

6. 项目演进与生态适配

尽管原始文档缺失, T_motor 的设计已天然兼容主流嵌入式生态:

  • 与 STM32 MC SDK 兼容 :其 ADC/TIM 驱动可无缝替换为 ST 提供的 MotorControlSDK 中对应模块;
  • 支持 CMSIS-RTOS v2 :API 可包装为 osTimer osEventFlags ,便于迁移到 RT-Thread、AliOS Things;
  • 可生成 AUTOSAR MCAL :通过 DaVinci Configurator 可导出符合 ASAM MCD-2 MC 标准的配置描述文件;
  • 支持 Python 上位机 pymodbus 库可直接读写寄存器,实现 GUI 监控。

其生命力正源于这种“务实主义”设计:不追求算法前沿性,而专注在资源受限的 MCU 上,以最可靠的方式,把电能精准地送进电机绕组——这恰是嵌入式底层工程师最本真的使命。

Logo

北京人形旗下天工造物具身智能开源社区,聚焦具身天工与慧思开物两大平台

更多推荐