Skip to content

Commit 9749c8e

Browse files
committed
doc clean
1 parent 6e1e50a commit 9749c8e

3 files changed

Lines changed: 367 additions & 98 deletions

File tree

README.md

Lines changed: 198 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -1,49 +1,62 @@
1-
# robot.cpp
1+
# Robot.cpp
22

3-
`robot.cpp` currently builds a robot model frontend around two engine-style
4-
runtimes:
3+
[中文](README_zh.md)
54

6-
- `src/models/smolvla`: SmolVLA runtime with `smolvla_engine.h`.
7-
- `src/models/pi0`: pi0 runtime with `pi0_engine.h`.
8-
- `src/models/model_factory.cpp`: selects a robotcpp model wrapper for
9-
`model-cli` and `model-server`.
10-
- `robot_server`: TCP protocol, server, and client examples.
11-
- `tools`: GGUF conversion, tensor mapping, and inspection utilities.
12-
- `eval`: LIBERO evaluation runners for LeRobot baselines and `model-server`.
5+
[Demo placeholder]
136

14-
Generated build directories, checkpoints, artifacts, and datasets should stay
15-
out of git under `build*/`, `ckpts/`, `artifacts/`, and `data/`.
7+
![1783392980125](image/README_zh/1783392980125.png)
168

17-
## Build
9+
Robot.cpp is a lightweight on-device robot model inference framework built on top of llama.cpp. It inherits llama.cpp's zero-dependency and lightweight philosophy: robot model inference can run without complex Python dependency setup or PyTorch environment configuration. This makes Robot.cpp especially useful for cross-platform deployment and edge devices where environment setup is often painful.
1810

19-
```sh
11+
The core concept in Robot.cpp is [`model-server`](robot_server/README.md), which provides the main unified model interface. In practice, you start `model-server`; it listens for robot inference requests, receives observations from the robot, runs the underlying model forward pass, and returns the generated action. To keep the system lightweight and dependency-free, the communication layer uses a custom TCP protocol.
12+
13+
For robot-side usage, this repository provides examples for both simulation and real hardware: LIBERO as a simulation template, and the low-cost SO-101 as a real-robot template. The project is organized around the following concepts:
14+
15+
* `model-client`: a client for communicating with `model-server`. It wraps the communication protocol and sends requests to `model-server`. We provide both C++ and Python clients.
16+
* `policy`: an abstraction layer that uses `model-client` and connects it to a specific robot or simulation system. A policy receives observations from the robot platform, processes them, sends them through `model-client`, and returns the final action output. This layer hides the communication details and is easier to use.
17+
* `platform`: a concrete robot platform responsible for sensor management and robot control.
18+
19+
We also provide two tools to support robot model development:
20+
21+
* [`hf2gguf`](tools/hf2gguf/README.md): converts safetensors checkpoints into the GGUF files used by this project.
22+
* [`quant`](tools/quant/README_zh.md): selectively quantizes arbitrary tensor groups in a model. Users only need to adjust a YAML plan to generate quantized GGUF files.
23+
24+
---
25+
26+
## Quick Start
27+
28+
```bash
29+
git clone https://github.com/Robot-cpp/robot.cpp
30+
cd robot.cpp
2031
git submodule update --init --recursive
21-
cmake -S . -B build -DROBOT_CPP_BUILD_ROBOT_SERVER=ON
22-
cmake --build build --target model-cli model-server
2332
```
2433

25-
`ROBOT_CPP_BUILD_ROBOT_SERVER` is the only project-level build option. The build
26-
no longer registers CTest targets or the old public shared C ABI.
34+
This section introduces three usage paths to help you quickly understand the repository:
2735

28-
## Checks
36+
* Starting `model-server` and connecting it to a minimal dummy `model-client`.
37+
* Using `model-server` in a simulation platform, using LIBERO as the example.
38+
* Using `model-server` on a real robot, using SO-101 as the example.
2939

30-
Install and run the local checks with:
40+
### Start model-server and connect a dummy client
3141

32-
```sh
33-
python -m pip install pre-commit ruff clang-format
34-
pre-commit install
35-
pre-commit run --all-files
36-
```
42+
We use SmolVLA GGUF files as the example for starting `model-server`.
43+
44+
#### Step 0: Download a GGUF model
45+
46+
Download a sample GGUF model from Hugging Face: [huggingface.co/rrobottt/smolvla-so101-fp32](https://huggingface.co/rrobottt/smolvla-so101-fp32)
3747

38-
The hook set follows the same shape as `llama.cpp`'s pre-commit setup, but is
39-
kept local and lightweight: Python fatal checks through `ruff`, and C/C++
40-
format checks through `clang-format`. GitHub Actions runs the same hooks on all
41-
tracked files in pushes and pull requests.
48+
#### Step 1: Start model-server
4249

43-
## SmolVLA Server
50+
There are two ways to start `model-server`.
4451

45-
```sh
46-
./build/bin/model-server \
52+
##### Option 1: Download a prebuilt binary
53+
54+
For several platforms and configurations, we provide prebuilt `model-server` binaries on the release page.
55+
56+
After downloading, run `model-server` like this:
57+
58+
```bash
59+
./model-server \
4760
--model-type smolvla \
4861
--llm /path/to/smolvla-llm-f32.gguf \
4962
--mmproj /path/to/mmproj-smolvla-f32.gguf \
@@ -53,68 +66,167 @@ tracked files in pushes and pull requests.
5366
--port 5555
5467
```
5568

56-
The helper scripts under `robot_server/shell/` wrap the same command for common
57-
local setups. Use `MODEL_TYPE=smolvla` or `MODEL_TYPE=pi0` with the Linux
58-
launchers when switching models.
69+
##### Option 2: Build locally
5970

60-
## pi0 Server
71+
For general local setups, we provide ready-to-use build-and-launch shells for three platforms. You can modify the environment variables inside the scripts, or override them directly with `export`. See [robot_server/README.md](robot_server/README.md) for details.
6172

62-
Converted pi0 checkpoints are expected as split GGUF components:
73+
| Backend | macOS | Linux | Windows |
74+
| ------- | ------------------------------------------------------- | -------------------------------------------------------- | ----------------------------------------------------------- |
75+
| CUDA | - | `robot_server/shell/launch_robot_server_linux_cuda.sh` | `robot_server/shell/launch_robot_server_windows_cuda.bat` |
76+
| CPU | `robot_server/shell/launch_robot_server_mac_cpu.sh` | `robot_server/shell/launch_robot_server_linux_cpu.sh` | `robot_server/shell/launch_robot_server_windows_cpu.bat` |
77+
| Metal | `robot_server/shell/launch_robot_server_mac_metal.sh` | - | - |
6378

64-
```sh
65-
GGUF_DIR=ckpts/pi0-libero-finetuned-v044/robotcpp-split
66-
MODEL=robotcpp-pi0-libero-finetuned-v044
79+
When startup succeeds, you should see:
6780

68-
./build/bin/model-server \
69-
--model-type pi0 \
70-
--vit "${GGUF_DIR}/${MODEL}.vit.gguf" \
71-
--mmproj "${GGUF_DIR}/${MODEL}.mmproj.gguf" \
72-
--llm "${GGUF_DIR}/${MODEL}.llm.gguf" \
73-
--tokenizer "${GGUF_DIR}/${MODEL}.tokenizer.gguf" \
74-
--state-gguf "${GGUF_DIR}/${MODEL}.state.gguf" \
75-
--action-decoder "${GGUF_DIR}/${MODEL}.action_decoder.gguf" \
76-
--host 127.0.0.1 \
77-
--port 5555
81+
```text
82+
[model-server] listening on 127.0.0.1:5555 model=smolvla
7883
```
7984

80-
## model-cli
81-
82-
`model-cli` uses the same robotcpp model wrappers as `model-server`, so CLI and
83-
server predictions share one runtime path. For pi0, pass image names that match
84-
the checkpoint metadata. The LIBERO v044 checkpoint expects two image views:
85-
86-
```sh
87-
GGUF_DIR=ckpts/pi0-libero-finetuned-v044/robotcpp-split
88-
MODEL=robotcpp-pi0-libero-finetuned-v044
89-
IMAGE0=agentview.png
90-
IMAGE1=eye_in_hand.png
91-
92-
./build/bin/model-cli \
93-
--model-type pi0 \
94-
--image "${IMAGE0}" \
95-
--image "${IMAGE1}" \
96-
--image-name observation.images.image \
97-
--image-name observation.images.image2 \
98-
--state "$(python3 -c 'print(",".join(["0"] * 32))')" \
99-
--task "pick up the fork" \
100-
--vit "${GGUF_DIR}/${MODEL}.vit.gguf" \
101-
--mmproj "${GGUF_DIR}/${MODEL}.mmproj.gguf" \
102-
--llm "${GGUF_DIR}/${MODEL}.llm.gguf" \
103-
--tokenizer "${GGUF_DIR}/${MODEL}.tokenizer.gguf" \
104-
--state-gguf "${GGUF_DIR}/${MODEL}.state.gguf" \
105-
--action-decoder "${GGUF_DIR}/${MODEL}.action_decoder.gguf"
85+
#### Step 2: Send one dummy request to model-server
86+
87+
After the server starts, it listens for requests. We provide a minimal example that sends a random observation request. You can use either Python or C++.
88+
89+
##### Minimal Python example
90+
91+
```bash
92+
pip install numpy
93+
python robot_client/examples/python/minimal_example.py
10694
```
10795

108-
Use repeated `--image` and `--image-name` arguments when a checkpoint expects
109-
multiple image views. Values are paired by order.
96+
##### Minimal C++ example
97+
98+
We provide a build-to-run example in `robot_client/shell/cpp_client_example.sh`. Adjust these environment variables as needed:
99+
100+
| Environment variable | Default | Purpose |
101+
| -------------------- | ---------------------------------------- | ----------------------------------------------------------------------- |
102+
| `ROBOT_CPP_ROOT` | unset; required | Repository root. |
103+
| `BUILD_DIR` | `${ROBOT_CPP_ROOT}/build_robot_client` | C++ client CMake build directory. |
104+
| `PORT` | `5555` | Server port used by the client. |
105+
| `BUILD_CLIENT` | `0` | Whether to force rebuild the client. Set to `1` to rebuild even if the binary already exists. |
106+
| `CMAKE_BIN` | `cmake` | CMake command path, useful for selecting a custom CMake binary. |
107+
108+
Then run:
109+
110+
```bash
111+
bash robot_client/shell/cpp_client_example.sh
112+
```
113+
114+
### Using model-server in simulation, using LIBERO as the example
115+
116+
See the [LIBERO simulation evaluation guide](eval/libero/README.md).
117+
118+
### Using model-server on real hardware, using SO-101 as the example
119+
120+
See the [SO-101 deployment guide](eval/lerobot_so101/README.md). A video tutorial is also planned (bilibili link).
121+
122+
---
123+
124+
## Performance
125+
126+
We benchmark Robot.cpp on several platforms. Each measurement uses 5 warmup runs and 100 loop runs. The reported latency is the average time from receiving the image, through preprocessing and forward inference, to producing a usable action chunk, measured in milliseconds. All state projectors remain in f32 precision.
127+
128+
For the LIBERO setting, the input contains two 256x256 images and an 8-dimensional state. For the SO-101 real-robot setting, the input contains one 224x224 image and a 6-dimensional state.
129+
130+
For SmolVLA preprocessing, we follow the official default setting: images are first resized to 512x512.
131+
132+
| Model | Mac M4 Pro (CPU) | Mac M4 Pro (Metal) | RTX 4090 | RTX 3060 | A100 | Jetson AGX Orin |
133+
| ---------------------- | ---------------: | -----------------: | -------: | -------: | ---: | --------------- |
134+
| smolvla@libero (bf16*) | 527 | 216 | 28 | | 43 | |
135+
| smolvla@libero (f32) | 577 | 236 | 32 | | 41 | |
136+
| smolvla@so-101 (bf16*) | 339 | 145 | 23 | | 35 | |
137+
| smolvla@so-101 (f32) | 396 | 158 | 24 | | 33 | |
138+
| pi0@libero (f32) | 1839 | 710 | 83 | | 79 | |
139+
| pi0@libero (bf16*) | 1954 | 635 | 57 | | 70 | |
140+
141+
> `bf16*`: on Mac, f16 results are used in place of bf16 because current Mac bf16 support is not ideal.
142+
143+
---
144+
145+
## Model Zoo
146+
147+
This section lists converted GGUF models that can be used directly with `model-server` for smoke tests and quick starts. For your own real-world scenarios, we recommend using [`hf2gguf`](tools/hf2gguf/README.md) to generate your own GGUF models. Different components can also use different precisions; in practice, the best precision choice is often component-specific. In our examples, the state projector always stays in f32, while the other GGUF files follow the listed precision. You can mix and match them to explore better accuracy/performance tradeoffs.
148+
149+
| Model | Benchmark | Precision | Link |
150+
| ------- | --------- | --------- | ----------------------------------------------------------------------- |
151+
| SmolVLA | SO-101 | bf16 | [smolvla-so101-bf16](https://huggingface.co/rrobottt/smolvla-so101-bf16) |
152+
| SmolVLA | SO-101 | f16 | [smolvla-so101-fp16](https://huggingface.co/rrobottt/smolvla-so101-fp16) |
153+
| SmolVLA | SO-101 | f32 | [smolvla-so101-fp32](https://huggingface.co/rrobottt/smolvla-so101-fp32) |
154+
| pi0 | LIBERO | bf16 | [pi-libero-bf16](https://huggingface.co/rrobottt/pi-libero-bf16) |
155+
| pi0 | LIBERO | f16 | [pi0-libero-f16](https://huggingface.co/rrobottt/pi0-libero-f16) |
156+
| pi0 | LIBERO | f32 | [pi0-libero-f32](https://huggingface.co/rrobottt/pi0-libero-f32) |
157+
158+
---
159+
160+
## Repository Layout
161+
162+
Key directories:
163+
164+
```text
165+
robot.cpp/
166+
├── src/
167+
│ ├── model-cli.cpp # Debug/smoke entrypoint for invoking the Model layer from the command line
168+
│ └── models/
169+
│ ├── model.h # Unified Model abstraction: predict / reset / type
170+
│ ├── model_factory.cpp # Creates concrete models from --model-type
171+
│ ├── ggml_backend.* # Shared ggml backend / buffer / scheduler abstractions
172+
│ ├── gguf_loader.* # Shared GGUF loading abstraction
173+
│ ├── smolvla/ # SmolVLA runtime implementation
174+
│ └── pi0/ # pi0 runtime implementation
175+
├── robot_server/
176+
│ ├── model-server.cpp # Persistent daemon entrypoint; listens for local TCP requests
177+
│ ├── protocol.* # Little-endian binary protocol
178+
│ ├── session.* / socket.* # Connections, packet I/O, and cross-platform socket wrappers
179+
│ ├── model_adapter.* # Glue between protocol observations and the Model layer
180+
│ ├── shell/ # macOS / Linux / Windows model-server launch scripts
181+
│ └── test/ # Tests and helper scripts
182+
├── robot_client/
183+
│ ├── cpp/ # C++ model-client
184+
│ ├── python/ # Python model-client
185+
│ ├── policy/ # Policy wrappers for robot platforms / simulations
186+
│ ├── examples/ # Minimal client examples
187+
│ └── shell/ # Client build and run scripts
188+
├── tools/
189+
│ ├── hf2gguf/ # Hugging Face checkpoint -> GGUF conversion tools
190+
│ └── quant/ # YAML-plan-based selective GGUF tensor quantization tool
191+
├── eval/
192+
│ ├── base_platform.py # Shared base class for real-robot platforms
193+
│ ├── libero/ # LIBERO simulation evaluation
194+
│ └── lerobot_so101/ # SO-101 real-robot scripts and examples
195+
└── third_party/
196+
├── llama.cpp/ # ggml / llama.cpp backend
197+
└── lerobot/ # LeRobot dependency or reference code
198+
```
199+
200+
---
201+
202+
## Extension and Contribution
203+
204+
Robot.cpp welcomes community contributions for new model runtimes, platform adapters, evaluation flows, model conversion tools, and performance optimization. We aim to keep the core inference framework lightweight, cross-platform, and easy to reproduce, while allowing different robot models and platforms to connect through a unified interface.
205+
206+
If you want to extend this project, start with these documents:
207+
208+
* [How to add a new model](src/readme_zh.md)
209+
* How to add a new platform: [real robot](eval/README.md), [simulation](eval/HOW_TO_ADD_NEW_SIM.md).
210+
211+
Issues and PRs are welcome. For larger model-architecture changes, protocol changes, or platform abstraction changes, we recommend opening an issue first to align on the interface boundary.
212+
213+
---
214+
215+
## License
216+
217+
Robot.cpp source code is released under the Apache License, Version 2.0. See [LICENSE](LICENSE) for the full license text.
218+
219+
This repository also includes third-party open-source components, each under its own license. See the license files under `third_party/` for details.
220+
221+
---
222+
223+
## Acknowledgements
110224

111-
## Evaluation
225+
Robot.cpp's design and implementation benefit from several excellent open-source projects:
112226

113-
LIBERO evaluation docs: [English](eval/libero/README.md) /
114-
[中文](eval/libero/README_zh.md).
227+
* [llama.cpp](https://github.com/ggerganov/llama.cpp): provides lightweight local inference, the GGML/GGUF ecosystem, and cross-platform backend foundations. This project continues building robot model inference capabilities on top of its engineering philosophy and low-level runtime.
228+
* [LeRobot](https://github.com/huggingface/lerobot): provides reference implementations for robot data, policy training, and real-robot integration. The SO-101 real-robot example and parts of the evaluation flow in this project are inspired by the LeRobot ecosystem.
229+
* [LIBERO](https://github.com/Lifelong-Robot-Learning/LIBERO): provides robot simulation tasks and evaluation benchmarks. The LIBERO simulation evaluation flow in this project is based on its task environments and benchmark design.
230+
* [OpenPI](https://github.com/Physical-Intelligence/openpi): provides the pi0 policy model and related open-source implementation. The pi0 runtime, conversion, and evaluation work in this project references OpenPI's model design.
115231

116-
- One-command model-server LIBERO eval:
117-
`bash eval/libero/scripts/run_model_server.sh`
118-
- LeRobot baseline: `python -m eval.libero.runners.run_lerobot`
119-
- LeRobot policy latency: `python -m eval.libero.runners.latency_lerobot`
120-
- model-server rollout: `python -m eval.libero.runners.run_model_server`
232+
Thanks to these projects and communities for their contributions to robot learning and on-device inference.

0 commit comments

Comments
 (0)