Skip to content

Add pyserial workaround for Revo2Touch sensor API on older SDK#1

Open
brownwa wants to merge 1 commit into
BrainCoTech:developfrom
brownwa:claude/v2-touch-pyserial-workaround
Open

Add pyserial workaround for Revo2Touch sensor API on older SDK#1
brownwa wants to merge 1 commit into
BrainCoTech:developfrom
brownwa:claude/v2-touch-pyserial-workaround

Conversation

@brownwa
Copy link
Copy Markdown

@brownwa brownwa commented Apr 14, 2026

Summary

The libbc_stark_sdk.so currently shipped via download-lib.sh is version 0.4.3, which hard-codes every touch-sensor API as "deprecated for current firmware" and returns empty — even on Revo2Touch hardware where modbus_get_device_info reports hardware_type = 4 and the physical sensors are installed and alive:

WARN touch_sensor_setup: deprecated for current firmware
WARN touch_sensor_calibrate: deprecated for current firmware
WARN get_touch_sensor_status: deprecated for current firmware, return empty
WARN stark_get_touch_sensor_raw_data: deprecated for current firmware, return empty

Version 0.8.1 of the SDK (shipped with unitreerobotics/brainco_hand_service) adds STARK_HARDWARE_TYPE_REVO2_TOUCH = 4 and accepts the touch-API calls on the same hands — but users of this repo can't easily pick it up without swapping out the .so, which risks breaking the ROS 2 wrapper.

This PR adds a standalone workaround that bypasses the SDK version mismatch entirely.

What's added

ros2_stark_ws/src/ros2_stark_controller/scripts/touch_sensor_pyserial.py

Talks the same Modbus RTU commands the 0.8.1 SDK's modbus_get_touch_status sends internally, using only pyserial. Works on any installed SDK version.

pip install pyserial
python3 scripts/touch_sensor_pyserial.py --dual --seconds 30

Press a fingertip and see per-finger normal_force go from 0 to ~2500.

FAQ_en.md section 7 — explains the SDK-version gotcha with both the "upgrade the .so" and "use the workaround" paths.

Register layout (reverse-engineered)

Reverse-engineered by time-aligning single-finger presses against the live register dump, cross-checked against what libbc_stark_sdk 0.8.1 logs at TRACE level.

read input registers @ 4200, count 30:

  regs[0..14]  = 3 per finger, interleaved f0..f4 (normal, tangential, tang_dir)
  regs[15..24] = 2 per finger, interleaved f0..f4 (self_proximity lo/hi u32 halves)
  regs[25..29] = per-finger counter / status, ignore

Finger order: f0=thumb, f1=index, f2=middle, f3=ring, f4=pinky.

The firmware writes 0xFFFF as a "no data" sentinel on idle tangential fields; the script masks those to 0.

Verification

Tested on a Revo2Touch hand (serial BCXTL2334J..., firmware 1.0.14.U). All 10 fingertip channels (thumb/index/middle/ring/pinky × left + right) return a crisp 0-to-2500 normal_force when pressed. Idle readings sit at 0. Palm has no sensor — only fingertips.

Why ship this rather than just upgrade the SDK?

Three reasons:

  1. Upgrading libbc_stark_sdk.so to 0.8.1 requires a matching header-file update and a firmware_type bump in the config YAML, which is a larger and more disruptive change than a standalone script.
  2. The workaround is useful even after an SDK upgrade as a minimal dependency-free reference for talking to the sensors from environments where the Rust SDK is inconvenient.
  3. It documents the Modbus protocol externally — useful for anyone writing a non-Python client.

Happy to follow up with a full SDK upgrade PR if that path is preferred, but the workaround gets touch data flowing today with zero risk to existing installs.

Test plan

  • On a Revo2Touch hand, pip install pyserial && python3 scripts/touch_sensor_pyserial.py --dual succeeds and logs touch enable + calibrate: ok for both hands.
  • Pressing any fingertip produces a normal_force reading ≥ 500 on the corresponding finger.
  • Releasing returns the reading to 0 within one poll interval.
  • On a Revo2Basic hand, the script runs without crashing (readings stay at 0).

🤖 Generated with Claude Code

The libbc_stark_sdk.so currently shipped via download-lib.sh is version
0.4.3, which hard-codes every touch-sensor API as "deprecated for current
firmware" and returns empty, even on Revo2Touch hardware where
modbus_get_device_info reports hardware_type=4.  Version 0.8.1 of the SDK
(shipped with unitreerobotics/brainco_hand_service) does support the
touch APIs and talks to the same hands correctly.

This PR adds a standalone workaround that sidesteps the SDK version
mismatch entirely: scripts/touch_sensor_pyserial.py talks the same
Modbus RTU commands the newer SDK sends, using only pyserial, and works
on any installed SDK version.  Verified on a Revo2Touch hand running
firmware 1.0.14.U — all 10 fingertip channels (thumb/index/middle/ring/
pinky × left+right) return a crisp 0-to-2500 normal_force reading when
pressed.

Also adds an FAQ entry (FAQ_en.md section 7) explaining the SDK-version
gotcha and both the "upgrade the .so" and "use the workaround" paths.

Register layout at address 4200 (30 x uint16, reverse-engineered by
time-aligning single-finger presses and cross-checked against what
libbc_stark_sdk 0.8.1 logs under TRACE):

  regs[0..14]  = 3 per finger, interleaved (normal_force,
                 tangential_force, tangential_direction)
  regs[15..24] = 2 per finger, interleaved (self_proximity
                 as u32 lo/hi halves)
  regs[25..29] = per-finger counter / status (not useful)

The firmware writes 0xFFFF as a "no data" sentinel on idle tangential
fields; the script masks those to 0.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant