OpenArm 101 — SocketCAN Setup, ROS2 & Data Collection Guide
Complete guide to connecting the OpenArm 101 over SocketCAN, configuring control profiles, collecting imitation learning data, and deploying the cloud agent for platform-based teleoperation.
1. Overview
The OpenArm 101 is a 7-DOF, human-scale robot arm built for data-driven manipulation research. It uses SocketCAN — the standard Linux CAN-bus interface — rather than proprietary USB protocols, making it compatible with any Linux machine that has a CAN adapter. Its modular aluminum frame, M6 mounting grid, and anthropomorphic kinematics make it a natural fit for imitation learning pipelines that rely on natural human demonstrations.
Key differentiators compared to other research arms: SocketCAN for broad Linux compatibility, three named safety profiles (safe / slow / normal) to de-risk initial bring-up, 8 Hz real-time telemetry over WebSocket, gravity compensation and impedance control out of the box, and a one-click cloud agent (run_cloud_openarm_agent.sh) that connects the arm to the Fearless Platform in a single command.
CAD files are provided as OpenArm_v1.1_follower.STEP and OpenArm_v1.1_leader.STEP. The arm is sold and supported in Palo Alto at the Silicon Valley Robotics Center.
2. Hardware Specs
| Property | Value |
|---|---|
| Degrees of Freedom | 7 DOF per arm |
| Reach | 633 mm (human-scale) |
| Weight (per arm) | ~5.5 kg |
| Rated Payload | 4.1 kg |
| Peak Payload | 6.0 kg |
| Frame | Modular aluminum, anthropomorphic structure |
| Mounting | Uniform M6 grid |
| Communication | SocketCAN (standard Linux CAN-bus) |
| Default CAN interface | can0 (configurable via CAN_IFACE) |
| CAN FD | Disabled by default (CANFD_FLAG=--no-canfd) |
| Telemetry rate | 8 Hz (configurable via TELEMETRY_HZ) |
| Control profiles | safe / slow / normal |
| Control modes | Position, velocity, impedance, force; gravity compensation |
| Simulation | MuJoCo, Isaac Sim |
| CAD | OpenArm_v1.1_follower.STEP, OpenArm_v1.1_leader.STEP |
| OS requirement | Ubuntu Linux with SocketCAN support |
3. Quick Start
From unboxing to a live platform session in four steps:
-
Install the OpenArm CAN libraries.
# Ubuntu: add the official PPA and install sudo add-apt-repository -y ppa:openarm/main sudo apt update sudo apt install -y libopenarm-can-dev openarm-can-utils # Python bindings (for SDK use) pip install openarm-can
-
Configure the SocketCAN interface.
# Bring up can0 using the OpenArm utility openarm-can-configure-socketcan can0 # Verify the interface is UP ip link show can0
For a second arm, repeat withcan1. -
Create a session on the platform and launch the agent. Open platform.roboticscenter.ai → Teleop → Create New Session. Copy the session ID, then:
cd openarm-agent # One-click launcher (installs requirements automatically) ./run_cloud_openarm_agent.sh YOUR_SESSION_ID -
Control via the platform teleop panel. Open the session URL in your browser. Use the on-screen buttons or WASD+QE keyboard controls to command the arm. The arm moves at the
safeprofile by default.
python openarm_agent.py --backend wss://fearless-backend-533466225971.us-central1.run.app --session YOUR_SESSION_ID --mock
4. SDK Integration
The RoboticsCenter SDK wraps OpenArm under the unified platform session model. Install and connect in two commands:
pip install roboticscenter rc connect --device openarm_101 --port can0
For direct Python integration using the openarm-can library:
import openarm_can # Connect to the arm on can0 arm = openarm_can.OpenArm(interface="can0") arm.connect() arm.set_profile("safe") # safe | slow | normal # Read current joint state state = arm.get_joint_angles() print(state) # list of 7 angles in radians # Command a joint position target arm.set_joint_angles([0.0, 0.2, 0.0, -0.5, 0.0, 0.3, 0.0]) arm.disconnect()
Dual-arm (bimanual) one-click launch
For a bimanual setup with two arms on can0 and can1:
cd openarm-agent ./run_cloud_openarm_dual.sh YOUR_SESSION_ID # Optional environment variables: # BASE_NODE_ID=my-dual-openarm # PROFILE=safe|slow|normal
Environment variable reference
| Variable | Default | Description |
|---|---|---|
CAN_IFACE | can0 | SocketCAN interface name |
BACKEND_URL | production WSS URL | Override backend WebSocket URL |
NODE_ID | <hostname>-openarm | Node identifier shown in platform UI |
TELEMETRY_HZ | 8 | Joint telemetry reporting frequency |
CANFD_FLAG | --no-canfd | Set to empty string to enable CAN FD |
OPENARM_PROFILE | safe | Motion profile: safe, slow, or normal |
FEARLESS_TOKEN | — | Auth token required when platform auth is enabled |
5. Control Profiles
OpenArm ships with three named motion profiles that limit joint velocities and torques at the firmware level. Always start with safe when bringing up a new arm or working in a shared space.
| Profile | Use case | Notes |
|---|---|---|
safe |
Initial hardware bring-up, crowded workspaces, human-in-the-loop teleop | Lowest velocity and torque limits. Recommended default for all new setups. |
slow |
Demonstration recording, development testing | Middle tier. Suitable once the workspace is validated and collision zones are known. |
normal |
Trained policy execution, production data collection | Full-speed motion. Use only after validating the full workspace in safe and slow modes. |
Set the profile at launch time:
OPENARM_PROFILE=slow ./run_cloud_openarm_agent.sh YOUR_SESSION_ID
Or at runtime via the SDK:
arm.set_profile("normal")
safe mode before switching to normal. The normal profile disables software velocity damping — unexpected policy outputs can cause rapid arm movement.
6. ROS2 Integration
OpenArm has native ROS2 support with a complete URDF/XACRO model, ros2_controllers integration, and a MoveIt2 planning group configuration. The software stack provides bilateral teleoperation with force feedback, gravity compensation, impedance control, and force control modes.
# 1. Install CAN libraries (see Quick Start step 1) # 2. Configure SocketCAN openarm-can-configure-socketcan can0 # 3. Clone the OpenArm ROS2 driver (adjust to your workspace) cd <ros2_ws>/src git clone https://github.com/enactic/openarm_ros2.git # 4. Build cd <ros2_ws> colcon build --packages-select openarm_ros2 source install/setup.bash # 5. Launch the driver (publishes /joint_states and accepts /joint_commands) ros2 launch openarm_ros2 openarm.launch.py can_interface:=can0 # 6. Launch MoveIt2 planning ros2 launch openarm_moveit_config openarm_moveit.launch.py
Simulation (MuJoCo & Isaac Sim)
OpenArm's calibrated simulation models mirror the real arm's kinematics, dynamics, and actuation limits. State definitions and action spaces are identical between sim and real, enabling mixed-domain training and policy transfer without reconfiguration.
# MuJoCo — launch sim with the OpenArm model python -m mujoco.viewer --mjcf=openarm_v1.1.xml # Isaac Sim — use the provided USD asset # (contact SVRC for Isaac Sim asset access)
LeRobot integration
OpenArm is also compatible with the LeRobot data collection pipeline. Use the openarm_agent.py to record episodes in LeRobot HDF5 format:
# Record 10 episodes via LeRobot CLI (requires LeRobot + openarm-can installed)
lerobot-record \
--robot.type=openarm_101 \
--robot.can_interface=can0 \
--robot.profile=slow \
--dataset.repo_id=$USER/openarm_dataset \
--dataset.num_episodes=10 \
--dataset.episode_time_s=30 \
--dataset.single_task="Pick and place task."
7. Data Collection
The openarm_agent reports the following telemetry per frame during an active session or recording:
| Signal | Type | Description |
|---|---|---|
| Joint angles | float[7] | Current angle per joint in radians, reported at 8 Hz |
| Estimated motor states | dict | Per-motor velocity and current estimates from the CAN bus |
| Node network info | dict | CAN node IDs, bus load, and message latency |
| Robot status | str | Execution state: idle / executing / fault |
| Session ID | str | Platform-assigned session identifier |
| Timestamp | float64 | Unix timestamp with millisecond resolution |
To start a recording session, create a session in the platform, launch the agent, then press the record button in the teleop panel or use the SDK:
from roboticscenter import OpenArm101
arm = OpenArm101.connect(can_interface="can0", profile="slow")
print(f"Session: {arm.session_url}")
with arm.record_episode(task="grasp cup") as episode:
# Teleoperate or run a script here
# Episode is saved and uploaded when the context exits
pass
Recorded episodes appear in the platform Episode Browser immediately after the recording session ends. Each episode includes joint angle trajectories, robot status events, and a manifest with task metadata.
8. Troubleshooting
| Symptom | Likely cause | Fix |
|---|---|---|
| CAN interface not found | USB-CAN adapter not recognized or driver not loaded | Run ip link show to list all interfaces. If can0 is missing, check that your USB-CAN adapter is plugged in and the kernel module is loaded: sudo modprobe can_dev. |
| Telemetry not reporting | CAN bus not configured or arm not powered | Run openarm-can-configure-socketcan can0 and confirm ip link show can0 shows UP. Verify the arm's power LED is on. |
| Arm moves unexpectedly fast | Profile set to normal in an unvalidated workspace |
Switch to OPENARM_PROFILE=safe and re-validate the full workspace before re-enabling normal. |
| Policy execution inconsistent | Mismatch between sim and real joint limits | Verify the MuJoCo or Isaac Sim model version matches the hardware version (v1.1). Re-check the joint angle offsets in the URDF against the physical arm's zero configuration. |
| Platform WebSocket disconnects | Network instability or backend timeout | The agent auto-reconnects. If reconnects fail, restart the agent with the same session ID — the session persists and all previously recorded episodes remain accessible. |
ip link show can0 and the agent log (set LOG_LEVEL=debug before re-running). Same-day support is available in Palo Alto.