Commit Graph
5 Commits
Author SHA1 Message Date
caowangrenbo 944774eab3 refactor(log): 日志文案改 ASCII 英文,修 ROS_INFO 中文乱码
ROS_INFO/WARN/ERROR 走的不是 printf,而是 rosconsole -> log4cxx,后者按进程当前的
C 语言环境对消息做一次窄/宽字符转码。节点从未调用 setlocale,LC_CTYPE 停在默认的
"C"(ASCII),于是非 ASCII 的每个字节被替换成一个 '?'——一个汉字 3 字节正好 3 个
'?'。而 [config] 摘要那条 std::cout 路径直接写字节、不转码,所以之前只有 ROS_* 的
日志乱码。备选方案是 setlocale(LC_CTYPE, "")(3 行即可修),这里采用"运行时输出一律
英文":英文日志不依赖语言环境,systemd/robot_upstart 拉起时也不会因缺 LANG 复发。

改动与校验:
- invicta_hardware / invicta_remote / invicta_deploy / invicta_msgs 共 20 个文件、
  202 处字符串字面量改为 ASCII 英文。中文代码注释、标识符、话题名、JSON/TOML 键名、
  日志前缀一律未动(把字面量内容挖空后与改前做骨架比对,20 个文件零差异)。
- printf 格式说明符(%s/%d/%zu/%.1f/%02X ...)的数量、类型、顺序逐文件与改前一致。
- 顺带 ASCII 化非中文字符:° -> deg、± -> +/-、× -> x、→ -> ->、框线 -> "+==+",
  并修正了启动横幅框线宽度差 2 列的问题。
- motion_defs.h 的 GaitName / MotionParamName 显示名改英文(只用于日志与回包文案);
  协议字段仍传整数(bs["MotionState"] = int(...)),不影响上位机协议。

注意:invicta_remote 回给手柄的 Unsupported / "Not allowed operation" 文案也变为英文,
会出现在上位机错误列表里。

已在 SBC(aarch64, Noetic)编译确认。
2026-10-23 15:39:55 +08:00
caowangrenbo 46bbb06978 feat(hardware): 标定归硬件;按 name 选关节 + kSetZero;toml++ 改 vendored
标定边界上移到 invicta_hardware:
- raw↔model 的 dir/offset 由 hardware 独家施加(话题收发都是模型帧),
  deploy 的 InvictaInterface 退化为透传,invicta_deploy.toml 不再有 dir/offset_deg。
  这样 [joint_limits](模型帧)与被限幅的指令同帧,/joint_states 也是模型角。

关节选择(部分接入 / 单腿调试):
- JointCommandArray 的 name 即本次要控制的关节子集(空 = 全部已配置关节)。
- 未选中的关节写「零力矩自由」块,而不是留全 0——按协议 (0,0,0,0,0) 会解码成
  P_MIN/V_MIN/T_MIN,其中 tau=T_MIN(摆臂 -100 N·m)是危险的前馈力矩。
- 新增 control_word kSetZero(6) -> 0xEF,只作用于选中的摆臂(轮毂不支持,跳过)。

调试脚本 invicta_hardware/scripts/hw_debug_test.py:
- 只起 hardware 节点调试:monitor/damping/angle/wheel/offset/zero 六种模式 + --joints。
- 限幅参数硬编码;发指令时默认回显模型角。

构建:toml++ 改为 vendored single-header(三个包各 third_party/tomlplusplus/toml++/toml.hpp),
   去掉 find_package(tomlplusplus) 与 -DTOML_HEADER_ONLY(单头自带 header-only)。

已在容器(localhost/custom-ros-noetic)中全新 catkin_make + smoke_test 验证通过。
2026-10-23 13:44:27 +08:00
caowangrenbo 594885b9e8 feat(hardware): 接入 SocketCAN 与智身模组协议,补温度诊断和指令看门狗
- hardware: 新增 can_bus.h / joint_module_protocol.h,实现使能/失能/运行帧与
  12 字节反馈帧编解码;ReadHardware/WriteHardware 落地,控制字按协议语义映射
  (kErrorReset 按重新使能处理,kGetStatus 无需请求)
- hardware: 温度/驱动状态/电压经 /joint_diagnostics 发布(默认 10 Hz,可配置)
- hardware: 指令看门狗,100 ms 无指令转阻尼,避免上游挂掉后重发最后一帧
- hardware: 限幅与归一化边界分离——[joint_limits] 是唯一实际限幅,加载期校验
  其不超过 [motor.*] 的归一化边界;力矩按峰值扭矩夹紧,kp/kd 越界夹紧并告警
- hardware: require_can 开关,无 CAN 时可只发状态(冒烟测试用)
- remote: 1002/4 关节按 M20 的 16 槽上报(swing→HipY、wheel→Wheel,其余占位 0),
  1002/5 温度改由 /joint_diagnostics 提供
- deploy: 启动时序等订阅者出现再发(ROS1 无 latch,否则整段丢失)
- msgs: 新增 JointDiagnostics
- docs: 智身模组 CANFD 协议整理、待办清单
2026-10-22 11:05:49 +08:00
caowangrenbo a173383756 refactor(config) + feat(model): 每节点一份 TOML 取代 ROS yaml;8 关节两自由度腿与单连杆 IK
配置(节点自治,跨包不共享):
- 新增各节点自己的 config/<节点>.toml(deploy / remote / hardware),只放本节点参数;删除三份 *.yaml
- 各节点自带配置结构与加载器(deploy_config.h / remote_config.h / hardware_config.h),
  删除 state_machine/parameters/ 与 ControlParameters
- TOML 解析库 toml++ 改为系统安装:find_package(tomlplusplus REQUIRED),以 header-only 方式编译,
  库源码不进仓库、目标机不需部署运行时 .so
- launch 只传 config_file;改 TOML 不需重编,改配置头自动触发该节点重编

机器人模型(按本机构型改):
- 16 关节三关节腿 → 8 关节(每腿 摆臂 + 轮)
- IK 改为单连杆反解 θ = splay_sign·acos(h/L);趴下 h=0 → 摆臂水平(±90°)
- 步态倒向:趴下时前腿向前、后腿向后(splay_sign 前 +1 / 后 −1),与 M20 相反
- 起立/趴下用样条 + 速度前馈;轮 kp 恒 0;限位改为逐关节查表
- 精简死参数:机身长宽、髋偏置、轮半径、力矩限制、通用策略参数,以及 auto_calibrate 与 ±360° 回绕标定
- 硬件侧参数入库:电机量程(P65MAXS/W190S)、CAN 通道与仲裁 ID、使能帧数/间隔、每腿 bus/canid、台架增益

保留(未改动 HEAD 已有功能):多步态模型预加载与运行中切换、站立后自动进 RL 与就绪自检、
遥测四路上报、阻尼态单调时钟计时、策略输出 NaN 保护

验证(ROS Noetic 容器,干净构建):
- 四个包 catkin_make rc=0
- /joint_states 200 Hz(8 关节名与配置一致)、/motion_state 20 Hz
- IK 目标角:站立 ±16.3°、收腿 ±66.4°、趴下 ±90.0°;趴下指令实测峰值 1.5708 rad
- 协议 MotionParam=1/4 触发 idle→standup→liedown;自动进 RL 自检在零反馈下正确拦住

待实测:摆臂长度/站趴高度、各关节 dir/offset_deg;invicta_hardware 的 CAN 读写仍为 TODO
2026-10-21 21:39:49 +08:00
caowangrenbo cf70b1a1d7 Initial commit: extract M20 sim2real into ROS1 invicta project
Source: DeepRoboticsLab/sdk_deploy (BSD-3-Clause), M20 sim2real part only.

Packages:
- invicta_msgs: JointCommandArray, MotionCommand, MotionState; standard messages
  (sensor_msgs/JointState, sensor_msgs/Imu) elsewhere; shared motion value defs.
- invicta_deploy: state machine (idle/standup/rl/joint-damping/lie-down), ONNX
  policy with per-gait models, auto RL entry after standup with readiness checks,
  safety loop, gait->model table; no protocol/network code.
- invicta_remote: vendor basic_server protocol (UDP + JSON, proto.md V1.2.0),
  header/MsgId, 0xE0xx error codes, motion/usage-mode/gait translation, telemetry
  1002/3,4,5,6 (2/10/2/2 Hz); publishes /motion_command, subscribes /motion_state.
- invicta_hardware: joint/IMU bridge skeleton (SocketCAN I/O is TODO), publishes
  sensor_msgs/JointState + sensor_msgs/Imu, consumes /joint_commands.

Verified on ROS Noetic (Ubuntu 20.04) in docker: clean catkin_make, 200 Hz joint
state / 50 Hz RL commands / 20 Hz state report, protocol conformance (MotionParam,
gait preconditions, error codes), telemetry push, and end-to-end switching of two
policy models with a real remote controller.
2026-10-21 00:46:29 +08:00