Record/replay studio, manual recorder kit, and new-robot install tooling

Dashboard (web/hand_web.py)
- Record/replay panel driving g1_record_replay.py as a pty child: take library
  (replay/download/duplicate/rename/delete/upload/delete-all), pause & resume,
  and in-take key buttons that grey out in the --fingers modes the recorder
  ignores (measured: in touch mode the keys change nothing at all).
- /api/restart is container-aware: it kills inspire_g1 and lets the supervisor
  relaunch it. It used to run manage.sh, which started a SECOND inspire_g1
  beside the supervised one - two writers on one RS-485 bus - and never
  returned.
- Shape/combo libraries take a .bak on every write, with an undo button. Both
  files are rewritten in full, so deleting the last entry was unrecoverable.

recorder/
- The recorder lives in this project now: one source of truth for the CLI and
  the dashboard, with pause/resume added to replay.
- record.sh picks a runtime by itself (a python with the SDK, the vendored SDK,
  or the inspire-hand container). bundle.sh packs a ~340KB portable kit.

tools/
- preflight.sh: read-only readiness report for a new robot (hardware, docker,
  build prerequisites, per-robot settings) ending in an install-path verdict.
- fetch_deps.sh: stage build dependencies, verifying the libs are aarch64.
- export_ui.py: regenerate an embedding app's vendored copy of the UI.

docker/
- build_image.sh resolves its dependencies from several layouts: deps/ inside
  the project, /usr/local, a source install prefix, or a ROS2 colcon workspace
  (where the idl headers live when /usr/local has none).
- web/ is copied in the last layer, so dashboard edits skip the C++ rebuild.
- restart=always, and start.sh always builds so an edit cannot silently run a
  stale image.

deps/unitree_sdk2 is vendored so a robot that has never seen the SDK can build.
Docs: README quickstart + embedding notes, SETUP_G1 corrected (that udev rule
stopped creating /dev/inspire_* symlinks a while ago), ROBOT_README describing
a live install.
This commit is contained in:
kassam 2026-08-28 20:27:28 +04:00
parent 6b850c7826
commit 2a78f1b609
907 changed files with 166343 additions and 32 deletions

View File

@ -29,8 +29,29 @@ container, waits until the dashboard actually answers, and prints the URL:
http://10.255.254.88:8088 http://10.255.254.88:8088
``` ```
### On a NEW robot, check first
```bash
./tools/preflight.sh
```
Changes nothing; prints PASS/MISS for hardware, Docker, the build prerequisites and
the per-robot settings that misbehave *silently*, then tells you which install path
is open. Two paths:
- **Bring the image** (no SDK, no internet, no compile on the target):
`docker save inspire-hand:latest | gzip > inspire-hand.tar.gz` → copy →
`gunzip -c inspire-hand.tar.gz | docker load`
- **Build there** — needs `~/unitree_sdk2`, CycloneDDS in `/usr/local` (including the
`idl` headers) and internet. `build_image.sh` pulls those from the host.
Then, once per robot, give the LEFT hand RS-485 id 2 —
`docker exec inspire-hand ./build/hand_setid <left-port> 1 2`. After that the hands are
identified by id rather than USB path, so no pin can swap them. See [SETUP_G1.md](SETUP_G1.md).
| command | does | | command | does |
|---|---| |---|---|
| `./tools/preflight.sh` | can this robot run it, and what's missing |
| `./start.sh` | start (builds the image if missing) | | `./start.sh` | start (builds the image if missing) |
| `./start.sh stop` | stop the container | | `./start.sh stop` | stop the container |
| `./start.sh restart` | stop + start | | `./start.sh restart` | stop + start |
@ -38,6 +59,10 @@ container, waits until the dashboard actually answers, and prints the URL:
| `./start.sh logs` | follow the container log | | `./start.sh logs` | follow the container log |
| `./start.sh rebuild` | force an image rebuild, then start | | `./start.sh rebuild` | force an image rebuild, then start |
**It does not start by itself.** There is no restart policy and no systemd unit — a rebooted
robot comes up with the hands free, and this stack takes them only when you run `./start.sh`.
Stop it with `./start.sh stop`.
**Run it on the robot.** Run it on the workstation and it rsyncs this folder to the robot **Run it on the robot.** Run it on the workstation and it rsyncs this folder to the robot
and runs itself there — the hands, the DDS link to the arm and Docker are all on the robot, and runs itself there — the hands, the DDS link to the arm and Docker are all on the robot,
so there is nothing to run locally. Override the target with `ROBOT=unitree@10.255.254.88`. so there is nothing to run locally. Override the target with `ROBOT=unitree@10.255.254.88`.
@ -97,6 +122,20 @@ while watching `rt/inspire/cmd`:
The panel greys out keys the current mode ignores and says why, so a dead button is never a The panel greys out keys the current mode ignores and says why, so a dead button is never a
mystery. Note `[` and `;` also un-park thumb_rot, while `o` returns it to tucked. mystery. Note `[` and `;` also un-park thumb_rot, while `o` returns it to tucked.
### Without the dashboard
The same script runs from a terminal — see [recorder/README.md](recorder/README.md):
```bash
cd recorder
./record.sh doctor # which runtime it will use
./record.sh record --output wave --seconds 20
./bundle.sh # pack it to carry elsewhere (~2 MB)
```
`record.sh` picks a runtime for you (a python with the SDK, the vendored SDK, or the
`inspire-hand` container) so the CLI still works when Docker or the dashboard is down.
### The take library ### The take library
Per take: **▶ replay · ⬇ download · ⧉ duplicate · ✎ rename · 🗑 delete**, plus **⬆ Upload** Per take: **▶ replay · ⬇ download · ⧉ duplicate · ✎ rename · 🗑 delete**, plus **⬆ Upload**
@ -163,8 +202,17 @@ process backgrounded by a non-interactive shell inherits `SIG_IGN`, and it survi
running at once. `./start.sh restart` re-runs `ClearError`. Still stuck: power-cycle the running at once. `./start.sh restart` re-runs `ClearError`. Still stuck: power-cycle the
hands (24 V). hands (24 V).
**"Port drift" warning** — the service opened different ttys than are live now; the CH340 **"Port drift" warning** — the service opened different ttys than are live now. Harmless in
adapters re-enumerate on the hub. Restart. itself: `inspire_g1` pins each hand by USB **path**, not by ttyUSB number, so left/right never
swap. The churn comes from a card reader (`05e3:0749`) sharing the hands' hub and
power-cycling ~851×/hour with no card in it. Stop it for good (needs root, once):
```bash
sudo cp udev/99-inspire-hub-cardreader.rules /etc/udev/rules.d/ && sudo udevadm control --reload
for d in /sys/bus/usb/devices/*/; do \
[ "$(cat $d/idVendor 2>/dev/null)" = "05e3" ] && [ "$(cat $d/idProduct 2>/dev/null)" = "0749" ] \
&& echo 0 | sudo tee $d/authorized; done
```
**A finger reads as dead (0 current, no movement)** — its force-sensor zero has drifted past **A finger reads as dead (0 current, no movement)** — its force-sensor zero has drifted past
the grip-force limit, so the RH56 refuses to drive it. `inspire_g1` measures the resting the grip-force limit, so the RH56 refuses to drive it. `inspire_g1` measures the resting
@ -192,6 +240,25 @@ Docker specifics: [docker/README.md](docker/README.md).
--- ---
## Embedding the dashboard elsewhere
Sanad's **Hands** tab serves a code copy of this UI with every `/api/` rewritten to
`/api/hands/`, and proxies those calls back to `:8088`. A hand-extracted copy goes stale
silently, so regenerate it from the source instead:
```bash
# after any dashboard change
python3 tools/export_ui.py --prefix hands --out <sanad>/Sanad/dashboard/static/hands.html
# or just check whether a copy is current (exit 1 if stale)
python3 tools/export_ui.py --prefix hands --check <sanad>/Sanad/dashboard/static/hands.html
```
The embedding app needs `network_mode: host` (or an explicit `SANAD_HANDS_BASE`) to reach
`127.0.0.1:8088`, and this stack must be running — see the start note above.
---
## Service protocol (upstream) ## Service protocol (upstream)
Send `unitree_go::msg::dds::MotorCmds_` to `rt/inspire/cmd`; read Send `unitree_go::msg::dds::MotorCmds_` to `rt/inspire/cmd`; read

244
ROBOT_README.md Normal file
View File

@ -0,0 +1,244 @@
# Inspire RH56 hands — what is installed on this robot
Everything for the two Inspire RH56 hands: the RS-485 service, the DDS bridge, the web
dashboard, and the arm+hand record/replay studio. All of it runs in **one Docker container**.
Installed 2026-08-26 on the G1's Jetson (PC2), Ubuntu 20.04 / aarch64.
| | |
|---|---|
| Dashboard | `http://192.168.123.164:8088` (ethernet) · `http://10.255.254.68:8088` (wifi) |
| Project | `~/DFX_inspire_service` |
| Manual recorder kit | `~/manual_recorder` |
| Your data (survives rebuilds) | `~/hand_data` — shapes, combos, `DataG1/` takes |
| Image | `inspire-hand:latest`, built on this robot |
| Canonical source | workstation: `Project/G1/DFX_inspire_service` |
---
## 1. Run it
```bash
cd ~/DFX_inspire_service
./start.sh # build if needed → run → wait until it answers → print the URL
./start.sh status # running? serving what? hands alive?
./start.sh stop
./start.sh logs # follow the container log
./start.sh rebuild # force an image rebuild
```
It starts on boot (`--restart unless-stopped`). To stop that: change `--restart no` in
`docker/run.sh` and re-run `./start.sh`.
`./start.sh` always rebuilds first — the layer cache makes that a second or two, and it means
an edited dashboard can never keep running the old image.
---
## 2. What runs where
```
inspire_g1 RS-485 → both hands, publishes rt/inspire/state (supervised, auto-restarts)
hand_bridge TCP 127.0.0.1:7799 → rt/inspire/cmd + force-follow
hand_web.py the dashboard on :8088, and it spawns the recorder
```
All three inside the `inspire-hand` container, started by `docker/start.sh`. Container paths:
`/opt/hand` (service + dashboard), `/opt/recorder` (recorder + `DataG1`).
Flags that matter: `--network host` (DDS needs it), `--privileged -v /dev:/dev` (the CH340
adapters re-enumerate), `-v ~/hand_data:/opt/hand/data`, `-v ~/hand_data/DataG1:/opt/recorder/DataG1`.
---
## 3. The dashboard
| card | what it does |
|---|---|
| Fingers | 12 sliders, presets, save/load named shapes |
| Force follow | press a fingertip and it closes under your hand — the RH56 is not back-drivable, so this admittance loop is the only way to shape it by hand |
| Joint tracker | angle traces + force, current, force limit, temperature, ERROR/STATUS |
| Diagnostics | live read-back + close→open self-test, per hand |
| Read back | copy the hand's pose into the sliders |
| Arm + hand combo | built-in arm actions fused with a hand pose ⚠ arm moves |
| Record / replay | record the arm + hand, replay, manage the library ⚠ arm moves |
| Library | manage saved shapes and combos (with ↺ undo) |
### Record / replay
A take holds the arms ~3 s then goes **limp** — have hold of the arm before that. Fingers
cannot be posed by hand, so drive them with the in-take keys or your saved shapes. At the end
the recorder offers a preview (⚠ replays it — the arm moves) and then a save; both are
answered in the panel. **Stop** interrupts cleanly (arm goes home, then releases) — it does
not kill. Replay has **⏸ Pause / ▶ Resume**; a pause holds the frame rather than dropping the
arm.
In-take keys: `o`/`c` both open/close · `[` `]` right · `;` `'` left · `1`-`9` saved shapes ·
`f` arm/disarm follow. Whether they do anything depends on the mode:
| `--fingers` | keys | records |
|---|---|---|
| `touch` *(default)* | **ignored** — the hand holds the rest pose | how far a finger closes, from how hard you press |
| `position` | drive the hand for real | the measured angle |
| `external` | ignored — no hand commands sent | the angle the sliders reach |
| `follow` | only `f` and the shape keys | the angle you push a finger into |
The panel greys out keys the current mode ignores.
Take library: **▶ replay · ⬇ download · ⧉ duplicate · ✎ rename · 🗑 delete**, plus **⬆ Upload**
and **🗑 Delete all**. `arm_home.jsonl` is hidden and protected — it is the home pose every
take returns through, not a recording.
---
## 4. Without the dashboard (the backup plan)
The same script, from a terminal. Installed at `~/manual_recorder`:
```bash
cd ~/manual_recorder/recorder
./record.sh doctor # which runtime it will use
./record.sh record --output wave --seconds 20
./record.sh replay --input wave --speed 0.5
```
`record.sh` finds a runtime by itself — a python that can import `unitree_sdk2py`, the
vendored SDK, or (here) the **container**, which has the SDK baked in. `DataG1` is symlinked
to `~/hand_data/DataG1`, so CLI takes and dashboard takes are the same library.
Raw equivalent:
```bash
docker exec -it -w /opt/recorder inspire-hand python3 g1_record_replay.py eth0 \
record --output wave --seconds 20
```
`-it` matters — without a TTY the in-take keys and pause do not work.
Carry it elsewhere: `./bundle.sh``manual_recorder_<date>.tar.gz` (~340 KB), or
`--with-takes` to include recordings.
---
## 5. Per-robot state — read this
**Hands are identified by USB path, not by id.** Both answer at RS-485 id 1, so
`INSPIRE_RIGHT_PATH=1-2.2.1.1` in `docker/run.sh` decides which is which:
```
RIGHT = /dev/ttyUSB1 (usb 1-2.2.1.1)
LEFT = /dev/ttyUSB0 (usb 1-2.2.3)
```
Move an adapter to another socket and left/right silently swap. The permanent fix, once:
```bash
# confirm ttyUSB0 really is the LEFT hand first — this writes a permanent id
docker exec inspire-hand ./build/hand_setid /dev/ttyUSB0 1 2
```
After that identity is `id 1 = right, id 2 = left`, immune to replugs and hub changes.
**Force-sensor zeros have drifted** on both hands. `inspire_g1` measures the resting offset at
startup and raises that hand's grip limit so the affected fingers do not read as dead — but
touch-mode recording thresholds off exactly that signal, so light presses read wrong. The real
fix is re-zeroing with the hands unloaded.
**A card reader (`05e3:0749`) shares the hands' USB hub** and power-cycles constantly with no
card in it, which re-enumerates the branch and shuffles the `ttyUSB` numbers. Stop it for good:
```bash
./start.sh usbfix # installs a udev rule + deauthorizes it (asks for your password)
```
---
## 6. Changes made to this robot during install
| change | why | revert |
|---|---|---|
| `unitree` added to the `docker` group | every docker call was permission-denied | `sudo gpasswd -d unitree docker` |
| wifi radio unblocked, joined `BusinessPro_TP_5G` (`10.255.254.68`) | robot was ethernet-only | `sudo nmcli radio wifi off` |
| wifi route metric → 50 | `eth0` held the default route, so internet went out the robot-internal link and died; the in-image `pip` build needs internet | `sudo nmcli con mod BusinessPro_TP_5G ipv4.route-metric -1` |
`eth0`'s own configuration was not touched — robot-internal traffic is unaffected.
---
## 7. Rebuilding / redeploying
Workstation is canonical. Push and restart:
```bash
# from the workstation
rsync -az --exclude build/ Project/G1/DFX_inspire_service/ unitree@192.168.123.164:~/DFX_inspire_service/
ssh unitree@192.168.123.164 'cd ~/DFX_inspire_service && ./start.sh'
```
`./start.sh` run *from* the workstation does the same thing by itself (it rsyncs and re-runs
over SSH). `ROBOT=unitree@10.255.254.68 ./start.sh` targets the wifi address.
### How the image was built here
This robot had no `~/unitree_sdk2` and no `idl` headers in `/usr/local`, so the build used:
- `deps/unitree_sdk2` — shipped inside the project
- `/usr/local/include` — its CycloneDDS C/C++ headers and libs
- `~/cyclonedds_ws/install/cyclonedds/include/idl` — the idl headers, from its ROS2 colcon
workspace (a plain C++ install leaves those out, and the in-image `pip cyclonedds` build
needs them)
`./tools/preflight.sh` reports all of this and says which install path is open.
For a robot with none of it, carry the image instead:
```bash
docker save inspire-hand:latest | gzip > inspire-hand.tar.gz # here
gunzip -c inspire-hand.tar.gz | docker load # there
```
---
## 8. Troubleshooting
**`service=false`, `ports=none`** — no `/dev/ttyUSB*`. Check both CH340 adapters are in and
the hands have 24 V. `lsusb | grep 1a86` should list two. The supervisor starts `inspire_g1`
within ~3 s of them appearing.
**Fingers do not move (thumb might)** — usually a latched actuator fault from two `inspire_g1`
running at once. Press **Restart** in the dashboard (re-runs `ClearError`); still stuck,
power-cycle the hands (24 V).
**A finger reads as dead (0 current, no movement)** — its force-sensor zero drifted past the
grip limit, so the RH56 refuses to drive it. Startup raises the limit; the log names the
fingers.
**"Port drift" warning** — the ttys renumbered. Harmless (hands are pinned by USB path); the
card reader is the cause — see `usbfix` above.
**`rt/inspire/state` reads all zeros** — cosmetic; the CH340s echo their own TX, so read-back
is unreliable. Commands are unaffected.
**Two `inspire_g1` instances** — they collide on the RS-485 bus. `docker/run.sh` kills
host-native copies before starting. Kill with `pkill -x inspire_g1`, never `pkill -f`.
**Recorder says "not found"** — the image was built without `recorder/`. `./start.sh rebuild`.
---
## 9. Safety
- A take makes the **arms go limp** after ~3 s. Be holding the arm.
- **Replay and preview move the arm** through the whole recording.
- Never run a CLI take while the dashboard has one going — two writers on the same topics.
- Do not run the native `manage.sh` path while the container is up, for the same reason.
---
## 10. Removing it
```bash
./start.sh stop
docker rmi inspire-hand:latest
rm -rf ~/DFX_inspire_service ~/manual_recorder # ~/hand_data holds your takes — keep it
```

View File

@ -35,16 +35,32 @@ cd ~/DFX_inspire_service
./build.sh # -> build/inspire_g1, inspire_h1, hand_example ./build.sh # -> build/inspire_g1, inspire_h1, hand_example
``` ```
## 2. Stable serial names + no-sudo access (one-time, needs sudo) ## 2. Serial access + telling the two hands apart (one-time)
Both hand adapters are CH340s with identical USB serial, so we pin names by Both adapters are CH340s reporting the **same** USB serial, so there is nothing
physical port and grant access via udev: intrinsic to key on. Two separate problems, two separate answers:
**Access.** The udev rule grants `0666` to any CH340 tty — it does **not** create
`/dev/inspire_*` symlinks any more (per-port symlinks broke whenever the adapters
moved to a different hub socket). Only needed for the native path; the container
runs privileged with `/dev` mounted and does not care:
```bash ```bash
sudo cp ~/DFX_inspire_service/udev/99-inspire-hands.rules /etc/udev/rules.d/ sudo cp ~/DFX_inspire_service/udev/99-inspire-hands.rules /etc/udev/rules.d/
sudo udevadm control --reload-rules && sudo udevadm trigger sudo udevadm control --reload-rules && sudo udevadm trigger
ls -l /dev/inspire_right /dev/inspire_left # both should now exist ls -l /dev/ttyUSB* # two nodes, world-writable
``` ```
`inspire_g1.cpp` opens `/dev/inspire_right` + `/dev/inspire_left`.
Mapping (corrected after live test): right → USB port `1-2.2.1.1`, left → `1-2.2.3`. **Identity.** `inspire_g1` resolves which tty is which hand, best first:
1. **RS-485 id**`id 1 = right, id 2 = left`. Wiring-independent and permanent;
immune to replugs, hub changes and enumeration order. Set it once per robot:
```bash
docker exec inspire-hand ./build/hand_setid <left-hand-port> 1 2
```
2. `INSPIRE_RIGHT_PATH` / `INSPIRE_LEFT_PATH` — pin by physical USB socket
(`run.sh` ships `1-2.2.1.1`, which is **this** robot's topology).
3. USB path order — the fallback, and the one that can silently swap the hands
on unfamiliar hardware.
On a new robot, do (1). Then (2) and (3) stop mattering.
## 3. Run + test ## 3. Run + test
```bash ```bash

View File

@ -0,0 +1,35 @@
FROM ubuntu:20.04
ENV TZ=Asia/Shanghai
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
ENV DEBIAN_FRONTEND=noninteractive
USER root
# install zsh and oh-my-zsh
RUN apt update && apt-get install -y git wget zsh && \
wget https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh && chmod +x install.sh
RUN ./install.sh
RUN git clone https://github.com/zsh-users/zsh-autosuggestions.git ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-autosuggestions && \
apt install zsh-syntax-highlighting
# configure zsh
RUN echo 'export ZSH=$HOME/.oh-my-zsh' >> ~/.zshrc && \
echo 'ZSH_THEME="ys"' >> ~/.zshrc && \
echo 'plugins=(git zsh-autosuggestions)' >> ~/.zshrc && \
echo 'source $ZSH/oh-my-zsh.sh' >> ~/.zshrc && \
echo 'source /usr/share/zsh-syntax-highlighting/zsh-syntax-highlighting.zsh' >> ~/.zshrc
RUN chsh -s /bin/zsh
# install build tools
RUN apt-get install -y build-essential gcc-9 g++-9 gdb cmake ninja-build
RUN update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-9 100 \
&& update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-9 100
# install libraries
RUN apt-get install -y libyaml-cpp-dev libeigen3-dev
WORKDIR /workspace
CMD ["zsh"]

View File

@ -0,0 +1,29 @@
{
"name": "Existing Docker Compose (Extend)",
"dockerComposeFile": [
"docker-compose.yml"
],
"service": "devcontainer",
"workspaceFolder": "/workspace",
"customizations": {
"vscode": {
"extensions": [
"gitlab.gitlab-workflow",
"llvm-vs-code-extensions.vscode-clangd",
"xaver.clang-format",
"ms-vscode.cmake-tools",
"zxh404.vscode-proto3",
"donjayamanne.githistory",
"mhutchie.git-graph",
"matepek.vscode-catch2-test-adapter",
"ryanluker.vscode-coverage-gutters",
"donjayamanne.python-extension-pack",
"adam-bender.commit-message-editor",
"axetroy.vscode-changelog-generator",
"vsliveshare.vsliveshare",
"bierner.markdown-mermaid",
"vadimcn.vscode-lldb"
]
}
}
}

View File

@ -0,0 +1,25 @@
version: '3'
services:
devcontainer:
volumes:
- ..:/workspace:cached
- /tmp/.X11-unix:/tmp/.X11-unix:rw
- /mnt/wslg:/mnt/wslg
- /root/.gazebo/models/:/root/.gazebo/models/
- /var/run/docker.sock:/var/run/docker.sock
- $HOME/.Xauthority:/tmp/.Xauthority:rw
environment:
- DISPLAY=${DISPLAY}
- XAUTHORITY=/tmp/.Xauthority
cap_add:
- SYS_PTRACE
command: /bin/sh -c "while sleep 1000; do :; done"
build:
context: .
dockerfile: Dockerfile.devcontainer
privileged: true
network_mode: "host"

View File

@ -0,0 +1,29 @@
name: C/C++ Build Workflow
on:
push:
branches: [ "main" ]
pull_request:
branches: [ "main" ]
jobs:
build:
runs-on: ubuntu-latest # Use latest runner to host the container
container:
image: ubuntu:20.04
options: --privileged # Needed for some build tools
steps:
- uses: actions/checkout@v4
- name: Install dependencies
run: |
export DEBIAN_FRONTEND=noninteractive
apt-get update
apt-get install -y cmake g++ build-essential libyaml-cpp-dev libeigen3-dev
- name: CMake build
run: |
cmake -Bbuild
cmake --build build -j$(nproc)

8
deps/unitree_sdk2/.gitignore vendored Normal file
View File

@ -0,0 +1,8 @@
# IDE
.vscode
# cpp
build
#cland
.cache

82
deps/unitree_sdk2/CMakeLists.txt vendored Normal file
View File

@ -0,0 +1,82 @@
cmake_minimum_required(VERSION 3.5)
project(unitree_sdk2 VERSION 2.0.0)
## Project Options
option(BUILD_EXAMPLES "Build examples" ON)
## Set compiler to use c++ 17 features
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_EXTENSIONS OFF)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
## Chosse build type
set(default_build_type "Release")
if (NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
message(STATUS "Setting build type to '${default_build_type}' as none was specified.")
set(CMAKE_BUILD_TYPE "${default_build_type}" CACHE
STRING "Choose the type of build." FORCE)
# Set the possible values of build type for cmake-gui
set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS
"Debug" "Release" "MinSizeRel" "RelWithDebInfo")
endif ()
## Use GNUInstallDirs to install libraries into correct locations on all platforms.
include(GNUInstallDirs)
## Put all binary files into /bin and libraries into /lib
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/${CMAKE_INSTALL_LIBDIR})
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/${CMAKE_INSTALL_LIBDIR})
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_BINARY_DIR}/${CMAKE_INSTALL_BINDIR})
## Check system architecture
message(STATUS "Current system architecture: ${CMAKE_SYSTEM_PROCESSOR}")
## Import thirdparty libraries
add_subdirectory(thirdparty)
## Import Unitree SDK2 library
set(UNITREE_SDK_PATH ${CMAKE_CURRENT_LIST_DIR}/lib/${CMAKE_SYSTEM_PROCESSOR})
find_library(UNITREE_SDK_LIB unitree_sdk2 PATHS ${UNITREE_SDK_PATH} NO_DEFAULT_PATH)
if (NOT UNITREE_SDK_LIB)
message(FATAL_ERROR "Unitree SDK library for the architecture is not found")
else ()
message(STATUS "Unitree SDK library found at: ${UNITREE_SDK_LIB}")
endif ()
message(STATUS "Importing: ${UNITREE_SDK_LIB}")
find_package(Threads REQUIRED)
add_library(unitree_sdk2 STATIC IMPORTED GLOBAL)
set_target_properties(unitree_sdk2 PROPERTIES
IMPORTED_LOCATION ${UNITREE_SDK_LIB})
target_link_libraries(unitree_sdk2 INTERFACE ddsc ddscxx Threads::Threads)
target_include_directories(unitree_sdk2 INTERFACE
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>
$<INSTALL_INTERFACE:include>)
if (BUILD_EXAMPLES)
add_subdirectory(example)
endif ()
## Install the library
install(DIRECTORY include/
DESTINATION ${CMAKE_INSTALL_INCLUDEDIR})
install(FILES ${UNITREE_SDK_LIB}
DESTINATION ${CMAKE_INSTALL_LIBDIR})
install(FILES cmake/unitree_sdk2Targets.cmake
DESTINATION lib/cmake/unitree_sdk2)
include(CMakePackageConfigHelpers)
write_basic_package_version_file(
unitree_sdk2ConfigVersion.cmake
VERSION "${${PROJECT_NAME}_VERSION_MAJOR}.${${PROJECT_NAME}_VERSION_MINOR}.${${PROJECT_NAME}_VERSION_PATCH}"
COMPATIBILITY ExactVersion)
configure_file(cmake/unitree_sdk2Config.cmake.in unitree_sdk2Config.cmake @ONLY)
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/unitree_sdk2Config.cmake"
"${CMAKE_CURRENT_BINARY_DIR}/unitree_sdk2ConfigVersion.cmake"
DESTINATION lib/cmake/unitree_sdk2)

29
deps/unitree_sdk2/LICENSE vendored Normal file
View File

@ -0,0 +1,29 @@
BSD 3-Clause License
Copyright (c) 2016-2023 HangZhou YuShu TECHNOLOGY CO.,LTD. ("Unitree Robotics")
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
1. Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
3. Neither the name of the copyright holder nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

60
deps/unitree_sdk2/README.md vendored Normal file
View File

@ -0,0 +1,60 @@
# unitree_sdk2
Unitree robot sdk version 2.
### Prebuild environment
* OS (Ubuntu 20.04 LTS)
* CPU (aarch64 and x86_64)
* Compiler (gcc version 9.4.0)
### Environment Setup
Before building or running the SDK, ensure the following dependencies are installed:
- CMake (version 3.10 or higher)
- GCC (version 9.4.0)
- Make
You can install the required packages on Ubuntu 20.04 with:
```bash
apt-get update
apt-get install -y cmake g++ build-essential libyaml-cpp-dev libeigen3-dev libboost-all-dev libspdlog-dev libfmt-dev
```
### Build examples
To build the examples inside this repository:
```bash
mkdir build
cd build
cmake ..
make
```
### Installation
To build your own application with the SDK, you can install the unitree_sdk2 to your system directory:
```bash
mkdir build
cd build
cmake ..
sudo make install
```
Or install unitree_sdk2 to a specified directory:
```bash
mkdir build
cd build
cmake .. -DCMAKE_INSTALL_PREFIX=/opt/unitree_robotics
sudo make install
```
You can refer to `example/cmake_sample` on how to import the unitree_sdk2 into your CMake project.
Note that if you install the library to other places other than `/opt/unitree_robotics`, you need to make sure the path is added to "${CMAKE_PREFIX_PATH}" so that cmake can find it with "find_package()".
### Notice
For more reference information, please go to [Unitree Document Center](https://support.unitree.com/home/zh/developer).

View File

@ -0,0 +1,490 @@
# This is the CMakeCache file.
# For build in directory: /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
# It was generated by CMake: /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake
# You can edit this file to change values found and used by cmake.
# If you do not want to change any of the values, simply exit the editor.
# If you do want to change a value, simply edit, save, and exit the editor.
# The syntax for the file is as follows:
# KEY:TYPE=VALUE
# KEY is the name of a variable in the cache.
# TYPE is a hint to GUIs for the type of VALUE, DO NOT EDIT TYPE!.
# VALUE is the current value for the KEY.
########################
# EXTERNAL cache entries
########################
//Build examples
BUILD_EXAMPLES:BOOL=OFF
//Path to a program.
CMAKE_ADDR2LINE:FILEPATH=/usr/bin/addr2line
//Path to a program.
CMAKE_AR:FILEPATH=/usr/bin/ar
//Choose the type of build.
CMAKE_BUILD_TYPE:STRING=Release
//Enable/Disable color output during build.
CMAKE_COLOR_MAKEFILE:BOOL=ON
//CXX compiler
CMAKE_CXX_COMPILER:FILEPATH=/usr/bin/c++
//A wrapper around 'ar' adding the appropriate '--plugin' option
// for the GCC compiler
CMAKE_CXX_COMPILER_AR:FILEPATH=/usr/bin/gcc-ar-13
//A wrapper around 'ranlib' adding the appropriate '--plugin' option
// for the GCC compiler
CMAKE_CXX_COMPILER_RANLIB:FILEPATH=/usr/bin/gcc-ranlib-13
//Flags used by the CXX compiler during all build types.
CMAKE_CXX_FLAGS:STRING=
//Flags used by the CXX compiler during DEBUG builds.
CMAKE_CXX_FLAGS_DEBUG:STRING=-g
//Flags used by the CXX compiler during MINSIZEREL builds.
CMAKE_CXX_FLAGS_MINSIZEREL:STRING=-Os -DNDEBUG
//Flags used by the CXX compiler during RELEASE builds.
CMAKE_CXX_FLAGS_RELEASE:STRING=-O3 -DNDEBUG
//Flags used by the CXX compiler during RELWITHDEBINFO builds.
CMAKE_CXX_FLAGS_RELWITHDEBINFO:STRING=-O2 -g -DNDEBUG
//C compiler
CMAKE_C_COMPILER:FILEPATH=/usr/bin/cc
//A wrapper around 'ar' adding the appropriate '--plugin' option
// for the GCC compiler
CMAKE_C_COMPILER_AR:FILEPATH=/usr/bin/gcc-ar-13
//A wrapper around 'ranlib' adding the appropriate '--plugin' option
// for the GCC compiler
CMAKE_C_COMPILER_RANLIB:FILEPATH=/usr/bin/gcc-ranlib-13
//Flags used by the C compiler during all build types.
CMAKE_C_FLAGS:STRING=
//Flags used by the C compiler during DEBUG builds.
CMAKE_C_FLAGS_DEBUG:STRING=-g
//Flags used by the C compiler during MINSIZEREL builds.
CMAKE_C_FLAGS_MINSIZEREL:STRING=-Os -DNDEBUG
//Flags used by the C compiler during RELEASE builds.
CMAKE_C_FLAGS_RELEASE:STRING=-O3 -DNDEBUG
//Flags used by the C compiler during RELWITHDEBINFO builds.
CMAKE_C_FLAGS_RELWITHDEBINFO:STRING=-O2 -g -DNDEBUG
//Path to a program.
CMAKE_DLLTOOL:FILEPATH=CMAKE_DLLTOOL-NOTFOUND
//Flags used by the linker during all build types.
CMAKE_EXE_LINKER_FLAGS:STRING=
//Flags used by the linker during DEBUG builds.
CMAKE_EXE_LINKER_FLAGS_DEBUG:STRING=
//Flags used by the linker during MINSIZEREL builds.
CMAKE_EXE_LINKER_FLAGS_MINSIZEREL:STRING=
//Flags used by the linker during RELEASE builds.
CMAKE_EXE_LINKER_FLAGS_RELEASE:STRING=
//Flags used by the linker during RELWITHDEBINFO builds.
CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO:STRING=
//Enable/Disable output of compile commands during generation.
CMAKE_EXPORT_COMPILE_COMMANDS:BOOL=
//Value Computed by CMake.
CMAKE_FIND_PACKAGE_REDIRECTS_DIR:STATIC=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/pkgRedirects
//User executables (bin)
CMAKE_INSTALL_BINDIR:PATH=bin
//Read-only architecture-independent data (DATAROOTDIR)
CMAKE_INSTALL_DATADIR:PATH=
//Read-only architecture-independent data root (share)
CMAKE_INSTALL_DATAROOTDIR:PATH=share
//Documentation root (DATAROOTDIR/doc/PROJECT_NAME)
CMAKE_INSTALL_DOCDIR:PATH=
//C header files (include)
CMAKE_INSTALL_INCLUDEDIR:PATH=include
//Info documentation (DATAROOTDIR/info)
CMAKE_INSTALL_INFODIR:PATH=
//Object code libraries (lib)
CMAKE_INSTALL_LIBDIR:PATH=lib
//Program executables (libexec)
CMAKE_INSTALL_LIBEXECDIR:PATH=libexec
//Locale-dependent data (DATAROOTDIR/locale)
CMAKE_INSTALL_LOCALEDIR:PATH=
//Modifiable single-machine data (var)
CMAKE_INSTALL_LOCALSTATEDIR:PATH=var
//Man documentation (DATAROOTDIR/man)
CMAKE_INSTALL_MANDIR:PATH=
//C header files for non-gcc (/usr/include)
CMAKE_INSTALL_OLDINCLUDEDIR:PATH=/usr/include
//Install path prefix, prepended onto install directories.
CMAKE_INSTALL_PREFIX:PATH=/home/zedx/.local/unitree_robotics
//Run-time variable data (LOCALSTATEDIR/run)
CMAKE_INSTALL_RUNSTATEDIR:PATH=
//System admin executables (sbin)
CMAKE_INSTALL_SBINDIR:PATH=sbin
//Modifiable architecture-independent data (com)
CMAKE_INSTALL_SHAREDSTATEDIR:PATH=com
//Read-only single-machine data (etc)
CMAKE_INSTALL_SYSCONFDIR:PATH=etc
//Path to a program.
CMAKE_LINKER:FILEPATH=/usr/bin/ld
//Path to a program.
CMAKE_MAKE_PROGRAM:FILEPATH=/usr/bin/gmake
//Flags used by the linker during the creation of modules during
// all build types.
CMAKE_MODULE_LINKER_FLAGS:STRING=
//Flags used by the linker during the creation of modules during
// DEBUG builds.
CMAKE_MODULE_LINKER_FLAGS_DEBUG:STRING=
//Flags used by the linker during the creation of modules during
// MINSIZEREL builds.
CMAKE_MODULE_LINKER_FLAGS_MINSIZEREL:STRING=
//Flags used by the linker during the creation of modules during
// RELEASE builds.
CMAKE_MODULE_LINKER_FLAGS_RELEASE:STRING=
//Flags used by the linker during the creation of modules during
// RELWITHDEBINFO builds.
CMAKE_MODULE_LINKER_FLAGS_RELWITHDEBINFO:STRING=
//Path to a program.
CMAKE_NM:FILEPATH=/usr/bin/nm
//Path to a program.
CMAKE_OBJCOPY:FILEPATH=/usr/bin/objcopy
//Path to a program.
CMAKE_OBJDUMP:FILEPATH=/usr/bin/objdump
//Value Computed by CMake
CMAKE_PROJECT_COMPAT_VERSION:STATIC=
//Value Computed by CMake
CMAKE_PROJECT_DESCRIPTION:STATIC=
//Value Computed by CMake
CMAKE_PROJECT_HOMEPAGE_URL:STATIC=
//Value Computed by CMake
CMAKE_PROJECT_NAME:STATIC=unitree_sdk2
//Value Computed by CMake
CMAKE_PROJECT_VERSION:STATIC=2.0.0
//Value Computed by CMake
CMAKE_PROJECT_VERSION_MAJOR:STATIC=2
//Value Computed by CMake
CMAKE_PROJECT_VERSION_MINOR:STATIC=0
//Value Computed by CMake
CMAKE_PROJECT_VERSION_PATCH:STATIC=0
//Value Computed by CMake
CMAKE_PROJECT_VERSION_TWEAK:STATIC=
//Path to a program.
CMAKE_RANLIB:FILEPATH=/usr/bin/ranlib
//Path to a program.
CMAKE_READELF:FILEPATH=/usr/bin/readelf
//Flags used by the linker during the creation of shared libraries
// during all build types.
CMAKE_SHARED_LINKER_FLAGS:STRING=
//Flags used by the linker during the creation of shared libraries
// during DEBUG builds.
CMAKE_SHARED_LINKER_FLAGS_DEBUG:STRING=
//Flags used by the linker during the creation of shared libraries
// during MINSIZEREL builds.
CMAKE_SHARED_LINKER_FLAGS_MINSIZEREL:STRING=
//Flags used by the linker during the creation of shared libraries
// during RELEASE builds.
CMAKE_SHARED_LINKER_FLAGS_RELEASE:STRING=
//Flags used by the linker during the creation of shared libraries
// during RELWITHDEBINFO builds.
CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO:STRING=
//If set, runtime paths are not added when installing shared libraries,
// but are added when building.
CMAKE_SKIP_INSTALL_RPATH:BOOL=NO
//If set, runtime paths are not added when using shared libraries.
CMAKE_SKIP_RPATH:BOOL=NO
//Flags used by the archiver during the creation of static libraries
// during all build types.
CMAKE_STATIC_LINKER_FLAGS:STRING=
//Flags used by the archiver during the creation of static libraries
// during DEBUG builds.
CMAKE_STATIC_LINKER_FLAGS_DEBUG:STRING=
//Flags used by the archiver during the creation of static libraries
// during MINSIZEREL builds.
CMAKE_STATIC_LINKER_FLAGS_MINSIZEREL:STRING=
//Flags used by the archiver during the creation of static libraries
// during RELEASE builds.
CMAKE_STATIC_LINKER_FLAGS_RELEASE:STRING=
//Flags used by the archiver during the creation of static libraries
// during RELWITHDEBINFO builds.
CMAKE_STATIC_LINKER_FLAGS_RELWITHDEBINFO:STRING=
//Path to a program.
CMAKE_STRIP:FILEPATH=/usr/bin/strip
//Path to a program.
CMAKE_TAPI:FILEPATH=CMAKE_TAPI-NOTFOUND
//If this value is on, makefiles will be generated without the
// .SILENT directive, and all commands will be echoed to the console
// during the make. This is useful for debugging only. With Visual
// Studio IDE projects all commands are done without /nologo.
CMAKE_VERBOSE_MAKEFILE:BOOL=FALSE
//Path to a library.
UNITREE_SDK_LIB:FILEPATH=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/lib/x86_64/libunitree_sdk2.a
//Value Computed by CMake
unitree_sdk2_BINARY_DIR:STATIC=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
//Value Computed by CMake
unitree_sdk2_IS_TOP_LEVEL:STATIC=ON
//Value Computed by CMake
unitree_sdk2_SOURCE_DIR:STATIC=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
########################
# INTERNAL cache entries
########################
//ADVANCED property for variable: CMAKE_ADDR2LINE
CMAKE_ADDR2LINE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_AR
CMAKE_AR-ADVANCED:INTERNAL=1
//STRINGS property for variable: CMAKE_BUILD_TYPE
CMAKE_BUILD_TYPE-STRINGS:INTERNAL=Debug;Release;MinSizeRel;RelWithDebInfo
//This is the directory where this CMakeCache.txt was created
CMAKE_CACHEFILE_DIR:INTERNAL=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
//Major version of cmake used to create the current loaded cache
CMAKE_CACHE_MAJOR_VERSION:INTERNAL=4
//Minor version of cmake used to create the current loaded cache
CMAKE_CACHE_MINOR_VERSION:INTERNAL=1
//Patch version of cmake used to create the current loaded cache
CMAKE_CACHE_PATCH_VERSION:INTERNAL=3
//ADVANCED property for variable: CMAKE_COLOR_MAKEFILE
CMAKE_COLOR_MAKEFILE-ADVANCED:INTERNAL=1
//Path to CMake executable.
CMAKE_COMMAND:INTERNAL=/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake
//Path to cpack program executable.
CMAKE_CPACK_COMMAND:INTERNAL=/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cpack
//Path to ctest program executable.
CMAKE_CTEST_COMMAND:INTERNAL=/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/ctest
//ADVANCED property for variable: CMAKE_CXX_COMPILER
CMAKE_CXX_COMPILER-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_COMPILER_AR
CMAKE_CXX_COMPILER_AR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_COMPILER_RANLIB
CMAKE_CXX_COMPILER_RANLIB-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_FLAGS
CMAKE_CXX_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_FLAGS_DEBUG
CMAKE_CXX_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_FLAGS_MINSIZEREL
CMAKE_CXX_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_FLAGS_RELEASE
CMAKE_CXX_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_CXX_FLAGS_RELWITHDEBINFO
CMAKE_CXX_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_COMPILER
CMAKE_C_COMPILER-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_COMPILER_AR
CMAKE_C_COMPILER_AR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_COMPILER_RANLIB
CMAKE_C_COMPILER_RANLIB-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_FLAGS
CMAKE_C_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_FLAGS_DEBUG
CMAKE_C_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_FLAGS_MINSIZEREL
CMAKE_C_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_FLAGS_RELEASE
CMAKE_C_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_C_FLAGS_RELWITHDEBINFO
CMAKE_C_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_DLLTOOL
CMAKE_DLLTOOL-ADVANCED:INTERNAL=1
//Executable file format
CMAKE_EXECUTABLE_FORMAT:INTERNAL=ELF
//ADVANCED property for variable: CMAKE_EXE_LINKER_FLAGS
CMAKE_EXE_LINKER_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_EXE_LINKER_FLAGS_DEBUG
CMAKE_EXE_LINKER_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_EXE_LINKER_FLAGS_MINSIZEREL
CMAKE_EXE_LINKER_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_EXE_LINKER_FLAGS_RELEASE
CMAKE_EXE_LINKER_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO
CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_EXPORT_COMPILE_COMMANDS
CMAKE_EXPORT_COMPILE_COMMANDS-ADVANCED:INTERNAL=1
//Name of external makefile project generator.
CMAKE_EXTRA_GENERATOR:INTERNAL=
//Name of generator.
CMAKE_GENERATOR:INTERNAL=Unix Makefiles
//Generator instance identifier.
CMAKE_GENERATOR_INSTANCE:INTERNAL=
//Name of generator platform.
CMAKE_GENERATOR_PLATFORM:INTERNAL=
//Name of generator toolset.
CMAKE_GENERATOR_TOOLSET:INTERNAL=
//Test CMAKE_HAVE_LIBC_PTHREAD
CMAKE_HAVE_LIBC_PTHREAD:INTERNAL=1
//Source directory with the top level CMakeLists.txt file for this
// project
CMAKE_HOME_DIRECTORY:INTERNAL=/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
//ADVANCED property for variable: CMAKE_INSTALL_BINDIR
CMAKE_INSTALL_BINDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_DATADIR
CMAKE_INSTALL_DATADIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_DATAROOTDIR
CMAKE_INSTALL_DATAROOTDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_DOCDIR
CMAKE_INSTALL_DOCDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_INCLUDEDIR
CMAKE_INSTALL_INCLUDEDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_INFODIR
CMAKE_INSTALL_INFODIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_LIBDIR
CMAKE_INSTALL_LIBDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_LIBEXECDIR
CMAKE_INSTALL_LIBEXECDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_LOCALEDIR
CMAKE_INSTALL_LOCALEDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_LOCALSTATEDIR
CMAKE_INSTALL_LOCALSTATEDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_MANDIR
CMAKE_INSTALL_MANDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_OLDINCLUDEDIR
CMAKE_INSTALL_OLDINCLUDEDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_RUNSTATEDIR
CMAKE_INSTALL_RUNSTATEDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_SBINDIR
CMAKE_INSTALL_SBINDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_SHAREDSTATEDIR
CMAKE_INSTALL_SHAREDSTATEDIR-ADVANCED:INTERNAL=1
//Install .so files without execute permission.
CMAKE_INSTALL_SO_NO_EXE:INTERNAL=1
//ADVANCED property for variable: CMAKE_INSTALL_SYSCONFDIR
CMAKE_INSTALL_SYSCONFDIR-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_LINKER
CMAKE_LINKER-ADVANCED:INTERNAL=1
//Name of CMakeLists files to read
CMAKE_LIST_FILE_NAME:INTERNAL=CMakeLists.txt
//ADVANCED property for variable: CMAKE_MAKE_PROGRAM
CMAKE_MAKE_PROGRAM-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_MODULE_LINKER_FLAGS
CMAKE_MODULE_LINKER_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_MODULE_LINKER_FLAGS_DEBUG
CMAKE_MODULE_LINKER_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_MODULE_LINKER_FLAGS_MINSIZEREL
CMAKE_MODULE_LINKER_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_MODULE_LINKER_FLAGS_RELEASE
CMAKE_MODULE_LINKER_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_MODULE_LINKER_FLAGS_RELWITHDEBINFO
CMAKE_MODULE_LINKER_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_NM
CMAKE_NM-ADVANCED:INTERNAL=1
//number of local generators
CMAKE_NUMBER_OF_MAKEFILES:INTERNAL=2
//ADVANCED property for variable: CMAKE_OBJCOPY
CMAKE_OBJCOPY-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_OBJDUMP
CMAKE_OBJDUMP-ADVANCED:INTERNAL=1
//Platform information initialized
CMAKE_PLATFORM_INFO_INITIALIZED:INTERNAL=1
//ADVANCED property for variable: CMAKE_RANLIB
CMAKE_RANLIB-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_READELF
CMAKE_READELF-ADVANCED:INTERNAL=1
//Path to CMake installation.
CMAKE_ROOT:INTERNAL=/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1
//ADVANCED property for variable: CMAKE_SHARED_LINKER_FLAGS
CMAKE_SHARED_LINKER_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SHARED_LINKER_FLAGS_DEBUG
CMAKE_SHARED_LINKER_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SHARED_LINKER_FLAGS_MINSIZEREL
CMAKE_SHARED_LINKER_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SHARED_LINKER_FLAGS_RELEASE
CMAKE_SHARED_LINKER_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO
CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SKIP_INSTALL_RPATH
CMAKE_SKIP_INSTALL_RPATH-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_SKIP_RPATH
CMAKE_SKIP_RPATH-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STATIC_LINKER_FLAGS
CMAKE_STATIC_LINKER_FLAGS-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STATIC_LINKER_FLAGS_DEBUG
CMAKE_STATIC_LINKER_FLAGS_DEBUG-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STATIC_LINKER_FLAGS_MINSIZEREL
CMAKE_STATIC_LINKER_FLAGS_MINSIZEREL-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STATIC_LINKER_FLAGS_RELEASE
CMAKE_STATIC_LINKER_FLAGS_RELEASE-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STATIC_LINKER_FLAGS_RELWITHDEBINFO
CMAKE_STATIC_LINKER_FLAGS_RELWITHDEBINFO-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_STRIP
CMAKE_STRIP-ADVANCED:INTERNAL=1
//ADVANCED property for variable: CMAKE_TAPI
CMAKE_TAPI-ADVANCED:INTERNAL=1
//uname command
CMAKE_UNAME:INTERNAL=/usr/bin/uname
//ADVANCED property for variable: CMAKE_VERBOSE_MAKEFILE
CMAKE_VERBOSE_MAKEFILE-ADVANCED:INTERNAL=1
//Details about finding Threads
FIND_PACKAGE_MESSAGE_DETAILS_Threads:INTERNAL=[TRUE][v()]
//CMAKE_INSTALL_PREFIX during last run
_GNUInstallDirs_LAST_CMAKE_INSTALL_PREFIX:INTERNAL=/home/zedx/.local/unitree_robotics

View File

@ -0,0 +1,84 @@
set(CMAKE_C_COMPILER "/usr/bin/cc")
set(CMAKE_C_COMPILER_ARG1 "")
set(CMAKE_C_COMPILER_ID "GNU")
set(CMAKE_C_COMPILER_VERSION "13.3.0")
set(CMAKE_C_COMPILER_VERSION_INTERNAL "")
set(CMAKE_C_COMPILER_WRAPPER "")
set(CMAKE_C_STANDARD_COMPUTED_DEFAULT "17")
set(CMAKE_C_EXTENSIONS_COMPUTED_DEFAULT "ON")
set(CMAKE_C_STANDARD_LATEST "23")
set(CMAKE_C_COMPILE_FEATURES "c_std_90;c_function_prototypes;c_std_99;c_restrict;c_variadic_macros;c_std_11;c_static_assert;c_std_17;c_std_23")
set(CMAKE_C90_COMPILE_FEATURES "c_std_90;c_function_prototypes")
set(CMAKE_C99_COMPILE_FEATURES "c_std_99;c_restrict;c_variadic_macros")
set(CMAKE_C11_COMPILE_FEATURES "c_std_11;c_static_assert")
set(CMAKE_C17_COMPILE_FEATURES "c_std_17")
set(CMAKE_C23_COMPILE_FEATURES "c_std_23")
set(CMAKE_C_PLATFORM_ID "Linux")
set(CMAKE_C_SIMULATE_ID "")
set(CMAKE_C_COMPILER_FRONTEND_VARIANT "GNU")
set(CMAKE_C_COMPILER_APPLE_SYSROOT "")
set(CMAKE_C_SIMULATE_VERSION "")
set(CMAKE_C_COMPILER_ARCHITECTURE_ID "x86_64")
set(CMAKE_AR "/usr/bin/ar")
set(CMAKE_C_COMPILER_AR "/usr/bin/gcc-ar-13")
set(CMAKE_RANLIB "/usr/bin/ranlib")
set(CMAKE_C_COMPILER_RANLIB "/usr/bin/gcc-ranlib-13")
set(CMAKE_LINKER "/usr/bin/ld")
set(CMAKE_LINKER_LINK "")
set(CMAKE_LINKER_LLD "")
set(CMAKE_C_COMPILER_LINKER "/usr/bin/ld")
set(CMAKE_C_COMPILER_LINKER_ID "GNU")
set(CMAKE_C_COMPILER_LINKER_VERSION 2.42)
set(CMAKE_C_COMPILER_LINKER_FRONTEND_VARIANT GNU)
set(CMAKE_MT "")
set(CMAKE_TAPI "CMAKE_TAPI-NOTFOUND")
set(CMAKE_COMPILER_IS_GNUCC 1)
set(CMAKE_C_COMPILER_LOADED 1)
set(CMAKE_C_COMPILER_WORKS TRUE)
set(CMAKE_C_ABI_COMPILED TRUE)
set(CMAKE_C_COMPILER_ENV_VAR "CC")
set(CMAKE_C_COMPILER_ID_RUN 1)
set(CMAKE_C_SOURCE_FILE_EXTENSIONS c;m)
set(CMAKE_C_IGNORE_EXTENSIONS h;H;o;O;obj;OBJ;def;DEF;rc;RC)
set(CMAKE_C_LINKER_PREFERENCE 10)
set(CMAKE_C_LINKER_DEPFILE_SUPPORTED TRUE)
set(CMAKE_LINKER_PUSHPOP_STATE_SUPPORTED TRUE)
set(CMAKE_C_LINKER_PUSHPOP_STATE_SUPPORTED TRUE)
# Save compiler ABI information.
set(CMAKE_C_SIZEOF_DATA_PTR "8")
set(CMAKE_C_COMPILER_ABI "ELF")
set(CMAKE_C_BYTE_ORDER "LITTLE_ENDIAN")
set(CMAKE_C_LIBRARY_ARCHITECTURE "x86_64-linux-gnu")
if(CMAKE_C_SIZEOF_DATA_PTR)
set(CMAKE_SIZEOF_VOID_P "${CMAKE_C_SIZEOF_DATA_PTR}")
endif()
if(CMAKE_C_COMPILER_ABI)
set(CMAKE_INTERNAL_PLATFORM_ABI "${CMAKE_C_COMPILER_ABI}")
endif()
if(CMAKE_C_LIBRARY_ARCHITECTURE)
set(CMAKE_LIBRARY_ARCHITECTURE "x86_64-linux-gnu")
endif()
set(CMAKE_C_CL_SHOWINCLUDES_PREFIX "")
if(CMAKE_C_CL_SHOWINCLUDES_PREFIX)
set(CMAKE_CL_SHOWINCLUDES_PREFIX "${CMAKE_C_CL_SHOWINCLUDES_PREFIX}")
endif()
set(CMAKE_C_IMPLICIT_INCLUDE_DIRECTORIES "/usr/lib/gcc/x86_64-linux-gnu/13/include;/usr/local/include;/usr/include/x86_64-linux-gnu;/usr/include")
set(CMAKE_C_IMPLICIT_LINK_LIBRARIES "gcc;gcc_s;c;gcc;gcc_s")
set(CMAKE_C_IMPLICIT_LINK_DIRECTORIES "/usr/lib/gcc/x86_64-linux-gnu/13;/usr/lib/x86_64-linux-gnu;/usr/lib;/lib/x86_64-linux-gnu;/lib")
set(CMAKE_C_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "")

View File

@ -0,0 +1,104 @@
set(CMAKE_CXX_COMPILER "/usr/bin/c++")
set(CMAKE_CXX_COMPILER_ARG1 "")
set(CMAKE_CXX_COMPILER_ID "GNU")
set(CMAKE_CXX_COMPILER_VERSION "13.3.0")
set(CMAKE_CXX_COMPILER_VERSION_INTERNAL "")
set(CMAKE_CXX_COMPILER_WRAPPER "")
set(CMAKE_CXX_STANDARD_COMPUTED_DEFAULT "17")
set(CMAKE_CXX_EXTENSIONS_COMPUTED_DEFAULT "ON")
set(CMAKE_CXX_STANDARD_LATEST "23")
set(CMAKE_CXX_COMPILE_FEATURES "cxx_std_98;cxx_template_template_parameters;cxx_std_11;cxx_alias_templates;cxx_alignas;cxx_alignof;cxx_attributes;cxx_auto_type;cxx_constexpr;cxx_decltype;cxx_decltype_incomplete_return_types;cxx_default_function_template_args;cxx_defaulted_functions;cxx_defaulted_move_initializers;cxx_delegating_constructors;cxx_deleted_functions;cxx_enum_forward_declarations;cxx_explicit_conversions;cxx_extended_friend_declarations;cxx_extern_templates;cxx_final;cxx_func_identifier;cxx_generalized_initializers;cxx_inheriting_constructors;cxx_inline_namespaces;cxx_lambdas;cxx_local_type_template_args;cxx_long_long_type;cxx_noexcept;cxx_nonstatic_member_init;cxx_nullptr;cxx_override;cxx_range_for;cxx_raw_string_literals;cxx_reference_qualified_functions;cxx_right_angle_brackets;cxx_rvalue_references;cxx_sizeof_member;cxx_static_assert;cxx_strong_enums;cxx_thread_local;cxx_trailing_return_types;cxx_unicode_literals;cxx_uniform_initialization;cxx_unrestricted_unions;cxx_user_literals;cxx_variadic_macros;cxx_variadic_templates;cxx_std_14;cxx_aggregate_default_initializers;cxx_attribute_deprecated;cxx_binary_literals;cxx_contextual_conversions;cxx_decltype_auto;cxx_digit_separators;cxx_generic_lambdas;cxx_lambda_init_captures;cxx_relaxed_constexpr;cxx_return_type_deduction;cxx_variable_templates;cxx_std_17;cxx_std_20;cxx_std_23")
set(CMAKE_CXX98_COMPILE_FEATURES "cxx_std_98;cxx_template_template_parameters")
set(CMAKE_CXX11_COMPILE_FEATURES "cxx_std_11;cxx_alias_templates;cxx_alignas;cxx_alignof;cxx_attributes;cxx_auto_type;cxx_constexpr;cxx_decltype;cxx_decltype_incomplete_return_types;cxx_default_function_template_args;cxx_defaulted_functions;cxx_defaulted_move_initializers;cxx_delegating_constructors;cxx_deleted_functions;cxx_enum_forward_declarations;cxx_explicit_conversions;cxx_extended_friend_declarations;cxx_extern_templates;cxx_final;cxx_func_identifier;cxx_generalized_initializers;cxx_inheriting_constructors;cxx_inline_namespaces;cxx_lambdas;cxx_local_type_template_args;cxx_long_long_type;cxx_noexcept;cxx_nonstatic_member_init;cxx_nullptr;cxx_override;cxx_range_for;cxx_raw_string_literals;cxx_reference_qualified_functions;cxx_right_angle_brackets;cxx_rvalue_references;cxx_sizeof_member;cxx_static_assert;cxx_strong_enums;cxx_thread_local;cxx_trailing_return_types;cxx_unicode_literals;cxx_uniform_initialization;cxx_unrestricted_unions;cxx_user_literals;cxx_variadic_macros;cxx_variadic_templates")
set(CMAKE_CXX14_COMPILE_FEATURES "cxx_std_14;cxx_aggregate_default_initializers;cxx_attribute_deprecated;cxx_binary_literals;cxx_contextual_conversions;cxx_decltype_auto;cxx_digit_separators;cxx_generic_lambdas;cxx_lambda_init_captures;cxx_relaxed_constexpr;cxx_return_type_deduction;cxx_variable_templates")
set(CMAKE_CXX17_COMPILE_FEATURES "cxx_std_17")
set(CMAKE_CXX20_COMPILE_FEATURES "cxx_std_20")
set(CMAKE_CXX23_COMPILE_FEATURES "cxx_std_23")
set(CMAKE_CXX26_COMPILE_FEATURES "")
set(CMAKE_CXX_PLATFORM_ID "Linux")
set(CMAKE_CXX_SIMULATE_ID "")
set(CMAKE_CXX_COMPILER_FRONTEND_VARIANT "GNU")
set(CMAKE_CXX_COMPILER_APPLE_SYSROOT "")
set(CMAKE_CXX_SIMULATE_VERSION "")
set(CMAKE_CXX_COMPILER_ARCHITECTURE_ID "x86_64")
set(CMAKE_AR "/usr/bin/ar")
set(CMAKE_CXX_COMPILER_AR "/usr/bin/gcc-ar-13")
set(CMAKE_RANLIB "/usr/bin/ranlib")
set(CMAKE_CXX_COMPILER_RANLIB "/usr/bin/gcc-ranlib-13")
set(CMAKE_LINKER "/usr/bin/ld")
set(CMAKE_LINKER_LINK "")
set(CMAKE_LINKER_LLD "")
set(CMAKE_CXX_COMPILER_LINKER "/usr/bin/ld")
set(CMAKE_CXX_COMPILER_LINKER_ID "GNU")
set(CMAKE_CXX_COMPILER_LINKER_VERSION 2.42)
set(CMAKE_CXX_COMPILER_LINKER_FRONTEND_VARIANT GNU)
set(CMAKE_MT "")
set(CMAKE_TAPI "CMAKE_TAPI-NOTFOUND")
set(CMAKE_COMPILER_IS_GNUCXX 1)
set(CMAKE_CXX_COMPILER_LOADED 1)
set(CMAKE_CXX_COMPILER_WORKS TRUE)
set(CMAKE_CXX_ABI_COMPILED TRUE)
set(CMAKE_CXX_COMPILER_ENV_VAR "CXX")
set(CMAKE_CXX_COMPILER_ID_RUN 1)
set(CMAKE_CXX_SOURCE_FILE_EXTENSIONS C;M;c++;cc;cpp;cxx;m;mm;mpp;CPP;ixx;cppm;ccm;cxxm;c++m)
set(CMAKE_CXX_IGNORE_EXTENSIONS inl;h;hpp;HPP;H;o;O;obj;OBJ;def;DEF;rc;RC)
foreach (lang IN ITEMS C OBJC OBJCXX)
if (CMAKE_${lang}_COMPILER_ID_RUN)
foreach(extension IN LISTS CMAKE_${lang}_SOURCE_FILE_EXTENSIONS)
list(REMOVE_ITEM CMAKE_CXX_SOURCE_FILE_EXTENSIONS ${extension})
endforeach()
endif()
endforeach()
set(CMAKE_CXX_LINKER_PREFERENCE 30)
set(CMAKE_CXX_LINKER_PREFERENCE_PROPAGATES 1)
set(CMAKE_CXX_LINKER_DEPFILE_SUPPORTED TRUE)
set(CMAKE_LINKER_PUSHPOP_STATE_SUPPORTED TRUE)
set(CMAKE_CXX_LINKER_PUSHPOP_STATE_SUPPORTED TRUE)
# Save compiler ABI information.
set(CMAKE_CXX_SIZEOF_DATA_PTR "8")
set(CMAKE_CXX_COMPILER_ABI "ELF")
set(CMAKE_CXX_BYTE_ORDER "LITTLE_ENDIAN")
set(CMAKE_CXX_LIBRARY_ARCHITECTURE "x86_64-linux-gnu")
if(CMAKE_CXX_SIZEOF_DATA_PTR)
set(CMAKE_SIZEOF_VOID_P "${CMAKE_CXX_SIZEOF_DATA_PTR}")
endif()
if(CMAKE_CXX_COMPILER_ABI)
set(CMAKE_INTERNAL_PLATFORM_ABI "${CMAKE_CXX_COMPILER_ABI}")
endif()
if(CMAKE_CXX_LIBRARY_ARCHITECTURE)
set(CMAKE_LIBRARY_ARCHITECTURE "x86_64-linux-gnu")
endif()
set(CMAKE_CXX_CL_SHOWINCLUDES_PREFIX "")
if(CMAKE_CXX_CL_SHOWINCLUDES_PREFIX)
set(CMAKE_CL_SHOWINCLUDES_PREFIX "${CMAKE_CXX_CL_SHOWINCLUDES_PREFIX}")
endif()
set(CMAKE_CXX_IMPLICIT_INCLUDE_DIRECTORIES "/usr/include/c++/13;/usr/include/x86_64-linux-gnu/c++/13;/usr/include/c++/13/backward;/usr/lib/gcc/x86_64-linux-gnu/13/include;/usr/local/include;/usr/include/x86_64-linux-gnu;/usr/include")
set(CMAKE_CXX_IMPLICIT_LINK_LIBRARIES "stdc++;m;gcc_s;gcc;c;gcc_s;gcc")
set(CMAKE_CXX_IMPLICIT_LINK_DIRECTORIES "/usr/lib/gcc/x86_64-linux-gnu/13;/usr/lib/x86_64-linux-gnu;/usr/lib;/lib/x86_64-linux-gnu;/lib")
set(CMAKE_CXX_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "")
set(CMAKE_CXX_COMPILER_CLANG_RESOURCE_DIR "")
set(CMAKE_CXX_COMPILER_IMPORT_STD "")
### Imported target for C++23 standard library
set(CMAKE_CXX23_COMPILER_IMPORT_STD_NOT_FOUND_MESSAGE "Unsupported generator: Unix Makefiles")

View File

@ -0,0 +1,15 @@
set(CMAKE_HOST_SYSTEM "Linux-6.17.0-35-generic")
set(CMAKE_HOST_SYSTEM_NAME "Linux")
set(CMAKE_HOST_SYSTEM_VERSION "6.17.0-35-generic")
set(CMAKE_HOST_SYSTEM_PROCESSOR "x86_64")
set(CMAKE_SYSTEM "Linux-6.17.0-35-generic")
set(CMAKE_SYSTEM_NAME "Linux")
set(CMAKE_SYSTEM_VERSION "6.17.0-35-generic")
set(CMAKE_SYSTEM_PROCESSOR "x86_64")
set(CMAKE_CROSSCOMPILING "FALSE")
set(CMAKE_SYSTEM_LOADED 1)

View File

@ -0,0 +1,934 @@
#ifdef __cplusplus
# error "A C++ compiler has been selected for C."
#endif
#if defined(__18CXX)
# define ID_VOID_MAIN
#endif
#if defined(__CLASSIC_C__)
/* cv-qualifiers did not exist in K&R C */
# define const
# define volatile
#endif
#if !defined(__has_include)
/* If the compiler does not have __has_include, pretend the answer is
always no. */
# define __has_include(x) 0
#endif
/* Version number components: V=Version, R=Revision, P=Patch
Version date components: YYYY=Year, MM=Month, DD=Day */
#if defined(__INTEL_COMPILER) || defined(__ICC)
# define COMPILER_ID "Intel"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# if defined(__GNUC__)
# define SIMULATE_ID "GNU"
# endif
/* __INTEL_COMPILER = VRP prior to 2021, and then VVVV for 2021 and later,
except that a few beta releases use the old format with V=2021. */
# if __INTEL_COMPILER < 2021 || __INTEL_COMPILER == 202110 || __INTEL_COMPILER == 202111
# define COMPILER_VERSION_MAJOR DEC(__INTEL_COMPILER/100)
# define COMPILER_VERSION_MINOR DEC(__INTEL_COMPILER/10 % 10)
# if defined(__INTEL_COMPILER_UPDATE)
# define COMPILER_VERSION_PATCH DEC(__INTEL_COMPILER_UPDATE)
# else
# define COMPILER_VERSION_PATCH DEC(__INTEL_COMPILER % 10)
# endif
# else
# define COMPILER_VERSION_MAJOR DEC(__INTEL_COMPILER)
# define COMPILER_VERSION_MINOR DEC(__INTEL_COMPILER_UPDATE)
/* The third version component from --version is an update index,
but no macro is provided for it. */
# define COMPILER_VERSION_PATCH DEC(0)
# endif
# if defined(__INTEL_COMPILER_BUILD_DATE)
/* __INTEL_COMPILER_BUILD_DATE = YYYYMMDD */
# define COMPILER_VERSION_TWEAK DEC(__INTEL_COMPILER_BUILD_DATE)
# endif
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
# if defined(__GNUC__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
# elif defined(__GNUG__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUG__)
# endif
# if defined(__GNUC_MINOR__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
# endif
# if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
#elif (defined(__clang__) && defined(__INTEL_CLANG_COMPILER)) || defined(__INTEL_LLVM_COMPILER)
# define COMPILER_ID "IntelLLVM"
#if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
#endif
#if defined(__GNUC__)
# define SIMULATE_ID "GNU"
#endif
/* __INTEL_LLVM_COMPILER = VVVVRP prior to 2021.2.0, VVVVRRPP for 2021.2.0 and
* later. Look for 6 digit vs. 8 digit version number to decide encoding.
* VVVV is no smaller than the current year when a version is released.
*/
#if __INTEL_LLVM_COMPILER < 1000000L
# define COMPILER_VERSION_MAJOR DEC(__INTEL_LLVM_COMPILER/100)
# define COMPILER_VERSION_MINOR DEC(__INTEL_LLVM_COMPILER/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__INTEL_LLVM_COMPILER % 10)
#else
# define COMPILER_VERSION_MAJOR DEC(__INTEL_LLVM_COMPILER/10000)
# define COMPILER_VERSION_MINOR DEC(__INTEL_LLVM_COMPILER/100 % 100)
# define COMPILER_VERSION_PATCH DEC(__INTEL_LLVM_COMPILER % 100)
#endif
#if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
#endif
#if defined(__GNUC__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
#elif defined(__GNUG__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUG__)
#endif
#if defined(__GNUC_MINOR__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
#endif
#if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
#endif
#elif defined(__PATHCC__)
# define COMPILER_ID "PathScale"
# define COMPILER_VERSION_MAJOR DEC(__PATHCC__)
# define COMPILER_VERSION_MINOR DEC(__PATHCC_MINOR__)
# if defined(__PATHCC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__PATHCC_PATCHLEVEL__)
# endif
#elif defined(__BORLANDC__) && defined(__CODEGEARC_VERSION__)
# define COMPILER_ID "Embarcadero"
# define COMPILER_VERSION_MAJOR HEX(__CODEGEARC_VERSION__>>24 & 0x00FF)
# define COMPILER_VERSION_MINOR HEX(__CODEGEARC_VERSION__>>16 & 0x00FF)
# define COMPILER_VERSION_PATCH DEC(__CODEGEARC_VERSION__ & 0xFFFF)
#elif defined(__BORLANDC__)
# define COMPILER_ID "Borland"
/* __BORLANDC__ = 0xVRR */
# define COMPILER_VERSION_MAJOR HEX(__BORLANDC__>>8)
# define COMPILER_VERSION_MINOR HEX(__BORLANDC__ & 0xFF)
#elif defined(__WATCOMC__) && __WATCOMC__ < 1200
# define COMPILER_ID "Watcom"
/* __WATCOMC__ = VVRR */
# define COMPILER_VERSION_MAJOR DEC(__WATCOMC__ / 100)
# define COMPILER_VERSION_MINOR DEC((__WATCOMC__ / 10) % 10)
# if (__WATCOMC__ % 10) > 0
# define COMPILER_VERSION_PATCH DEC(__WATCOMC__ % 10)
# endif
#elif defined(__WATCOMC__)
# define COMPILER_ID "OpenWatcom"
/* __WATCOMC__ = VVRP + 1100 */
# define COMPILER_VERSION_MAJOR DEC((__WATCOMC__ - 1100) / 100)
# define COMPILER_VERSION_MINOR DEC((__WATCOMC__ / 10) % 10)
# if (__WATCOMC__ % 10) > 0
# define COMPILER_VERSION_PATCH DEC(__WATCOMC__ % 10)
# endif
#elif defined(__SUNPRO_C)
# define COMPILER_ID "SunPro"
# if __SUNPRO_C >= 0x5100
/* __SUNPRO_C = 0xVRRP */
# define COMPILER_VERSION_MAJOR HEX(__SUNPRO_C>>12)
# define COMPILER_VERSION_MINOR HEX(__SUNPRO_C>>4 & 0xFF)
# define COMPILER_VERSION_PATCH HEX(__SUNPRO_C & 0xF)
# else
/* __SUNPRO_CC = 0xVRP */
# define COMPILER_VERSION_MAJOR HEX(__SUNPRO_C>>8)
# define COMPILER_VERSION_MINOR HEX(__SUNPRO_C>>4 & 0xF)
# define COMPILER_VERSION_PATCH HEX(__SUNPRO_C & 0xF)
# endif
#elif defined(__HP_cc)
# define COMPILER_ID "HP"
/* __HP_cc = VVRRPP */
# define COMPILER_VERSION_MAJOR DEC(__HP_cc/10000)
# define COMPILER_VERSION_MINOR DEC(__HP_cc/100 % 100)
# define COMPILER_VERSION_PATCH DEC(__HP_cc % 100)
#elif defined(__DECC)
# define COMPILER_ID "Compaq"
/* __DECC_VER = VVRRTPPPP */
# define COMPILER_VERSION_MAJOR DEC(__DECC_VER/10000000)
# define COMPILER_VERSION_MINOR DEC(__DECC_VER/100000 % 100)
# define COMPILER_VERSION_PATCH DEC(__DECC_VER % 10000)
#elif defined(__IBMC__) && defined(__COMPILER_VER__)
# define COMPILER_ID "zOS"
/* __IBMC__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMC__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMC__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMC__ % 10)
#elif defined(__open_xl__) && defined(__clang__)
# define COMPILER_ID "IBMClang"
# define COMPILER_VERSION_MAJOR DEC(__open_xl_version__)
# define COMPILER_VERSION_MINOR DEC(__open_xl_release__)
# define COMPILER_VERSION_PATCH DEC(__open_xl_modification__)
# define COMPILER_VERSION_TWEAK DEC(__open_xl_ptf_fix_level__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(__ibmxl__) && defined(__clang__)
# define COMPILER_ID "XLClang"
# define COMPILER_VERSION_MAJOR DEC(__ibmxl_version__)
# define COMPILER_VERSION_MINOR DEC(__ibmxl_release__)
# define COMPILER_VERSION_PATCH DEC(__ibmxl_modification__)
# define COMPILER_VERSION_TWEAK DEC(__ibmxl_ptf_fix_level__)
#elif defined(__IBMC__) && !defined(__COMPILER_VER__) && __IBMC__ >= 800
# define COMPILER_ID "XL"
/* __IBMC__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMC__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMC__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMC__ % 10)
#elif defined(__IBMC__) && !defined(__COMPILER_VER__) && __IBMC__ < 800
# define COMPILER_ID "VisualAge"
/* __IBMC__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMC__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMC__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMC__ % 10)
#elif defined(__NVCOMPILER)
# define COMPILER_ID "NVHPC"
# define COMPILER_VERSION_MAJOR DEC(__NVCOMPILER_MAJOR__)
# define COMPILER_VERSION_MINOR DEC(__NVCOMPILER_MINOR__)
# if defined(__NVCOMPILER_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__NVCOMPILER_PATCHLEVEL__)
# endif
#elif defined(__PGI)
# define COMPILER_ID "PGI"
# define COMPILER_VERSION_MAJOR DEC(__PGIC__)
# define COMPILER_VERSION_MINOR DEC(__PGIC_MINOR__)
# if defined(__PGIC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__PGIC_PATCHLEVEL__)
# endif
#elif defined(__clang__) && defined(__cray__)
# define COMPILER_ID "CrayClang"
# define COMPILER_VERSION_MAJOR DEC(__cray_major__)
# define COMPILER_VERSION_MINOR DEC(__cray_minor__)
# define COMPILER_VERSION_PATCH DEC(__cray_patchlevel__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(_CRAYC)
# define COMPILER_ID "Cray"
# define COMPILER_VERSION_MAJOR DEC(_RELEASE_MAJOR)
# define COMPILER_VERSION_MINOR DEC(_RELEASE_MINOR)
#elif defined(__TI_COMPILER_VERSION__)
# define COMPILER_ID "TI"
/* __TI_COMPILER_VERSION__ = VVVRRRPPP */
# define COMPILER_VERSION_MAJOR DEC(__TI_COMPILER_VERSION__/1000000)
# define COMPILER_VERSION_MINOR DEC(__TI_COMPILER_VERSION__/1000 % 1000)
# define COMPILER_VERSION_PATCH DEC(__TI_COMPILER_VERSION__ % 1000)
#elif defined(__CLANG_FUJITSU)
# define COMPILER_ID "FujitsuClang"
# define COMPILER_VERSION_MAJOR DEC(__FCC_major__)
# define COMPILER_VERSION_MINOR DEC(__FCC_minor__)
# define COMPILER_VERSION_PATCH DEC(__FCC_patchlevel__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(__FUJITSU)
# define COMPILER_ID "Fujitsu"
# if defined(__FCC_version__)
# define COMPILER_VERSION __FCC_version__
# elif defined(__FCC_major__)
# define COMPILER_VERSION_MAJOR DEC(__FCC_major__)
# define COMPILER_VERSION_MINOR DEC(__FCC_minor__)
# define COMPILER_VERSION_PATCH DEC(__FCC_patchlevel__)
# endif
# if defined(__fcc_version)
# define COMPILER_VERSION_INTERNAL DEC(__fcc_version)
# elif defined(__FCC_VERSION)
# define COMPILER_VERSION_INTERNAL DEC(__FCC_VERSION)
# endif
#elif defined(__ghs__)
# define COMPILER_ID "GHS"
/* __GHS_VERSION_NUMBER = VVVVRP */
# ifdef __GHS_VERSION_NUMBER
# define COMPILER_VERSION_MAJOR DEC(__GHS_VERSION_NUMBER / 100)
# define COMPILER_VERSION_MINOR DEC(__GHS_VERSION_NUMBER / 10 % 10)
# define COMPILER_VERSION_PATCH DEC(__GHS_VERSION_NUMBER % 10)
# endif
#elif defined(__TASKING__)
# define COMPILER_ID "Tasking"
# define COMPILER_VERSION_MAJOR DEC(__VERSION__/1000)
# define COMPILER_VERSION_MINOR DEC(__VERSION__ % 100)
# define COMPILER_VERSION_INTERNAL DEC(__VERSION__)
#elif defined(__ORANGEC__)
# define COMPILER_ID "OrangeC"
# define COMPILER_VERSION_MAJOR DEC(__ORANGEC_MAJOR__)
# define COMPILER_VERSION_MINOR DEC(__ORANGEC_MINOR__)
# define COMPILER_VERSION_PATCH DEC(__ORANGEC_PATCHLEVEL__)
#elif defined(__RENESAS__)
# define COMPILER_ID "Renesas"
/* __RENESAS_VERSION__ = 0xVVRRPP00 */
# define COMPILER_VERSION_MAJOR HEX(__RENESAS_VERSION__ >> 24 & 0xFF)
# define COMPILER_VERSION_MINOR HEX(__RENESAS_VERSION__ >> 16 & 0xFF)
# define COMPILER_VERSION_PATCH HEX(__RENESAS_VERSION__ >> 8 & 0xFF)
#elif defined(__TINYC__)
# define COMPILER_ID "TinyCC"
#elif defined(__BCC__)
# define COMPILER_ID "Bruce"
#elif defined(__SCO_VERSION__)
# define COMPILER_ID "SCO"
#elif defined(__ARMCC_VERSION) && !defined(__clang__)
# define COMPILER_ID "ARMCC"
#if __ARMCC_VERSION >= 1000000
/* __ARMCC_VERSION = VRRPPPP */
# define COMPILER_VERSION_MAJOR DEC(__ARMCC_VERSION/1000000)
# define COMPILER_VERSION_MINOR DEC(__ARMCC_VERSION/10000 % 100)
# define COMPILER_VERSION_PATCH DEC(__ARMCC_VERSION % 10000)
#else
/* __ARMCC_VERSION = VRPPPP */
# define COMPILER_VERSION_MAJOR DEC(__ARMCC_VERSION/100000)
# define COMPILER_VERSION_MINOR DEC(__ARMCC_VERSION/10000 % 10)
# define COMPILER_VERSION_PATCH DEC(__ARMCC_VERSION % 10000)
#endif
#elif defined(__clang__) && defined(__apple_build_version__)
# define COMPILER_ID "AppleClang"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# define COMPILER_VERSION_MAJOR DEC(__clang_major__)
# define COMPILER_VERSION_MINOR DEC(__clang_minor__)
# define COMPILER_VERSION_PATCH DEC(__clang_patchlevel__)
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
# define COMPILER_VERSION_TWEAK DEC(__apple_build_version__)
#elif defined(__clang__) && defined(__ARMCOMPILER_VERSION)
# define COMPILER_ID "ARMClang"
# define COMPILER_VERSION_MAJOR DEC(__ARMCOMPILER_VERSION/1000000)
# define COMPILER_VERSION_MINOR DEC(__ARMCOMPILER_VERSION/10000 % 100)
# define COMPILER_VERSION_PATCH DEC(__ARMCOMPILER_VERSION/100 % 100)
# define COMPILER_VERSION_INTERNAL DEC(__ARMCOMPILER_VERSION)
#elif defined(__clang__) && defined(__ti__)
# define COMPILER_ID "TIClang"
# define COMPILER_VERSION_MAJOR DEC(__ti_major__)
# define COMPILER_VERSION_MINOR DEC(__ti_minor__)
# define COMPILER_VERSION_PATCH DEC(__ti_patchlevel__)
# define COMPILER_VERSION_INTERNAL DEC(__ti_version__)
#elif defined(__clang__)
# define COMPILER_ID "Clang"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# define COMPILER_VERSION_MAJOR DEC(__clang_major__)
# define COMPILER_VERSION_MINOR DEC(__clang_minor__)
# define COMPILER_VERSION_PATCH DEC(__clang_patchlevel__)
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
#elif defined(__LCC__) && (defined(__GNUC__) || defined(__GNUG__) || defined(__MCST__))
# define COMPILER_ID "LCC"
# define COMPILER_VERSION_MAJOR DEC(__LCC__ / 100)
# define COMPILER_VERSION_MINOR DEC(__LCC__ % 100)
# if defined(__LCC_MINOR__)
# define COMPILER_VERSION_PATCH DEC(__LCC_MINOR__)
# endif
# if defined(__GNUC__) && defined(__GNUC_MINOR__)
# define SIMULATE_ID "GNU"
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
# if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
# endif
#elif defined(__GNUC__)
# define COMPILER_ID "GNU"
# define COMPILER_VERSION_MAJOR DEC(__GNUC__)
# if defined(__GNUC_MINOR__)
# define COMPILER_VERSION_MINOR DEC(__GNUC_MINOR__)
# endif
# if defined(__GNUC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
#elif defined(_MSC_VER)
# define COMPILER_ID "MSVC"
/* _MSC_VER = VVRR */
# define COMPILER_VERSION_MAJOR DEC(_MSC_VER / 100)
# define COMPILER_VERSION_MINOR DEC(_MSC_VER % 100)
# if defined(_MSC_FULL_VER)
# if _MSC_VER >= 1400
/* _MSC_FULL_VER = VVRRPPPPP */
# define COMPILER_VERSION_PATCH DEC(_MSC_FULL_VER % 100000)
# else
/* _MSC_FULL_VER = VVRRPPPP */
# define COMPILER_VERSION_PATCH DEC(_MSC_FULL_VER % 10000)
# endif
# endif
# if defined(_MSC_BUILD)
# define COMPILER_VERSION_TWEAK DEC(_MSC_BUILD)
# endif
#elif defined(_ADI_COMPILER)
# define COMPILER_ID "ADSP"
#if defined(__VERSIONNUM__)
/* __VERSIONNUM__ = 0xVVRRPPTT */
# define COMPILER_VERSION_MAJOR DEC(__VERSIONNUM__ >> 24 & 0xFF)
# define COMPILER_VERSION_MINOR DEC(__VERSIONNUM__ >> 16 & 0xFF)
# define COMPILER_VERSION_PATCH DEC(__VERSIONNUM__ >> 8 & 0xFF)
# define COMPILER_VERSION_TWEAK DEC(__VERSIONNUM__ & 0xFF)
#endif
#elif defined(__IAR_SYSTEMS_ICC__) || defined(__IAR_SYSTEMS_ICC)
# define COMPILER_ID "IAR"
# if defined(__VER__) && defined(__ICCARM__)
# define COMPILER_VERSION_MAJOR DEC((__VER__) / 1000000)
# define COMPILER_VERSION_MINOR DEC(((__VER__) / 1000) % 1000)
# define COMPILER_VERSION_PATCH DEC((__VER__) % 1000)
# define COMPILER_VERSION_INTERNAL DEC(__IAR_SYSTEMS_ICC__)
# elif defined(__VER__) && (defined(__ICCAVR__) || defined(__ICCRX__) || defined(__ICCRH850__) || defined(__ICCRL78__) || defined(__ICC430__) || defined(__ICCRISCV__) || defined(__ICCV850__) || defined(__ICC8051__) || defined(__ICCSTM8__))
# define COMPILER_VERSION_MAJOR DEC((__VER__) / 100)
# define COMPILER_VERSION_MINOR DEC((__VER__) - (((__VER__) / 100)*100))
# define COMPILER_VERSION_PATCH DEC(__SUBVERSION__)
# define COMPILER_VERSION_INTERNAL DEC(__IAR_SYSTEMS_ICC__)
# endif
#elif defined(__DCC__) && defined(_DIAB_TOOL)
# define COMPILER_ID "Diab"
# define COMPILER_VERSION_MAJOR DEC(__VERSION_MAJOR_NUMBER__)
# define COMPILER_VERSION_MINOR DEC(__VERSION_MINOR_NUMBER__)
# define COMPILER_VERSION_PATCH DEC(__VERSION_ARCH_FEATURE_NUMBER__)
# define COMPILER_VERSION_TWEAK DEC(__VERSION_BUG_FIX_NUMBER__)
#elif defined(__SDCC_VERSION_MAJOR) || defined(SDCC)
# define COMPILER_ID "SDCC"
# if defined(__SDCC_VERSION_MAJOR)
# define COMPILER_VERSION_MAJOR DEC(__SDCC_VERSION_MAJOR)
# define COMPILER_VERSION_MINOR DEC(__SDCC_VERSION_MINOR)
# define COMPILER_VERSION_PATCH DEC(__SDCC_VERSION_PATCH)
# else
/* SDCC = VRP */
# define COMPILER_VERSION_MAJOR DEC(SDCC/100)
# define COMPILER_VERSION_MINOR DEC(SDCC/10 % 10)
# define COMPILER_VERSION_PATCH DEC(SDCC % 10)
# endif
/* These compilers are either not known or too old to define an
identification macro. Try to identify the platform and guess that
it is the native compiler. */
#elif defined(__hpux) || defined(__hpua)
# define COMPILER_ID "HP"
#else /* unknown compiler */
# define COMPILER_ID ""
#endif
/* Construct the string literal in pieces to prevent the source from
getting matched. Store it in a pointer rather than an array
because some compilers will just produce instructions to fill the
array rather than assigning a pointer to a static array. */
char const* info_compiler = "INFO" ":" "compiler[" COMPILER_ID "]";
#ifdef SIMULATE_ID
char const* info_simulate = "INFO" ":" "simulate[" SIMULATE_ID "]";
#endif
#ifdef __QNXNTO__
char const* qnxnto = "INFO" ":" "qnxnto[]";
#endif
#if defined(__CRAYXT_COMPUTE_LINUX_TARGET)
char const *info_cray = "INFO" ":" "compiler_wrapper[CrayPrgEnv]";
#endif
#define STRINGIFY_HELPER(X) #X
#define STRINGIFY(X) STRINGIFY_HELPER(X)
/* Identify known platforms by name. */
#if defined(__linux) || defined(__linux__) || defined(linux)
# define PLATFORM_ID "Linux"
#elif defined(__MSYS__)
# define PLATFORM_ID "MSYS"
#elif defined(__CYGWIN__)
# define PLATFORM_ID "Cygwin"
#elif defined(__MINGW32__)
# define PLATFORM_ID "MinGW"
#elif defined(__APPLE__)
# define PLATFORM_ID "Darwin"
#elif defined(_WIN32) || defined(__WIN32__) || defined(WIN32)
# define PLATFORM_ID "Windows"
#elif defined(__FreeBSD__) || defined(__FreeBSD)
# define PLATFORM_ID "FreeBSD"
#elif defined(__NetBSD__) || defined(__NetBSD)
# define PLATFORM_ID "NetBSD"
#elif defined(__OpenBSD__) || defined(__OPENBSD)
# define PLATFORM_ID "OpenBSD"
#elif defined(__sun) || defined(sun)
# define PLATFORM_ID "SunOS"
#elif defined(_AIX) || defined(__AIX) || defined(__AIX__) || defined(__aix) || defined(__aix__)
# define PLATFORM_ID "AIX"
#elif defined(__hpux) || defined(__hpux__)
# define PLATFORM_ID "HP-UX"
#elif defined(__HAIKU__)
# define PLATFORM_ID "Haiku"
#elif defined(__BeOS) || defined(__BEOS__) || defined(_BEOS)
# define PLATFORM_ID "BeOS"
#elif defined(__QNX__) || defined(__QNXNTO__)
# define PLATFORM_ID "QNX"
#elif defined(__tru64) || defined(_tru64) || defined(__TRU64__)
# define PLATFORM_ID "Tru64"
#elif defined(__riscos) || defined(__riscos__)
# define PLATFORM_ID "RISCos"
#elif defined(__sinix) || defined(__sinix__) || defined(__SINIX__)
# define PLATFORM_ID "SINIX"
#elif defined(__UNIX_SV__)
# define PLATFORM_ID "UNIX_SV"
#elif defined(__bsdos__)
# define PLATFORM_ID "BSDOS"
#elif defined(_MPRAS) || defined(MPRAS)
# define PLATFORM_ID "MP-RAS"
#elif defined(__osf) || defined(__osf__)
# define PLATFORM_ID "OSF1"
#elif defined(_SCO_SV) || defined(SCO_SV) || defined(sco_sv)
# define PLATFORM_ID "SCO_SV"
#elif defined(__ultrix) || defined(__ultrix__) || defined(_ULTRIX)
# define PLATFORM_ID "ULTRIX"
#elif defined(__XENIX__) || defined(_XENIX) || defined(XENIX)
# define PLATFORM_ID "Xenix"
#elif defined(__WATCOMC__)
# if defined(__LINUX__)
# define PLATFORM_ID "Linux"
# elif defined(__DOS__)
# define PLATFORM_ID "DOS"
# elif defined(__OS2__)
# define PLATFORM_ID "OS2"
# elif defined(__WINDOWS__)
# define PLATFORM_ID "Windows3x"
# elif defined(__VXWORKS__)
# define PLATFORM_ID "VxWorks"
# else /* unknown platform */
# define PLATFORM_ID
# endif
#elif defined(__INTEGRITY)
# if defined(INT_178B)
# define PLATFORM_ID "Integrity178"
# else /* regular Integrity */
# define PLATFORM_ID "Integrity"
# endif
# elif defined(_ADI_COMPILER)
# define PLATFORM_ID "ADSP"
#else /* unknown platform */
# define PLATFORM_ID
#endif
/* For windows compilers MSVC and Intel we can determine
the architecture of the compiler being used. This is because
the compilers do not have flags that can change the architecture,
but rather depend on which compiler is being used
*/
#if defined(_WIN32) && defined(_MSC_VER)
# if defined(_M_IA64)
# define ARCHITECTURE_ID "IA64"
# elif defined(_M_ARM64EC)
# define ARCHITECTURE_ID "ARM64EC"
# elif defined(_M_X64) || defined(_M_AMD64)
# define ARCHITECTURE_ID "x64"
# elif defined(_M_IX86)
# define ARCHITECTURE_ID "X86"
# elif defined(_M_ARM64)
# define ARCHITECTURE_ID "ARM64"
# elif defined(_M_ARM)
# if _M_ARM == 4
# define ARCHITECTURE_ID "ARMV4I"
# elif _M_ARM == 5
# define ARCHITECTURE_ID "ARMV5I"
# else
# define ARCHITECTURE_ID "ARMV" STRINGIFY(_M_ARM)
# endif
# elif defined(_M_MIPS)
# define ARCHITECTURE_ID "MIPS"
# elif defined(_M_SH)
# define ARCHITECTURE_ID "SHx"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__WATCOMC__)
# if defined(_M_I86)
# define ARCHITECTURE_ID "I86"
# elif defined(_M_IX86)
# define ARCHITECTURE_ID "X86"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__IAR_SYSTEMS_ICC__) || defined(__IAR_SYSTEMS_ICC)
# if defined(__ICCARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__ICCRX__)
# define ARCHITECTURE_ID "RX"
# elif defined(__ICCRH850__)
# define ARCHITECTURE_ID "RH850"
# elif defined(__ICCRL78__)
# define ARCHITECTURE_ID "RL78"
# elif defined(__ICCRISCV__)
# define ARCHITECTURE_ID "RISCV"
# elif defined(__ICCAVR__)
# define ARCHITECTURE_ID "AVR"
# elif defined(__ICC430__)
# define ARCHITECTURE_ID "MSP430"
# elif defined(__ICCV850__)
# define ARCHITECTURE_ID "V850"
# elif defined(__ICC8051__)
# define ARCHITECTURE_ID "8051"
# elif defined(__ICCSTM8__)
# define ARCHITECTURE_ID "STM8"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__ghs__)
# if defined(__PPC64__)
# define ARCHITECTURE_ID "PPC64"
# elif defined(__ppc__)
# define ARCHITECTURE_ID "PPC"
# elif defined(__ARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__x86_64__)
# define ARCHITECTURE_ID "x64"
# elif defined(__i386__)
# define ARCHITECTURE_ID "X86"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__clang__) && defined(__ti__)
# if defined(__ARM_ARCH)
# define ARCHITECTURE_ID "ARM"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__TI_COMPILER_VERSION__)
# if defined(__TI_ARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__MSP430__)
# define ARCHITECTURE_ID "MSP430"
# elif defined(__TMS320C28XX__)
# define ARCHITECTURE_ID "TMS320C28x"
# elif defined(__TMS320C6X__) || defined(_TMS320C6X)
# define ARCHITECTURE_ID "TMS320C6x"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
# elif defined(__ADSPSHARC__)
# define ARCHITECTURE_ID "SHARC"
# elif defined(__ADSPBLACKFIN__)
# define ARCHITECTURE_ID "Blackfin"
#elif defined(__TASKING__)
# if defined(__CTC__) || defined(__CPTC__)
# define ARCHITECTURE_ID "TriCore"
# elif defined(__CMCS__)
# define ARCHITECTURE_ID "MCS"
# elif defined(__CARM__) || defined(__CPARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__CARC__)
# define ARCHITECTURE_ID "ARC"
# elif defined(__C51__)
# define ARCHITECTURE_ID "8051"
# elif defined(__CPCP__)
# define ARCHITECTURE_ID "PCP"
# else
# define ARCHITECTURE_ID ""
# endif
#elif defined(__RENESAS__)
# if defined(__CCRX__)
# define ARCHITECTURE_ID "RX"
# elif defined(__CCRL__)
# define ARCHITECTURE_ID "RL78"
# elif defined(__CCRH__)
# define ARCHITECTURE_ID "RH850"
# else
# define ARCHITECTURE_ID ""
# endif
#else
# define ARCHITECTURE_ID
#endif
/* Convert integer to decimal digit literals. */
#define DEC(n) \
('0' + (((n) / 10000000)%10)), \
('0' + (((n) / 1000000)%10)), \
('0' + (((n) / 100000)%10)), \
('0' + (((n) / 10000)%10)), \
('0' + (((n) / 1000)%10)), \
('0' + (((n) / 100)%10)), \
('0' + (((n) / 10)%10)), \
('0' + ((n) % 10))
/* Convert integer to hex digit literals. */
#define HEX(n) \
('0' + ((n)>>28 & 0xF)), \
('0' + ((n)>>24 & 0xF)), \
('0' + ((n)>>20 & 0xF)), \
('0' + ((n)>>16 & 0xF)), \
('0' + ((n)>>12 & 0xF)), \
('0' + ((n)>>8 & 0xF)), \
('0' + ((n)>>4 & 0xF)), \
('0' + ((n) & 0xF))
/* Construct a string literal encoding the version number. */
#ifdef COMPILER_VERSION
char const* info_version = "INFO" ":" "compiler_version[" COMPILER_VERSION "]";
/* Construct a string literal encoding the version number components. */
#elif defined(COMPILER_VERSION_MAJOR)
char const info_version[] = {
'I', 'N', 'F', 'O', ':',
'c','o','m','p','i','l','e','r','_','v','e','r','s','i','o','n','[',
COMPILER_VERSION_MAJOR,
# ifdef COMPILER_VERSION_MINOR
'.', COMPILER_VERSION_MINOR,
# ifdef COMPILER_VERSION_PATCH
'.', COMPILER_VERSION_PATCH,
# ifdef COMPILER_VERSION_TWEAK
'.', COMPILER_VERSION_TWEAK,
# endif
# endif
# endif
']','\0'};
#endif
/* Construct a string literal encoding the internal version number. */
#ifdef COMPILER_VERSION_INTERNAL
char const info_version_internal[] = {
'I', 'N', 'F', 'O', ':',
'c','o','m','p','i','l','e','r','_','v','e','r','s','i','o','n','_',
'i','n','t','e','r','n','a','l','[',
COMPILER_VERSION_INTERNAL,']','\0'};
#elif defined(COMPILER_VERSION_INTERNAL_STR)
char const* info_version_internal = "INFO" ":" "compiler_version_internal[" COMPILER_VERSION_INTERNAL_STR "]";
#endif
/* Construct a string literal encoding the version number components. */
#ifdef SIMULATE_VERSION_MAJOR
char const info_simulate_version[] = {
'I', 'N', 'F', 'O', ':',
's','i','m','u','l','a','t','e','_','v','e','r','s','i','o','n','[',
SIMULATE_VERSION_MAJOR,
# ifdef SIMULATE_VERSION_MINOR
'.', SIMULATE_VERSION_MINOR,
# ifdef SIMULATE_VERSION_PATCH
'.', SIMULATE_VERSION_PATCH,
# ifdef SIMULATE_VERSION_TWEAK
'.', SIMULATE_VERSION_TWEAK,
# endif
# endif
# endif
']','\0'};
#endif
/* Construct the string literal in pieces to prevent the source from
getting matched. Store it in a pointer rather than an array
because some compilers will just produce instructions to fill the
array rather than assigning a pointer to a static array. */
char const* info_platform = "INFO" ":" "platform[" PLATFORM_ID "]";
char const* info_arch = "INFO" ":" "arch[" ARCHITECTURE_ID "]";
#define C_STD_99 199901L
#define C_STD_11 201112L
#define C_STD_17 201710L
#define C_STD_23 202311L
#ifdef __STDC_VERSION__
# define C_STD __STDC_VERSION__
#endif
#if !defined(__STDC__) && !defined(__clang__) && !defined(__RENESAS__)
# if defined(_MSC_VER) || defined(__ibmxl__) || defined(__IBMC__)
# define C_VERSION "90"
# else
# define C_VERSION
# endif
#elif C_STD > C_STD_17
# define C_VERSION "23"
#elif C_STD > C_STD_11
# define C_VERSION "17"
#elif C_STD > C_STD_99
# define C_VERSION "11"
#elif C_STD >= C_STD_99
# define C_VERSION "99"
#else
# define C_VERSION "90"
#endif
const char* info_language_standard_default =
"INFO" ":" "standard_default[" C_VERSION "]";
const char* info_language_extensions_default = "INFO" ":" "extensions_default["
#if (defined(__clang__) || defined(__GNUC__) || defined(__xlC__) || \
defined(__TI_COMPILER_VERSION__) || defined(__RENESAS__)) && \
!defined(__STRICT_ANSI__)
"ON"
#else
"OFF"
#endif
"]";
/*--------------------------------------------------------------------------*/
#ifdef ID_VOID_MAIN
void main() {}
#else
# if defined(__CLASSIC_C__)
int main(argc, argv) int argc; char *argv[];
# else
int main(int argc, char* argv[])
# endif
{
int require = 0;
require += info_compiler[argc];
require += info_platform[argc];
require += info_arch[argc];
#ifdef COMPILER_VERSION_MAJOR
require += info_version[argc];
#endif
#if defined(COMPILER_VERSION_INTERNAL) || defined(COMPILER_VERSION_INTERNAL_STR)
require += info_version_internal[argc];
#endif
#ifdef SIMULATE_ID
require += info_simulate[argc];
#endif
#ifdef SIMULATE_VERSION_MAJOR
require += info_simulate_version[argc];
#endif
#if defined(__CRAYXT_COMPUTE_LINUX_TARGET)
require += info_cray[argc];
#endif
require += info_language_standard_default[argc];
require += info_language_extensions_default[argc];
(void)argv;
return require;
}
#endif

Binary file not shown.

View File

@ -0,0 +1,949 @@
/* This source file must have a .cpp extension so that all C++ compilers
recognize the extension without flags. Borland does not know .cxx for
example. */
#ifndef __cplusplus
# error "A C compiler has been selected for C++."
#endif
#if !defined(__has_include)
/* If the compiler does not have __has_include, pretend the answer is
always no. */
# define __has_include(x) 0
#endif
/* Version number components: V=Version, R=Revision, P=Patch
Version date components: YYYY=Year, MM=Month, DD=Day */
#if defined(__INTEL_COMPILER) || defined(__ICC)
# define COMPILER_ID "Intel"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# if defined(__GNUC__)
# define SIMULATE_ID "GNU"
# endif
/* __INTEL_COMPILER = VRP prior to 2021, and then VVVV for 2021 and later,
except that a few beta releases use the old format with V=2021. */
# if __INTEL_COMPILER < 2021 || __INTEL_COMPILER == 202110 || __INTEL_COMPILER == 202111
# define COMPILER_VERSION_MAJOR DEC(__INTEL_COMPILER/100)
# define COMPILER_VERSION_MINOR DEC(__INTEL_COMPILER/10 % 10)
# if defined(__INTEL_COMPILER_UPDATE)
# define COMPILER_VERSION_PATCH DEC(__INTEL_COMPILER_UPDATE)
# else
# define COMPILER_VERSION_PATCH DEC(__INTEL_COMPILER % 10)
# endif
# else
# define COMPILER_VERSION_MAJOR DEC(__INTEL_COMPILER)
# define COMPILER_VERSION_MINOR DEC(__INTEL_COMPILER_UPDATE)
/* The third version component from --version is an update index,
but no macro is provided for it. */
# define COMPILER_VERSION_PATCH DEC(0)
# endif
# if defined(__INTEL_COMPILER_BUILD_DATE)
/* __INTEL_COMPILER_BUILD_DATE = YYYYMMDD */
# define COMPILER_VERSION_TWEAK DEC(__INTEL_COMPILER_BUILD_DATE)
# endif
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
# if defined(__GNUC__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
# elif defined(__GNUG__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUG__)
# endif
# if defined(__GNUC_MINOR__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
# endif
# if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
#elif (defined(__clang__) && defined(__INTEL_CLANG_COMPILER)) || defined(__INTEL_LLVM_COMPILER)
# define COMPILER_ID "IntelLLVM"
#if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
#endif
#if defined(__GNUC__)
# define SIMULATE_ID "GNU"
#endif
/* __INTEL_LLVM_COMPILER = VVVVRP prior to 2021.2.0, VVVVRRPP for 2021.2.0 and
* later. Look for 6 digit vs. 8 digit version number to decide encoding.
* VVVV is no smaller than the current year when a version is released.
*/
#if __INTEL_LLVM_COMPILER < 1000000L
# define COMPILER_VERSION_MAJOR DEC(__INTEL_LLVM_COMPILER/100)
# define COMPILER_VERSION_MINOR DEC(__INTEL_LLVM_COMPILER/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__INTEL_LLVM_COMPILER % 10)
#else
# define COMPILER_VERSION_MAJOR DEC(__INTEL_LLVM_COMPILER/10000)
# define COMPILER_VERSION_MINOR DEC(__INTEL_LLVM_COMPILER/100 % 100)
# define COMPILER_VERSION_PATCH DEC(__INTEL_LLVM_COMPILER % 100)
#endif
#if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
#endif
#if defined(__GNUC__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
#elif defined(__GNUG__)
# define SIMULATE_VERSION_MAJOR DEC(__GNUG__)
#endif
#if defined(__GNUC_MINOR__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
#endif
#if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
#endif
#elif defined(__PATHCC__)
# define COMPILER_ID "PathScale"
# define COMPILER_VERSION_MAJOR DEC(__PATHCC__)
# define COMPILER_VERSION_MINOR DEC(__PATHCC_MINOR__)
# if defined(__PATHCC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__PATHCC_PATCHLEVEL__)
# endif
#elif defined(__BORLANDC__) && defined(__CODEGEARC_VERSION__)
# define COMPILER_ID "Embarcadero"
# define COMPILER_VERSION_MAJOR HEX(__CODEGEARC_VERSION__>>24 & 0x00FF)
# define COMPILER_VERSION_MINOR HEX(__CODEGEARC_VERSION__>>16 & 0x00FF)
# define COMPILER_VERSION_PATCH DEC(__CODEGEARC_VERSION__ & 0xFFFF)
#elif defined(__BORLANDC__)
# define COMPILER_ID "Borland"
/* __BORLANDC__ = 0xVRR */
# define COMPILER_VERSION_MAJOR HEX(__BORLANDC__>>8)
# define COMPILER_VERSION_MINOR HEX(__BORLANDC__ & 0xFF)
#elif defined(__WATCOMC__) && __WATCOMC__ < 1200
# define COMPILER_ID "Watcom"
/* __WATCOMC__ = VVRR */
# define COMPILER_VERSION_MAJOR DEC(__WATCOMC__ / 100)
# define COMPILER_VERSION_MINOR DEC((__WATCOMC__ / 10) % 10)
# if (__WATCOMC__ % 10) > 0
# define COMPILER_VERSION_PATCH DEC(__WATCOMC__ % 10)
# endif
#elif defined(__WATCOMC__)
# define COMPILER_ID "OpenWatcom"
/* __WATCOMC__ = VVRP + 1100 */
# define COMPILER_VERSION_MAJOR DEC((__WATCOMC__ - 1100) / 100)
# define COMPILER_VERSION_MINOR DEC((__WATCOMC__ / 10) % 10)
# if (__WATCOMC__ % 10) > 0
# define COMPILER_VERSION_PATCH DEC(__WATCOMC__ % 10)
# endif
#elif defined(__SUNPRO_CC)
# define COMPILER_ID "SunPro"
# if __SUNPRO_CC >= 0x5100
/* __SUNPRO_CC = 0xVRRP */
# define COMPILER_VERSION_MAJOR HEX(__SUNPRO_CC>>12)
# define COMPILER_VERSION_MINOR HEX(__SUNPRO_CC>>4 & 0xFF)
# define COMPILER_VERSION_PATCH HEX(__SUNPRO_CC & 0xF)
# else
/* __SUNPRO_CC = 0xVRP */
# define COMPILER_VERSION_MAJOR HEX(__SUNPRO_CC>>8)
# define COMPILER_VERSION_MINOR HEX(__SUNPRO_CC>>4 & 0xF)
# define COMPILER_VERSION_PATCH HEX(__SUNPRO_CC & 0xF)
# endif
#elif defined(__HP_aCC)
# define COMPILER_ID "HP"
/* __HP_aCC = VVRRPP */
# define COMPILER_VERSION_MAJOR DEC(__HP_aCC/10000)
# define COMPILER_VERSION_MINOR DEC(__HP_aCC/100 % 100)
# define COMPILER_VERSION_PATCH DEC(__HP_aCC % 100)
#elif defined(__DECCXX)
# define COMPILER_ID "Compaq"
/* __DECCXX_VER = VVRRTPPPP */
# define COMPILER_VERSION_MAJOR DEC(__DECCXX_VER/10000000)
# define COMPILER_VERSION_MINOR DEC(__DECCXX_VER/100000 % 100)
# define COMPILER_VERSION_PATCH DEC(__DECCXX_VER % 10000)
#elif defined(__IBMCPP__) && defined(__COMPILER_VER__)
# define COMPILER_ID "zOS"
/* __IBMCPP__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMCPP__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMCPP__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMCPP__ % 10)
#elif defined(__open_xl__) && defined(__clang__)
# define COMPILER_ID "IBMClang"
# define COMPILER_VERSION_MAJOR DEC(__open_xl_version__)
# define COMPILER_VERSION_MINOR DEC(__open_xl_release__)
# define COMPILER_VERSION_PATCH DEC(__open_xl_modification__)
# define COMPILER_VERSION_TWEAK DEC(__open_xl_ptf_fix_level__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(__ibmxl__) && defined(__clang__)
# define COMPILER_ID "XLClang"
# define COMPILER_VERSION_MAJOR DEC(__ibmxl_version__)
# define COMPILER_VERSION_MINOR DEC(__ibmxl_release__)
# define COMPILER_VERSION_PATCH DEC(__ibmxl_modification__)
# define COMPILER_VERSION_TWEAK DEC(__ibmxl_ptf_fix_level__)
#elif defined(__IBMCPP__) && !defined(__COMPILER_VER__) && __IBMCPP__ >= 800
# define COMPILER_ID "XL"
/* __IBMCPP__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMCPP__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMCPP__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMCPP__ % 10)
#elif defined(__IBMCPP__) && !defined(__COMPILER_VER__) && __IBMCPP__ < 800
# define COMPILER_ID "VisualAge"
/* __IBMCPP__ = VRP */
# define COMPILER_VERSION_MAJOR DEC(__IBMCPP__/100)
# define COMPILER_VERSION_MINOR DEC(__IBMCPP__/10 % 10)
# define COMPILER_VERSION_PATCH DEC(__IBMCPP__ % 10)
#elif defined(__NVCOMPILER)
# define COMPILER_ID "NVHPC"
# define COMPILER_VERSION_MAJOR DEC(__NVCOMPILER_MAJOR__)
# define COMPILER_VERSION_MINOR DEC(__NVCOMPILER_MINOR__)
# if defined(__NVCOMPILER_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__NVCOMPILER_PATCHLEVEL__)
# endif
#elif defined(__PGI)
# define COMPILER_ID "PGI"
# define COMPILER_VERSION_MAJOR DEC(__PGIC__)
# define COMPILER_VERSION_MINOR DEC(__PGIC_MINOR__)
# if defined(__PGIC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__PGIC_PATCHLEVEL__)
# endif
#elif defined(__clang__) && defined(__cray__)
# define COMPILER_ID "CrayClang"
# define COMPILER_VERSION_MAJOR DEC(__cray_major__)
# define COMPILER_VERSION_MINOR DEC(__cray_minor__)
# define COMPILER_VERSION_PATCH DEC(__cray_patchlevel__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(_CRAYC)
# define COMPILER_ID "Cray"
# define COMPILER_VERSION_MAJOR DEC(_RELEASE_MAJOR)
# define COMPILER_VERSION_MINOR DEC(_RELEASE_MINOR)
#elif defined(__TI_COMPILER_VERSION__)
# define COMPILER_ID "TI"
/* __TI_COMPILER_VERSION__ = VVVRRRPPP */
# define COMPILER_VERSION_MAJOR DEC(__TI_COMPILER_VERSION__/1000000)
# define COMPILER_VERSION_MINOR DEC(__TI_COMPILER_VERSION__/1000 % 1000)
# define COMPILER_VERSION_PATCH DEC(__TI_COMPILER_VERSION__ % 1000)
#elif defined(__CLANG_FUJITSU)
# define COMPILER_ID "FujitsuClang"
# define COMPILER_VERSION_MAJOR DEC(__FCC_major__)
# define COMPILER_VERSION_MINOR DEC(__FCC_minor__)
# define COMPILER_VERSION_PATCH DEC(__FCC_patchlevel__)
# define COMPILER_VERSION_INTERNAL_STR __clang_version__
#elif defined(__FUJITSU)
# define COMPILER_ID "Fujitsu"
# if defined(__FCC_version__)
# define COMPILER_VERSION __FCC_version__
# elif defined(__FCC_major__)
# define COMPILER_VERSION_MAJOR DEC(__FCC_major__)
# define COMPILER_VERSION_MINOR DEC(__FCC_minor__)
# define COMPILER_VERSION_PATCH DEC(__FCC_patchlevel__)
# endif
# if defined(__fcc_version)
# define COMPILER_VERSION_INTERNAL DEC(__fcc_version)
# elif defined(__FCC_VERSION)
# define COMPILER_VERSION_INTERNAL DEC(__FCC_VERSION)
# endif
#elif defined(__ghs__)
# define COMPILER_ID "GHS"
/* __GHS_VERSION_NUMBER = VVVVRP */
# ifdef __GHS_VERSION_NUMBER
# define COMPILER_VERSION_MAJOR DEC(__GHS_VERSION_NUMBER / 100)
# define COMPILER_VERSION_MINOR DEC(__GHS_VERSION_NUMBER / 10 % 10)
# define COMPILER_VERSION_PATCH DEC(__GHS_VERSION_NUMBER % 10)
# endif
#elif defined(__TASKING__)
# define COMPILER_ID "Tasking"
# define COMPILER_VERSION_MAJOR DEC(__VERSION__/1000)
# define COMPILER_VERSION_MINOR DEC(__VERSION__ % 100)
# define COMPILER_VERSION_INTERNAL DEC(__VERSION__)
#elif defined(__ORANGEC__)
# define COMPILER_ID "OrangeC"
# define COMPILER_VERSION_MAJOR DEC(__ORANGEC_MAJOR__)
# define COMPILER_VERSION_MINOR DEC(__ORANGEC_MINOR__)
# define COMPILER_VERSION_PATCH DEC(__ORANGEC_PATCHLEVEL__)
#elif defined(__RENESAS__)
# define COMPILER_ID "Renesas"
/* __RENESAS_VERSION__ = 0xVVRRPP00 */
# define COMPILER_VERSION_MAJOR HEX(__RENESAS_VERSION__ >> 24 & 0xFF)
# define COMPILER_VERSION_MINOR HEX(__RENESAS_VERSION__ >> 16 & 0xFF)
# define COMPILER_VERSION_PATCH HEX(__RENESAS_VERSION__ >> 8 & 0xFF)
#elif defined(__SCO_VERSION__)
# define COMPILER_ID "SCO"
#elif defined(__ARMCC_VERSION) && !defined(__clang__)
# define COMPILER_ID "ARMCC"
#if __ARMCC_VERSION >= 1000000
/* __ARMCC_VERSION = VRRPPPP */
# define COMPILER_VERSION_MAJOR DEC(__ARMCC_VERSION/1000000)
# define COMPILER_VERSION_MINOR DEC(__ARMCC_VERSION/10000 % 100)
# define COMPILER_VERSION_PATCH DEC(__ARMCC_VERSION % 10000)
#else
/* __ARMCC_VERSION = VRPPPP */
# define COMPILER_VERSION_MAJOR DEC(__ARMCC_VERSION/100000)
# define COMPILER_VERSION_MINOR DEC(__ARMCC_VERSION/10000 % 10)
# define COMPILER_VERSION_PATCH DEC(__ARMCC_VERSION % 10000)
#endif
#elif defined(__clang__) && defined(__apple_build_version__)
# define COMPILER_ID "AppleClang"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# define COMPILER_VERSION_MAJOR DEC(__clang_major__)
# define COMPILER_VERSION_MINOR DEC(__clang_minor__)
# define COMPILER_VERSION_PATCH DEC(__clang_patchlevel__)
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
# define COMPILER_VERSION_TWEAK DEC(__apple_build_version__)
#elif defined(__clang__) && defined(__ARMCOMPILER_VERSION)
# define COMPILER_ID "ARMClang"
# define COMPILER_VERSION_MAJOR DEC(__ARMCOMPILER_VERSION/1000000)
# define COMPILER_VERSION_MINOR DEC(__ARMCOMPILER_VERSION/10000 % 100)
# define COMPILER_VERSION_PATCH DEC(__ARMCOMPILER_VERSION/100 % 100)
# define COMPILER_VERSION_INTERNAL DEC(__ARMCOMPILER_VERSION)
#elif defined(__clang__) && defined(__ti__)
# define COMPILER_ID "TIClang"
# define COMPILER_VERSION_MAJOR DEC(__ti_major__)
# define COMPILER_VERSION_MINOR DEC(__ti_minor__)
# define COMPILER_VERSION_PATCH DEC(__ti_patchlevel__)
# define COMPILER_VERSION_INTERNAL DEC(__ti_version__)
#elif defined(__clang__)
# define COMPILER_ID "Clang"
# if defined(_MSC_VER)
# define SIMULATE_ID "MSVC"
# endif
# define COMPILER_VERSION_MAJOR DEC(__clang_major__)
# define COMPILER_VERSION_MINOR DEC(__clang_minor__)
# define COMPILER_VERSION_PATCH DEC(__clang_patchlevel__)
# if defined(_MSC_VER)
/* _MSC_VER = VVRR */
# define SIMULATE_VERSION_MAJOR DEC(_MSC_VER / 100)
# define SIMULATE_VERSION_MINOR DEC(_MSC_VER % 100)
# endif
#elif defined(__LCC__) && (defined(__GNUC__) || defined(__GNUG__) || defined(__MCST__))
# define COMPILER_ID "LCC"
# define COMPILER_VERSION_MAJOR DEC(__LCC__ / 100)
# define COMPILER_VERSION_MINOR DEC(__LCC__ % 100)
# if defined(__LCC_MINOR__)
# define COMPILER_VERSION_PATCH DEC(__LCC_MINOR__)
# endif
# if defined(__GNUC__) && defined(__GNUC_MINOR__)
# define SIMULATE_ID "GNU"
# define SIMULATE_VERSION_MAJOR DEC(__GNUC__)
# define SIMULATE_VERSION_MINOR DEC(__GNUC_MINOR__)
# if defined(__GNUC_PATCHLEVEL__)
# define SIMULATE_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
# endif
#elif defined(__GNUC__) || defined(__GNUG__)
# define COMPILER_ID "GNU"
# if defined(__GNUC__)
# define COMPILER_VERSION_MAJOR DEC(__GNUC__)
# else
# define COMPILER_VERSION_MAJOR DEC(__GNUG__)
# endif
# if defined(__GNUC_MINOR__)
# define COMPILER_VERSION_MINOR DEC(__GNUC_MINOR__)
# endif
# if defined(__GNUC_PATCHLEVEL__)
# define COMPILER_VERSION_PATCH DEC(__GNUC_PATCHLEVEL__)
# endif
#elif defined(_MSC_VER)
# define COMPILER_ID "MSVC"
/* _MSC_VER = VVRR */
# define COMPILER_VERSION_MAJOR DEC(_MSC_VER / 100)
# define COMPILER_VERSION_MINOR DEC(_MSC_VER % 100)
# if defined(_MSC_FULL_VER)
# if _MSC_VER >= 1400
/* _MSC_FULL_VER = VVRRPPPPP */
# define COMPILER_VERSION_PATCH DEC(_MSC_FULL_VER % 100000)
# else
/* _MSC_FULL_VER = VVRRPPPP */
# define COMPILER_VERSION_PATCH DEC(_MSC_FULL_VER % 10000)
# endif
# endif
# if defined(_MSC_BUILD)
# define COMPILER_VERSION_TWEAK DEC(_MSC_BUILD)
# endif
#elif defined(_ADI_COMPILER)
# define COMPILER_ID "ADSP"
#if defined(__VERSIONNUM__)
/* __VERSIONNUM__ = 0xVVRRPPTT */
# define COMPILER_VERSION_MAJOR DEC(__VERSIONNUM__ >> 24 & 0xFF)
# define COMPILER_VERSION_MINOR DEC(__VERSIONNUM__ >> 16 & 0xFF)
# define COMPILER_VERSION_PATCH DEC(__VERSIONNUM__ >> 8 & 0xFF)
# define COMPILER_VERSION_TWEAK DEC(__VERSIONNUM__ & 0xFF)
#endif
#elif defined(__IAR_SYSTEMS_ICC__) || defined(__IAR_SYSTEMS_ICC)
# define COMPILER_ID "IAR"
# if defined(__VER__) && defined(__ICCARM__)
# define COMPILER_VERSION_MAJOR DEC((__VER__) / 1000000)
# define COMPILER_VERSION_MINOR DEC(((__VER__) / 1000) % 1000)
# define COMPILER_VERSION_PATCH DEC((__VER__) % 1000)
# define COMPILER_VERSION_INTERNAL DEC(__IAR_SYSTEMS_ICC__)
# elif defined(__VER__) && (defined(__ICCAVR__) || defined(__ICCRX__) || defined(__ICCRH850__) || defined(__ICCRL78__) || defined(__ICC430__) || defined(__ICCRISCV__) || defined(__ICCV850__) || defined(__ICC8051__) || defined(__ICCSTM8__))
# define COMPILER_VERSION_MAJOR DEC((__VER__) / 100)
# define COMPILER_VERSION_MINOR DEC((__VER__) - (((__VER__) / 100)*100))
# define COMPILER_VERSION_PATCH DEC(__SUBVERSION__)
# define COMPILER_VERSION_INTERNAL DEC(__IAR_SYSTEMS_ICC__)
# endif
#elif defined(__DCC__) && defined(_DIAB_TOOL)
# define COMPILER_ID "Diab"
# define COMPILER_VERSION_MAJOR DEC(__VERSION_MAJOR_NUMBER__)
# define COMPILER_VERSION_MINOR DEC(__VERSION_MINOR_NUMBER__)
# define COMPILER_VERSION_PATCH DEC(__VERSION_ARCH_FEATURE_NUMBER__)
# define COMPILER_VERSION_TWEAK DEC(__VERSION_BUG_FIX_NUMBER__)
/* These compilers are either not known or too old to define an
identification macro. Try to identify the platform and guess that
it is the native compiler. */
#elif defined(__hpux) || defined(__hpua)
# define COMPILER_ID "HP"
#else /* unknown compiler */
# define COMPILER_ID ""
#endif
/* Construct the string literal in pieces to prevent the source from
getting matched. Store it in a pointer rather than an array
because some compilers will just produce instructions to fill the
array rather than assigning a pointer to a static array. */
char const* info_compiler = "INFO" ":" "compiler[" COMPILER_ID "]";
#ifdef SIMULATE_ID
char const* info_simulate = "INFO" ":" "simulate[" SIMULATE_ID "]";
#endif
#ifdef __QNXNTO__
char const* qnxnto = "INFO" ":" "qnxnto[]";
#endif
#if defined(__CRAYXT_COMPUTE_LINUX_TARGET)
char const *info_cray = "INFO" ":" "compiler_wrapper[CrayPrgEnv]";
#endif
#define STRINGIFY_HELPER(X) #X
#define STRINGIFY(X) STRINGIFY_HELPER(X)
/* Identify known platforms by name. */
#if defined(__linux) || defined(__linux__) || defined(linux)
# define PLATFORM_ID "Linux"
#elif defined(__MSYS__)
# define PLATFORM_ID "MSYS"
#elif defined(__CYGWIN__)
# define PLATFORM_ID "Cygwin"
#elif defined(__MINGW32__)
# define PLATFORM_ID "MinGW"
#elif defined(__APPLE__)
# define PLATFORM_ID "Darwin"
#elif defined(_WIN32) || defined(__WIN32__) || defined(WIN32)
# define PLATFORM_ID "Windows"
#elif defined(__FreeBSD__) || defined(__FreeBSD)
# define PLATFORM_ID "FreeBSD"
#elif defined(__NetBSD__) || defined(__NetBSD)
# define PLATFORM_ID "NetBSD"
#elif defined(__OpenBSD__) || defined(__OPENBSD)
# define PLATFORM_ID "OpenBSD"
#elif defined(__sun) || defined(sun)
# define PLATFORM_ID "SunOS"
#elif defined(_AIX) || defined(__AIX) || defined(__AIX__) || defined(__aix) || defined(__aix__)
# define PLATFORM_ID "AIX"
#elif defined(__hpux) || defined(__hpux__)
# define PLATFORM_ID "HP-UX"
#elif defined(__HAIKU__)
# define PLATFORM_ID "Haiku"
#elif defined(__BeOS) || defined(__BEOS__) || defined(_BEOS)
# define PLATFORM_ID "BeOS"
#elif defined(__QNX__) || defined(__QNXNTO__)
# define PLATFORM_ID "QNX"
#elif defined(__tru64) || defined(_tru64) || defined(__TRU64__)
# define PLATFORM_ID "Tru64"
#elif defined(__riscos) || defined(__riscos__)
# define PLATFORM_ID "RISCos"
#elif defined(__sinix) || defined(__sinix__) || defined(__SINIX__)
# define PLATFORM_ID "SINIX"
#elif defined(__UNIX_SV__)
# define PLATFORM_ID "UNIX_SV"
#elif defined(__bsdos__)
# define PLATFORM_ID "BSDOS"
#elif defined(_MPRAS) || defined(MPRAS)
# define PLATFORM_ID "MP-RAS"
#elif defined(__osf) || defined(__osf__)
# define PLATFORM_ID "OSF1"
#elif defined(_SCO_SV) || defined(SCO_SV) || defined(sco_sv)
# define PLATFORM_ID "SCO_SV"
#elif defined(__ultrix) || defined(__ultrix__) || defined(_ULTRIX)
# define PLATFORM_ID "ULTRIX"
#elif defined(__XENIX__) || defined(_XENIX) || defined(XENIX)
# define PLATFORM_ID "Xenix"
#elif defined(__WATCOMC__)
# if defined(__LINUX__)
# define PLATFORM_ID "Linux"
# elif defined(__DOS__)
# define PLATFORM_ID "DOS"
# elif defined(__OS2__)
# define PLATFORM_ID "OS2"
# elif defined(__WINDOWS__)
# define PLATFORM_ID "Windows3x"
# elif defined(__VXWORKS__)
# define PLATFORM_ID "VxWorks"
# else /* unknown platform */
# define PLATFORM_ID
# endif
#elif defined(__INTEGRITY)
# if defined(INT_178B)
# define PLATFORM_ID "Integrity178"
# else /* regular Integrity */
# define PLATFORM_ID "Integrity"
# endif
# elif defined(_ADI_COMPILER)
# define PLATFORM_ID "ADSP"
#else /* unknown platform */
# define PLATFORM_ID
#endif
/* For windows compilers MSVC and Intel we can determine
the architecture of the compiler being used. This is because
the compilers do not have flags that can change the architecture,
but rather depend on which compiler is being used
*/
#if defined(_WIN32) && defined(_MSC_VER)
# if defined(_M_IA64)
# define ARCHITECTURE_ID "IA64"
# elif defined(_M_ARM64EC)
# define ARCHITECTURE_ID "ARM64EC"
# elif defined(_M_X64) || defined(_M_AMD64)
# define ARCHITECTURE_ID "x64"
# elif defined(_M_IX86)
# define ARCHITECTURE_ID "X86"
# elif defined(_M_ARM64)
# define ARCHITECTURE_ID "ARM64"
# elif defined(_M_ARM)
# if _M_ARM == 4
# define ARCHITECTURE_ID "ARMV4I"
# elif _M_ARM == 5
# define ARCHITECTURE_ID "ARMV5I"
# else
# define ARCHITECTURE_ID "ARMV" STRINGIFY(_M_ARM)
# endif
# elif defined(_M_MIPS)
# define ARCHITECTURE_ID "MIPS"
# elif defined(_M_SH)
# define ARCHITECTURE_ID "SHx"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__WATCOMC__)
# if defined(_M_I86)
# define ARCHITECTURE_ID "I86"
# elif defined(_M_IX86)
# define ARCHITECTURE_ID "X86"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__IAR_SYSTEMS_ICC__) || defined(__IAR_SYSTEMS_ICC)
# if defined(__ICCARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__ICCRX__)
# define ARCHITECTURE_ID "RX"
# elif defined(__ICCRH850__)
# define ARCHITECTURE_ID "RH850"
# elif defined(__ICCRL78__)
# define ARCHITECTURE_ID "RL78"
# elif defined(__ICCRISCV__)
# define ARCHITECTURE_ID "RISCV"
# elif defined(__ICCAVR__)
# define ARCHITECTURE_ID "AVR"
# elif defined(__ICC430__)
# define ARCHITECTURE_ID "MSP430"
# elif defined(__ICCV850__)
# define ARCHITECTURE_ID "V850"
# elif defined(__ICC8051__)
# define ARCHITECTURE_ID "8051"
# elif defined(__ICCSTM8__)
# define ARCHITECTURE_ID "STM8"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__ghs__)
# if defined(__PPC64__)
# define ARCHITECTURE_ID "PPC64"
# elif defined(__ppc__)
# define ARCHITECTURE_ID "PPC"
# elif defined(__ARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__x86_64__)
# define ARCHITECTURE_ID "x64"
# elif defined(__i386__)
# define ARCHITECTURE_ID "X86"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__clang__) && defined(__ti__)
# if defined(__ARM_ARCH)
# define ARCHITECTURE_ID "ARM"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
#elif defined(__TI_COMPILER_VERSION__)
# if defined(__TI_ARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__MSP430__)
# define ARCHITECTURE_ID "MSP430"
# elif defined(__TMS320C28XX__)
# define ARCHITECTURE_ID "TMS320C28x"
# elif defined(__TMS320C6X__) || defined(_TMS320C6X)
# define ARCHITECTURE_ID "TMS320C6x"
# else /* unknown architecture */
# define ARCHITECTURE_ID ""
# endif
# elif defined(__ADSPSHARC__)
# define ARCHITECTURE_ID "SHARC"
# elif defined(__ADSPBLACKFIN__)
# define ARCHITECTURE_ID "Blackfin"
#elif defined(__TASKING__)
# if defined(__CTC__) || defined(__CPTC__)
# define ARCHITECTURE_ID "TriCore"
# elif defined(__CMCS__)
# define ARCHITECTURE_ID "MCS"
# elif defined(__CARM__) || defined(__CPARM__)
# define ARCHITECTURE_ID "ARM"
# elif defined(__CARC__)
# define ARCHITECTURE_ID "ARC"
# elif defined(__C51__)
# define ARCHITECTURE_ID "8051"
# elif defined(__CPCP__)
# define ARCHITECTURE_ID "PCP"
# else
# define ARCHITECTURE_ID ""
# endif
#elif defined(__RENESAS__)
# if defined(__CCRX__)
# define ARCHITECTURE_ID "RX"
# elif defined(__CCRL__)
# define ARCHITECTURE_ID "RL78"
# elif defined(__CCRH__)
# define ARCHITECTURE_ID "RH850"
# else
# define ARCHITECTURE_ID ""
# endif
#else
# define ARCHITECTURE_ID
#endif
/* Convert integer to decimal digit literals. */
#define DEC(n) \
('0' + (((n) / 10000000)%10)), \
('0' + (((n) / 1000000)%10)), \
('0' + (((n) / 100000)%10)), \
('0' + (((n) / 10000)%10)), \
('0' + (((n) / 1000)%10)), \
('0' + (((n) / 100)%10)), \
('0' + (((n) / 10)%10)), \
('0' + ((n) % 10))
/* Convert integer to hex digit literals. */
#define HEX(n) \
('0' + ((n)>>28 & 0xF)), \
('0' + ((n)>>24 & 0xF)), \
('0' + ((n)>>20 & 0xF)), \
('0' + ((n)>>16 & 0xF)), \
('0' + ((n)>>12 & 0xF)), \
('0' + ((n)>>8 & 0xF)), \
('0' + ((n)>>4 & 0xF)), \
('0' + ((n) & 0xF))
/* Construct a string literal encoding the version number. */
#ifdef COMPILER_VERSION
char const* info_version = "INFO" ":" "compiler_version[" COMPILER_VERSION "]";
/* Construct a string literal encoding the version number components. */
#elif defined(COMPILER_VERSION_MAJOR)
char const info_version[] = {
'I', 'N', 'F', 'O', ':',
'c','o','m','p','i','l','e','r','_','v','e','r','s','i','o','n','[',
COMPILER_VERSION_MAJOR,
# ifdef COMPILER_VERSION_MINOR
'.', COMPILER_VERSION_MINOR,
# ifdef COMPILER_VERSION_PATCH
'.', COMPILER_VERSION_PATCH,
# ifdef COMPILER_VERSION_TWEAK
'.', COMPILER_VERSION_TWEAK,
# endif
# endif
# endif
']','\0'};
#endif
/* Construct a string literal encoding the internal version number. */
#ifdef COMPILER_VERSION_INTERNAL
char const info_version_internal[] = {
'I', 'N', 'F', 'O', ':',
'c','o','m','p','i','l','e','r','_','v','e','r','s','i','o','n','_',
'i','n','t','e','r','n','a','l','[',
COMPILER_VERSION_INTERNAL,']','\0'};
#elif defined(COMPILER_VERSION_INTERNAL_STR)
char const* info_version_internal = "INFO" ":" "compiler_version_internal[" COMPILER_VERSION_INTERNAL_STR "]";
#endif
/* Construct a string literal encoding the version number components. */
#ifdef SIMULATE_VERSION_MAJOR
char const info_simulate_version[] = {
'I', 'N', 'F', 'O', ':',
's','i','m','u','l','a','t','e','_','v','e','r','s','i','o','n','[',
SIMULATE_VERSION_MAJOR,
# ifdef SIMULATE_VERSION_MINOR
'.', SIMULATE_VERSION_MINOR,
# ifdef SIMULATE_VERSION_PATCH
'.', SIMULATE_VERSION_PATCH,
# ifdef SIMULATE_VERSION_TWEAK
'.', SIMULATE_VERSION_TWEAK,
# endif
# endif
# endif
']','\0'};
#endif
/* Construct the string literal in pieces to prevent the source from
getting matched. Store it in a pointer rather than an array
because some compilers will just produce instructions to fill the
array rather than assigning a pointer to a static array. */
char const* info_platform = "INFO" ":" "platform[" PLATFORM_ID "]";
char const* info_arch = "INFO" ":" "arch[" ARCHITECTURE_ID "]";
#define CXX_STD_98 199711L
#define CXX_STD_11 201103L
#define CXX_STD_14 201402L
#define CXX_STD_17 201703L
#define CXX_STD_20 202002L
#define CXX_STD_23 202302L
#if defined(__INTEL_COMPILER) && defined(_MSVC_LANG)
# if _MSVC_LANG > CXX_STD_17
# define CXX_STD _MSVC_LANG
# elif _MSVC_LANG == CXX_STD_17 && defined(__cpp_aggregate_paren_init)
# define CXX_STD CXX_STD_20
# elif _MSVC_LANG > CXX_STD_14 && __cplusplus > CXX_STD_17
# define CXX_STD CXX_STD_20
# elif _MSVC_LANG > CXX_STD_14
# define CXX_STD CXX_STD_17
# elif defined(__INTEL_CXX11_MODE__) && defined(__cpp_aggregate_nsdmi)
# define CXX_STD CXX_STD_14
# elif defined(__INTEL_CXX11_MODE__)
# define CXX_STD CXX_STD_11
# else
# define CXX_STD CXX_STD_98
# endif
#elif defined(_MSC_VER) && defined(_MSVC_LANG)
# if _MSVC_LANG > __cplusplus
# define CXX_STD _MSVC_LANG
# else
# define CXX_STD __cplusplus
# endif
#elif defined(__NVCOMPILER)
# if __cplusplus == CXX_STD_17 && defined(__cpp_aggregate_paren_init)
# define CXX_STD CXX_STD_20
# else
# define CXX_STD __cplusplus
# endif
#elif defined(__INTEL_COMPILER) || defined(__PGI)
# if __cplusplus == CXX_STD_11 && defined(__cpp_namespace_attributes)
# define CXX_STD CXX_STD_17
# elif __cplusplus == CXX_STD_11 && defined(__cpp_aggregate_nsdmi)
# define CXX_STD CXX_STD_14
# else
# define CXX_STD __cplusplus
# endif
#elif (defined(__IBMCPP__) || defined(__ibmxl__)) && defined(__linux__)
# if __cplusplus == CXX_STD_11 && defined(__cpp_aggregate_nsdmi)
# define CXX_STD CXX_STD_14
# else
# define CXX_STD __cplusplus
# endif
#elif __cplusplus == 1 && defined(__GXX_EXPERIMENTAL_CXX0X__)
# define CXX_STD CXX_STD_11
#else
# define CXX_STD __cplusplus
#endif
const char* info_language_standard_default = "INFO" ":" "standard_default["
#if CXX_STD > CXX_STD_23
"26"
#elif CXX_STD > CXX_STD_20
"23"
#elif CXX_STD > CXX_STD_17
"20"
#elif CXX_STD > CXX_STD_14
"17"
#elif CXX_STD > CXX_STD_11
"14"
#elif CXX_STD >= CXX_STD_11
"11"
#else
"98"
#endif
"]";
const char* info_language_extensions_default = "INFO" ":" "extensions_default["
#if (defined(__clang__) || defined(__GNUC__) || defined(__xlC__) || \
defined(__TI_COMPILER_VERSION__) || defined(__RENESAS__)) && \
!defined(__STRICT_ANSI__)
"ON"
#else
"OFF"
#endif
"]";
/*--------------------------------------------------------------------------*/
int main(int argc, char* argv[])
{
int require = 0;
require += info_compiler[argc];
require += info_platform[argc];
require += info_arch[argc];
#ifdef COMPILER_VERSION_MAJOR
require += info_version[argc];
#endif
#if defined(COMPILER_VERSION_INTERNAL) || defined(COMPILER_VERSION_INTERNAL_STR)
require += info_version_internal[argc];
#endif
#ifdef SIMULATE_ID
require += info_simulate[argc];
#endif
#ifdef SIMULATE_VERSION_MAJOR
require += info_simulate_version[argc];
#endif
#if defined(__CRAYXT_COMPUTE_LINUX_TARGET)
require += info_cray[argc];
#endif
require += info_language_standard_default[argc];
require += info_language_extensions_default[argc];
(void)argv;
return require;
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,16 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# Relative path conversion top directories.
set(CMAKE_RELATIVE_PATH_TOP_SOURCE "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2")
set(CMAKE_RELATIVE_PATH_TOP_BINARY "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install")
# Force unix paths in dependencies.
set(CMAKE_FORCE_UNIX_PATHS 1)
# The C and CXX include file regular expressions for this directory.
set(CMAKE_C_INCLUDE_REGEX_SCAN "^.*$")
set(CMAKE_C_INCLUDE_REGEX_COMPLAIN "^$")
set(CMAKE_CXX_INCLUDE_REGEX_SCAN ${CMAKE_C_INCLUDE_REGEX_SCAN})
set(CMAKE_CXX_INCLUDE_REGEX_COMPLAIN ${CMAKE_C_INCLUDE_REGEX_COMPLAIN})

View File

@ -0,0 +1,8 @@
{
"InstallScripts" :
[
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/cmake_install.cmake",
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/cmake_install.cmake"
],
"Parallel" : false
}

View File

@ -0,0 +1,162 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# The generator used is:
set(CMAKE_DEPENDS_GENERATOR "Unix Makefiles")
# The top level Makefile was generated from the following files:
set(CMAKE_MAKEFILE_DEPENDS
"CMakeCache.txt"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/CMakeLists.txt"
"CMakeFiles/4.1.3/CMakeCCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCXXCompiler.cmake"
"CMakeFiles/4.1.3/CMakeSystem.cmake"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/cmake/unitree_sdk2Config.cmake.in"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/CMakeLists.txt"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/BasicConfigVersion-ExactVersion.cmake.in"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCCompiler.cmake.in"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCCompilerABI.c"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCXXCompiler.cmake.in"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCXXCompilerABI.cpp"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCXXInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCommonLanguageInclude.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeCompilerIdDetection.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCXXCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCompilerABI.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCompilerId.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineCompilerSupport.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeDetermineSystem.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeFindBinUtils.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeGenericSystem.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeInitializeConfigs.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeLanguageInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakePackageConfigHelpers.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeParseImplicitIncludeInfo.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeParseImplicitLinkInfo.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeParseLibraryArchitecture.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeSystem.cmake.in"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeSystemSpecificInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeSystemSpecificInitialize.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeTestCCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeTestCXXCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeTestCompilerCommon.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CMakeUnixFindMake.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CheckCSourceCompiles.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CheckIncludeFile.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/CheckLibraryExists.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/ADSP-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/ARMCC-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/ARMClang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/AppleClang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Borland-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Bruce-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/CMakeCommonCompilerMacros.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Clang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Clang-DetermineCompilerInternal.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Compaq-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Compaq-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Cray-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/CrayClang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Diab-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Embarcadero-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Fujitsu-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/FujitsuClang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GHS-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU-C.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU-CXX.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU-FindBinUtils.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/GNU.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/HP-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/HP-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IAR-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IBMCPP-C-DetermineVersionInternal.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IBMCPP-CXX-DetermineVersionInternal.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IBMClang-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IBMClang-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Intel-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/IntelLLVM-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/LCC-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/LCC-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/MSVC-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/NVHPC-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/NVIDIA-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/OpenWatcom-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/OrangeC-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/PGI-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/PathScale-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Renesas-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/SCO-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/SDCC-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/SunPro-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/SunPro-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/TI-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/TIClang-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Tasking-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/TinyCC-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/VisualAge-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/VisualAge-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/Watcom-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/XL-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/XL-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/XLClang-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/XLClang-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/zOS-C-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Compiler/zOS-CXX-DetermineCompiler.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/FindPackageHandleStandardArgs.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/FindPackageMessage.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/FindThreads.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/GNUInstallDirs.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeCLinkerInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeCXXLinkerInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeCommonLinkerInformation.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeDetermineLinkerId.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeInspectCLinker.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CMakeInspectCXXLinker.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/CheckSourceCompiles.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Internal/FeatureTesting.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Linker/GNU-C.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Linker/GNU-CXX.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Linker/GNU.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linker/GNU.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linker/Linux-GNU-C.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linker/Linux-GNU-CXX.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linker/Linux-GNU.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux-Determine-CXX.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux-GNU-C.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux-GNU-CXX.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux-GNU.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux-Initialize.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/Linux.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/Platform/UnixPaths.cmake"
"/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/share/cmake-4.1/Modules/WriteBasicConfigVersionFile.cmake"
)
# The corresponding makefile is:
set(CMAKE_MAKEFILE_OUTPUTS
"Makefile"
"CMakeFiles/cmake.check_cache"
)
# Byproducts of CMake generate step:
set(CMAKE_MAKEFILE_PRODUCTS
"CMakeFiles/4.1.3/CMakeSystem.cmake"
"CMakeFiles/4.1.3/CMakeCCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCXXCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCXXCompiler.cmake"
"CMakeFiles/4.1.3/CMakeCXXCompiler.cmake"
"unitree_sdk2ConfigVersion.cmake"
"unitree_sdk2Config.cmake"
"CMakeFiles/CMakeDirectoryInformation.cmake"
"thirdparty/CMakeFiles/CMakeDirectoryInformation.cmake"
)
# Dependency information for all targets:
set(CMAKE_DEPEND_INFO_FILES
)

View File

@ -0,0 +1,109 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# Default target executed when no arguments are given to make.
default_target: all
.PHONY : default_target
#=============================================================================
# Special targets provided by cmake.
# Disable implicit rules so canonical targets will work.
.SUFFIXES:
# Disable VCS-based implicit rules.
% : %,v
# Disable VCS-based implicit rules.
% : RCS/%
# Disable VCS-based implicit rules.
% : RCS/%,v
# Disable VCS-based implicit rules.
% : SCCS/s.%
# Disable VCS-based implicit rules.
% : s.%
.SUFFIXES: .hpux_make_needs_suffix_list
# Command-line flag to silence nested $(MAKE).
$(VERBOSE)MAKESILENT = -s
#Suppress display of executed commands.
$(VERBOSE).SILENT:
# A target that is always out of date.
cmake_force:
.PHONY : cmake_force
#=============================================================================
# Set environment variables for the build.
# The shell in which to execute make rules.
SHELL = /bin/sh
# The CMake executable.
CMAKE_COMMAND = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake
# The command to remove a file.
RM = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -E rm -f
# Escaping for special characters.
EQUALS = =
# The top-level source directory on which CMake was run.
CMAKE_SOURCE_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
# The top-level build directory on which CMake was run.
CMAKE_BINARY_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
#=============================================================================
# Directory level rules for the build root directory
# The main recursive "all" target.
all: thirdparty/all
.PHONY : all
# The main recursive "codegen" target.
codegen: thirdparty/codegen
.PHONY : codegen
# The main recursive "preinstall" target.
preinstall: thirdparty/preinstall
.PHONY : preinstall
# The main recursive "clean" target.
clean: thirdparty/clean
.PHONY : clean
#=============================================================================
# Directory level rules for directory thirdparty
# Recursive "all" directory target.
thirdparty/all:
.PHONY : thirdparty/all
# Recursive "codegen" directory target.
thirdparty/codegen:
.PHONY : thirdparty/codegen
# Recursive "preinstall" directory target.
thirdparty/preinstall:
.PHONY : thirdparty/preinstall
# Recursive "clean" directory target.
thirdparty/clean:
.PHONY : thirdparty/clean
#=============================================================================
# Special targets to cleanup operation of make.
# Special rule to run CMake to check the build system integrity.
# No rule that depends on this can have commands that come from listfiles
# because they might be regenerated.
cmake_check_build_system:
$(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 0
.PHONY : cmake_check_build_system

View File

@ -0,0 +1,12 @@
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/edit_cache.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/rebuild_cache.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/list_install_components.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/install.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/install/local.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles/install/strip.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/edit_cache.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/rebuild_cache.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/list_install_components.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/install.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/install/local.dir
/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/CMakeFiles/install/strip.dir

View File

@ -0,0 +1 @@
# This file is generated by cmake for dependency checking of the CMakeCache.txt file

View File

@ -0,0 +1 @@
0

189
deps/unitree_sdk2/build_install/Makefile vendored Normal file
View File

@ -0,0 +1,189 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# Default target executed when no arguments are given to make.
default_target: all
.PHONY : default_target
# Allow only one "make -f Makefile2" at a time, but pass parallelism.
.NOTPARALLEL:
#=============================================================================
# Special targets provided by cmake.
# Disable implicit rules so canonical targets will work.
.SUFFIXES:
# Disable VCS-based implicit rules.
% : %,v
# Disable VCS-based implicit rules.
% : RCS/%
# Disable VCS-based implicit rules.
% : RCS/%,v
# Disable VCS-based implicit rules.
% : SCCS/s.%
# Disable VCS-based implicit rules.
% : s.%
.SUFFIXES: .hpux_make_needs_suffix_list
# Command-line flag to silence nested $(MAKE).
$(VERBOSE)MAKESILENT = -s
#Suppress display of executed commands.
$(VERBOSE).SILENT:
# A target that is always out of date.
cmake_force:
.PHONY : cmake_force
#=============================================================================
# Set environment variables for the build.
# The shell in which to execute make rules.
SHELL = /bin/sh
# The CMake executable.
CMAKE_COMMAND = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake
# The command to remove a file.
RM = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -E rm -f
# Escaping for special characters.
EQUALS = =
# The top-level source directory on which CMake was run.
CMAKE_SOURCE_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
# The top-level build directory on which CMake was run.
CMAKE_BINARY_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
#=============================================================================
# Targets provided globally by CMake.
# Special rule for the target edit_cache
edit_cache:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "No interactive CMake dialog available..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -E echo No\ interactive\ CMake\ dialog\ available.
.PHONY : edit_cache
# Special rule for the target edit_cache
edit_cache/fast: edit_cache
.PHONY : edit_cache/fast
# Special rule for the target rebuild_cache
rebuild_cache:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Running CMake to regenerate build system..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake --regenerate-during-build -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
.PHONY : rebuild_cache
# Special rule for the target rebuild_cache
rebuild_cache/fast: rebuild_cache
.PHONY : rebuild_cache/fast
# Special rule for the target list_install_components
list_install_components:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Available install components are: \"Unspecified\""
.PHONY : list_install_components
# Special rule for the target list_install_components
list_install_components/fast: list_install_components
.PHONY : list_install_components/fast
# Special rule for the target install
install: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Install the project..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -P cmake_install.cmake
.PHONY : install
# Special rule for the target install
install/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Install the project..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -P cmake_install.cmake
.PHONY : install/fast
# Special rule for the target install/local
install/local: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing only the local directory..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_LOCAL_ONLY=1 -P cmake_install.cmake
.PHONY : install/local
# Special rule for the target install/local
install/local/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing only the local directory..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_LOCAL_ONLY=1 -P cmake_install.cmake
.PHONY : install/local/fast
# Special rule for the target install/strip
install/strip: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing the project stripped..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_DO_STRIP=1 -P cmake_install.cmake
.PHONY : install/strip
# Special rule for the target install/strip
install/strip/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing the project stripped..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_DO_STRIP=1 -P cmake_install.cmake
.PHONY : install/strip/fast
# The main all target
all: cmake_check_build_system
$(CMAKE_COMMAND) -E cmake_progress_start /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install//CMakeFiles/progress.marks
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 all
$(CMAKE_COMMAND) -E cmake_progress_start /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles 0
.PHONY : all
# The main clean target
clean:
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 clean
.PHONY : clean
# The main clean target
clean/fast: clean
.PHONY : clean/fast
# Prepare targets for installation.
preinstall: all
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 preinstall
.PHONY : preinstall
# Prepare targets for installation.
preinstall/fast:
$(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 preinstall
.PHONY : preinstall/fast
# clear depends
depend:
$(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 1
.PHONY : depend
# Help Target
help:
@echo "The following are some of the valid targets for this Makefile:"
@echo "... all (the default if no target is provided)"
@echo "... clean"
@echo "... depend"
@echo "... edit_cache"
@echo "... install"
@echo "... install/local"
@echo "... install/strip"
@echo "... list_install_components"
@echo "... rebuild_cache"
.PHONY : help
#=============================================================================
# Special targets to cleanup operation of make.
# Special rule to run CMake to check the build system integrity.
# No rule that depends on this can have commands that come from listfiles
# because they might be regenerated.
cmake_check_build_system:
$(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 0
.PHONY : cmake_check_build_system

View File

@ -0,0 +1,91 @@
# Install script for directory: /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
# Set the install prefix
if(NOT DEFINED CMAKE_INSTALL_PREFIX)
set(CMAKE_INSTALL_PREFIX "/home/zedx/.local/unitree_robotics")
endif()
string(REGEX REPLACE "/$" "" CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}")
# Set the install configuration name.
if(NOT DEFINED CMAKE_INSTALL_CONFIG_NAME)
if(BUILD_TYPE)
string(REGEX REPLACE "^[^A-Za-z0-9_]+" ""
CMAKE_INSTALL_CONFIG_NAME "${BUILD_TYPE}")
else()
set(CMAKE_INSTALL_CONFIG_NAME "Release")
endif()
message(STATUS "Install configuration: \"${CMAKE_INSTALL_CONFIG_NAME}\"")
endif()
# Set the component getting installed.
if(NOT CMAKE_INSTALL_COMPONENT)
if(COMPONENT)
message(STATUS "Install component: \"${COMPONENT}\"")
set(CMAKE_INSTALL_COMPONENT "${COMPONENT}")
else()
set(CMAKE_INSTALL_COMPONENT)
endif()
endif()
# Install shared libraries without execute permission?
if(NOT DEFINED CMAKE_INSTALL_SO_NO_EXE)
set(CMAKE_INSTALL_SO_NO_EXE "1")
endif()
# Is this installation the result of a crosscompile?
if(NOT DEFINED CMAKE_CROSSCOMPILING)
set(CMAKE_CROSSCOMPILING "FALSE")
endif()
# Set path to fallback-tool for dependency-resolution.
if(NOT DEFINED CMAKE_OBJDUMP)
set(CMAKE_OBJDUMP "/usr/bin/objdump")
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/include" TYPE DIRECTORY FILES "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/include/")
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/lib" TYPE FILE FILES "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/lib/x86_64/libunitree_sdk2.a")
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/lib/cmake/unitree_sdk2" TYPE FILE FILES "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/cmake/unitree_sdk2Targets.cmake")
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/lib/cmake/unitree_sdk2" TYPE FILE FILES
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/unitree_sdk2Config.cmake"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/unitree_sdk2ConfigVersion.cmake"
)
endif()
if(NOT CMAKE_INSTALL_LOCAL_ONLY)
# Include the install script for each subdirectory.
include("/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/cmake_install.cmake")
endif()
string(REPLACE ";" "\n" CMAKE_INSTALL_MANIFEST_CONTENT
"${CMAKE_INSTALL_MANIFEST_FILES}")
if(CMAKE_INSTALL_LOCAL_ONLY)
file(WRITE "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/install_local_manifest.txt"
"${CMAKE_INSTALL_MANIFEST_CONTENT}")
endif()
if(CMAKE_INSTALL_COMPONENT)
if(CMAKE_INSTALL_COMPONENT MATCHES "^[a-zA-Z0-9_.+-]+$")
set(CMAKE_INSTALL_MANIFEST "install_manifest_${CMAKE_INSTALL_COMPONENT}.txt")
else()
string(MD5 CMAKE_INST_COMP_HASH "${CMAKE_INSTALL_COMPONENT}")
set(CMAKE_INSTALL_MANIFEST "install_manifest_${CMAKE_INST_COMP_HASH}.txt")
unset(CMAKE_INST_COMP_HASH)
endif()
else()
set(CMAKE_INSTALL_MANIFEST "install_manifest.txt")
endif()
if(NOT CMAKE_INSTALL_LOCAL_ONLY)
file(WRITE "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/${CMAKE_INSTALL_MANIFEST}"
"${CMAKE_INSTALL_MANIFEST_CONTENT}")
endif()

View File

@ -0,0 +1,756 @@
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/obstacles_avoid/obstacles_avoid_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/obstacles_avoid/obstacles_avoid_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/config/config_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/config/config_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/config/config_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/utrack/utrack_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/utrack/utrack_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/public/jsonize_type.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/robot_state/robot_state_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/robot_state/robot_state_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/robot_state/robot_state_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/vui/vui_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/vui/vui_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/vui/vui_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/video/video_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/video/video_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/video/video_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/sport/sport_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/sport/sport_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/go2/sport/sport_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h2/loco/h2_loco_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h2/loco/h2_loco_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h2/loco/h2_loco_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/future/request_future.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/server/server.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/server/server_stub.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/server/server_base.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/server/lease_server.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/client/lease_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/client/client_base.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/client/client_stub.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/client/client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h1/loco/h1_loco_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h1/loco/h1_loco_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/h1/loco/h1_loco_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/as2/sport/sport_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/as2/sport/sport_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/as2/sport/sport_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/arm/g1_arm_action_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/arm/g1_arm_action_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/arm/g1_arm_action_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/common/terminations.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/loco/g1_loco_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/loco/g1_loco_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/loco/g1_loco_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/agv/g1_agv_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/agv/g1_agv_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/agv/g1_agv_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/audio/g1_audio_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/audio/g1_audio_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/g1/audio/g1_audio_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/RequestPolicy_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/Response_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/Request_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/RequestHeader_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/RequestLease_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/RequestIdentity_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/ResponseHeader_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_idl_decl/ResponseStatus_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_request_response.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/internal/internal_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/config/config_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/config/config_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/config/config_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/robot_state/robot_state_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/robot_state/robot_state_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/robot_state/robot_state_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/front_video/front_video_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/front_video/front_video_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/front_video/front_video_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/back_video/back_video_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/back_video/back_video_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/back_video/back_video_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/motion_switcher/motion_switcher_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/motion_switcher/motion_switcher_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/motion_switcher/motion_switcher_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/sport/sport_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/sport/sport_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/b2/sport/sport_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/channel/channel_namer.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/channel/channel_subscriber.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/channel/channel_publisher.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/channel/channel_factory.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/channel/channel_labor.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/audio/audio_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/audio/audio_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/audio/audio_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/sport/sport_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/sport/sport_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/a2/sport/sport_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/loco/r1_loco_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/loco/r1_loco_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/loco/r1_loco_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/audio/audio_api.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/audio/audio_client.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/r1/audio/audio_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/robot/serialize/serialize.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/time/time_tool.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/time/sleep.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/block_queue.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/json/json.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/json/jsonize.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/json/json_config.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/any.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/future.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/thread.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/thread_task.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/thread_decl.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/thread_pool.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/thread/recurrent_thread.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_buffer.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_logger.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_decl.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_writer.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_initor.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_keeper.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_store.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/log/log_policy.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/os.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/decl.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/exception.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/service/dds_service.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/service/base/service_decl.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/service/base/service_application.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/service/base/service_base.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/service/base/service_config.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/string_tool.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/assert.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/lock/lock.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/filesystem/file.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/filesystem/directory.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/filesystem/filesystem.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_qos.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_qos_parameter.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_callback.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_exception.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_qos_policy_parameter.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_topic_channel.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_parameter.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_native.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_qos_realize.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_qos_policy.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_traits.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_error.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_easy_model.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_factory_model.hpp
/home/zedx/.local/unitree_robotics/include/unitree/common/dds/dds_entity.hpp
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/go2/defines.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/go2/go2.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/go2/go2_sub.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/go2/go2_pub.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/g1/g1_sub.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/g1/defines.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/g1/g1.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/robots/g1/g1_pub.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/common/Subscription.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/common/Publisher.h
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/common/unitree_joystick.hpp
/home/zedx/.local/unitree_robotics/include/unitree/dds_wrapper/common/crc.h
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/WirelessController_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/SportModeCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/Res_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/UwbSwitch_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/VoxelMapCompressed_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/SportModeState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/MotorStates_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/ConfigChangeStatus_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/BmsCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/LowState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/TimeSpec_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/BmsState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/UwbState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/Go2FrontVideoData_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/Error_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/MotorCmds_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/InterfaceConfig_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/MotorCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/Req_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/PathPoint_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/LowCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/AudioData_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/LidarState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/MotorState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/IMUState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/go2/HeightMap_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg_doubleimu/doubleIMUState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/TwistWithCovarianceStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Quaternion_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Pose_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Vector3_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/String_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Time_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PoseStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Twist_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/TwistStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/TwistWithCovariance_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PointCloud2_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PointStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Point_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Point32_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PointField_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PoseWithCovarianceStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Imu_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/QuaternionStamped_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/MapMetaData_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/PoseWithCovariance_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/OccupancyGrid_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Odometry_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Header_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/ros2/Pose2D_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/AgvBmsState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/MainBoardState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/HandState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/SportModeState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/BmsCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/LowState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/BmsState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/MotorCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/LowCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/HandCmd_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/MotorState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/IMUState_.hpp
/home/zedx/.local/unitree_robotics/include/unitree/idl/hg/PressSensorState_.hpp
/home/zedx/.local/unitree_robotics/lib/libunitree_sdk2.a
/home/zedx/.local/unitree_robotics/lib/cmake/unitree_sdk2/unitree_sdk2Targets.cmake
/home/zedx/.local/unitree_robotics/lib/cmake/unitree_sdk2/unitree_sdk2Config.cmake
/home/zedx/.local/unitree_robotics/lib/cmake/unitree_sdk2/unitree_sdk2ConfigVersion.cmake
/home/zedx/.local/unitree_robotics/lib/libddsc.so
/home/zedx/.local/unitree_robotics/lib/libddsc.so.0
/home/zedx/.local/unitree_robotics/lib/libddscxx.so
/home/zedx/.local/unitree_robotics/lib/libddscxx.so.0
/home/zedx/.local/unitree_robotics/include/ddsc/dds.h
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/RankImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/SubscriberDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/SampleInfoImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/GenerationCountImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/QueryDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/cond/QueryConditionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/cond/ReadConditionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/qos/SubscriberQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/qos/DataReaderQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/AnyDataReaderDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/BuiltinSubscriberDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/sub/CoherentAccessDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/basic_cdr_ser.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/cdr_enums.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/cdr_stream.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/fragchain.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/extended_cdr_v1_ser.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/entity_properties.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cdr/extended_cdr_v2_ser.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/ObjectDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/Mutex.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/ScopedLock.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/EntitySet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/QosProviderDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/config.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/status/StatusDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/type_helpers.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/ConditionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/FunctorHolder.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/ShadowParticipant.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/StatusConditionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/GuardConditionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/cond/WaitSetDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/MiscUtils.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/EntityDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/InstanceHandleDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/EntityRegistry.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/TimeHelper.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/policy/QosPolicyCountDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/policy/PolicyDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/policy/ProprietaryPolicyKind.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/policy/Policy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/policy/TPolicy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/ObjectSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/ReportUtils.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/WeakReferenceSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/Missing.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/ListenerDispatcher.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/core/DDScObjectDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/CoherentSetDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/AnyDataWriterDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/SuspendedPublicationDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/qos/DataWriterQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/qos/PublisherQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/pub/PublisherDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/ForwardDeclarations.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/datatopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/BuiltinTopicCopy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/AnyTopicDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/AnyTopicListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/CDRBlob.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/BuiltinTopicKeyDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/BuiltinTopicTraits.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/TopicTraits.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/qos/TopicQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/BuiltinTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/TopicDescriptionDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/TBuiltinTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/BuiltinTopicDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/FilterDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/hash.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/topic/TopicListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/Domain.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/DomainWrap.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/qos/DomainParticipantQosDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/DomainParticipantRegistry.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/DomainParticipantDelegate.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/org/eclipse/cyclonedds/domain/DomainParticipantListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/ddssub.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TGenerationCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/Rank.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TDataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/Subscriber.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/status/DataState.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/status/detail/DataStateImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/LoanedSamples.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TSampleRef.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/SampleRef.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/SubscriberListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/SharedSamples.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/SampleInfo.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/TReadCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/TQueryCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/QueryCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/detail/QueryCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/detail/TQueryConditionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/detail/TReadConditionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/detail/ReadCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/cond/ReadCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/DataReaderListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/AnyDataReaderListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/AnyDataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/qos/DataReaderQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/qos/SubscriberQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/qos/detail/DataReaderQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/qos/detail/SubscriberQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TSampleInfo.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TSampleImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TSampleInfoImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/ddssub.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/Rank.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/Subscriber.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TCoherentAccessImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TGenerationCountImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TSubscriberImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/LoanedSamples.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TRankImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TSampleRefImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/SampleRef.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/SharedSamples.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/SampleInfo.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/SamplesHolder.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/AnyDataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TQueryImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TAnyDataReaderImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/GenerationCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/Manipulators.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/SharedSamplesImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/Sample.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/LoanedSamplesImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/DataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/TDataReaderImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/CoherentAccess.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/detail/Query.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TSubscriber.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TSample.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/GenerationCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TCoherentAccess.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TAnyDataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/Sample.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/DataReader.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TRank.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/TQuery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/CoherentAccess.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/sub/Query.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/LengthUnlimited.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/ref_traits.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/SafeEnumeration.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/BuiltinTopicTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/ddscore.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/TInstanceHandle.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/InstanceHandle.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/TQosProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/status/State.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/status/TStatus.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/status/Status.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/status/detail/Status.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/status/detail/TStatusImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/refmacros.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Entity.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Reference.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TypeProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/DynamicData.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/UnionType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TAnnotation.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/CollectionTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TMemberType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TTypeProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/Annotations.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/UnionCase.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TypeKind.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/MemberType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/PrimitiveTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TDynamicType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/StructType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/TypeProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/DynamicData.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/UnionType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/CollectionTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/UnionCase.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/MemberType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/PrimitiveTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/Annotation.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/StructType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/detail/DynamicType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TDynamicData.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TCollectionTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/TStructType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/xtypes/DynamicType.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/types.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/TWaitSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/WaitSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/TCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/StatusCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/GuardCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/Condition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/WaitSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/StatusCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/GuardCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/TGuardConditionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/Condition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/TConditionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/TStatusConditionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/detail/TWaitSetImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/TGuardCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/cond/TStatusCondition.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Time.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Value.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/macros.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/WeakReference.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Optional.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/TBuiltinTopicTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/array.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/ref_traits.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/inttypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/BuiltinTopicTypes.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/ddscore.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/ReferenceImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/TInstanceHandleImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/InstanceHandle.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/Entity.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/TEntityImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/Value.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/WeakReferenceImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/macros.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/TQosProviderImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/TEntityQosImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/array.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/module_docs.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/conformance.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/old_win_stdint.h
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/export.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/detail/QosProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/TEntityQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/TQosPolicyCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/TCorePolicy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/PolicyKind.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/QosPolicyCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/detail/TCorePolicyImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/detail/QosPolicyCount.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/detail/CorePolicy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/detail/TQosPolicyCountImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/policy/CorePolicy.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Exception.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/conformance.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/External.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/Duration.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/TEntity.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/core/QosProvider.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/PublisherListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/AnyDataWriter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/Publisher.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/TAnyDataWriter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/qos/DataWriterQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/qos/detail/DataWriterQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/qos/detail/PublisherQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/qos/PublisherQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/SuspendedPublication.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/DataWriter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/TSuspendedPublication.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/AnyDataWriter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/Publisher.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/TPublisherImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/SuspendedPublication.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/TAnyDataWriterImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/DataWriter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/TCoherentSetImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/ddspub.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/CoherentSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/TSuspendedPublicationImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/detail/DataWriterImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/AnyDataWriterListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/DataWriterListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/ddspub.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/CoherentSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/TCoherentSet.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/pub/TPublisher.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/dds.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/LICENSE
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TBuiltinTopicKey.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TopicInstance.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/Topic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/AnyTopicListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/Filter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/MultiTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/BuiltinTopicKey.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TopicTraits.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/qos/TopicQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/qos/detail/TopicQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TContentFilteredTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/ddstopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/BuiltinTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TopicDescription.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/Topic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/Filter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TBuiltinTopicKeyImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/MultiTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/BuiltinTopicKey.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TFilterImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TTopicImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/ddstopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TContentFilteredTopicImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/BuiltinTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TopicDescription.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TTopicDescriptionImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/AnyTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TopicInstanceImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TBuiltinTopicImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/ContentFilteredTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/detail/TAnyTopicImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/AnyTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TBuiltinTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TFilter.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/ContentFilteredTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TMultiTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TTopicDescription.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TAnyTopic.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/topic/TopicListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/discovery.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/TDomainParticipant.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/qos/detail/DomainParticipantQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/qos/DomainParticipantQos.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/DomainParticipant.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/ddsdomain.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/detail/TDomainParticipantImpl.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/detail/DomainParticipant.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/detail/ddsdomain.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/find.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/domain/DomainParticipantListener.hpp
/home/zedx/.local/unitree_robotics/include/ddscxx/dds/features.hpp
/home/zedx/.local/unitree_robotics/include/dds/config.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_status.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_statistics.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_error.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_qosdefs.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_listener.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_loan_api.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_impl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_data_allocator.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_qos.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_opcodes.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_public_alloc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_rhc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_basic_types.h
/home/zedx/.local/unitree_robotics/include/dds/ddsc/dds_internal_api.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_bswap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_bitset.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_serdata_plist.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_builtin_topic_if.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_tran.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_serdata_pserop.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typeinfo.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_protocol.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_cfgelems.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_acknack.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_pcap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_domaingv.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_init.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_list_genptr.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_inverse_uint32_set.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_ownip.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_plist_generic.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_addrset.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_entity_index.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_unused.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_security_msg.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_log.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_vendor.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_ddsi_discovery.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_participant.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_raweth.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_cdrstream.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_entity.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_xevent.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_deadline.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_list_tmpl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typeinfo.idl
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_lat_estim.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_security_omg.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_receive.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_serdata_default.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_lease.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_rhc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_xmsg.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_deliver_locally.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_rtps.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_security_util.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_gc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_thread.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_lifespan.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_time.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_typewrap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_vnet.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_portmapping.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_sertopic.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_typelookup.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_cfgunits.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typelookup.idl
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_hbcontrol.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_typebuilder.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_ipaddr.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_iid.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_tcp.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_sertype.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_tkmap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_config_impl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typemap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typemap.idl
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_serdata.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_shm_transport.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_security_exchange.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_handshake.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_proxy_endpoint.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_keyhash.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_transmit.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_statistics.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_freelist.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_wraddrset.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_udp.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_typelookup.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/sysdeps.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_proxy_participant.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_ssl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_whc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_guid.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xt_impl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_typelib.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_sockwaitset.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_mcgroup.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_pmd.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_plist.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_entity_match.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_debmon.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_topic.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_radmin.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_endpoint.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_feature_check.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_config.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_misc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_threadmon.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_locator.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/q_qosmatch.h
/home/zedx/.local/unitree_robotics/include/dds/ddsi/ddsi_xqos.h
/home/zedx/.local/unitree_robotics/include/dds/features.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/time/freertos.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/dynlib.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/environ.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/process.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/md5.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/static_assert.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/threads/posix.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/threads/freertos.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/threads/windows.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/misc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sync.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/countargs.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/io.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/avl.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/retcode.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/cdtors.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/mh3.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sched.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/heap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/types.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sockets.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/rusage.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/bswap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/expand_vars.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sync/posix.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sync/freertos.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sync/windows.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/ifaddrs.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/time.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/align.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/iovec.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/atomics.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/strtod.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/fibheap.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/attributes.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/xmlparser.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/types/posix.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/types/windows.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/types/vxworks.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/random.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/threads.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/log.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/circlist.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/netstat.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/string.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/arch.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/endian.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/strtol.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/filesystem.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sockets/posix.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/sockets/windows.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/atomics/arm.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/atomics/msvc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/atomics/sun.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/atomics/gcc.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/hopscotch.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/filesystem/posix.h
/home/zedx/.local/unitree_robotics/include/dds/ddsrt/filesystem/windows.h
/home/zedx/.local/unitree_robotics/include/dds/version.h
/home/zedx/.local/unitree_robotics/include/dds/export.h
/home/zedx/.local/unitree_robotics/include/dds/dds.h

View File

@ -0,0 +1,16 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# Relative path conversion top directories.
set(CMAKE_RELATIVE_PATH_TOP_SOURCE "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2")
set(CMAKE_RELATIVE_PATH_TOP_BINARY "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install")
# Force unix paths in dependencies.
set(CMAKE_FORCE_UNIX_PATHS 1)
# The C and CXX include file regular expressions for this directory.
set(CMAKE_C_INCLUDE_REGEX_SCAN "^.*$")
set(CMAKE_C_INCLUDE_REGEX_COMPLAIN "^$")
set(CMAKE_CXX_INCLUDE_REGEX_SCAN ${CMAKE_C_INCLUDE_REGEX_SCAN})
set(CMAKE_CXX_INCLUDE_REGEX_COMPLAIN ${CMAKE_C_INCLUDE_REGEX_COMPLAIN})

View File

@ -0,0 +1 @@
0

View File

@ -0,0 +1,189 @@
# CMAKE generated file: DO NOT EDIT!
# Generated by "Unix Makefiles" Generator, CMake Version 4.1
# Default target executed when no arguments are given to make.
default_target: all
.PHONY : default_target
# Allow only one "make -f Makefile2" at a time, but pass parallelism.
.NOTPARALLEL:
#=============================================================================
# Special targets provided by cmake.
# Disable implicit rules so canonical targets will work.
.SUFFIXES:
# Disable VCS-based implicit rules.
% : %,v
# Disable VCS-based implicit rules.
% : RCS/%
# Disable VCS-based implicit rules.
% : RCS/%,v
# Disable VCS-based implicit rules.
% : SCCS/s.%
# Disable VCS-based implicit rules.
% : s.%
.SUFFIXES: .hpux_make_needs_suffix_list
# Command-line flag to silence nested $(MAKE).
$(VERBOSE)MAKESILENT = -s
#Suppress display of executed commands.
$(VERBOSE).SILENT:
# A target that is always out of date.
cmake_force:
.PHONY : cmake_force
#=============================================================================
# Set environment variables for the build.
# The shell in which to execute make rules.
SHELL = /bin/sh
# The CMake executable.
CMAKE_COMMAND = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake
# The command to remove a file.
RM = /home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -E rm -f
# Escaping for special characters.
EQUALS = =
# The top-level source directory on which CMake was run.
CMAKE_SOURCE_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2
# The top-level build directory on which CMake was run.
CMAKE_BINARY_DIR = /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install
#=============================================================================
# Targets provided globally by CMake.
# Special rule for the target edit_cache
edit_cache:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "No interactive CMake dialog available..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -E echo No\ interactive\ CMake\ dialog\ available.
.PHONY : edit_cache
# Special rule for the target edit_cache
edit_cache/fast: edit_cache
.PHONY : edit_cache/fast
# Special rule for the target rebuild_cache
rebuild_cache:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Running CMake to regenerate build system..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake --regenerate-during-build -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
.PHONY : rebuild_cache
# Special rule for the target rebuild_cache
rebuild_cache/fast: rebuild_cache
.PHONY : rebuild_cache/fast
# Special rule for the target list_install_components
list_install_components:
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Available install components are: \"Unspecified\""
.PHONY : list_install_components
# Special rule for the target list_install_components
list_install_components/fast: list_install_components
.PHONY : list_install_components/fast
# Special rule for the target install
install: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Install the project..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -P cmake_install.cmake
.PHONY : install
# Special rule for the target install
install/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Install the project..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -P cmake_install.cmake
.PHONY : install/fast
# Special rule for the target install/local
install/local: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing only the local directory..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_LOCAL_ONLY=1 -P cmake_install.cmake
.PHONY : install/local
# Special rule for the target install/local
install/local/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing only the local directory..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_LOCAL_ONLY=1 -P cmake_install.cmake
.PHONY : install/local/fast
# Special rule for the target install/strip
install/strip: preinstall
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing the project stripped..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_DO_STRIP=1 -P cmake_install.cmake
.PHONY : install/strip
# Special rule for the target install/strip
install/strip/fast: preinstall/fast
@$(CMAKE_COMMAND) -E cmake_echo_color "--switch=$(COLOR)" --cyan "Installing the project stripped..."
/home/zedx/miniconda3/lib/python3.13/site-packages/cmake/data/bin/cmake -DCMAKE_INSTALL_DO_STRIP=1 -P cmake_install.cmake
.PHONY : install/strip/fast
# The main all target
all: cmake_check_build_system
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(CMAKE_COMMAND) -E cmake_progress_start /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty//CMakeFiles/progress.marks
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 thirdparty/all
$(CMAKE_COMMAND) -E cmake_progress_start /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/CMakeFiles 0
.PHONY : all
# The main clean target
clean:
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 thirdparty/clean
.PHONY : clean
# The main clean target
clean/fast: clean
.PHONY : clean/fast
# Prepare targets for installation.
preinstall: all
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 thirdparty/preinstall
.PHONY : preinstall
# Prepare targets for installation.
preinstall/fast:
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(MAKE) $(MAKESILENT) -f CMakeFiles/Makefile2 thirdparty/preinstall
.PHONY : preinstall/fast
# clear depends
depend:
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 1
.PHONY : depend
# Help Target
help:
@echo "The following are some of the valid targets for this Makefile:"
@echo "... all (the default if no target is provided)"
@echo "... clean"
@echo "... depend"
@echo "... edit_cache"
@echo "... install"
@echo "... install/local"
@echo "... install/strip"
@echo "... list_install_components"
@echo "... rebuild_cache"
.PHONY : help
#=============================================================================
# Special targets to cleanup operation of make.
# Special rule to run CMake to check the build system integrity.
# No rule that depends on this can have commands that come from listfiles
# because they might be regenerated.
cmake_check_build_system:
cd /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install && $(CMAKE_COMMAND) -S$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles/Makefile.cmake 0
.PHONY : cmake_check_build_system

View File

@ -0,0 +1,63 @@
# Install script for directory: /home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty
# Set the install prefix
if(NOT DEFINED CMAKE_INSTALL_PREFIX)
set(CMAKE_INSTALL_PREFIX "/home/zedx/.local/unitree_robotics")
endif()
string(REGEX REPLACE "/$" "" CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}")
# Set the install configuration name.
if(NOT DEFINED CMAKE_INSTALL_CONFIG_NAME)
if(BUILD_TYPE)
string(REGEX REPLACE "^[^A-Za-z0-9_]+" ""
CMAKE_INSTALL_CONFIG_NAME "${BUILD_TYPE}")
else()
set(CMAKE_INSTALL_CONFIG_NAME "Release")
endif()
message(STATUS "Install configuration: \"${CMAKE_INSTALL_CONFIG_NAME}\"")
endif()
# Set the component getting installed.
if(NOT CMAKE_INSTALL_COMPONENT)
if(COMPONENT)
message(STATUS "Install component: \"${COMPONENT}\"")
set(CMAKE_INSTALL_COMPONENT "${COMPONENT}")
else()
set(CMAKE_INSTALL_COMPONENT)
endif()
endif()
# Install shared libraries without execute permission?
if(NOT DEFINED CMAKE_INSTALL_SO_NO_EXE)
set(CMAKE_INSTALL_SO_NO_EXE "1")
endif()
# Is this installation the result of a crosscompile?
if(NOT DEFINED CMAKE_CROSSCOMPILING)
set(CMAKE_CROSSCOMPILING "FALSE")
endif()
# Set path to fallback-tool for dependency-resolution.
if(NOT DEFINED CMAKE_OBJDUMP)
set(CMAKE_OBJDUMP "/usr/bin/objdump")
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/lib" TYPE FILE FILES
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/lib/x86_64/libddsc.so"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/lib/x86_64/libddsc.so.0"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/lib/x86_64/libddscxx.so"
"/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/lib/x86_64/libddscxx.so.0"
)
endif()
if(CMAKE_INSTALL_COMPONENT STREQUAL "Unspecified" OR NOT CMAKE_INSTALL_COMPONENT)
file(INSTALL DESTINATION "${CMAKE_INSTALL_PREFIX}/include" TYPE DIRECTORY FILES "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/thirdparty/include/")
endif()
string(REPLACE ";" "\n" CMAKE_INSTALL_MANIFEST_CONTENT
"${CMAKE_INSTALL_MANIFEST_FILES}")
if(CMAKE_INSTALL_LOCAL_ONLY)
file(WRITE "/home/zedx/Robotics_workspace/yslootahtech/Project/R1/sdk/unitree_sdk2/build_install/thirdparty/install_local_manifest.txt"
"${CMAKE_INSTALL_MANIFEST_CONTENT}")
endif()

View File

@ -0,0 +1,7 @@
include(CMakeFindDependencyMacro)
# Same syntax as find_package
find_dependency(Threads REQUIRED)
# Add the targets file
include("${CMAKE_CURRENT_LIST_DIR}/unitree_sdk2Targets.cmake")

View File

@ -0,0 +1,83 @@
# This is a basic version file for the Config-mode of find_package().
# It is used by write_basic_package_version_file() as input file for configure_file()
# to create a version-file which can be installed along a config.cmake file.
#
# The created file sets PACKAGE_VERSION_EXACT if the current version string and
# the requested version string are exactly the same and it sets
# PACKAGE_VERSION_COMPATIBLE if the current version is equal to the requested version.
# The tweak version component is ignored.
# The variable CVF_VERSION must be set before calling configure_file().
if (PACKAGE_FIND_VERSION_RANGE)
message(AUTHOR_WARNING
"`find_package()` specify a version range but the version strategy "
"(ExactVersion) of the module `${PACKAGE_FIND_NAME}` is incompatible "
"with this request. Only the lower endpoint of the range will be used.")
endif()
set(PACKAGE_VERSION "2.0.0")
if("2.0.0" MATCHES "^([0-9]+)\\.([0-9]+)\\.([0-9]+)") # strip the tweak version
set(CVF_VERSION_MAJOR "${CMAKE_MATCH_1}")
set(CVF_VERSION_MINOR "${CMAKE_MATCH_2}")
set(CVF_VERSION_PATCH "${CMAKE_MATCH_3}")
if(NOT CVF_VERSION_MAJOR VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" CVF_VERSION_MAJOR "${CVF_VERSION_MAJOR}")
endif()
if(NOT CVF_VERSION_MINOR VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" CVF_VERSION_MINOR "${CVF_VERSION_MINOR}")
endif()
if(NOT CVF_VERSION_PATCH VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" CVF_VERSION_PATCH "${CVF_VERSION_PATCH}")
endif()
set(CVF_VERSION_NO_TWEAK "${CVF_VERSION_MAJOR}.${CVF_VERSION_MINOR}.${CVF_VERSION_PATCH}")
else()
set(CVF_VERSION_NO_TWEAK "2.0.0")
endif()
if(PACKAGE_FIND_VERSION MATCHES "^([0-9]+)\\.([0-9]+)\\.([0-9]+)") # strip the tweak version
set(REQUESTED_VERSION_MAJOR "${CMAKE_MATCH_1}")
set(REQUESTED_VERSION_MINOR "${CMAKE_MATCH_2}")
set(REQUESTED_VERSION_PATCH "${CMAKE_MATCH_3}")
if(NOT REQUESTED_VERSION_MAJOR VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" REQUESTED_VERSION_MAJOR "${REQUESTED_VERSION_MAJOR}")
endif()
if(NOT REQUESTED_VERSION_MINOR VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" REQUESTED_VERSION_MINOR "${REQUESTED_VERSION_MINOR}")
endif()
if(NOT REQUESTED_VERSION_PATCH VERSION_EQUAL 0)
string(REGEX REPLACE "^0+" "" REQUESTED_VERSION_PATCH "${REQUESTED_VERSION_PATCH}")
endif()
set(REQUESTED_VERSION_NO_TWEAK
"${REQUESTED_VERSION_MAJOR}.${REQUESTED_VERSION_MINOR}.${REQUESTED_VERSION_PATCH}")
else()
set(REQUESTED_VERSION_NO_TWEAK "${PACKAGE_FIND_VERSION}")
endif()
if(REQUESTED_VERSION_NO_TWEAK STREQUAL CVF_VERSION_NO_TWEAK)
set(PACKAGE_VERSION_COMPATIBLE TRUE)
else()
set(PACKAGE_VERSION_COMPATIBLE FALSE)
endif()
if(PACKAGE_FIND_VERSION STREQUAL PACKAGE_VERSION)
set(PACKAGE_VERSION_EXACT TRUE)
endif()
# if the installed or the using project don't have CMAKE_SIZEOF_VOID_P set, ignore it:
if("${CMAKE_SIZEOF_VOID_P}" STREQUAL "" OR "8" STREQUAL "")
return()
endif()
# check that the installed version has the same 32/64bit-ness as the one which is currently searching:
if(NOT CMAKE_SIZEOF_VOID_P STREQUAL "8")
math(EXPR installedBits "8 * 8")
set(PACKAGE_VERSION "${PACKAGE_VERSION} (${installedBits}bit)")
set(PACKAGE_VERSION_UNSUITABLE TRUE)
endif()

View File

@ -0,0 +1,7 @@
include(CMakeFindDependencyMacro)
# Same syntax as find_package
find_dependency(Threads REQUIRED)
# Add the targets file
include("${CMAKE_CURRENT_LIST_DIR}/unitree_sdk2Targets.cmake")

View File

@ -0,0 +1,96 @@
if(CMAKE_VERSION VERSION_LESS 3.5.0)
message(FATAL_ERROR "This file relies on consumers using CMake 3.5.0 or greater.")
endif()
cmake_policy(PUSH)
cmake_policy(VERSION 2.6)
# Commands may need to know the format version.
set(CMAKE_IMPORT_FILE_VERSION 1)
# Protect against multiple inclusion, which would fail when already imported targets are added once more.
set(_targetsDefined)
set(_targetsNotDefined)
set(_expectedTargets)
foreach(_expectedTarget unitree_sdk2)
list(APPEND _expectedTargets ${_expectedTarget})
if(NOT TARGET ${_expectedTarget})
list(APPEND _targetsNotDefined ${_expectedTarget})
endif()
if(TARGET ${_expectedTarget})
list(APPEND _targetsDefined ${_expectedTarget})
endif()
endforeach()
if("${_targetsDefined}" STREQUAL "${_expectedTargets}")
unset(_targetsDefined)
unset(_targetsNotDefined)
unset(_expectedTargets)
set(CMAKE_IMPORT_FILE_VERSION)
cmake_policy(POP)
return()
endif()
if(NOT "${_targetsDefined}" STREQUAL "")
message(FATAL_ERROR "Some (but not all) targets in this export set were already defined.\nTargets Defined: ${_targetsDefined}\nTargets not yet defined: ${_targetsNotDefined}\n")
endif()
unset(_targetsDefined)
unset(_targetsNotDefined)
unset(_expectedTargets)
# Compute the installation prefix relative to this file.
get_filename_component(_IMPORT_PREFIX "${CMAKE_CURRENT_LIST_FILE}" PATH)
get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
get_filename_component(_IMPORT_PREFIX "${_IMPORT_PREFIX}" PATH)
if(_IMPORT_PREFIX STREQUAL "/")
set(_IMPORT_PREFIX "")
endif()
# Create imported target ddsc and ddscxx
add_library(ddsc SHARED IMPORTED GLOBAL)
set_target_properties(ddsc PROPERTIES
IMPORTED_LOCATION ${_IMPORT_PREFIX}/lib/libddsc.so
INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include;${_IMPORT_PREFIX}/include"
INTERFACE_LINK_LIBRARIES "Threads::Threads"
IMPORTED_NO_SONAME TRUE)
add_library(ddscxx SHARED IMPORTED GLOBAL)
set_target_properties(ddscxx PROPERTIES
IMPORTED_LOCATION ${_IMPORT_PREFIX}/lib/libddscxx.so
INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include;${_IMPORT_PREFIX}/include/ddscxx"
INTERFACE_LINK_LIBRARIES "Threads::Threads"
IMPORTED_NO_SONAME TRUE)
# Create imported target unitree_sdk2
add_library(unitree_sdk2 STATIC IMPORTED GLOBAL)
set_target_properties(unitree_sdk2 PROPERTIES
IMPORTED_LOCATION ${_IMPORT_PREFIX}/lib/libunitree_sdk2.a
INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include;${_IMPORT_PREFIX}/include"
INTERFACE_LINK_LIBRARIES "ddsc;ddscxx;Threads::Threads"
LINKER_LANGUAGE CXX
)
# Cleanup temporary variables.
set(_IMPORT_PREFIX)
# Loop over all imported files and verify that they actually exist
foreach(target ${_IMPORT_CHECK_TARGETS} )
foreach(file ${_IMPORT_CHECK_FILES_FOR_${target}} )
if(NOT EXISTS "${file}" )
message(FATAL_ERROR "The imported target \"${target}\" references the file
\"${file}\"
but this file does not exist. Possible reasons include:
* The file was deleted, renamed, or moved to another location.
* An install or uninstall procedure did not complete successfully.
* The installation package was faulty and contained
\"${CMAKE_CURRENT_LIST_FILE}\"
but not all the files it references.
")
endif()
endforeach()
unset(_IMPORT_CHECK_FILES_FOR_${target})
endforeach()
unset(_IMPORT_CHECK_TARGETS)
# Commands beyond this point should not need to know the version.
set(CMAKE_IMPORT_FILE_VERSION)
cmake_policy(POP)

View File

@ -0,0 +1,16 @@
add_subdirectory(helloworld)
add_subdirectory(wireless_controller)
add_subdirectory(jsonize)
add_subdirectory(state_machine)
add_subdirectory(go2)
add_subdirectory(b2)
add_subdirectory(h1)
add_subdirectory(g1)
add_subdirectory(go2w)
add_subdirectory(b2w)
add_subdirectory(a2)
add_subdirectory(r1)
add_subdirectory(h2)
add_subdirectory(as2)

View File

@ -0,0 +1,8 @@
add_executable(a2_sport_client sport/a2_sport_client.cpp)
target_link_libraries(a2_sport_client unitree_sdk2)
add_executable(a2_sport_state sport/a2_sport_state.cpp)
target_link_libraries(a2_sport_state unitree_sdk2)
add_executable(a2_audio_client_example audio/a2_audio_client_example.cpp)
target_link_libraries(a2_audio_client_example unitree_sdk2)

View File

@ -0,0 +1,175 @@
#include <fstream>
#include <iostream>
#include <thread>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/idl/ros2/String_.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/robot/a2/audio/audio_client.hpp>
#include "wav.hpp"
#define AUDIO_FILE_PATH "../example/a2/audio/test.wav"
#define AUDIO_SUBSCRIBE_TOPIC "rt/audio_msg"
#define GROUP_IP "239.168.123.161"
#define PORT 5555
#define WAV_SECOND 5 // record seconds
#define WAV_LEN (16000 * 2 * WAV_SECOND)
#define WAV_LEN_ONCE (16000 * 2 * 160 / 1000)
#define CHUNK_SIZE 96000 // 3 seconds
int sock;
void asr_handler(const void *msg) {
std_msgs::msg::dds_::String_ *resMsg = (std_msgs::msg::dds_::String_ *)msg;
std::cout << "Topic:\"rt/audio_msg\" recv: " << resMsg->data() << std::endl;
}
std::string get_local_ip_for_multicast() {
struct ifaddrs *ifaddr, *ifa;
char host[NI_MAXHOST];
std::string result = "";
getifaddrs(&ifaddr);
for (ifa = ifaddr; ifa != nullptr; ifa = ifa->ifa_next) {
if (!ifa->ifa_addr || ifa->ifa_addr->sa_family != AF_INET) continue;
getnameinfo(ifa->ifa_addr, sizeof(struct sockaddr_in), host, NI_MAXHOST,
NULL, 0, NI_NUMERICHOST);
std::string ip(host);
if (ip.find("192.168.123.") == 0) {
result = ip;
break;
}
}
freeifaddrs(ifaddr);
return result;
}
void thread_mic(void) {
sock = socket(AF_INET, SOCK_DGRAM, 0);
sockaddr_in local_addr{};
local_addr.sin_family = AF_INET;
local_addr.sin_port = htons(PORT);
local_addr.sin_addr.s_addr = INADDR_ANY;
bind(sock, (sockaddr *)&local_addr, sizeof(local_addr));
ip_mreq mreq{};
inet_pton(AF_INET, GROUP_IP, &mreq.imr_multiaddr);
std::string local_ip = get_local_ip_for_multicast();
std::cout << "local ip: " << local_ip << std::endl;
mreq.imr_interface.s_addr = inet_addr(local_ip.c_str());
setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq));
int total_bytes = 0;
std::vector<int16_t> pcm_data;
pcm_data.reserve(WAV_LEN / 2);
std::cout << "start record!" << std::endl;
while (total_bytes < WAV_LEN) {
char buffer[WAV_LEN_ONCE];
ssize_t len = recvfrom(sock, buffer, sizeof(buffer), 0, nullptr, nullptr);
if (len > 0) {
size_t sample_count = len / 2;
const int16_t *samples = reinterpret_cast<const int16_t *>(buffer);
pcm_data.insert(pcm_data.end(), samples, samples + sample_count);
total_bytes += len;
}
}
WriteWave("record.wav", 16000, pcm_data.data(), pcm_data.size(), 1);
std::cout << "record finish! save to record.wav " << std::endl;
}
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: audio_client_example [NetWorkInterface(eth0)]"
<< std::endl;
exit(0);
}
int32_t ret;
/*
* Initilaize ChannelFactory
*/
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::a2::AudioClient client;
client.Init();
client.SetTimeout(10.0f);
/*ASR message Example*/
unitree::robot::ChannelSubscriber<std_msgs::msg::dds_::String_> subscriber(
AUDIO_SUBSCRIBE_TOPIC);
subscriber.InitChannel(asr_handler);
/*Volume Example*/
uint8_t volume;
ret = client.GetVolume(volume);
std::cout << "GetVolume API ret:" << ret
<< " volume = " << std::to_string(volume) << std::endl;
ret = client.SetVolume(100);
std::cout << "SetVolume to 100% , API ret:" << ret << std::endl;
/*TTS Example*/
ret = client.TtsMaker("你好。我是宇树科技的机器人。例程启动成功",
0); // Auto play
std::cout << "TtsMaker API ret:" << ret << std::endl;
unitree::common::Sleep(5);
ret = client.TtsMaker(
"Hello. I'm a robot from Unitree Robotics. The example has started "
"successfully. ",
1); // Engilsh TTS
std::cout << "TtsMaker API ret:" << ret << std::endl;
unitree::common::Sleep(8);
/*Audio Play Example*/
int32_t sample_rate = -1;
int8_t num_channels = 0;
bool filestate = false;
std::vector<uint8_t> pcm =
ReadWave(AUDIO_FILE_PATH, &sample_rate, &num_channels, &filestate);
std::cout << "wav file sample_rate = " << sample_rate
<< " num_channels = " << std::to_string(num_channels)
<< " filestate =" << filestate << "filesize = " << pcm.size()
<< std::endl;
if (filestate && sample_rate == 16000 && num_channels == 1) {
size_t total_size = pcm.size();
size_t offset = 0;
int chunk_index = 0;
std::string stream_id =
std::to_string(unitree::common::GetCurrentTimeMillisecond());
while (offset < total_size) {
size_t remaining = total_size - offset;
size_t current_chunk_size =
std::min(static_cast<size_t>(CHUNK_SIZE), remaining);
std::vector<uint8_t> chunk(pcm.begin() + offset,
pcm.begin() + offset + current_chunk_size);
client.PlayStream("example", stream_id, chunk);
unitree::common::Sleep(1);
std::cout << "Playing size: " << offset << std::endl;
offset += current_chunk_size;
}
ret = client.PlayStop(stream_id); // stop playback after transmission ends
} else {
std::cout << "audio file format error, please check!" << std::endl;
}
/*LED Control Example*/
client.LedControl(0, 255, 0);
unitree::common::Sleep(1);
client.LedControl(0, 0, 0);
unitree::common::Sleep(1);
client.LedControl(0, 0, 255);
std::cout << "AudioClient api test finish , asr start..." << std::endl;
std::thread mic_t(thread_mic);
while (1) {
sleep(1); // wait for asr message
}
mic_t.join();
return 0;
}

Binary file not shown.

View File

@ -0,0 +1,232 @@
#ifndef __UT_ROBOT_WAV_READER_HPP__
#define __UT_ROBOT_WAV_READER_HPP__
struct WaveHeader {
void SeekToDataChunk(std::istream &is) {
while (is && subchunk2_id != 0x61746164) {
is.seekg(subchunk2_size, std::istream::cur);
is.read(reinterpret_cast<char *>(&subchunk2_id), sizeof(int32_t));
is.read(reinterpret_cast<char *>(&subchunk2_size), sizeof(int32_t));
}
}
int32_t chunk_id;
int32_t chunk_size;
int32_t format;
int32_t subchunk1_id;
int32_t subchunk1_size;
int16_t audio_format;
int16_t num_channels;
int32_t sample_rate;
int32_t byte_rate;
int16_t block_align;
int16_t bits_per_sample;
int32_t subchunk2_id; // a tag of this chunk
int32_t subchunk2_size; // size of subchunk2
};
static_assert(sizeof(WaveHeader) == 44);
std::vector<uint8_t> ReadWaveImpl(std::istream &is, int32_t *sampling_rate,
int8_t *channelCount, bool *is_ok) {
WaveHeader header{};
is.read(reinterpret_cast<char *>(&header.chunk_id), sizeof(header.chunk_id));
// F F I R
if (header.chunk_id != 0x46464952) {
printf("Expected chunk_id RIFF. Given: 0x%08x\n", header.chunk_id);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.chunk_size),
sizeof(header.chunk_size));
is.read(reinterpret_cast<char *>(&header.format), sizeof(header.format));
// E V A W
if (header.format != 0x45564157) {
printf("Expected format WAVE. Given: 0x%08x\n", header.format);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.subchunk1_id),
sizeof(header.subchunk1_id));
is.read(reinterpret_cast<char *>(&header.subchunk1_size),
sizeof(header.subchunk1_size));
if (header.subchunk1_id == 0x4b4e554a) {
// skip junk padding
is.seekg(header.subchunk1_size, std::istream::cur);
is.read(reinterpret_cast<char *>(&header.subchunk1_id),
sizeof(header.subchunk1_id));
is.read(reinterpret_cast<char *>(&header.subchunk1_size),
sizeof(header.subchunk1_size));
}
if (header.subchunk1_id != 0x20746d66) {
printf("Expected subchunk1_id 0x20746d66. Given: 0x%08x\n",
header.subchunk1_id);
*is_ok = false;
return {};
}
if (header.subchunk1_size != 16 &&
header.subchunk1_size != 18) { // 16 for PCM
printf("Expected subchunk1_size 16. Given: %d\n", header.subchunk1_size);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.audio_format),
sizeof(header.audio_format));
if (header.audio_format != 1) { // 1 for PCM
printf("Expected audio_format 1. Given: %d\n", header.audio_format);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.num_channels),
sizeof(header.num_channels));
*channelCount = (int8_t)header.num_channels;
is.read(reinterpret_cast<char *>(&header.sample_rate),
sizeof(header.sample_rate));
is.read(reinterpret_cast<char *>(&header.byte_rate),
sizeof(header.byte_rate));
is.read(reinterpret_cast<char *>(&header.block_align),
sizeof(header.block_align));
is.read(reinterpret_cast<char *>(&header.bits_per_sample),
sizeof(header.bits_per_sample));
if (header.byte_rate !=
(header.sample_rate * header.num_channels * header.bits_per_sample / 8)) {
printf("Incorrect byte rate: %d. Expected: %d", header.byte_rate,
(header.sample_rate * header.num_channels * header.bits_per_sample /
8));
*is_ok = false;
return {};
}
if (header.block_align !=
(header.num_channels * header.bits_per_sample / 8)) {
printf("Incorrect block align: %d. Expected: %d\n", header.block_align,
(header.num_channels * header.bits_per_sample / 8));
*is_ok = false;
return {};
}
if (header.bits_per_sample != 16) { // we support only 16 bits per sample
printf("Expected bits_per_sample 16. Given: %d\n", header.bits_per_sample);
*is_ok = false;
return {};
}
if (header.subchunk1_size == 18) {
int16_t extra_size = -1;
is.read(reinterpret_cast<char *>(&extra_size), sizeof(int16_t));
if (extra_size != 0) {
printf(
"Extra size should be 0 for wave from NAudio. Current extra size "
"%d\n",
extra_size);
*is_ok = false;
return {};
}
}
is.read(reinterpret_cast<char *>(&header.subchunk2_id),
sizeof(header.subchunk2_id));
is.read(reinterpret_cast<char *>(&header.subchunk2_size),
sizeof(header.subchunk2_size));
header.SeekToDataChunk(is);
if (!is) {
*is_ok = false;
return {};
}
*sampling_rate = header.sample_rate;
// header.subchunk2_size contains the number of bytes in the data.
// As we assume each sample contains two bytes, so it is divided by 2 here
std::vector<int16_t> samples(header.subchunk2_size / 2);
is.read(reinterpret_cast<char *>(samples.data()), header.subchunk2_size);
if (!is) {
*is_ok = false;
return {};
}
std::vector<uint8_t> ans(samples.size() * 2);
for (int32_t i = 0; i != static_cast<int32_t>(samples.size()); ++i) {
ans[i * 2] = samples[i] & 0xFF;
ans[i * 2 + 1] = (samples[i] >> 8) & 0xFF;
}
*is_ok = true;
return ans;
}
std::vector<uint8_t> ReadWave(const std::string &filename,
int32_t *sampling_rate, int8_t *channelCount,
bool *is_ok) {
std::ifstream is(filename, std::ifstream::binary);
auto samples = ReadWaveImpl(is, sampling_rate, channelCount, is_ok);
return samples;
}
bool WriteWave(const std::string &filename, int32_t sampling_rate,
const int16_t *samples, int32_t n, uint8_t num_channels) {
WaveHeader header{};
header.chunk_id = 0x46464952; // FFIR
header.format = 0x45564157; // EVAW
header.subchunk1_id = 0x20746d66; // "fmt "
header.subchunk1_size = 16; // 16 for PCM
header.audio_format = 1; // PCM =1
int32_t bits_per_sample = 16; // int16_t
header.num_channels = num_channels;
header.sample_rate = sampling_rate;
header.byte_rate = sampling_rate * num_channels * bits_per_sample / 8;
header.block_align = num_channels * bits_per_sample / 8;
header.bits_per_sample = bits_per_sample;
header.subchunk2_id = 0x61746164; // atad
header.subchunk2_size = n * num_channels * bits_per_sample / 8;
header.chunk_size = 36 + header.subchunk2_size;
std::vector<int16_t> samples_int16(n * num_channels);
for (int32_t i = 0; i != n * num_channels; ++i) {
samples_int16[i] = samples[i];
}
std::ofstream os(filename, std::ios::binary);
if (!os) {
printf("Failed to create %s", filename.c_str());
return false;
}
os.write(reinterpret_cast<const char *>(&header), sizeof(header));
os.write(reinterpret_cast<const char *>(samples_int16.data()),
samples_int16.size() * sizeof(int16_t));
if (!os) {
printf("Write %s failed", filename.c_str());
return false;
}
return true;
}
#endif

View File

@ -0,0 +1,315 @@
#include <iostream>
#include <string>
#include <chrono>
#include <mutex>
#include <thread>
#include <pthread.h>
#include <stdexcept>
#include <cmath>
#include <unitree/robot/a2/sport/sport_client.hpp>
using namespace std;
struct TestOption
{
std::string name;
int id;
};
const vector<TestOption> option_list =
{
{"damp", 0},
{"balance_stand", 1},
{"stop_move", 2},
{"stand_down", 3},
{"recovery_stand", 4},
{"move", 5},
{"switch_gait", 6},
{"speed_level", 7},
{"get_state", 8},
{"recovery_switch", 9},
{"body_height", 10},
{"stand_up", 11},
// Caution: test in open area
{"enter_leftside_gait", 12},
{"exit_leftside_gait", 13},
{"enter_handstand", 14},
{"exit_handstand", 15},
{"front_flip", 16},
{"back_flip", 17},
{"pose", 18},
{"euler", 19},
{"reset_estimator", 20},
{"square_trajectory", 21},
{"circle_trajectory", 22},
};
int ConvertToInt(const std::string &str)
{
try
{
std::stoi(str);
return std::stoi(str);
}
catch (const std::invalid_argument &)
{
return -1;
}
catch (const std::out_of_range &)
{
return -1;
}
}
class UserInterface
{
public:
UserInterface() {};
~UserInterface() {};
void terminalHandle()
{
std::string input;
std::getline(std::cin, input);
if (input.compare("list") == 0)
{
for (TestOption option : option_list)
{
std::cout << option.name << ", id: " << option.id << std::endl;
}
}
for (TestOption option : option_list)
{
if (input.compare(option.name) == 0 || ConvertToInt(input) == option.id)
{
test_option_->id = option.id;
test_option_->name = option.name;
std::cout << "Test: " << test_option_->name << ", test_id: " << test_option_->id << std::endl;
}
}
};
TestOption *test_option_;
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
TestOption test_option;
test_option.id = 1;
unitree::robot::a2::SportClient sport_client;
sport_client.SetTimeout(25.0f);
sport_client.Init();
UserInterface user_interface;
user_interface.test_option_ = &test_option;
std::cout << "Input \"list \" to list all test option ..." << std::endl;
long res_count = 0;
while (1)
{
auto time_start_trick = std::chrono::high_resolution_clock::now();
static const constexpr auto dt = std::chrono::microseconds(20000); // 50Hz
user_interface.terminalHandle();
int res = 1;
if (test_option.id == 0)
{
res = sport_client.Damp();
}
else if (test_option.id == 1)
{
res = sport_client.BalanceStand();
}
else if (test_option.id == 2)
{
res = sport_client.StopMove();
}
else if (test_option.id == 3)
{
res = sport_client.StandDown();
}
else if (test_option.id == 4)
{
res = sport_client.RecoveryStand();
}
else if (test_option.id == 5)
{
res = sport_client.Move(0.0, 0.0, 0.5);
}
else if (test_option.id == 6)
{
res = sport_client.SwitchGait(0);
}
else if (test_option.id == 7)
{
res = sport_client.SpeedLevel(1);
}
else if (test_option.id == 8)
{
std::map<std::string, std::string> state_map;
res = sport_client.GetState(state_map);
std::cout << "fsm_id: " << state_map["fsm_id"] << std::endl;
std::cout << "fsm_name: " << state_map["fsm_name"] << std::endl;
std::cout << "speed_level: " << state_map["speed_level"] << std::endl;
std::cout << "auto_recovery_switch: " << state_map["auto_recovery_switch"] << std::endl;
std::cout << "process_state: " << state_map["process_state"] << std::endl;
}
else if (test_option.id == 9)
{
res = sport_client.SetAutoRecovery(0);
}
else if (test_option.id == 10)
{
res = sport_client.BodyHeight(0.3f);
}
else if (test_option.id == 11)
{
res = sport_client.StandUp();
}
else if (test_option.id == 12)
{
res = sport_client.LeftSideGait(1);
}
else if (test_option.id == 13)
{
res = sport_client.LeftSideGait(0);
}
else if (test_option.id == 14)
{
res = sport_client.HandStand(1);
}
else if (test_option.id == 15)
{
res = sport_client.HandStand(0);
}
else if (test_option.id == 16)
{
res = sport_client.FrontFlip();
}
else if (test_option.id == 17)
{
res = sport_client.BackFlip();
}
else if (test_option.id == 18)
{
res = sport_client.BodyPosition(0.2f, 0.2f, -0.2f, 0.2f);
}
else if (test_option.id == 19)
{
res = sport_client.Euler(0.2f, 0.3f, 0.3f);
}
else if (test_option.id == 20)
{
res = sport_client.ResetEstimator();
}
else if (test_option.id == 21)
{
// 矩形轨迹: 1.0m x 1.0m, 带加减速过程的密集路径点
std::vector<unitree::robot::a2::PathPoint> path;
unitree::robot::a2::PathPoint pt;
// ===== 边1: (0,0)→(1,0), 向前 1m, 0-4s =====
pt.t_from_start = 0.0f; pt.x = 0.00f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 0.5f; pt.x = 0.03f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 1.0f; pt.x = 0.12f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 1.5f; pt.x = 0.28f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 2.0f; pt.x = 0.45f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 2.5f; pt.x = 0.62f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 3.0f; pt.x = 0.78f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 3.5f; pt.x = 0.94f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 4.0f; pt.x = 1.00f; pt.y = 0.0f; pt.yaw = 0.0f; path.push_back(pt);
// ===== 边2: (1,0)→(1,1), 左移 1m, 4-8s =====
pt.t_from_start = 4.5f; pt.x = 1.00f; pt.y = 0.03f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 5.0f; pt.x = 1.00f; pt.y = 0.12f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 5.5f; pt.x = 1.00f; pt.y = 0.28f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 6.0f; pt.x = 1.00f; pt.y = 0.45f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 6.5f; pt.x = 1.00f; pt.y = 0.62f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 7.0f; pt.x = 1.00f; pt.y = 0.78f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 7.5f; pt.x = 1.00f; pt.y = 0.94f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 8.0f; pt.x = 1.00f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
// ===== 边3: (1,1)→(0,1), 后退 1m, 8-13s =====
pt.t_from_start = 8.5f; pt.x = 0.97f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 9.0f; pt.x = 0.90f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 9.5f; pt.x = 0.78f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 10.0f; pt.x = 0.62f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 10.5f; pt.x = 0.45f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 11.0f; pt.x = 0.28f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 11.5f; pt.x = 0.12f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 12.0f; pt.x = 0.03f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 13.0f; pt.x = 0.00f; pt.y = 1.00f; pt.yaw = 0.0f; path.push_back(pt);
// ===== 边4: (0,1)→(0,0), 右移 1m, 13-16s =====
pt.t_from_start = 13.5f; pt.x = 0.00f; pt.y = 0.94f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 14.0f; pt.x = 0.00f; pt.y = 0.78f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 14.5f; pt.x = 0.00f; pt.y = 0.55f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 15.0f; pt.x = 0.00f; pt.y = 0.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 15.5f; pt.x = 0.00f; pt.y = 0.00f; pt.yaw = 0.0f; path.push_back(pt);
pt.t_from_start = 16.0f; pt.x = 0.00f; pt.y = 0.00f; pt.yaw = 0.0f; path.push_back(pt);
res = sport_client.Trajectory(path, 1);
}
else if (test_option.id == 22)
{
// 圆形轨迹: 半径1.0m, 圆心(0.0,1.0), 逆时针
const float R = 1.0f, cx = 0.0f, cy = 1.0f;
const float TOTAL_TIME = 20.0f; // <-- 修改此处调整总时长(s)
const float T_ACCEL = 0.25f * TOTAL_TIME; // 加速段
const float T_CRUISE = 0.50f * TOTAL_TIME; // 匀速段
const float T_DECEL = 0.25f * TOTAL_TIME; // 减速段
const int N = 36;
std::vector<unitree::robot::a2::PathPoint> path;
for (int i = 0; i <= N; ++i)
{
float frac = (float)i / N;
float t;
if (frac <= 0.25f)
t = T_ACCEL * (frac / 0.25f);
else if (frac <= 0.75f)
t = T_ACCEL + T_CRUISE * ((frac - 0.25f) / 0.5f);
else
t = T_ACCEL + T_CRUISE + T_DECEL * ((frac - 0.75f) / 0.25f);
float angle = -M_PI_2 + 2.0f * M_PI * frac;
unitree::robot::a2::PathPoint pt;
pt.t_from_start = t;
pt.x = cx + R * cosf(angle);
pt.y = cy + R * sinf(angle);
pt.yaw = 0.0f;
path.push_back(pt);
}
res = sport_client.Trajectory(path, 1);
}
if (res < 0)
{
res_count += 1;
std::cout << "Request error for: " << option_list[test_option.id].name << ", code: " << res << ", count: " << res_count << std::endl;
}
else
{
res_count = 0;
std::cout << "Request successed: " << option_list[test_option.id].name << ", code: " << res << std::endl;
}
std::this_thread::sleep_until(time_start_trick + dt);
}
return 0;
}

View File

@ -0,0 +1,68 @@
#include <cmath>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/SportModeState_.hpp>
#define TOPIC_HIGHSTATE "rt/lf/sportmodestate"
using namespace unitree::common;
const std::vector<std::string> FSM_STATE_STR = {
"PASSIVE",
"STAND_DOWN",
"STAND_UP",
"DEFAULT_MODE",
"RUNNING_MODE",
"CLIMB_MODE",
"LEFT_SIDE_GAIT",
"RIGHT_SIDE_GAIT",
"HANDSTAND",
"BIPED_STAND",
"FRONT_FLIP",
"BACK_FLIP",
"RECOVERY",
"BASE_HEIGHT_CTRL"};
class Custom
{
public:
Custom()
{
suber.reset(new unitree::robot::ChannelSubscriber<unitree_go::msg::dds_::SportModeState_>(TOPIC_HIGHSTATE));
suber->InitChannel(std::bind(&Custom::HighStateHandler, this, std::placeholders::_1), 1);
};
void HighStateHandler(const void *message)
{
state = *(unitree_go::msg::dds_::SportModeState_ *)message;
std::cout << "Position: " << state.position()[0] << ", " << state.position()[1] << ", " << state.position()[2] << std::endl;
std::cout << "Velocity: " << state.velocity()[0] << ", " << state.velocity()[1] << ", " << state.velocity()[2] << std::endl;
std::cout << "Mode: " << FSM_STATE_STR[int(state.mode())] << std::endl;
std::cout << "Progress: " << state.progress() << std::endl;
// std::cout << "IMU rpy: " << state.imu_state().rpy()[0] << ", " << state.imu_state().rpy()[1] << ", " << state.imu_state().rpy()[2] << std::endl;
};
unitree_go::msg::dds_::SportModeState_ state;
unitree::robot::ChannelSubscriberPtr<unitree_go::msg::dds_::SportModeState_> suber;
float dt = 0.05; // 控制步长0.001~0.01
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,5 @@
add_executable(as2_sport_client sport/as2_sport_client.cpp)
target_link_libraries(as2_sport_client unitree_sdk2)
add_executable(as2_sport_state sport/as2_sport_state.cpp)
target_link_libraries(as2_sport_state unitree_sdk2)

View File

@ -0,0 +1,312 @@
#include <iostream>
#include <string>
#include <chrono>
#include <mutex>
#include <thread>
#include <pthread.h>
#include <stdexcept>
#include <unitree/robot/as2/sport/sport_client.hpp>
using namespace std;
struct TestOption
{
std::string name;
int id;
};
const vector<TestOption> option_list =
{
{"damp", 0},
{"balance_stand", 1},
{"stop_move", 2},
{"stand_down", 3},
{"recovery_stand", 4},
{"move", 5},
{"switch_gait", 6},
{"speed_level", 7},
{"get_state", 8},
{"recovery_switch", 9},
{"body_height", 10},
{"stand_up", 11},
// Caution: test in open area
{"enter_leftside_gait", 12},
{"exit_leftside_gait", 13},
{"enter_handstand", 14},
{"exit_handstand", 15},
{"front_flip", 16},
{"back_flip", 17},
{"pose", 18},
{"euler", 19},
{"switch_joystick", 20},
{"enter_biped_stand", 21},
{"exit_biped_stand", 22},
{"enter_rightside_gait", 23},
{"exit_rightside_gait", 24},
{"greeting", 25},
{"heart", 26},
{"content", 27},
{"dance1", 28},
{"dance2", 29},
{"handshake", 30},
{"stretch", 31},
{"enter_sit", 32},
{"exit_sit", 33},
{"front_jump", 34},
{"push_up", 35},
{"up_jump", 36},
};
int ConvertToInt(const std::string &str)
{
try
{
std::stoi(str);
return std::stoi(str);
}
catch (const std::invalid_argument &)
{
return -1;
}
catch (const std::out_of_range &)
{
return -1;
}
}
class UserInterface
{
public:
UserInterface() {};
~UserInterface() {};
void terminalHandle()
{
std::string input;
std::getline(std::cin, input);
if (input.compare("list") == 0)
{
for (TestOption option : option_list)
{
std::cout << option.name << ", id: " << option.id << std::endl;
}
}
for (TestOption option : option_list)
{
if (input.compare(option.name) == 0 || ConvertToInt(input) == option.id)
{
test_option_->id = option.id;
test_option_->name = option.name;
std::cout << "Test: " << test_option_->name << ", test_id: " << test_option_->id << std::endl;
}
}
};
TestOption *test_option_;
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
TestOption test_option;
test_option.id = 1;
unitree::robot::as2::SportClient sport_client;
sport_client.SetTimeout(25.0f);
sport_client.Init();
UserInterface user_interface;
user_interface.test_option_ = &test_option;
std::cout << "Input \"list \" to list all test option ..." << std::endl;
long res_count = 0;
while (1)
{
auto time_start_trick = std::chrono::high_resolution_clock::now();
static const constexpr auto dt = std::chrono::microseconds(20000); // 50Hz
user_interface.terminalHandle();
int res = 1;
if (test_option.id == 0)
{
res = sport_client.Damp();
}
else if (test_option.id == 1)
{
res = sport_client.BalanceStand();
}
else if (test_option.id == 2)
{
res = sport_client.StopMove();
}
else if (test_option.id == 3)
{
res = sport_client.StandDown();
}
else if (test_option.id == 4)
{
res = sport_client.RecoveryStand();
}
else if (test_option.id == 5)
{
res = sport_client.Move(0.0, 0.0, 0.5);
}
else if (test_option.id == 6)
{
res = sport_client.SwitchGait(0);
}
else if (test_option.id == 7)
{
res = sport_client.SpeedLevel(1);
}
else if (test_option.id == 8)
{
std::map<std::string, std::string> state_map;
res = sport_client.GetState(state_map);
std::cout << "fsm_id: " << state_map["fsm_id"] << std::endl;
std::cout << "fsm_name: " << state_map["fsm_name"] << std::endl;
std::cout << "speed_level: " << state_map["speed_level"] << std::endl;
std::cout << "auto_recovery_switch: " << state_map["auto_recovery_switch"] << std::endl;
std::cout << "process_state: " << state_map["process_state"] << std::endl;
}
else if (test_option.id == 9)
{
res = sport_client.SetAutoRecovery(0);
}
else if (test_option.id == 10)
{
res = sport_client.BodyHeight(0.3f);
}
else if (test_option.id == 11)
{
res = sport_client.StandUp();
}
else if (test_option.id == 12)
{
res = sport_client.LeftSideGait(1);
}
else if (test_option.id == 13)
{
res = sport_client.LeftSideGait(0);
}
else if (test_option.id == 14)
{
res = sport_client.HandStand(1);
}
else if (test_option.id == 15)
{
res = sport_client.HandStand(0);
}
else if (test_option.id == 16)
{
res = sport_client.FrontFlip();
}
else if (test_option.id == 17)
{
res = sport_client.BackFlip();
}
else if (test_option.id == 18)
{
res = sport_client.BodyPosition(0.2f, 0.2f, -0.2f, 0.2f);
}
else if (test_option.id == 19)
{
res = sport_client.Euler(0.2f, 0.3f, 0.3f);
}
else if (test_option.id == 20)
{
res = sport_client.SwitchJoystick(0);
}
else if (test_option.id == 21)
{
res = sport_client.BipedStand(1);
}
else if (test_option.id == 22)
{
res = sport_client.BipedStand(0);
}
else if (test_option.id == 23)
{
res = sport_client.RightSideGait(1);
}
else if (test_option.id == 24)
{
res = sport_client.RightSideGait(0);
}
else if (test_option.id == 25)
{
res = sport_client.Greeting();
}
else if (test_option.id == 26)
{
res = sport_client.Heart();
}
else if (test_option.id == 27)
{
res = sport_client.Content();
}
else if (test_option.id == 28)
{
res = sport_client.Dance1();
}
else if (test_option.id == 29)
{
res = sport_client.Dance2();
}
else if (test_option.id == 30)
{
res = sport_client.Handshake();
}
else if (test_option.id == 31)
{
res = sport_client.Stretch();
}
else if (test_option.id == 32)
{
res = sport_client.Sit(1);
}
else if (test_option.id == 33)
{
res = sport_client.Sit(0);
}
else if (test_option.id == 34)
{
res = sport_client.FrontJump();
}
else if (test_option.id == 35)
{
res = sport_client.PushUp();
}
else if (test_option.id == 36)
{
res = sport_client.UpJump();
}
if (res < 0)
{
res_count += 1;
std::cout << "Request error for: " << option_list[test_option.id].name << ", code: " << res << ", count: " << res_count << std::endl;
}
else
{
res_count = 0;
std::cout << "Request successed: " << option_list[test_option.id].name << ", code: " << res << std::endl;
}
std::this_thread::sleep_until(time_start_trick + dt);
}
return 0;
}

View File

@ -0,0 +1,68 @@
#include <cmath>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/SportModeState_.hpp>
#define TOPIC_HIGHSTATE "rt/lf/sportmodestate"
using namespace unitree::common;
const std::vector<std::string> FSM_STATE_STR = {
"PASSIVE",
"STAND_DOWN",
"STAND_UP",
"DEFAULT_MODE",
"RUNNING_MODE",
"CLIMB_MODE",
"LEFT_SIDE_GAIT",
"RIGHT_SIDE_GAIT",
"HANDSTAND",
"BIPED_STAND",
"FRONT_FLIP",
"BACK_FLIP",
"RECOVERY",
"BASE_HEIGHT_CTRL"};
class Custom
{
public:
Custom()
{
suber.reset(new unitree::robot::ChannelSubscriber<unitree_go::msg::dds_::SportModeState_>(TOPIC_HIGHSTATE));
suber->InitChannel(std::bind(&Custom::HighStateHandler, this, std::placeholders::_1), 1);
};
void HighStateHandler(const void *message)
{
state = *(unitree_go::msg::dds_::SportModeState_ *)message;
std::cout << "Position: " << state.position()[0] << ", " << state.position()[1] << ", " << state.position()[2] << std::endl;
std::cout << "Velocity: " << state.velocity()[0] << ", " << state.velocity()[1] << ", " << state.velocity()[2] << std::endl;
std::cout << "Mode: " << FSM_STATE_STR[int(state.mode())] << std::endl;
std::cout << "Progress: " << state.progress() << std::endl;
// std::cout << "IMU rpy: " << state.imu_state().rpy()[0] << ", " << state.imu_state().rpy()[1] << ", " << state.imu_state().rpy()[2] << std::endl;
};
unitree_go::msg::dds_::SportModeState_ state;
unitree::robot::ChannelSubscriberPtr<unitree_go::msg::dds_::SportModeState_> suber;
float dt = 0.05; // 控制步长0.001~0.01
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,5 @@
add_executable(b2_sport_client b2_sport_client.cpp)
target_link_libraries(b2_sport_client unitree_sdk2)
add_executable(b2_stand_example b2_stand_example.cpp)
target_link_libraries(b2_stand_example unitree_sdk2)

View File

@ -0,0 +1,185 @@
#include <iostream>
#include <string>
#include <chrono>
#include <mutex>
#include <thread>
#include <pthread.h>
#include <stdexcept>
#include <unitree/robot/b2/sport/sport_client.hpp>
using namespace std;
struct TestOption
{
std::string name;
int id;
};
const vector<TestOption> option_list =
{
{"damp", 0},
{"balance_stand", 1},
{"stop_move", 2},
{"stand_down", 3},
{"recovery_stand", 4},
{"move", 5},
{"switch_gait", 6},
{"speed_level", 7},
{"hand_stand", 8},
{"auto_recovery_set", 9},
{"free_walk", 11},
{"classic_walk", 12},
{"fast_walk", 13},
{"euler", 14},
};
int ConvertToInt(const std::string &str)
{
try
{
std::stoi(str);
return std::stoi(str);
}
catch (const std::invalid_argument &)
{
return -1;
}
catch (const std::out_of_range &)
{
return -1;
}
}
class UserInterface
{
public:
UserInterface() {};
~UserInterface() {};
void terminalHandle()
{
std::string input;
std::getline(std::cin, input);
if (input.compare("list") == 0)
{
for (TestOption option : option_list)
{
std::cout << option.name << ", id: " << option.id << std::endl;
}
}
for (TestOption option : option_list)
{
if (input.compare(option.name) == 0 || ConvertToInt(input) == option.id)
{
test_option_->id = option.id;
test_option_->name = option.name;
std::cout << "Test: " << test_option_->name << ", test_id: " << test_option_->id << std::endl;
}
}
};
TestOption *test_option_;
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
TestOption test_option;
test_option.id = 1;
unitree::robot::b2::SportClient sport_client;
sport_client.SetTimeout(25.0f);
sport_client.Init();
UserInterface user_interface;
user_interface.test_option_ = &test_option;
std::cout << "Input \"list \" to list all test option ..." << std::endl;
long res_count = 0;
while (1)
{
auto time_start_trick = std::chrono::high_resolution_clock::now();
static const constexpr auto dt = std::chrono::microseconds(20000); // 50Hz
user_interface.terminalHandle();
int res = 1;
if (test_option.id == 0)
{
res = sport_client.Damp();
}
else if (test_option.id == 1)
{
res = sport_client.BalanceStand();
}
else if (test_option.id == 2)
{
res = sport_client.StopMove();
}
else if (test_option.id == 3)
{
res = sport_client.StandDown();
}
else if (test_option.id == 4)
{
res = sport_client.RecoveryStand();
}
else if (test_option.id == 5)
{
res = sport_client.Move(0.0, 0.0, 0.5);
}
else if (test_option.id == 6)
{
res = sport_client.SwitchGait(0);
}
else if (test_option.id == 7)
{
res = sport_client.SpeedLevel(1);
}
else if (test_option.id == 8)
{
res = sport_client.HandStand(true);
}
else if (test_option.id == 9)
{
res = sport_client.AutoRecoverySet(true);
}
else if (test_option.id == 11)
{
res = sport_client.FreeWalk();
}
else if (test_option.id == 12)
{
res = sport_client.ClassicWalk(true);
}
else if (test_option.id == 13)
{
res = sport_client.FastWalk(true);
}
else if (test_option.id == 14)
{
res = sport_client.Euler(0.0, 0.2, 0.0);
}
if (res < 0)
{
res_count += 1;
std::cout << "Request error for: " << option_list[test_option.id].name << ", code: " << res << ", count: " << res_count << std::endl;
}
else
{
res_count = 0;
std::cout << "Request successed: " << option_list[test_option.id].name << ", code: " << res << std::endl;
}
std::this_thread::sleep_until(time_start_trick + dt);
}
return 0;
}

View File

@ -0,0 +1,350 @@
#include <iostream>
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/LowState_.hpp>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/common/thread/thread.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree::robot::b2;
#define TOPIC_LOWCMD "rt/lowcmd"
#define TOPIC_LOWSTATE "rt/lowstate"
constexpr double PosStopF = (2.146E+9f);
constexpr double VelStopF = (16000.0f);
class Custom
{
public:
explicit Custom(){}
~Custom(){}
void Init();
void Start();
private:
void InitLowCmd();
void LowStateMessageHandler(const void* messages);
void LowCmdWrite();
int queryMotionStatus();
std::string queryServiceName(std::string form,std::string name);
private:
float Kp = 1000.0;
float Kd = 10.0;
double time_consume = 0;
int rate_count = 0;
int sin_count = 0;
int motiontime = 0;
float dt = 0.002; // 0.001~0.01
MotionSwitcherClient msc;
unitree_go::msg::dds_::LowCmd_ low_cmd{}; // default init
unitree_go::msg::dds_::LowState_ low_state{}; // default init
/*publisher*/
ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_> lowcmd_publisher;
/*subscriber*/
ChannelSubscriberPtr<unitree_go::msg::dds_::LowState_> lowstate_subscriber;
/*LowCmd write thread*/
ThreadPtr lowCmdWriteThreadPtr;
float _targetPos_1[12] = {0.0, 1.36, -2.65, 0.0, 1.36, -2.65,
0.2, 1.36, -2.65, 0.2, 1.36, -2.65};
float _targetPos_2[12] = {0.0, 0.67, -1.3, 0.0, 0.67, -1.3,
0.0, 0.67, -1.3, 0.0, 0.67, -1.3};
float _targetPos_3[12] = {0.0, 1.36, -2.65, 0.0, 1.36, -2.65,
0.0, 1.36, -2.65, 0.0, 1.36, -2.65};
float _targetPos_4[12] = {-0.5, 1.36, -2.65, 0.5, 1.36, -2.65,
-0.5, 1.36, -2.65, 0.5, 1.36, -2.65};
float _startPos[12];
float _duration_1 = 500;
float _duration_2 = 900;
float _duration_3 = 1000;
float _duration_4 = 1100;
float _duration_5 = 500;
float _percent_1 = 0;
float _percent_2 = 0;
float _percent_3 = 0;
float _percent_4 = 0;
float _percent_5 = 0;
bool firstRun = true;
bool done = false;
};
uint32_t crc32_core(uint32_t* ptr, uint32_t len)
{
unsigned int xbit = 0;
unsigned int data = 0;
unsigned int CRC32 = 0xFFFFFFFF;
const unsigned int dwPolynomial = 0x04c11db7;
for (unsigned int i = 0; i < len; i++)
{
xbit = 1 << 31;
data = ptr[i];
for (unsigned int bits = 0; bits < 32; bits++)
{
if (CRC32 & 0x80000000)
{
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
}
else
{
CRC32 <<= 1;
}
if (data & xbit)
CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
}
void Custom::Init()
{
InitLowCmd();
/*create publisher*/
lowcmd_publisher.reset(new ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(TOPIC_LOWCMD));
lowcmd_publisher->InitChannel();
/*create subscriber*/
lowstate_subscriber.reset(new ChannelSubscriber<unitree_go::msg::dds_::LowState_>(TOPIC_LOWSTATE));
lowstate_subscriber->InitChannel(std::bind(&Custom::LowStateMessageHandler, this, std::placeholders::_1), 1);
/*init MotionSwitcherClient*/
msc.SetTimeout(10.0f);
msc.Init();
/*Shut down motion control-related service*/
while(queryMotionStatus())
{
std::cout << "Try to deactivate the motion control-related service." << std::endl;
int32_t ret = msc.ReleaseMode();
if (ret == 0) {
std::cout << "ReleaseMode succeeded." << std::endl;
} else {
std::cout << "ReleaseMode failed. Error code: " << ret << std::endl;
}
sleep(5);
}
}
void Custom::InitLowCmd()
{
low_cmd.head()[0] = 0xFE;
low_cmd.head()[1] = 0xEF;
low_cmd.level_flag() = 0xFF;
low_cmd.gpio() = 0;
for(int i=0; i<20; i++)
{
low_cmd.motor_cmd()[i].mode() = (0x0A); // motor switch to servo (PMSM) mode
low_cmd.motor_cmd()[i].q() = (PosStopF);
low_cmd.motor_cmd()[i].kp() = (0);
low_cmd.motor_cmd()[i].dq() = (VelStopF);
low_cmd.motor_cmd()[i].kd() = (0);
low_cmd.motor_cmd()[i].tau() = (0);
}
}
int Custom::queryMotionStatus()
{
std::string robotForm,motionName;
int motionStatus;
int32_t ret = msc.CheckMode(robotForm,motionName);
if (ret == 0) {
std::cout << "CheckMode succeeded." << std::endl;
} else {
std::cout << "CheckMode failed. Error code: " << ret << std::endl;
}
if(motionName.empty())
{
std::cout << "The motion control-related service is deactivated." << std::endl;
motionStatus = 0;
}
else
{
std::string serviceName = queryServiceName(robotForm,motionName);
std::cout << "Service: "<< serviceName<< " is activate" << std::endl;
motionStatus = 1;
}
return motionStatus;
}
std::string Custom::queryServiceName(std::string form,std::string name)
{
if(form == "0")
{
if(name == "normal" ) return "sport_mode";
if(name == "ai" ) return "ai_sport";
if(name == "advanced" ) return "advanced_sport";
}
else
{
if(name == "ai-w" ) return "wheeled_sport(go2W)";
if(name == "normal-w" ) return "wheeled_sport(b2W)";
}
return "";
}
void Custom::Start()
{
/*loop publishing thread*/
lowCmdWriteThreadPtr = CreateRecurrentThreadEx("writebasiccmd", UT_CPU_ID_NONE, 2000, &Custom::LowCmdWrite, this);
}
void Custom::LowStateMessageHandler(const void* message)
{
low_state = *(unitree_go::msg::dds_::LowState_*)message;
}
void Custom::LowCmdWrite()
{
if(_percent_5<1)
{
std::cout<<"Read sensor data example: "<<std::endl;
std::cout<<"Joint 0 pos: "<<low_state.motor_state()[0].q()<<std::endl;
std::cout<<"Imu accelerometer : "<<"x: "<<low_state.imu_state().accelerometer()[0]<<" y: "<<low_state.imu_state().accelerometer()[1]<<" z: "<<low_state.imu_state().accelerometer()[2]<<std::endl;
std::cout<<"Foot force "<<low_state.foot_force()[0]<<std::endl;
std::cout<<std::endl;
}
if((_percent_5 == 1) && ( done == false))
{
std::cout<<"The example is done! "<<std::endl;
std::cout<<std::endl;
done = true;
}
motiontime++;
if(motiontime>=500)
{
if(firstRun)
{
for(int i = 0; i < 12; i++)
{
_startPos[i] = low_state.motor_state()[i].q();
}
firstRun = false;
}
_percent_1 += (float)1 / _duration_1;
_percent_1 = _percent_1 > 1 ? 1 : _percent_1;
if (_percent_1 < 1)
{
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_1) * _startPos[j] + _percent_1 * _targetPos_1[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 < 1))
{
_percent_2 += (float)1 / _duration_2;
_percent_2 = _percent_2 > 1 ? 1 : _percent_2;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_2) * _targetPos_1[j] + _percent_2 * _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3<1))
{
_percent_3 += (float)1 / _duration_3;
_percent_3 = _percent_3 > 1 ? 1 : _percent_3;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3==1)&&(_percent_4<1))
{
_percent_4 += (float)1 / _duration_4;
_percent_4 = _percent_4 > 1 ? 1 : _percent_4;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_4) * _targetPos_2[j] + _percent_4 * _targetPos_3[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3==1)&&(_percent_4==1)&&((_percent_5<=1)))
{
_percent_5 += (float)1 / _duration_5;
_percent_5 = _percent_5 > 1 ? 1 : _percent_5;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_5) * _targetPos_3[j] + _percent_5 * _targetPos_4[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
low_cmd.crc() = crc32_core((uint32_t *)&low_cmd, (sizeof(unitree_go::msg::dds_::LowCmd_)>>2)-1);
lowcmd_publisher->Write(low_cmd);
}
}
int main(int argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
std::cout << "WARNING: Make sure the robot is lying on the ground." << std::endl
<< "Press Enter to continue..." << std::endl;
std::cin.ignore();
ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
custom.Init();
custom.Start();
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,5 @@
add_executable(b2w_sport_client b2w_sport_client.cpp)
target_link_libraries(b2w_sport_client unitree_sdk2)
add_executable(b2w_stand_example b2w_stand_example.cpp)
target_link_libraries(b2w_stand_example unitree_sdk2)

View File

@ -0,0 +1,170 @@
#include <iostream>
#include <string>
#include <chrono>
#include <mutex>
#include <thread>
#include <pthread.h>
#include <stdexcept>
#include <unitree/robot/b2/sport/sport_client.hpp>
using namespace std;
struct TestOption
{
std::string name;
int id;
};
const vector<TestOption> option_list =
{{"damp", 0},
{"stand_up", 1},
{"stand_down", 2},
{"move forward", 3},
{"move lateral", 4},
{"move rotate", 5},
{"stop_move", 6},
{"switch_gait", 7},
{"switch_gait", 8},
{"recovery", 9},
};
int ConvertToInt(const std::string &str)
{
try
{
std::stoi(str);
return std::stoi(str);
}
catch (const std::invalid_argument &)
{
return -1;
}
catch (const std::out_of_range &)
{
return -1;
}
}
class UserInterface
{
public:
UserInterface(){};
~UserInterface(){};
void terminalHandle()
{
std::string input;
std::getline(std::cin, input);
if (input.compare("list") == 0)
{
for (TestOption option : option_list)
{
std::cout << option.name << ", id: " << option.id << std::endl;
}
}
for (TestOption option : option_list)
{
if (input.compare(option.name) == 0 || ConvertToInt(input) == option.id)
{
test_option_->id = option.id;
test_option_->name = option.name;
std::cout << "Test: " << test_option_->name << ", test_id: " << test_option_->id << std::endl;
}
}
};
TestOption *test_option_;
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
TestOption test_option;
test_option.id = 1;
unitree::robot::b2::SportClient sport_client;
sport_client.SetTimeout(25.0f);
sport_client.Init();
UserInterface user_interface;
user_interface.test_option_ = &test_option;
std::cout << "Input \"list \" to list all test option ..." << std::endl;
long res_count = 0;
while (1)
{
auto time_start_trick = std::chrono::high_resolution_clock::now();
static const constexpr auto dt = std::chrono::microseconds(20000); // 50Hz
user_interface.terminalHandle();
int res = 1;
if (test_option.id == 0)
{
res = sport_client.Damp();
}
else if (test_option.id == 1)
{
res = sport_client.StandUp();
}
else if (test_option.id == 2)
{
res = sport_client.StandDown();
}
else if (test_option.id == 3)
{
res = sport_client.Move(0.3, 0, 0);// the robot will move for 0.5 seconds before stopping.
// If the Move command is called in a loop, the robot will continue moving.
// If no Move request is received within 0.5 seconds, the robot will automatically stop.
}
else if (test_option.id == 4)
{
res = sport_client.Move(0, 0.3, 0);// the robot will move for 0.5 seconds before stopping.
// If the Move command is called in a loop, the robot will continue moving.
// If no Move request is received within 0.5 seconds, the robot will automatically stop.
}
else if (test_option.id == 5)
{
res = sport_client.Move(0, 0, 0.5);// the robot will move for 0.5 seconds before stopping.
// If the Move command is called in a loop, the robot will continue moving.
// If no Move request is received within 0.5 seconds, the robot will automatically stop.
}
else if (test_option.id == 6)
{
res = sport_client.StopMove();
}
else if (test_option.id == 7)
{
res = sport_client.SwitchGait(0);
}
else if (test_option.id == 8)
{
res = sport_client.SwitchGait(1);
}
else if (test_option.id == 9)
{
res = sport_client.RecoveryStand();
}
if (res < 0)
{
res_count += 1;
std::cout << "Request error for: " << option_list[test_option.id].name << ", code: " << res << ", count: " << res_count << std::endl;
}
else
{
res_count = 0;
std::cout << "Request successed: " << option_list[test_option.id].name << ", code: " << res << std::endl;
}
std::this_thread::sleep_until(time_start_trick + dt);
}
return 0;
}

View File

@ -0,0 +1,372 @@
#include <iostream>
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/LowState_.hpp>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/common/thread/thread.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
#include <unitree/robot/b2/sport/sport_client.hpp>
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree::robot::b2;
#define TOPIC_LOWCMD "rt/lowcmd"
#define TOPIC_LOWSTATE "rt/lowstate"
constexpr double PosStopF = (2.146E+9f);
constexpr double VelStopF = (16000.0f);
class Custom
{
public:
explicit Custom(){}
~Custom(){}
void Init();
void Start();
private:
void InitLowCmd();
void LowStateMessageHandler(const void* messages);
void LowCmdWrite();
int queryMotionStatus();
std::string queryServiceName(std::string form,std::string name);
private:
float Kp = 1000.0;
float Kd = 10.0;
double time_consume = 0;
int rate_count = 0;
int sin_count = 0;
int motiontime = 0;
float dt = 0.002; // 0.001~0.01
MotionSwitcherClient msc;
SportClient sc;
unitree_go::msg::dds_::LowCmd_ low_cmd{}; // default init
unitree_go::msg::dds_::LowState_ low_state{}; // default init
/*publisher*/
ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_> lowcmd_publisher;
/*subscriber*/
ChannelSubscriberPtr<unitree_go::msg::dds_::LowState_> lowstate_subscriber;
/*LowCmd write thread*/
ThreadPtr lowCmdWriteThreadPtr;
float _targetPos_1[12] = {0.0, 1.36, -2.65, 0.0, 1.36, -2.65,
-0.2, 1.36, -2.65, 0.2, 1.36, -2.65};
float _targetPos_2[12] = {0.0, 0.67, -1.3, 0.0, 0.67, -1.3,
0.0, 0.67, -1.3, 0.0, 0.67, -1.3};
float _targetPos_3[12] = {-0.65, 1.36, -2.65, 0.65, 1.36, -2.65,
-0.65, 1.36, -2.65, 0.65, 1.36, -2.65};
float _startPos[12];
float _duration_1 = 800;
float _duration_2 = 800;
float _duration_3 = 2000;
float _duration_4 = 1500;
float _percent_1 = 0;
float _percent_2 = 0;
float _percent_3 = 0;
float _percent_4 = 0;
bool firstRun = true;
bool done = false;
};
uint32_t crc32_core(uint32_t* ptr, uint32_t len)
{
unsigned int xbit = 0;
unsigned int data = 0;
unsigned int CRC32 = 0xFFFFFFFF;
const unsigned int dwPolynomial = 0x04c11db7;
for (unsigned int i = 0; i < len; i++)
{
xbit = 1 << 31;
data = ptr[i];
for (unsigned int bits = 0; bits < 32; bits++)
{
if (CRC32 & 0x80000000)
{
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
}
else
{
CRC32 <<= 1;
}
if (data & xbit)
CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
}
void Custom::Init()
{
InitLowCmd();
/*create publisher*/
lowcmd_publisher.reset(new ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(TOPIC_LOWCMD));
lowcmd_publisher->InitChannel();
/*create subscriber*/
lowstate_subscriber.reset(new ChannelSubscriber<unitree_go::msg::dds_::LowState_>(TOPIC_LOWSTATE));
lowstate_subscriber->InitChannel(std::bind(&Custom::LowStateMessageHandler, this, std::placeholders::_1), 1);
/*init MotionSwitcherClient*/
msc.SetTimeout(10.0f);
msc.Init();
/*Shut down motion control-related service*/
while(queryMotionStatus())
{
std::cout << "Try to deactivate the motion control-related service." << std::endl;
int32_t ret = msc.ReleaseMode();
if (ret == 0) {
std::cout << "ReleaseMode succeeded." << std::endl;
} else {
std::cout << "ReleaseMode failed. Error code: " << ret << std::endl;
}
sleep(5);
}
}
void Custom::InitLowCmd()
{
low_cmd.head()[0] = 0xFE;
low_cmd.head()[1] = 0xEF;
low_cmd.level_flag() = 0xFF;
low_cmd.gpio() = 0;
for(int i=0; i<20; i++)
{
low_cmd.motor_cmd()[i].mode() = (0x01); // motor switch to servo (PMSM) mode
low_cmd.motor_cmd()[i].q() = (PosStopF);
low_cmd.motor_cmd()[i].kp() = (0);
low_cmd.motor_cmd()[i].dq() = (VelStopF);
low_cmd.motor_cmd()[i].kd() = (0);
low_cmd.motor_cmd()[i].tau() = (0);
}
}
int Custom::queryMotionStatus()
{
std::string robotForm,motionName;
int motionStatus;
int32_t ret = msc.CheckMode(robotForm,motionName);
if (ret == 0) {
std::cout << "CheckMode succeeded." << std::endl;
} else {
std::cout << "CheckMode failed. Error code: " << ret << std::endl;
}
if(motionName.empty())
{
std::cout << "The motion control-related service is deactivated." << std::endl;
motionStatus = 0;
}
else
{
std::string serviceName = queryServiceName(robotForm,motionName);
std::cout << "Service: "<< serviceName<< " is activate" << std::endl;
motionStatus = 1;
}
return motionStatus;
}
std::string Custom::queryServiceName(std::string form,std::string name)
{
if(form == "0")
{
if(name == "normal" ) return "sport_mode";
if(name == "ai" ) return "ai_sport";
if(name == "advanced" ) return "advanced_sport";
}
else
{
if(name == "ai-w" ) return "wheeled_sport(go2W)";
if(name == "normal-w" ) return "wheeled_sport(b2W)";
}
return "";
}
void Custom::Start()
{
/*loop publishing thread*/
lowCmdWriteThreadPtr = CreateRecurrentThreadEx("writebasiccmd", UT_CPU_ID_NONE, 2000, &Custom::LowCmdWrite, this);
}
void Custom::LowStateMessageHandler(const void* message)
{
low_state = *(unitree_go::msg::dds_::LowState_*)message;
}
void Custom::LowCmdWrite()
{
if(_percent_4<1)
{
std::cout<<"Read sensor data example: "<<std::endl;
std::cout<<"Joint 0 pos: "<<low_state.motor_state()[0].q()<<std::endl;
std::cout<<"Imu accelerometer : "<<"x: "<<low_state.imu_state().accelerometer()[0]<<" y: "<<low_state.imu_state().accelerometer()[1]<<" z: "<<low_state.imu_state().accelerometer()[2]<<std::endl;
std::cout<<"Foot force "<<low_state.foot_force()[0]<<std::endl;
std::cout<<std::endl;
}
if((_percent_4 == 1) && ( done == false))
{
std::cout<<"The example is done! "<<std::endl;
std::cout<<std::endl;
done = true;
}
motiontime++;
if(motiontime>=500)
{
if(firstRun)
{
for(int i = 0; i < 12; i++)
{
_startPos[i] = low_state.motor_state()[i].q();
}
firstRun = false;
}
_percent_1 += (float)1 / _duration_1;
_percent_1 = _percent_1 > 1 ? 1 : _percent_1;
if (_percent_1 < 1)
{
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_1) * _startPos[j] + _percent_1 * _targetPos_1[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 < 1))
{
_percent_2 += (float)1 / _duration_2;
_percent_2 = _percent_2 > 1 ? 1 : _percent_2;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_2) * _targetPos_1[j] + _percent_2 * _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3<1))
{
_percent_3 += (float)1 / _duration_3;
_percent_3 = _percent_3 > 1 ? 1 : _percent_3;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
if(_percent_3<0.4)
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = 3;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
else if((_percent_3>=0.4)&&(_percent_3<0.8))
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = -3;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
else if(_percent_3>=0.8)
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3==1)&&((_percent_4<=1)))
{
_percent_4 += (float)1 / _duration_4;
_percent_4 = _percent_4 > 1 ? 1 : _percent_4;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_4) * _targetPos_2[j] + _percent_4 * _targetPos_3[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
low_cmd.crc() = crc32_core((uint32_t *)&low_cmd, (sizeof(unitree_go::msg::dds_::LowCmd_)>>2)-1);
lowcmd_publisher->Write(low_cmd);
}
}
int main(int argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
std::cout << "WARNING: Make sure the robot is lying on the ground." << std::endl
<< "Press Enter to continue..." << std::endl;
std::cin.ignore();
ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
custom.Init();
custom.Start();
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,53 @@
add_executable(g1_loco_client high_level/g1_loco_client_example.cpp)
target_link_libraries(g1_loco_client unitree_sdk2)
add_executable(g1_arm5_sdk_dds_example high_level/g1_arm5_sdk_dds_example.cpp)
target_link_libraries(g1_arm5_sdk_dds_example unitree_sdk2)
add_executable(g1_arm7_sdk_dds_example high_level/g1_arm7_sdk_dds_example.cpp)
target_link_libraries(g1_arm7_sdk_dds_example unitree_sdk2)
add_executable(g1_ankle_swing_example low_level/g1_ankle_swing_example.cpp)
target_link_libraries(g1_ankle_swing_example unitree_sdk2)
add_executable(g1_audio_client_example audio/g1_audio_client_example.cpp)
target_link_libraries(g1_audio_client_example unitree_sdk2)
add_executable(g1_dex3_example dex3/g1_dex3_example.cpp)
target_link_libraries(g1_dex3_example unitree_sdk2)
add_executable(g1_userctrl_dds_example high_level/g1_userctrl_dds_example.cpp)
target_link_libraries(g1_userctrl_dds_example unitree_sdk2)
find_package(Boost COMPONENTS program_options)
if(Boost_FOUND)
add_executable(g1_termination low_level/terminations.cpp)
target_link_libraries(g1_termination unitree_sdk2 Boost::program_options)
add_executable(g1_arm_action_example high_level/g1_arm_action_example.cpp)
target_link_libraries(g1_arm_action_example unitree_sdk2 Boost::program_options)
endif()
find_package(yaml-cpp QUIET)
if(yaml-cpp_FOUND)
if (${yaml-cpp_VERSION} VERSION_GREATER_EQUAL "0.6")
message(STATUS "Found yaml-cpp version ${yaml-cpp_VERSION}")
add_executable(g1_dual_arm_example low_level/g1_dual_arm_example.cpp)
target_link_libraries(g1_dual_arm_example PRIVATE unitree_sdk2 yaml-cpp)
target_compile_definitions(g1_dual_arm_example PUBLIC BLIB_DIR="${CMAKE_CURRENT_SOURCE_DIR}/low_level/behavior_lib/")
else()
message(STATUS "yaml-cpp version ${yaml-cpp_VERSION} is too old, skipping build of g1_dual_arm_example.")
endif()
endif()
add_executable(g1_agv_client_example g1d/g1_agv_client_example.cpp)
target_link_libraries(g1_agv_client_example unitree_sdk2)
add_executable(g1d_arm_example g1d/g1d_arm_example.cpp)
target_link_libraries(g1d_arm_example unitree_sdk2)
add_executable(g1d_height_control g1d/g1d_height_control.cpp)
target_link_libraries(g1d_height_control unitree_sdk2)
add_executable(g1_hand_sdk_example high_level/g1_hand_sdk_example.cpp)
target_link_libraries(g1_hand_sdk_example unitree_sdk2)

View File

@ -0,0 +1,175 @@
#include <fstream>
#include <iostream>
#include <thread>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/idl/ros2/String_.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/robot/g1/audio/g1_audio_client.hpp>
#include "wav.hpp"
#define AUDIO_FILE_PATH "../example/g1/audio/test.wav"
#define AUDIO_SUBSCRIBE_TOPIC "rt/audio_msg"
#define GROUP_IP "239.168.123.161"
#define PORT 5555
#define WAV_SECOND 5 // record seconds
#define WAV_LEN (16000 * 2 * WAV_SECOND)
#define WAV_LEN_ONCE (16000 * 2 * 160 / 1000)
#define CHUNK_SIZE 96000 // 3 seconds
int sock;
void asr_handler(const void *msg) {
std_msgs::msg::dds_::String_ *resMsg = (std_msgs::msg::dds_::String_ *)msg;
std::cout << "Topic:\"rt/audio_msg\" recv: " << resMsg->data() << std::endl;
}
std::string get_local_ip_for_multicast() {
struct ifaddrs *ifaddr, *ifa;
char host[NI_MAXHOST];
std::string result = "";
getifaddrs(&ifaddr);
for (ifa = ifaddr; ifa != nullptr; ifa = ifa->ifa_next) {
if (!ifa->ifa_addr || ifa->ifa_addr->sa_family != AF_INET) continue;
getnameinfo(ifa->ifa_addr, sizeof(struct sockaddr_in), host, NI_MAXHOST,
NULL, 0, NI_NUMERICHOST);
std::string ip(host);
if (ip.find("192.168.123.") == 0) {
result = ip;
break;
}
}
freeifaddrs(ifaddr);
return result;
}
void thread_mic(void) {
sock = socket(AF_INET, SOCK_DGRAM, 0);
sockaddr_in local_addr{};
local_addr.sin_family = AF_INET;
local_addr.sin_port = htons(PORT);
local_addr.sin_addr.s_addr = INADDR_ANY;
bind(sock, (sockaddr *)&local_addr, sizeof(local_addr));
ip_mreq mreq{};
inet_pton(AF_INET, GROUP_IP, &mreq.imr_multiaddr);
std::string local_ip = get_local_ip_for_multicast();
std::cout << "local ip: " << local_ip << std::endl;
mreq.imr_interface.s_addr = inet_addr(local_ip.c_str());
setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq));
int total_bytes = 0;
std::vector<int16_t> pcm_data;
pcm_data.reserve(WAV_LEN / 2);
std::cout << "start record!" << std::endl;
while (total_bytes < WAV_LEN) {
char buffer[WAV_LEN_ONCE];
ssize_t len = recvfrom(sock, buffer, sizeof(buffer), 0, nullptr, nullptr);
if (len > 0) {
size_t sample_count = len / 2;
const int16_t *samples = reinterpret_cast<const int16_t *>(buffer);
pcm_data.insert(pcm_data.end(), samples, samples + sample_count);
total_bytes += len;
}
}
WriteWave("record.wav", 16000, pcm_data.data(), pcm_data.size(), 1);
std::cout << "record finish! save to record.wav " << std::endl;
}
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: audio_client_example [NetWorkInterface(eth0)]"
<< std::endl;
exit(0);
}
int32_t ret;
/*
* Initilaize ChannelFactory
*/
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::g1::AudioClient client;
client.Init();
client.SetTimeout(10.0f);
/*ASR message Example*/
unitree::robot::ChannelSubscriber<std_msgs::msg::dds_::String_> subscriber(
AUDIO_SUBSCRIBE_TOPIC);
subscriber.InitChannel(asr_handler);
/*Volume Example*/
uint8_t volume;
ret = client.GetVolume(volume);
std::cout << "GetVolume API ret:" << ret
<< " volume = " << std::to_string(volume) << std::endl;
ret = client.SetVolume(100);
std::cout << "SetVolume to 100% , API ret:" << ret << std::endl;
/*TTS Example*/
ret = client.TtsMaker("你好。我是宇树科技的机器人。例程启动成功",
0); // Auto play
std::cout << "TtsMaker API ret:" << ret << std::endl;
unitree::common::Sleep(5);
ret = client.TtsMaker(
"Hello. I'm a robot from Unitree Robotics. The example has started "
"successfully. ",
1); // Engilsh TTS
std::cout << "TtsMaker API ret:" << ret << std::endl;
unitree::common::Sleep(8);
/*Audio Play Example*/
int32_t sample_rate = -1;
int8_t num_channels = 0;
bool filestate = false;
std::vector<uint8_t> pcm =
ReadWave(AUDIO_FILE_PATH, &sample_rate, &num_channels, &filestate);
std::cout << "wav file sample_rate = " << sample_rate
<< " num_channels = " << std::to_string(num_channels)
<< " filestate =" << filestate << "filesize = " << pcm.size()
<< std::endl;
if (filestate && sample_rate == 16000 && num_channels == 1) {
size_t total_size = pcm.size();
size_t offset = 0;
int chunk_index = 0;
std::string stream_id =
std::to_string(unitree::common::GetCurrentTimeMillisecond());
while (offset < total_size) {
size_t remaining = total_size - offset;
size_t current_chunk_size =
std::min(static_cast<size_t>(CHUNK_SIZE), remaining);
std::vector<uint8_t> chunk(pcm.begin() + offset,
pcm.begin() + offset + current_chunk_size);
client.PlayStream("example", stream_id, chunk);
unitree::common::Sleep(1);
std::cout << "Playing size: " << offset << std::endl;
offset += current_chunk_size;
}
ret = client.PlayStop(stream_id); // stop playback after transmission ends
} else {
std::cout << "audio file format error, please check!" << std::endl;
}
/*LED Control Example*/
client.LedControl(0, 255, 0);
unitree::common::Sleep(1);
client.LedControl(0, 0, 0);
unitree::common::Sleep(1);
client.LedControl(0, 0, 255);
std::cout << "AudioClient api test finish , asr start..." << std::endl;
std::thread mic_t(thread_mic);
while (1) {
sleep(1); // wait for asr message
}
mic_t.join();
return 0;
}

Binary file not shown.

View File

@ -0,0 +1,232 @@
#ifndef __UT_ROBOT_WAV_READER_HPP__
#define __UT_ROBOT_WAV_READER_HPP__
struct WaveHeader {
void SeekToDataChunk(std::istream &is) {
while (is && subchunk2_id != 0x61746164) {
is.seekg(subchunk2_size, std::istream::cur);
is.read(reinterpret_cast<char *>(&subchunk2_id), sizeof(int32_t));
is.read(reinterpret_cast<char *>(&subchunk2_size), sizeof(int32_t));
}
}
int32_t chunk_id;
int32_t chunk_size;
int32_t format;
int32_t subchunk1_id;
int32_t subchunk1_size;
int16_t audio_format;
int16_t num_channels;
int32_t sample_rate;
int32_t byte_rate;
int16_t block_align;
int16_t bits_per_sample;
int32_t subchunk2_id; // a tag of this chunk
int32_t subchunk2_size; // size of subchunk2
};
static_assert(sizeof(WaveHeader) == 44);
std::vector<uint8_t> ReadWaveImpl(std::istream &is, int32_t *sampling_rate,
int8_t *channelCount, bool *is_ok) {
WaveHeader header{};
is.read(reinterpret_cast<char *>(&header.chunk_id), sizeof(header.chunk_id));
// F F I R
if (header.chunk_id != 0x46464952) {
printf("Expected chunk_id RIFF. Given: 0x%08x\n", header.chunk_id);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.chunk_size),
sizeof(header.chunk_size));
is.read(reinterpret_cast<char *>(&header.format), sizeof(header.format));
// E V A W
if (header.format != 0x45564157) {
printf("Expected format WAVE. Given: 0x%08x\n", header.format);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.subchunk1_id),
sizeof(header.subchunk1_id));
is.read(reinterpret_cast<char *>(&header.subchunk1_size),
sizeof(header.subchunk1_size));
if (header.subchunk1_id == 0x4b4e554a) {
// skip junk padding
is.seekg(header.subchunk1_size, std::istream::cur);
is.read(reinterpret_cast<char *>(&header.subchunk1_id),
sizeof(header.subchunk1_id));
is.read(reinterpret_cast<char *>(&header.subchunk1_size),
sizeof(header.subchunk1_size));
}
if (header.subchunk1_id != 0x20746d66) {
printf("Expected subchunk1_id 0x20746d66. Given: 0x%08x\n",
header.subchunk1_id);
*is_ok = false;
return {};
}
if (header.subchunk1_size != 16 &&
header.subchunk1_size != 18) { // 16 for PCM
printf("Expected subchunk1_size 16. Given: %d\n", header.subchunk1_size);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.audio_format),
sizeof(header.audio_format));
if (header.audio_format != 1) { // 1 for PCM
printf("Expected audio_format 1. Given: %d\n", header.audio_format);
*is_ok = false;
return {};
}
is.read(reinterpret_cast<char *>(&header.num_channels),
sizeof(header.num_channels));
*channelCount = (int8_t)header.num_channels;
is.read(reinterpret_cast<char *>(&header.sample_rate),
sizeof(header.sample_rate));
is.read(reinterpret_cast<char *>(&header.byte_rate),
sizeof(header.byte_rate));
is.read(reinterpret_cast<char *>(&header.block_align),
sizeof(header.block_align));
is.read(reinterpret_cast<char *>(&header.bits_per_sample),
sizeof(header.bits_per_sample));
if (header.byte_rate !=
(header.sample_rate * header.num_channels * header.bits_per_sample / 8)) {
printf("Incorrect byte rate: %d. Expected: %d", header.byte_rate,
(header.sample_rate * header.num_channels * header.bits_per_sample /
8));
*is_ok = false;
return {};
}
if (header.block_align !=
(header.num_channels * header.bits_per_sample / 8)) {
printf("Incorrect block align: %d. Expected: %d\n", header.block_align,
(header.num_channels * header.bits_per_sample / 8));
*is_ok = false;
return {};
}
if (header.bits_per_sample != 16) { // we support only 16 bits per sample
printf("Expected bits_per_sample 16. Given: %d\n", header.bits_per_sample);
*is_ok = false;
return {};
}
if (header.subchunk1_size == 18) {
int16_t extra_size = -1;
is.read(reinterpret_cast<char *>(&extra_size), sizeof(int16_t));
if (extra_size != 0) {
printf(
"Extra size should be 0 for wave from NAudio. Current extra size "
"%d\n",
extra_size);
*is_ok = false;
return {};
}
}
is.read(reinterpret_cast<char *>(&header.subchunk2_id),
sizeof(header.subchunk2_id));
is.read(reinterpret_cast<char *>(&header.subchunk2_size),
sizeof(header.subchunk2_size));
header.SeekToDataChunk(is);
if (!is) {
*is_ok = false;
return {};
}
*sampling_rate = header.sample_rate;
// header.subchunk2_size contains the number of bytes in the data.
// As we assume each sample contains two bytes, so it is divided by 2 here
std::vector<int16_t> samples(header.subchunk2_size / 2);
is.read(reinterpret_cast<char *>(samples.data()), header.subchunk2_size);
if (!is) {
*is_ok = false;
return {};
}
std::vector<uint8_t> ans(samples.size() * 2);
for (int32_t i = 0; i != static_cast<int32_t>(samples.size()); ++i) {
ans[i * 2] = samples[i] & 0xFF;
ans[i * 2 + 1] = (samples[i] >> 8) & 0xFF;
}
*is_ok = true;
return ans;
}
std::vector<uint8_t> ReadWave(const std::string &filename,
int32_t *sampling_rate, int8_t *channelCount,
bool *is_ok) {
std::ifstream is(filename, std::ifstream::binary);
auto samples = ReadWaveImpl(is, sampling_rate, channelCount, is_ok);
return samples;
}
bool WriteWave(const std::string &filename, int32_t sampling_rate,
const int16_t *samples, int32_t n, uint8_t num_channels) {
WaveHeader header{};
header.chunk_id = 0x46464952; // FFIR
header.format = 0x45564157; // EVAW
header.subchunk1_id = 0x20746d66; // "fmt "
header.subchunk1_size = 16; // 16 for PCM
header.audio_format = 1; // PCM =1
int32_t bits_per_sample = 16; // int16_t
header.num_channels = num_channels;
header.sample_rate = sampling_rate;
header.byte_rate = sampling_rate * num_channels * bits_per_sample / 8;
header.block_align = num_channels * bits_per_sample / 8;
header.bits_per_sample = bits_per_sample;
header.subchunk2_id = 0x61746164; // atad
header.subchunk2_size = n * num_channels * bits_per_sample / 8;
header.chunk_size = 36 + header.subchunk2_size;
std::vector<int16_t> samples_int16(n * num_channels);
for (int32_t i = 0; i != n * num_channels; ++i) {
samples_int16[i] = samples[i];
}
std::ofstream os(filename, std::ios::binary);
if (!os) {
printf("Failed to create %s", filename.c_str());
return false;
}
os.write(reinterpret_cast<const char *>(&header), sizeof(header));
os.write(reinterpret_cast<const char *>(samples_int16.data()),
samples_int16.size() * sizeof(int16_t));
if (!os) {
printf("Write %s failed", filename.c_str());
return false;
}
return true;
}
#endif

View File

@ -0,0 +1,326 @@
#include <chrono>
#include <thread>
#include <unitree/idl/hg/HandState_.hpp> //replace your sdk path
#include <unitree/idl/hg/HandCmd_.hpp> //replace your sdk path
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <iostream>
#include <unistd.h>
#include <atomic>
#include <mutex>
#include <cmath>
#include <termios.h>
#include <unistd.h>
#include <eigen3/Eigen/Dense>
enum State {
INIT,
ROTATE,
GRIP,
STOP,
PRINT
};
// set URDF Limits
const float maxLimits_left[7]= { 1.05 , 1.05 , 1.75 , 0 , 0 , 0 , 0 }; // set max motor value
const float minLimits_left[7]= { -1.05 , -0.724 , 0 , -1.57 , -1.75 , -1.57 ,-1.75};
const float maxLimits_right[7]= { 1.05 , 0.742 , 0 , 1.57 , 1.75 , 1.57 , 1.75};
const float minLimits_right[7]= { -1.05 , -1.05 , -1.75, 0 , 0 , 0 ,0 };
// Initing the dds configuration
std::string dds_namespace = "rt/dex3/left";
std::string sub_namespace = "rt/dex3/left/state";
unitree::robot::ChannelPublisherPtr<unitree_hg::msg::dds_::HandCmd_> handcmd_publisher;
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::HandState_> handstate_subscriber;
unitree_hg::msg::dds_::HandCmd_ msg;
unitree_hg::msg::dds_::HandState_ state;
std::atomic<State> currentState(INIT);
std::mutex stateMutex;
#define MOTOR_MAX 7
#define SENSOR_MAX 9
uint8_t hand_id = 0;
typedef struct {
uint8_t id : 4;
uint8_t status : 3;
uint8_t timeout: 1;
} RIS_Mode_t;
// stateToString Method
const char* stateToString(State state) {
switch (state) {
case INIT: return "INIT";
case ROTATE: return "ROTATE";
case GRIP: return "GRIP";
case STOP: return "STOP";
case PRINT: return "PRINT";
default: return "UNKNOWN";
}
}
// Monitor user's input
char getNonBlockingInput() {
struct termios oldt, newt;
char ch;
int oldf;
tcgetattr(STDIN_FILENO, &oldt);
newt = oldt;
newt.c_lflag &= ~(ICANON | ECHO);
tcsetattr(STDIN_FILENO, TCSANOW, &newt);
oldf = fcntl(STDIN_FILENO, F_GETFL, 0);
fcntl(STDIN_FILENO, F_SETFL, oldf | O_NONBLOCK);
ch = getchar();
tcsetattr(STDIN_FILENO, TCSANOW, &oldt);
fcntl(STDIN_FILENO, F_SETFL, oldf);
return ch;
}
void userInputThread() {
while (true) {
char ch = getNonBlockingInput();
if (ch == 'q') {
std::cout << "Exiting..." << std::endl;
currentState = STOP;
break;
} else if (ch == 'r') {
currentState = ROTATE;
} else if (ch == 'g') {
currentState = GRIP;
} else if (ch == 'p') {
currentState = PRINT;
} else if (ch == 's') {
currentState = STOP;
}
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}
}
// this method can send kp and kd to motors
void rotateMotors(bool isLeftHand) {
static int _count = 1;
static int dir = 1;
const float* maxLimits = isLeftHand ? maxLimits_left : maxLimits_right;
const float* minLimits = isLeftHand ? minLimits_left : minLimits_right;
for (int i = 0; i < MOTOR_MAX; i++) {
RIS_Mode_t ris_mode;
ris_mode.id = i;
ris_mode.status = 0x01;
uint8_t mode = 0;
mode |= (ris_mode.id & 0x0F);
mode |= (ris_mode.status & 0x07) << 4;
mode |= (ris_mode.timeout & 0x01) << 7;
msg.motor_cmd()[i].mode(mode);
msg.motor_cmd()[i].tau(0);
msg.motor_cmd()[i].kp(0.5);
msg.motor_cmd()[i].kd(0.1);
float range = maxLimits[i] - minLimits[i];
float mid = (maxLimits[i] + minLimits[i]) / 2.0;
float amplitude = range / 2.0;
float q = mid + amplitude * sin(_count / 20000.0 * M_PI);
msg.motor_cmd()[i].q(q);
}
handcmd_publisher->Write(msg);
_count += dir;
if (_count >= 10000) {
dir = -1;
}
if (_count <= -10000) {
dir = 1;
}
usleep(100);
}
// this method can send static position to motors
void gripHand(bool isLeftHand) {
const float* maxLimits = isLeftHand ? maxLimits_left : maxLimits_right;
const float* minLimits = isLeftHand ? minLimits_left : minLimits_right;
for (int i = 0; i < MOTOR_MAX; i++) {
RIS_Mode_t ris_mode;
ris_mode.id = i;
ris_mode.status = 0x01;
uint8_t mode = 0;
mode |= (ris_mode.id & 0x0F);
mode |= (ris_mode.status & 0x07) << 4;
mode |= (ris_mode.timeout & 0x01) << 7;
msg.motor_cmd()[i].mode(mode);
msg.motor_cmd()[i].tau(0);
float mid = (maxLimits[i] + minLimits[i]) / 2.0;
msg.motor_cmd()[i].q(mid);
msg.motor_cmd()[i].dq(0);
msg.motor_cmd()[i].kp(1.5);
msg.motor_cmd()[i].kd(0.1);
}
handcmd_publisher->Write(msg);
usleep(1000000);
}
// this method can send dynamic position to motors
void stopMotors() {
for (int i = 0; i < MOTOR_MAX; i++) {
RIS_Mode_t ris_mode;
ris_mode.id = i;
ris_mode.status = 0x01;
ris_mode.timeout = 0x01;
uint8_t mode = 0;
mode |= (ris_mode.id & 0x0F);
mode |= (ris_mode.status & 0x07) << 4;
mode |= (ris_mode.timeout & 0x01) << 7;
msg.motor_cmd()[i].mode(mode);
msg.motor_cmd()[i].tau(0);
msg.motor_cmd()[i].dq(0);
msg.motor_cmd()[i].kp(0);
msg.motor_cmd()[i].kd(0);
msg.motor_cmd()[i].q(0);
}
handcmd_publisher->Write(msg);
usleep(1000000);
}
// this method can subscribe dds and show the position for now
void printState(bool isLeftHand){
Eigen::Matrix<float, 7, 1> q;
const float* maxLimits = isLeftHand ? maxLimits_left : maxLimits_right;
const float* minLimits = isLeftHand ? minLimits_left : minLimits_right;
for(int i = 0; i < 7; i++)
{
q(i) = state.motor_state()[i].q();
q(i) = (q(i) - minLimits[i] ) / (maxLimits[i] - minLimits[i]);
q(i) = std::clamp(q(i), 0.0f, 1.0f);
}
std::cout << "\033[2J\033[H";
std::cout << "-- Hand State --\n";
std::cout << "--- Current State: " << "Test" << " ---\n";
std::cout << "Commands:\n";
std::cout << " r - Rotate\n";
std::cout << " g - Grip\n";
std::cout << " t - Test\n";
std::cout << " q - Quit\n";
if(isLeftHand){
std::cout << " L: " << q.transpose() << std::endl;
}else std::cout << " R: " << q.transpose() << std::endl;
usleep(0.1 * 1e6);
}
void StateHandler(const void *message) {
state = *(unitree_hg::msg::dds_::HandState_ *)message;
}
int main(int argc, const char** argv)
{
std::cout << " --- Unitree Robotics --- \n";
std::cout << " Dex3 Hand Example \n\n";
std::string input;
std::cout << "Please input the hand id (L for left hand, R for right hand): ";
std::cin >> input;
if (input == "L") {
hand_id = 0;
dds_namespace = "rt/dex3/left";
sub_namespace = "rt/lf/dex3/left/state";
} else if (input == "R") {
hand_id = 1;
dds_namespace = "rt/dex3/right";
sub_namespace = "rt/lf/dex3/right/state";
} else {
std::cout << "Invalid hand id. Please input 'L' or 'R'." << std::endl;
return -1;
}
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
handcmd_publisher.reset(new unitree::robot::ChannelPublisher<unitree_hg::msg::dds_::HandCmd_>(dds_namespace + "/cmd"));
handstate_subscriber.reset(new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::HandState_>(sub_namespace));
handcmd_publisher->InitChannel();
handstate_subscriber->InitChannel(
std::bind(&StateHandler, std::placeholders::_1), 1);
state.motor_state().resize(MOTOR_MAX);
state.press_sensor_state().resize(SENSOR_MAX);
msg.motor_cmd().resize(MOTOR_MAX);
// handcmd_publisher->msg_.motor_cmd().resize(MOTOR_MAX);
std::thread inputThread(userInputThread);
State lastState = INIT;
while (true) {
State state;
{
std::lock_guard<std::mutex> lock(stateMutex);
state = currentState.load();
}
if (state != lastState) {
std::cout << "\n--- Current State: " << stateToString(state) << " ---\n";
std::cout << "Commands:\n";
std::cout << " r - Rotate\n";
std::cout << " g - Grip\n";
std::cout << " p - Print_state\n";
std::cout << " q - Quit\n";
std::cout << " s - Stop\n";
lastState = state;
}
switch (state) {
case INIT:
std::cout << "Initializing..." << std::endl;
currentState = ROTATE;
break;
case ROTATE:
rotateMotors(input == "L");
break;
case GRIP:
gripHand(input == "L");
break;
case STOP:
stopMotors();
break;
case PRINT:
printState(input == "L");
break;
default:
std::cout << "Invalid state!" << std::endl;
inputThread.join();
break;
}
}
return 0;
}

View File

@ -0,0 +1,53 @@
#include <unitree/robot/g1/agv/g1_agv_client.hpp>
#include <iostream>
#include <math.h>
#include <unistd.h>
extern "C" {
float sinf(float x);
}
int main()
{
/*
* Initilaize ChannelFactory
*/
unitree::robot::ChannelFactory::Instance()->Init(0);
unitree::robot::g1::AgvClient ac;
ac.SetTimeout(3.0f);
ac.Init();
//Test Api - Periodic motion
int cycle_count = 0;
const float cycle_period = 40.0f; // 40步完成一个周期
const float vx_amplitude = 0.3f;
const float vyaw_amplitude = 0.3f;
const float height_amplitude = 1.0f;
while (true)
{
// 使用正弦函数实现周期运动
float time_phase = (cycle_count % (int)cycle_period) / cycle_period * 2.0f * M_PI;
// 速度周期运动: vx和vyaw使用正弦波
float vx = vx_amplitude * sinf(time_phase);
float vyaw = vyaw_amplitude * sinf(time_phase);
int32_t ret = ac.Move(vx, 0.0f, vyaw);
std::cout << "Call Move vx:" << vx << " vyaw:" << vyaw << " ret:" << ret << std::endl;
usleep(50000); // 50ms
// 高度调节周期运动: 使用正弦波,周期与速度一致
float height = height_amplitude * sinf(time_phase);
int32_t ret2 = ac.HeightAdjust(height);
std::cout << "Call HeightAdjust height:" << height << " ret:" << ret2 << std::endl;
cycle_count++;
usleep(50000); // 50ms
}
return 0;
}

View File

@ -0,0 +1,292 @@
#include <cmath>
#include <memory>
#include <mutex>
#include <shared_mutex>
#include <thread>
#include <chrono>
#include "gamepad.hpp"
// DDS
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
// IDL
#include <unitree/idl/hg/IMUState_.hpp>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
static const std::string HG_CMD_TOPIC = "rt/lowcmd";
static const std::string HG_IMU_TORSO = "rt/secondary_imu";
static const std::string HG_STATE_TOPIC = "rt/lowstate";
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree_hg::msg::dds_;
template <typename T>
class DataBuffer {
public:
void SetData(const T &newData) {
std::unique_lock<std::shared_mutex> lock(mutex);
data = std::make_shared<T>(newData);
}
std::shared_ptr<const T> GetData() {
std::shared_lock<std::shared_mutex> lock(mutex);
return data ? data : nullptr;
}
void Clear() {
std::unique_lock<std::shared_mutex> lock(mutex);
data = nullptr;
}
private:
std::shared_ptr<T> data;
std::shared_mutex mutex;
};
const int G1D_NUM_MOTOR = 29;
// IMU状态结构体
struct ImuState {
std::array<float, 3> rpy = {};
std::array<float, 3> omega = {};
};
// 电机控制指令结构体
struct MotorCommand {
std::array<float, G1D_NUM_MOTOR> q_target = {};
std::array<float, G1D_NUM_MOTOR> dq_target = {};
std::array<float, G1D_NUM_MOTOR> kp = {};
std::array<float, G1D_NUM_MOTOR> kd = {};
std::array<float, G1D_NUM_MOTOR> tau_ff = {};
};
// 电机状态结构体
struct MotorState {
std::array<float, G1D_NUM_MOTOR> q = {};
std::array<float, G1D_NUM_MOTOR> dq = {};
};
// Stiffness for all G1D Joints
std::array<float, G1D_NUM_MOTOR> Kp{
0, 0, 0, 0, 0, 0, // empty
0, 0, 0, 0, 0, 0, // empty
60, 0, 40, // waist
40, 40, 40, 40, 40, 40, 40, // arms
40, 40, 40, 40, 40, 40, 40 // arms
};
// Damping for all G1D Joints
std::array<float, G1D_NUM_MOTOR> Kd{
0, 0, 0, 0, 0, 0, // empty
0, 0, 0, 0, 0, 0, // empty
1, 0, 1, // waist
1, 1, 1, 1, 1, 1, 1, // arms
1, 1, 1, 1, 1, 1, 1 // arms
};
uint8_t mode_machine_;
Gamepad gamepad_;
REMOTE_DATA_RX rx_;
DataBuffer<MotorState> motor_state_buffer_;
DataBuffer<MotorCommand> motor_command_buffer_;
DataBuffer<ImuState> imu_state_buffer_;
ThreadPtr command_writer_ptr_, control_thread_ptr_;
LowState_ g1d_low_state;
IMUState_ Torso_IMU;
bool A_PRESSED = false;
bool IMU_Get = false;
enum G1DJointIndex {
LeftHipPitch = 0, // NOTE INVALID for g1d
LeftHipRoll = 1, // NOTE INVALID for g1d
LeftHipYaw = 2, // NOTE INVALID for g1d
LeftKnee = 3, // NOTE INVALID for g1d
LeftAnklePitch = 4, // NOTE INVALID for g1d
LeftAnkleB = 4, // NOTE INVALID for g1d
LeftAnkleRoll = 5, // NOTE INVALID for g1d
LeftAnkleA = 5, // NOTE INVALID for g1d
RightHipPitch = 6, // NOTE INVALID for g1d
RightHipRoll = 7, // NOTE INVALID for g1d
RightHipYaw = 8, // NOTE INVALID for g1d
RightKnee = 9, // NOTE INVALID for g1d
RightAnklePitch = 10, // NOTE INVALID for g1d
RightAnkleB = 10, // NOTE INVALID for g1d
RightAnkleRoll = 11, // NOTE INVALID for g1d
RightAnkleA = 11, // NOTE INVALID for g1d
WaistYaw = 12,
WaistRoll = 13, // NOTE INVALID for g1d
WaistA = 13, // NOTE INVALID for g1d
WaistPitch = 14,
WaistB = 14, // NOTE INVALID for g1d
LeftShoulderPitch = 15,
LeftShoulderRoll = 16,
LeftShoulderYaw = 17,
LeftElbow = 18,
LeftWristRoll = 19,
LeftWristPitch = 20,
LeftWristYaw = 21,
RightShoulderPitch = 22,
RightShoulderRoll = 23,
RightShoulderYaw = 24,
RightElbow = 25,
RightWristRoll = 26,
RightWristPitch = 27,
RightWristYaw = 28
};
// CRC校验值计算
inline uint32_t Crc32Core(uint32_t *ptr, uint32_t len) {
uint32_t xbit = 0;
uint32_t data = 0;
uint32_t CRC32 = 0xFFFFFFFF;
const uint32_t dwPolynomial = 0x04c11db7;
for (uint32_t i = 0; i < len; i++) {
xbit = 1 << 31;
data = ptr[i];
for (uint32_t bits = 0; bits < 32; bits++) {
if (CRC32 & 0x80000000) {
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
} else
CRC32 <<= 1;
if (data & xbit) CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
};
// 躯干IMU消息回调函数
void imuTorsoHandler(const void *message) {
IMUState_ imu_torso = *(const IMUState_ *)message;
Torso_IMU = imu_torso;
}
// 底层状态消息回调函数
void LowStateHandler(const void *message) {
LowState_ low_state = *(const LowState_ *)message;
g1d_low_state = low_state;
if (low_state.crc() != Crc32Core((uint32_t *)&low_state, (sizeof(LowState_) >> 2) - 1)) {
std::cout << "[ERROR] CRC Error" << std::endl;
return;
}
// 获取关节电机数据
MotorState ms_tmp;
for (int i = 0; i < G1D_NUM_MOTOR; ++i) {
ms_tmp.q.at(i) = low_state.motor_state()[i].q();
ms_tmp.dq.at(i) = low_state.motor_state()[i].dq();
if (low_state.motor_state()[i].motorstate() && i <= RightAnkleRoll)
std::cout << "[ERROR] motor " << i << " with code " << low_state.motor_state()[i].motorstate() << "\n";
}
motor_state_buffer_.SetData(ms_tmp);
// 获取IMU数据
ImuState imu_tmp;
imu_tmp.omega = low_state.imu_state().gyroscope();
imu_tmp.rpy = low_state.imu_state().rpy();
imu_state_buffer_.SetData(imu_tmp);
IMU_Get = true;
// 更新遥控器状态
memcpy(rx_.buff, &low_state.wireless_remote()[0], 40);
gamepad_.update(rx_.RF_RX);
if(gamepad_.A.on_press) A_PRESSED = true;
// 更新机型编号
mode_machine_ = low_state.mode_machine();
}
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: g1d_arm_example network_interface" << std::endl;
exit(0);
}
std::string networkInterface = argv[1];
ChannelFactory::Instance()->Init(0, networkInterface);
// Publisher
ChannelPublisherPtr<LowCmd_> lowcmd_publisher(new ChannelPublisher<LowCmd_>(HG_CMD_TOPIC));
lowcmd_publisher->InitChannel();
// Subscriber
ChannelSubscriberPtr<LowState_> lowstate_subscriber(new ChannelSubscriber<LowState_>(HG_STATE_TOPIC));
lowstate_subscriber->InitChannel(LowStateHandler, 1);
ChannelSubscriberPtr<IMUState_> imu_subscriber(new ChannelSubscriber<IMUState_>(HG_IMU_TORSO));
imu_subscriber->InitChannel(imuTorsoHandler, 1);
// 等待接收到第一帧IMU数据打印躯干IMU状态信息
while(!IMU_Get){
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}
std::cout << "Torso IMU State: " << std::endl
<< "RPY = "
<< Torso_IMU.rpy()[0] << ", " << Torso_IMU.rpy()[1] << ", " << Torso_IMU.rpy()[2]
<< std::endl
<< "Gyro = "
<< Torso_IMU.gyroscope()[0] << ", " << Torso_IMU.gyroscope()[1] << ", " << Torso_IMU.gyroscope()[2]
<< std::endl;
// 等待遥控器A键按下
std::cout << "Press button A on the remote control to continue!" << std::endl;
while(true){
std::this_thread::sleep_for(std::chrono::milliseconds(10));
if(A_PRESSED){
A_PRESSED = false;
break;
}
}
std::cout << "A Pressed!" << std::endl;
// 手臂摆动
LowCmd_ dds_low_command;
dds_low_command.mode_pr() = static_cast<uint8_t>(0); //构造底层控制指令
dds_low_command.mode_machine() = mode_machine_;
for (size_t i = 0; i < G1D_NUM_MOTOR; i++) {
dds_low_command.motor_cmd().at(i).mode() = 1; // 1:Enable, 0:Disable
dds_low_command.motor_cmd().at(i).tau() = 0;
dds_low_command.motor_cmd().at(i).q() = motor_state_buffer_.GetData() -> q.at(i);
dds_low_command.motor_cmd().at(i).dq() = 0;
dds_low_command.motor_cmd().at(i).kp() = Kp.at(i);
dds_low_command.motor_cmd().at(i).kd() = Kd.at(i);
}
double control_dt = 0.002;
double max_P = M_PI * 30.0 / 180.0;
double t = 0.0;
std::cout << "Press button A on the remote control to exit the program!" << std::endl;
while(true){
double L_Shoulder_des = max_P * std::sin(2.0 * M_PI * t);
double R_Shoulder_des = -max_P * std::sin(2.0 * M_PI * t);
dds_low_command.motor_cmd().at(LeftShoulderPitch).q() = L_Shoulder_des;
dds_low_command.motor_cmd().at(RightShoulderPitch).q() = R_Shoulder_des;
dds_low_command.crc() = Crc32Core((uint32_t *)&dds_low_command, (sizeof(dds_low_command) >> 2) - 1);
lowcmd_publisher -> Write(dds_low_command); //发布底层控制指令
t += control_dt;
// 按下遥控器A键或键盘Ctrl+C退出程序
if(A_PRESSED){
A_PRESSED = false;
break;
}
std::this_thread::sleep_for(std::chrono::milliseconds(5));
}
return 0;
}

View File

@ -0,0 +1,184 @@
#include <algorithm>
#include <atomic>
#include <cerrno>
#include <chrono>
#include <cmath>
#include <csignal>
#include <cstdint>
#include <cstdlib>
#include <iomanip>
#include <iostream>
#include <string>
#include <thread>
#include <unitree/idl/ros2/Point32_.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/robot/g1/agv/g1_agv_client.hpp>
static const std::string G1D_HISPEED_STATE_TOPIC = "rt/hispeed_state";
using namespace unitree::robot;
using namespace geometry_msgs::msg::dds_;
volatile std::sig_atomic_t running = 1;
std::atomic<bool> height_received{false};
std::atomic<float> current_height{0.0F};
std::atomic<int64_t> last_height_time_ms{0};
int64_t NowMs() {
using namespace std::chrono;
return duration_cast<milliseconds>(steady_clock::now().time_since_epoch()).count();
}
//Process Ctrl+C interrupt signal.
void SignalHandler(int) {
running = 0;
}
void HispeedStateHandler(const void *message) {
const Point32_ *hispeed_state = static_cast<const Point32_ *>(message);
current_height.store(hispeed_state->y(), std::memory_order_relaxed);
last_height_time_ms.store(NowMs(), std::memory_order_release);
height_received.store(true, std::memory_order_release);
}
bool WaitForHeightData() {
while (running != 0 && !height_received.load(std::memory_order_acquire)) {
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}
return running != 0;
}
bool HeightDataTimeout() {
const int64_t last_time = last_height_time_ms.load(std::memory_order_acquire);
return last_time <= 0 || NowMs() - last_time > 500;
}
bool ParseFloat(const char *text, float *value) {
char *end = nullptr;
errno = 0;
const float parsed = std::strtof(text, &end);
if (text == end || *end != '\0' || errno == ERANGE || !std::isfinite(parsed)) {
return false;
}
*value = parsed;
return true;
}
void StopHeightAdjust(g1::AgvClient &agv_client) {
const int32_t ret = agv_client.HeightAdjust(0.0F);
if (ret != 0) {
std::cout << std::endl << "[WARN] HeightAdjust stop command failed, ret: " << ret << std::endl;
}
}
//Use PD controller to control the robot's height.
void height_control(g1::AgvClient &agv_client, float z) {
constexpr float kP = 20.0F;
constexpr float kD = 0.3F;
constexpr float kMaxVz = 0.8F;
constexpr float kArriveTolerance = 0.001F;
constexpr int kArriveStableCycles = 20;
constexpr auto kControlPeriod = std::chrono::milliseconds(50);
if (!WaitForHeightData()) {
StopHeightAdjust(agv_client);
return;
}
float previous_error = z - current_height.load(std::memory_order_relaxed);
int arrive_count = 0;
auto previous_time = std::chrono::steady_clock::now();
while (running != 0) {
if (HeightDataTimeout()) {
StopHeightAdjust(agv_client);
std::cout << std::endl << "[ERROR] Height data timeout." << std::endl;
return;
}
const auto now = std::chrono::steady_clock::now();
float dt = std::chrono::duration<float>(now - previous_time).count();
if (dt <= 0.0F) {
dt = std::chrono::duration<float>(kControlPeriod).count();
}
previous_time = now;
const float height = current_height.load(std::memory_order_relaxed);
const float error = z - height;
const float d_error = (error - previous_error) / dt;
previous_error = error;
float vz = kP * error + kD * d_error;
vz = std::clamp(vz, -kMaxVz, kMaxVz);
if (std::fabs(error) <= kArriveTolerance) {
vz = 0.0F;
++arrive_count;
} else {
arrive_count = 0;
}
const int32_t ret = agv_client.HeightAdjust(vz);
std::cout << "\rG1D column height: " << std::fixed << std::setprecision(4)
<< height << " m"
<< " | target: " << z << " m"
<< " | error: " << error << " m"
<< " | vz: " << vz << " " << std::flush;
if (ret != 0) {
StopHeightAdjust(agv_client);
std::cout << std::endl << "[ERROR] HeightAdjust failed, ret: " << ret << std::endl;
return;
}
if (arrive_count >= kArriveStableCycles) {
StopHeightAdjust(agv_client);
std::cout << std::endl
<< "Target height reached: " << std::fixed << std::setprecision(4)
<< z << " m" << std::endl;
return;
}
std::this_thread::sleep_for(kControlPeriod);
}
StopHeightAdjust(agv_client);
}
int main(int argc, char const *argv[]) {
if (argc < 3) {
std::cout << "Usage: g1d_height_control network_interface target_height_m" << std::endl;
return 0;
}
std::signal(SIGINT, SignalHandler);
const std::string network_interface = argv[1];
float target_height = 0.0F;
if (!ParseFloat(argv[2], &target_height)) {
std::cout << "Invalid target_height_m: " << argv[2] << std::endl;
return 0;
}
ChannelFactory::Instance()->Init(0, network_interface);
g1::AgvClient agv_client;
agv_client.SetTimeout(3.0F);
agv_client.Init();
ChannelSubscriberPtr<Point32_> hispeed_state_subscriber(
new ChannelSubscriber<Point32_>(G1D_HISPEED_STATE_TOPIC));
hispeed_state_subscriber->InitChannel(HispeedStateHandler, 1);
std::cout << "Subscribe topic: " << G1D_HISPEED_STATE_TOPIC << std::endl;
std::cout << "Waiting for height data..." << std::endl;
height_control(agv_client, target_height);
std::cout << std::endl << "Exit g1d_height_control." << std::endl;
return 0;
}

View File

@ -0,0 +1,128 @@
#pragma once
#include <cmath>
namespace unitree::common
{
// bytecode mapping for raw joystick data
// 16b
typedef union
{
struct
{
uint8_t R1 : 1;
uint8_t L1 : 1;
uint8_t start : 1;
uint8_t select : 1;
uint8_t R2 : 1;
uint8_t L2 : 1;
uint8_t F1 : 1;
uint8_t F2 : 1;
uint8_t A : 1;
uint8_t B : 1;
uint8_t X : 1;
uint8_t Y : 1;
uint8_t up : 1;
uint8_t right : 1;
uint8_t down : 1;
uint8_t left : 1;
} components;
uint16_t value;
} xKeySwitchUnion;
// 40 Byte (now used 24B)
typedef struct
{
uint8_t head[2];
xKeySwitchUnion btn;
float lx;
float rx;
float ry;
float L2;
float ly;
uint8_t idle[16];
} xRockerBtnDataStruct;
typedef union
{
xRockerBtnDataStruct RF_RX;
uint8_t buff[40];
} REMOTE_DATA_RX;
class Button
{
public:
Button() {}
void update(bool state)
{
on_press = state ? state != pressed : false;
on_release = state ? false : state != pressed;
pressed = state;
}
bool pressed = false;
bool on_press = false;
bool on_release = false;
};
class Gamepad
{
public:
Gamepad() {}
void update(xRockerBtnDataStruct &key_data)
{
lx = lx * (1 - smooth) + (std::fabs(key_data.lx) < dead_zone ? 0.0 : key_data.lx) * smooth;
rx = rx * (1 - smooth) + (std::fabs(key_data.rx) < dead_zone ? 0.0 : key_data.rx) * smooth;
ry = ry * (1 - smooth) + (std::fabs(key_data.ry) < dead_zone ? 0.0 : key_data.ry) * smooth;
l2 = l2 * (1 - smooth) + (std::fabs(key_data.L2) < dead_zone ? 0.0 : key_data.L2) * smooth;
ly = ly * (1 - smooth) + (std::fabs(key_data.ly) < dead_zone ? 0.0 : key_data.ly) * smooth;
R1.update(key_data.btn.components.R1);
L1.update(key_data.btn.components.L1);
start.update(key_data.btn.components.start);
select.update(key_data.btn.components.select);
R2.update(key_data.btn.components.R2);
L2.update(key_data.btn.components.L2);
F1.update(key_data.btn.components.F1);
F2.update(key_data.btn.components.F2);
A.update(key_data.btn.components.A);
B.update(key_data.btn.components.B);
X.update(key_data.btn.components.X);
Y.update(key_data.btn.components.Y);
up.update(key_data.btn.components.up);
right.update(key_data.btn.components.right);
down.update(key_data.btn.components.down);
left.update(key_data.btn.components.left);
}
float lx = 0.;
float rx = 0.;
float ry = 0.;
float l2 = 0.;
float ly = 0.;
float smooth = 0.03;
float dead_zone = 0.01;
Button R1;
Button L1;
Button start;
Button select;
Button R2;
Button L2;
Button F1;
Button F2;
Button A;
Button B;
Button X;
Button Y;
Button up;
Button right;
Button down;
Button left;
};
} // namespace unitree::common

View File

@ -0,0 +1,256 @@
#include <array>
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
static const std::string kTopicArmSDK = "rt/arm_sdk";
static const std::string kTopicState = "rt/lowstate";
constexpr float kPi = 3.141592654;
constexpr float kPi_2 = 1.57079632;
enum JointIndex {
// Left leg
kLeftHipPitch = 0,
kLeftHipRoll = 1,
kLeftHipYaw = 2,
kLeftKnee = 3,
kLeftAnkle = 4,
kLeftAnkleRoll = 5,
// Right leg
kRightHipPitch = 6,
kRightHipRoll = 7,
kRightHipYaw = 8,
kRightKnee = 9,
kRightAnkle = 10,
kRightAnkleRoll = 11,
kWaistYaw = 12,
kWaistRoll = 13,
kWaistPitch = 14,
// Left arm
kLeftShoulderPitch = 15,
kLeftShoulderRoll = 16,
kLeftShoulderYaw = 17,
kLeftElbowPitch = 18,
kLeftElbowRoll = 19,
// Right arm
kRightShoulderPitch = 22,
kRightShoulderRoll = 23,
kRightShoulderYaw = 24,
kRightElbowPitch = 25,
kRightElbowRoll = 26,
kNotUsedJoint = 29,
kNotUsedJoint1 = 30,
kNotUsedJoint2 = 31,
kNotUsedJoint3 = 32,
kNotUsedJoint4 = 33,
kNotUsedJoint5 = 34
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_>
arm_sdk_publisher;
unitree_hg::msg::dds_::LowCmd_ msg;
arm_sdk_publisher.reset(
new unitree::robot::ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(
kTopicArmSDK));
arm_sdk_publisher->InitChannel();
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_>
low_state_subscriber;
// create subscriber
unitree_hg::msg::dds_::LowState_ state_msg;
low_state_subscriber.reset(
new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
kTopicState));
low_state_subscriber->InitChannel([&](const void *msg) {
auto s = ( const unitree_hg::msg::dds_::LowState_* )msg;
memcpy( &state_msg, s, sizeof( unitree_hg::msg::dds_::LowState_ ) );
}, 1);
std::array<JointIndex, 13> arm_joints = {
JointIndex::kLeftShoulderPitch, JointIndex::kLeftShoulderRoll,
JointIndex::kLeftShoulderYaw, JointIndex::kLeftElbowPitch,
JointIndex::kLeftElbowRoll,
JointIndex::kRightShoulderPitch, JointIndex::kRightShoulderRoll,
JointIndex::kRightShoulderYaw, JointIndex::kRightElbowPitch,
JointIndex::kRightElbowRoll,
JointIndex::kWaistYaw,
JointIndex::kWaistRoll,
JointIndex::kWaistPitch};
float weight = 0.f;
float weight_rate = 0.2f;
float kp = 60.f;
float kd = 1.5f;
float dq = 0.f;
float tau_ff = 0.f;
float control_dt = 0.02f;
float max_joint_velocity = 0.5f;
float delta_weight = weight_rate * control_dt;
float max_joint_delta = max_joint_velocity * control_dt;
auto sleep_time =
std::chrono::milliseconds(static_cast<int>(control_dt / 0.001f));
std::array<float, 13> init_pos{0, 0, 0, 0, 0,
0, 0, 0, 0, 0,
0, 0, 0};
std::array<float, 13> target_pos = {0.f, kPi_2, 0.f, kPi_2, 0.f,
0.f, -kPi_2, 0.f, kPi_2, 0.f,
0.f, 0.f, 0.f};
// wait for init
std::cout << "Press ENTER to init arms ...";
std::cin.get();
// get current joint position
std::array<float, 13> current_jpos{};
std::cout<<"Current joint position: ";
for (int i = 0; i < arm_joints.size(); ++i) {
current_jpos.at(i) = state_msg.motor_state().at(arm_joints.at(i)).q();
std::cout << current_jpos.at(i) << " ";
}
std::cout << std::endl;
// set init pos
std::cout << "Initailizing arms ...";
float init_time = 2.0f;
int init_time_steps = static_cast<int>(init_time / control_dt);
for (int i = 0; i < init_time_steps; ++i) {
// set weight
weight = 1.0;
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
float phase = 1.0 * i / init_time_steps;
std::cout << "Phase: " << phase << std::endl;
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(init_pos.at(j) * phase + current_jpos.at(j) * (1 - phase));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
// wait for control
std::cout << "Press ENTER to start arm ctrl ..." << std::endl;
std::cin.get();
// start control
std::cout << "Start arm ctrl!" << std::endl;
float period = 5.f;
int num_time_steps = static_cast<int>(period / control_dt);
std::array<float, 13> current_jpos_des{};
// lift arms up
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(target_pos.at(j) - current_jpos_des.at(j),
-max_joint_delta, max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// put arms down
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(init_pos.at(j) - current_jpos_des.at(j), -max_joint_delta,
max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// stop control
std::cout << "Stoping arm ctrl ...";
float stop_time = 2.0f;
int stop_time_steps = static_cast<int>(stop_time / control_dt);
for (int i = 0; i < stop_time_steps; ++i) {
// increase weight
weight -= delta_weight;
weight = std::clamp(weight, 0.f, 1.f);
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(0);
// send dds msg
arm_sdk_publisher->Write(msg);
std::cout << "Done!" << std::endl;
return 0;
}

View File

@ -0,0 +1,262 @@
#include <array>
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
static const std::string kTopicArmSDK = "rt/arm_sdk";
static const std::string kTopicState = "rt/lowstate";
constexpr float kPi = 3.141592654;
constexpr float kPi_2 = 1.57079632;
enum JointIndex {
// Left leg
kLeftHipPitch,
kLeftHipRoll,
kLeftHipYaw,
kLeftKnee,
kLeftAnkle,
kLeftAnkleRoll,
// Right leg
kRightHipPitch,
kRightHipRoll,
kRightHipYaw,
kRightKnee,
kRightAnkle,
kRightAnkleRoll,
kWaistYaw,
kWaistRoll,
kWaistPitch,
// Left arm
kLeftShoulderPitch,
kLeftShoulderRoll,
kLeftShoulderYaw,
kLeftElbow,
kLeftWristRoll,
kLeftWristPitch,
kLeftWristYaw,
// Right arm
kRightShoulderPitch,
kRightShoulderRoll,
kRightShoulderYaw,
kRightElbow,
kRightWristRoll,
kRightWristPitch,
kRightWristYaw,
kNotUsedJoint,
kNotUsedJoint1,
kNotUsedJoint2,
kNotUsedJoint3,
kNotUsedJoint4,
kNotUsedJoint5
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_>
arm_sdk_publisher;
unitree_hg::msg::dds_::LowCmd_ msg;
arm_sdk_publisher.reset(
new unitree::robot::ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(
kTopicArmSDK));
arm_sdk_publisher->InitChannel();
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_>
low_state_subscriber;
// create subscriber
unitree_hg::msg::dds_::LowState_ state_msg;
low_state_subscriber.reset(
new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
kTopicState));
low_state_subscriber->InitChannel([&](const void *msg) {
auto s = ( const unitree_hg::msg::dds_::LowState_* )msg;
memcpy( &state_msg, s, sizeof( unitree_hg::msg::dds_::LowState_ ) );
}, 1);
std::array<JointIndex, 17> arm_joints = {
JointIndex::kLeftShoulderPitch, JointIndex::kLeftShoulderRoll,
JointIndex::kLeftShoulderYaw, JointIndex::kLeftElbow,
JointIndex::kLeftWristRoll, JointIndex::kLeftWristPitch,
JointIndex::kLeftWristYaw,
JointIndex::kRightShoulderPitch, JointIndex::kRightShoulderRoll,
JointIndex::kRightShoulderYaw, JointIndex::kRightElbow,
JointIndex::kRightWristRoll, JointIndex::kRightWristPitch,
JointIndex::kRightWristYaw,
JointIndex::kWaistYaw,
JointIndex::kWaistRoll,
JointIndex::kWaistPitch};
float weight = 0.f;
float weight_rate = 0.2f;
float kp = 60.f;
float kd = 1.5f;
float dq = 0.f;
float tau_ff = 0.f;
float control_dt = 0.02f;
float max_joint_velocity = 0.5f;
float delta_weight = weight_rate * control_dt;
float max_joint_delta = max_joint_velocity * control_dt;
auto sleep_time =
std::chrono::milliseconds(static_cast<int>(control_dt / 0.001f));
std::array<float, 17> init_pos{0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0,
0, 0, 0};
std::array<float, 17> target_pos = {0.f, kPi_2, 0.f, kPi_2, 0.f, 0.f, 0.f,
0.f, -kPi_2, 0.f, kPi_2, 0.f, 0.f, 0.f,
0, 0, 0};
// wait for init
std::cout << "Press ENTER to init arms ...";
std::cin.get();
// get current joint position
std::array<float, 17> current_jpos{};
std::cout<<"Current joint position: ";
for (int i = 0; i < arm_joints.size(); ++i) {
current_jpos.at(i) = state_msg.motor_state().at(arm_joints.at(i)).q();
std::cout << current_jpos.at(i) << " ";
}
std::cout << std::endl;
// set init pos
std::cout << "Initailizing arms ...";
float init_time = 2.0f;
int init_time_steps = static_cast<int>(init_time / control_dt);
for (int i = 0; i < init_time_steps; ++i) {
// increase weight
weight = 1.0;
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
float phase = 1.0 * i / init_time_steps;
std::cout << "Phase: " << phase << std::endl;
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(init_pos.at(j) * phase + current_jpos.at(j) * (1 - phase));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
// wait for control
std::cout << "Press ENTER to start arm ctrl ..." << std::endl;
std::cin.get();
// start control
std::cout << "Start arm ctrl!" << std::endl;
float period = 5.f;
int num_time_steps = static_cast<int>(period / control_dt);
std::array<float, 17> current_jpos_des{};
// lift arms up
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(target_pos.at(j) - current_jpos_des.at(j),
-max_joint_delta, max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// put arms down
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(init_pos.at(j) - current_jpos_des.at(j), -max_joint_delta,
max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// stop control
std::cout << "Stoping arm ctrl ...";
float stop_time = 2.0f;
int stop_time_steps = static_cast<int>(stop_time / control_dt);
for (int i = 0; i < stop_time_steps; ++i) {
// increase weight
weight -= delta_weight;
weight = std::clamp(weight, 0.f, 1.f);
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(0);
// send dds msg
arm_sdk_publisher->Write(msg);
std::cout << "Done!" << std::endl;
return 0;
}

View File

@ -0,0 +1,85 @@
/**
* @file g1_arm_action_example.cpp
* @brief This example demonstrates how to use the G1 Arm Action Client to execute predefined arm actions.
*/
#include "unitree/robot/g1/arm/g1_arm_action_error.hpp"
#include "unitree/robot/g1/arm/g1_arm_action_client.hpp"
#include <boost/program_options.hpp>
namespace po = boost::program_options;
using namespace unitree::robot;
using namespace unitree::robot::g1;
int main(int argc, const char** argv)
{
std::cout << " --- Unitree Robotics --- \n";
std::cout << " G1 Arm Action Example \n\n";
// Parse command line arguments
po::options_description desc("Unitree G1 Arm Action Example.");
desc.add_options()
("help,h", "show help message")
("network,n", po::value<std::string>()->default_value(""), "dds network interface")
("list,l", "list all supported actions")
("id,i", po::value<int>(), "action id to execute, 0 to list all supported actions")
("name", po::value<std::string>(), "custom action name to execute")
("stop", "stop the current custom action")
;
po::variables_map vm;
po::store(po::parse_command_line(argc, argv, desc), vm);
po::notify(vm);
if(argc < 2 || vm.count("help")) {
std::cout << desc << std::endl;
return 0;
}
// DDS Init
ChannelFactory::Instance()->Init(0, vm["network"].as<std::string>());
auto client = std::make_shared<G1ArmActionClient>();
client->Init();
// Attention: unitree actions are all less than 10s,
// but the custom actions may be longer.
client->SetTimeout(10.f);
if(vm.count("list") || (vm.count("id") && vm["id"].as<int>() == 0)){
std::string action_list_data;
int32_t ret = client->GetActionList(action_list_data);
if (ret != 0) {
std::cerr << "Failed to get action list, error code: " << ret << "\n";
}
std::cout << "Available actions:\n" << action_list_data << std::endl;
} else if (vm.count("id")) {
int32_t ret = client->ExecuteAction(vm["id"].as<int>());
if(ret != 0) {
switch (ret)
{
case UT_ROBOT_ARM_ACTION_ERR_ARMSDK:
std::cout << UT_ROBOT_ARM_ACTION_ERR_ARMSDK_DESC << std::endl;
break;
case UT_ROBOT_ARM_ACTION_ERR_HOLDING:
std::cout << UT_ROBOT_ARM_ACTION_ERR_HOLDING_DESC << std::endl;
break;
case UT_ROBOT_ARM_ACTION_ERR_INVALID_ACTION_ID:
std::cout << UT_ROBOT_ARM_ACTION_ERR_INVALID_ACTION_ID_DESC << std::endl;
break;
case UT_ROBOT_ARM_ACTION_ERR_INVALID_FSM_ID:
std::cout << "The actions are only supported in fsm id {500, 501, 801}" << std::endl;
std::cout << "You can subscribe the topic rt/sportmodestate to check the fsm id." << std::endl;
std::cout << "And in the state 801, the actions are only supported in the fsm mode {0, 3}." << std::endl;
std::cout << "If an error is still returned at this point, ignore this action.";
break;
default:
std::cerr << "Execute action failed, error code: " << ret << std::endl;
break;
}
}
} else if (vm.count("name")) {
int32_t ret = client->ExecuteAction(vm["name"].as<std::string>());
if(ret != 0) std::cout << "Execute custom action failed, error code: " << ret << std::endl;
} else if (vm.count("stop")) {
int32_t ret = client->StopCustomAction();
}
return 0;
};

View File

@ -0,0 +1,76 @@
// G1 Hand SDK Control Example
//
// Motor_real = weight * Hand_SDK + (1 - weight) * G1_Cmd
//
// Demonstrates how a user process injects commands for the 4 hand motors
// into ai_sport via the DDS topic `rt/hand_sdk`. This example takes full
// control of the hand (weight = 1.0) and toggles tau between +0.3 and
// -0.3 every second to alternate between "close" and "open".
//
//
// Run:
// ./hand_sdk_example # use default network interface
// ./hand_sdk_example eth0 # specify a network interface
#include <unitree/robot/channel/channel_factory.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/idl/go2/MotorCmds_.hpp>
#include <algorithm>
#include <chrono>
#include <thread>
class HandSdk {
public:
static constexpr int kMotorNum = 4;
explicit HandSdk(const std::string& topic = "rt/hand_sdk")
: publisher_(std::make_shared<unitree::robot::ChannelPublisher<
unitree_go::msg::dds_::MotorCmds_>>(topic)) {
publisher_->InitChannel();
msg_.cmds().resize(kMotorNum);
}
// weight is in [0, 1] and is encoded as `weight * 100` (uint8) in cmds[0].mode.
float weight() const {
return std::clamp(msg_.cmds()[0].mode() / 100.f, 0.f, 1.f);
}
void set_weight(float w) {
msg_.cmds()[0].mode(
static_cast<uint8_t>(std::clamp(w, 0.f, 1.f) * 100.f));
}
// Positive tau closes the hand, negative tau opens it.
void set_tau(float tau) {
for (int i = 0; i < kMotorNum; ++i) {
msg_.cmds()[i].tau(tau);
}
}
void write() { publisher_->Write(msg_); }
private:
std::shared_ptr<unitree::robot::ChannelPublisher<
unitree_go::msg::dds_::MotorCmds_>> publisher_;
unitree_go::msg::dds_::MotorCmds_ msg_;
};
int main(int argc, char** argv) {
if (argc > 1) {
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
} else {
unitree::robot::ChannelFactory::Instance()->Init(0);
}
HandSdk hand_sdk;
hand_sdk.set_weight(1.0f);
float tau = 0.3f;
while (true) {
tau = -tau;
hand_sdk.set_tau(tau);
hand_sdk.write();
std::this_thread::sleep_for(std::chrono::seconds(1));
}
return 0;
}

View File

@ -0,0 +1,267 @@
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/robot/g1/loco/g1_loco_api.hpp>
#include <unitree/robot/g1/loco/g1_loco_client.hpp>
std::vector<float> stringToFloatVector(const std::string &str) {
std::vector<float> result;
std::stringstream ss(str);
float num;
while (ss >> num) {
result.push_back(num);
// ignore any trailing whitespace
ss.ignore();
}
return result;
}
int main(int argc, char const *argv[]) {
std::map<std::string, std::string> args = {{"network_interface", "lo"}};
std::map<std::string, std::string> values;
for (int i = 1; i < argc; ++i) {
std::string arg = argv[i];
if (arg.substr(0, 2) == "--") {
size_t pos = arg.find("=");
std::string key, value;
if (pos != std::string::npos) {
key = arg.substr(2, pos - 2);
value = arg.substr(pos + 1);
if (value.front() == '"' && value.back() == '"') {
value = value.substr(1, value.length() - 2);
}
} else {
key = arg.substr(2);
value = "";
}
if (args.find(key) != args.end()) {
args[key] = value;
} else {
args.insert({{key, value}});
}
}
}
unitree::robot::ChannelFactory::Instance()->Init(0,
args["network_interface"]);
unitree::robot::g1::LocoClient client;
client.Init();
client.SetTimeout(10.f);
for (const auto &arg_pair : args) {
std::cout << "Processing command: [" << arg_pair.first << "] with param: ["
<< arg_pair.second << "] ..." << std::endl;
if (arg_pair.first == "network_interface") {
continue;
}
if (arg_pair.first == "get_fsm_id") {
int fsm_id;
client.GetFsmId(fsm_id);
std::cout << "current fsm_id: " << fsm_id << std::endl;
}
if (arg_pair.first == "get_fsm_mode") {
int fsm_mode;
client.GetFsmMode(fsm_mode);
std::cout << "current fsm_mode: " << fsm_mode << std::endl;
}
if (arg_pair.first == "get_balance_mode") {
int balance_mode;
client.GetBalanceMode(balance_mode);
std::cout << "current balance_mode: " << balance_mode << std::endl;
}
if (arg_pair.first == "get_swing_height") {
float swing_height;
client.GetSwingHeight(swing_height);
std::cout << "current swing_height: " << swing_height << std::endl;
}
if (arg_pair.first == "get_stand_height") {
float stand_height;
client.GetStandHeight(stand_height);
std::cout << "current stand_height: " << stand_height << std::endl;
}
if (arg_pair.first == "get_phase") {
std::vector<float> phase;
client.GetPhase(phase);
std::cout << "current phase: (";
for (const auto &p : phase) {
std::cout << p << ", ";
}
std::cout << ")" << std::endl;
}
if (arg_pair.first == "set_fsm_id") {
int fsm_id = std::stoi(arg_pair.second);
client.SetFsmId(fsm_id);
std::cout << "set fsm_id to " << fsm_id << std::endl;
}
if (arg_pair.first == "set_balance_mode") {
int balance_mode = std::stoi(arg_pair.second);
client.SetBalanceMode(balance_mode);
std::cout << "set balance_mode to " << balance_mode << std::endl;
}
if (arg_pair.first == "set_swing_height") {
float swing_height = std::stof(arg_pair.second);
client.SetSwingHeight(swing_height);
std::cout << "set swing_height to " << swing_height << std::endl;
}
if (arg_pair.first == "set_stand_height") {
float stand_height = std::stof(arg_pair.second);
client.SetStandHeight(stand_height);
std::cout << "set stand_height to " << stand_height << std::endl;
}
if (arg_pair.first == "set_velocity") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
auto param_size = param.size();
float vx, vy, omega, duration;
if (param_size == 3) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
duration = 1.f;
} else if (param_size == 4) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
duration = param.at(3);
} else {
std::cerr << "Invalid param size for method SetVelocity: " << param_size
<< std::endl;
return 1;
}
client.SetVelocity(vx, vy, omega, duration);
std::cout << "set velocity to " << arg_pair.second << std::endl;
}
if (arg_pair.first == "damp") {
client.Damp();
}
if (arg_pair.first == "start") {
client.Start();
}
if (arg_pair.first == "squat") {
client.Squat();
}
if (arg_pair.first == "sit") {
client.Sit();
}
if (arg_pair.first == "stand_up") {
client.StandUp();
}
if (arg_pair.first == "zero_torque") {
client.ZeroTorque();
}
if (arg_pair.first == "stop_move") {
client.StopMove();
}
if (arg_pair.first == "high_stand") {
client.HighStand();
}
if (arg_pair.first == "low_stand") {
client.LowStand();
}
if (arg_pair.first == "balance_stand") {
client.BalanceStand();
}
if (arg_pair.first == "continous_gait") {
bool flag;
if (arg_pair.second == "true") {
flag = true;
} else if (arg_pair.second == "false") {
flag = false;
} else {
std::cerr << "invalid argument: " << arg_pair.second << std::endl;
return 1;
}
client.ContinuousGait(flag);
}
if (arg_pair.first == "switch_move_mode") {
bool flag;
if (arg_pair.second == "true") {
flag = true;
} else if (arg_pair.second == "false") {
flag = false;
} else {
std::cerr << "invalid argument: " << arg_pair.second << std::endl;
return 1;
}
client.SwitchMoveMode(flag);
}
if (arg_pair.first == "move") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
auto param_size = param.size();
float vx, vy, omega;
if (param_size == 3) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
} else {
std::cerr << "Invalid param size for method SetVelocity: " << param_size
<< std::endl;
return 1;
}
client.Move(vx, vy, omega);
}
if (arg_pair.first == "set_task_id") {
int task_id = std::stoi(arg_pair.second);
client.SetTaskId(task_id);
std::cout << "set task_id to " << task_id << std::endl;
}
if (arg_pair.first == "shake_hand") {
client.ShakeHand(0);
std::cout << "Shake hand starts! Waiting for 10 s for ending"
<< std::endl;
std::this_thread::sleep_for(std::chrono::seconds(10));
std::cout << "Shake hand ends!" << std::endl;
client.ShakeHand(1);
}
if (arg_pair.first == "wave_hand") {
client.WaveHand();
std::cout << "wave hand" << std::endl;
}
if (arg_pair.first == "wave_hand_with_turn") {
client.WaveHand(true);
std::cout << "wave hand with turn" << std::endl;
}
if (arg_pair.first == "set_speed_mode") {
client.SetSpeedMode(std::stoi(arg_pair.second));
std::cout << "set speed mode" << std::endl;
}
std::cout << "Done!" << std::endl;
}
return 0;
}

View File

@ -0,0 +1,248 @@
#include <array>
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include "unitree/robot/g1/loco/g1_loco_api.hpp"
#include "unitree/robot/g1/loco/g1_loco_client.hpp"
static const std::string kTopicUserCtrl = "rt/user_lowcmd";
static const std::string kTopicState = "rt/lowstate";
enum JointIndex {
// Left leg
kLeftHipPitch,
kLeftHipRoll,
kLeftHipYaw,
kLeftKnee,
kLeftAnkle,
kLeftAnkleRoll,
// Right leg
kRightHipPitch,
kRightHipRoll,
kRightHipYaw,
kRightKnee,
kRightAnkle,
kRightAnkleRoll,
kWaistYaw,
kWaistRoll,
kWaistPitch,
// Left arm
kLeftShoulderPitch,
kLeftShoulderRoll,
kLeftShoulderYaw,
kLeftElbow,
kLeftWristRoll,
kLeftWristPitch,
kLeftWristYaw,
// Right arm
kRightShoulderPitch,
kRightShoulderRoll,
kRightShoulderYaw,
kRightElbow,
kRightWristRoll,
kRightWristPitch,
kRightWristYaw,
kNotUsedJoint,
kNotUsedJoint1,
kNotUsedJoint2,
kNotUsedJoint3,
kNotUsedJoint4,
kNotUsedJoint5
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_>
user_ctrl_publisher;
unitree_hg::msg::dds_::LowCmd_ msg;
user_ctrl_publisher.reset(
new unitree::robot::ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(
kTopicUserCtrl));
user_ctrl_publisher->InitChannel();
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_>
low_state_subscriber;
// create subscriber
unitree_hg::msg::dds_::LowState_ state_msg;
low_state_subscriber.reset(
new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
kTopicState));
low_state_subscriber->InitChannel([&](const void *msg) {
auto s = ( const unitree_hg::msg::dds_::LowState_* )msg;
memcpy( &state_msg, s, sizeof( unitree_hg::msg::dds_::LowState_ ) );
}, 1);
unitree::robot::g1::LocoClient client;
client.Init();
client.SetTimeout(5.f);
int current_fsm_id;
client.GetFsmId(current_fsm_id);
if(current_fsm_id != 1){
std::cout << "Current fsm is not PASSIVE, exitting ..." <<std::endl;
exit(-1);
}
float kp = 60.f;
float kd = 1.5f;
float dq = 0.f;
float tau_ff = 0.f;
float control_dt = 0.02f;
float max_joint_velocity = 0.5f;
float max_joint_delta = max_joint_velocity * control_dt;
auto sleep_time =
std::chrono::milliseconds(static_cast<int>(control_dt / 0.001f));
std::array<float, 29> init_pos{-0.1, 0, 0, 0.3, -0.2, 0,
-0.1, 0, 0, 0.3, -0.2, 0,
0, 0, 0,
0.2, 0.2, 0, 0.9, 0, 0, 0,
0.2, -0.2, 0, 0.9, 0, 0, 0};
std::array<float, 29> target_pos = {-1.0, 0, 0, 1.5, 0.2, 0,
-1.0, 0, 0, 1.5, 0.2, 0,
0, 0, 0,
0, 0.2, 0, 0, 0, 0, 0,
0, -0.2, 0, 0, 0, 0, 0};
// wait for init
std::cout << "Press ENTER to init user control ...";
std::cin.get();
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(j).q(0);
msg.motor_cmd().at(j).dq(0);
msg.motor_cmd().at(j).kp(0);
msg.motor_cmd().at(j).kd(kd);
msg.motor_cmd().at(j).tau(0);
}
user_ctrl_publisher->Write(msg);
client.SwitchToUserCtrl();
// get current joint position
std::array<float, 29> current_jpos{};
std::cout<<"Current joint position: ";
for (int i = 0; i < init_pos.size(); ++i) {
current_jpos.at(i) = state_msg.motor_state().at(i).q();
std::cout << current_jpos.at(i) << " ";
}
std::cout << std::endl;
// set init pos
std::cout << "Initailizing motors ...";
float init_time = 2.0f;
int init_time_steps = static_cast<int>(init_time / control_dt);
for (int i = 0; i < init_time_steps; ++i) {
float phase = 1.0 * i / init_time_steps;
std::cout << "Phase: " << phase << std::endl;
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(j).q(init_pos.at(j) * phase + current_jpos.at(j) * (1 - phase));
msg.motor_cmd().at(j).dq(dq);
msg.motor_cmd().at(j).kp(kp);
msg.motor_cmd().at(j).kd(kd);
msg.motor_cmd().at(j).tau(tau_ff);
}
// send dds msg
user_ctrl_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
// wait for control
std::cout << "Press ENTER to start user control ..." << std::endl;
std::cin.get();
// start control
std::cout << "Start user control!" << std::endl;
float period = 5.f;
int num_time_steps = static_cast<int>(period / control_dt);
std::array<float, 29> current_jpos_des{};
for (int i = 0; i < init_pos.size(); ++i) {
current_jpos_des.at(i) = state_msg.motor_state().at(i).q();
}
// lift arms up
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(target_pos.at(j) - current_jpos_des.at(j),
-max_joint_delta, max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(j).q(current_jpos_des.at(j));
msg.motor_cmd().at(j).dq(dq);
msg.motor_cmd().at(j).kp(kp);
msg.motor_cmd().at(j).kd(kd);
msg.motor_cmd().at(j).tau(tau_ff);
}
// send dds msg
user_ctrl_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// put arms down
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(init_pos.at(j) - current_jpos_des.at(j), -max_joint_delta,
max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(j).q(current_jpos_des.at(j));
msg.motor_cmd().at(j).dq(dq);
msg.motor_cmd().at(j).kp(kp);
msg.motor_cmd().at(j).kd(kd);
msg.motor_cmd().at(j).tau(tau_ff);
}
// send dds msg
user_ctrl_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// stop control
std::cout << "Stoping user control ...";
client.SwitchToInternalCtrl(unitree::robot::g1::InternalFsmMode::LAST);
std::cout << "Done!" << std::endl;
return 0;
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,371 @@
#include <cmath>
#include <memory>
#include <mutex>
#include <shared_mutex>
#include "gamepad.hpp"
// DDS
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
// IDL
#include <unitree/idl/hg/IMUState_.hpp>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
static const std::string HG_CMD_TOPIC = "rt/lowcmd";
static const std::string HG_IMU_TORSO = "rt/secondary_imu";
static const std::string HG_STATE_TOPIC = "rt/lowstate";
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree_hg::msg::dds_;
template <typename T>
class DataBuffer {
public:
void SetData(const T &newData) {
std::unique_lock<std::shared_mutex> lock(mutex);
data = std::make_shared<T>(newData);
}
std::shared_ptr<const T> GetData() {
std::shared_lock<std::shared_mutex> lock(mutex);
return data ? data : nullptr;
}
void Clear() {
std::unique_lock<std::shared_mutex> lock(mutex);
data = nullptr;
}
private:
std::shared_ptr<T> data;
std::shared_mutex mutex;
};
const int G1_NUM_MOTOR = 29;
struct ImuState {
std::array<float, 3> rpy = {};
std::array<float, 3> omega = {};
};
struct MotorCommand {
std::array<float, G1_NUM_MOTOR> q_target = {};
std::array<float, G1_NUM_MOTOR> dq_target = {};
std::array<float, G1_NUM_MOTOR> kp = {};
std::array<float, G1_NUM_MOTOR> kd = {};
std::array<float, G1_NUM_MOTOR> tau_ff = {};
};
struct MotorState {
std::array<float, G1_NUM_MOTOR> q = {};
std::array<float, G1_NUM_MOTOR> dq = {};
};
// Stiffness for all G1 Joints
std::array<float, G1_NUM_MOTOR> Kp{
60, 60, 60, 100, 40, 40, // legs
60, 60, 60, 100, 40, 40, // legs
60, 40, 40, // waist
40, 40, 40, 40, 40, 40, 40, // arms
40, 40, 40, 40, 40, 40, 40 // arms
};
// Damping for all G1 Joints
std::array<float, G1_NUM_MOTOR> Kd{
1, 1, 1, 2, 1, 1, // legs
1, 1, 1, 2, 1, 1, // legs
1, 1, 1, // waist
1, 1, 1, 1, 1, 1, 1, // arms
1, 1, 1, 1, 1, 1, 1 // arms
};
enum class Mode {
PR = 0, // Series Control for Ptich/Roll Joints
AB = 1 // Parallel Control for A/B Joints
};
enum G1JointIndex {
LeftHipPitch = 0,
LeftHipRoll = 1,
LeftHipYaw = 2,
LeftKnee = 3,
LeftAnklePitch = 4,
LeftAnkleB = 4,
LeftAnkleRoll = 5,
LeftAnkleA = 5,
RightHipPitch = 6,
RightHipRoll = 7,
RightHipYaw = 8,
RightKnee = 9,
RightAnklePitch = 10,
RightAnkleB = 10,
RightAnkleRoll = 11,
RightAnkleA = 11,
WaistYaw = 12,
WaistRoll = 13, // NOTE INVALID for g1 23dof/29dof with waist locked
WaistA = 13, // NOTE INVALID for g1 23dof/29dof with waist locked
WaistPitch = 14, // NOTE INVALID for g1 23dof/29dof with waist locked
WaistB = 14, // NOTE INVALID for g1 23dof/29dof with waist locked
LeftShoulderPitch = 15,
LeftShoulderRoll = 16,
LeftShoulderYaw = 17,
LeftElbow = 18,
LeftWristRoll = 19,
LeftWristPitch = 20, // NOTE INVALID for g1 23dof
LeftWristYaw = 21, // NOTE INVALID for g1 23dof
RightShoulderPitch = 22,
RightShoulderRoll = 23,
RightShoulderYaw = 24,
RightElbow = 25,
RightWristRoll = 26,
RightWristPitch = 27, // NOTE INVALID for g1 23dof
RightWristYaw = 28 // NOTE INVALID for g1 23dof
};
inline uint32_t Crc32Core(uint32_t *ptr, uint32_t len) {
uint32_t xbit = 0;
uint32_t data = 0;
uint32_t CRC32 = 0xFFFFFFFF;
const uint32_t dwPolynomial = 0x04c11db7;
for (uint32_t i = 0; i < len; i++) {
xbit = 1 << 31;
data = ptr[i];
for (uint32_t bits = 0; bits < 32; bits++) {
if (CRC32 & 0x80000000) {
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
} else
CRC32 <<= 1;
if (data & xbit) CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
};
class G1Example {
private:
double time_;
double control_dt_; // [2ms]
double duration_; // [3 s]
int counter_;
Mode mode_pr_;
uint8_t mode_machine_;
Gamepad gamepad_;
REMOTE_DATA_RX rx_;
DataBuffer<MotorState> motor_state_buffer_;
DataBuffer<MotorCommand> motor_command_buffer_;
DataBuffer<ImuState> imu_state_buffer_;
ChannelPublisherPtr<LowCmd_> lowcmd_publisher_;
ChannelSubscriberPtr<LowState_> lowstate_subscriber_;
ChannelSubscriberPtr<IMUState_> imutorso_subscriber_;
ThreadPtr command_writer_ptr_, control_thread_ptr_;
std::shared_ptr<unitree::robot::b2::MotionSwitcherClient> msc_;
public:
G1Example(std::string networkInterface)
: time_(0.0),
control_dt_(0.002),
duration_(3.0),
counter_(0),
mode_pr_(Mode::PR),
mode_machine_(0) {
ChannelFactory::Instance()->Init(0, networkInterface);
// try to shutdown motion control-related service
msc_ = std::make_shared<unitree::robot::b2::MotionSwitcherClient>();
msc_->SetTimeout(5.0f);
msc_->Init();
std::string form, name;
while (msc_->CheckMode(form, name), !name.empty()) {
if (msc_->ReleaseMode())
std::cout << "Failed to switch to Release Mode\n";
sleep(5);
}
// create publisher
lowcmd_publisher_.reset(new ChannelPublisher<LowCmd_>(HG_CMD_TOPIC));
lowcmd_publisher_->InitChannel();
// create subscriber
lowstate_subscriber_.reset(new ChannelSubscriber<LowState_>(HG_STATE_TOPIC));
lowstate_subscriber_->InitChannel(std::bind(&G1Example::LowStateHandler, this, std::placeholders::_1), 1);
imutorso_subscriber_.reset(new ChannelSubscriber<IMUState_>(HG_IMU_TORSO));
imutorso_subscriber_->InitChannel(std::bind(&G1Example::imuTorsoHandler, this, std::placeholders::_1), 1);
// create threads
command_writer_ptr_ = CreateRecurrentThreadEx("command_writer", UT_CPU_ID_NONE, 2000, &G1Example::LowCommandWriter, this);
control_thread_ptr_ = CreateRecurrentThreadEx("control", UT_CPU_ID_NONE, 2000, &G1Example::Control, this);
}
void imuTorsoHandler(const void *message) {
IMUState_ imu_torso = *(const IMUState_ *)message;
auto &rpy = imu_torso.rpy();
if (counter_ % 500 == 0)
printf("IMU.torso.rpy: %.2f %.2f %.2f\n", rpy[0], rpy[1], rpy[2]);
}
void LowStateHandler(const void *message) {
LowState_ low_state = *(const LowState_ *)message;
if (low_state.crc() != Crc32Core((uint32_t *)&low_state, (sizeof(LowState_) >> 2) - 1)) {
std::cout << "[ERROR] CRC Error" << std::endl;
return;
}
// get motor state
MotorState ms_tmp;
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
ms_tmp.q.at(i) = low_state.motor_state()[i].q();
ms_tmp.dq.at(i) = low_state.motor_state()[i].dq();
if (low_state.motor_state()[i].motorstate() && i <= RightAnkleRoll)
std::cout << "[ERROR] motor " << i << " with code " << low_state.motor_state()[i].motorstate() << "\n";
}
motor_state_buffer_.SetData(ms_tmp);
// get imu state
ImuState imu_tmp;
imu_tmp.omega = low_state.imu_state().gyroscope();
imu_tmp.rpy = low_state.imu_state().rpy();
imu_state_buffer_.SetData(imu_tmp);
// update gamepad
memcpy(rx_.buff, &low_state.wireless_remote()[0], 40);
gamepad_.update(rx_.RF_RX);
// update mode machine
if (mode_machine_ != low_state.mode_machine()) {
if (mode_machine_ == 0) std::cout << "G1 type: " << unsigned(low_state.mode_machine()) << std::endl;
mode_machine_ = low_state.mode_machine();
}
// report robot status every second
if (++counter_ % 500 == 0) {
counter_ = 0;
// IMU
auto &rpy = low_state.imu_state().rpy();
printf("IMU.pelvis.rpy: %.2f %.2f %.2f\n", rpy[0], rpy[1], rpy[2]);
// RC
printf("gamepad_.A.pressed: %d\n", static_cast<int>(gamepad_.A.pressed));
printf("gamepad_.B.pressed: %d\n", static_cast<int>(gamepad_.B.pressed));
printf("gamepad_.X.pressed: %d\n", static_cast<int>(gamepad_.X.pressed));
printf("gamepad_.Y.pressed: %d\n", static_cast<int>(gamepad_.Y.pressed));
// Motor
auto &ms = low_state.motor_state();
printf("All %d Motors:", G1_NUM_MOTOR);
printf("\nmode: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%u,", ms[i].mode());
printf("\npos: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%.2f,", ms[i].q());
printf("\nvel: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%.2f,", ms[i].dq());
printf("\ntau_est: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%.2f,", ms[i].tau_est());
printf("\ntemperature: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%d,%d;", ms[i].temperature()[0], ms[i].temperature()[1]);
printf("\nvol: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%.2f,", ms[i].vol());
printf("\nsensor: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%u,%u;", ms[i].sensor()[0], ms[i].sensor()[1]);
printf("\nmotorstate: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%u,", ms[i].motorstate());
printf("\nreserve: ");
for (int i = 0; i < G1_NUM_MOTOR; ++i) printf("%u,%u,%u,%u;", ms[i].reserve()[0], ms[i].reserve()[1], ms[i].reserve()[2], ms[i].reserve()[3]);
printf("\n");
}
}
void LowCommandWriter() {
LowCmd_ dds_low_command;
dds_low_command.mode_pr() = static_cast<uint8_t>(mode_pr_);
dds_low_command.mode_machine() = mode_machine_;
const std::shared_ptr<const MotorCommand> mc = motor_command_buffer_.GetData();
if (mc) {
for (size_t i = 0; i < G1_NUM_MOTOR; i++) {
dds_low_command.motor_cmd().at(i).mode() = 1; // 1:Enable, 0:Disable
dds_low_command.motor_cmd().at(i).tau() = mc->tau_ff.at(i);
dds_low_command.motor_cmd().at(i).q() = mc->q_target.at(i);
dds_low_command.motor_cmd().at(i).dq() = mc->dq_target.at(i);
dds_low_command.motor_cmd().at(i).kp() = mc->kp.at(i);
dds_low_command.motor_cmd().at(i).kd() = mc->kd.at(i);
}
dds_low_command.crc() = Crc32Core((uint32_t *)&dds_low_command, (sizeof(dds_low_command) >> 2) - 1);
lowcmd_publisher_->Write(dds_low_command);
}
}
void Control() {
MotorCommand motor_command_tmp;
const std::shared_ptr<const MotorState> ms = motor_state_buffer_.GetData();
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.q_target.at(i) = 0.0;
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.kp.at(i) = Kp[i];
motor_command_tmp.kd.at(i) = Kd[i];
}
if (ms) {
time_ += control_dt_;
if (time_ < duration_) {
// [Stage 1]: set robot to zero posture
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
double ratio = std::clamp(time_ / duration_, 0.0, 1.0);
motor_command_tmp.q_target.at(i) = (1.0 - ratio) * ms->q.at(i);
}
} else if (time_ < duration_ * 2) {
// [Stage 2]: swing ankle using PR mode
mode_pr_ = Mode::PR;
double max_P = M_PI * 30.0 / 180.0;
double max_R = M_PI * 10.0 / 180.0;
double t = time_ - duration_;
double L_P_des = max_P * std::sin(2.0 * M_PI * t);
double L_R_des = max_R * std::sin(2.0 * M_PI * t);
double R_P_des = max_P * std::sin(2.0 * M_PI * t);
double R_R_des = -max_R * std::sin(2.0 * M_PI * t);
motor_command_tmp.q_target.at(LeftAnklePitch) = L_P_des;
motor_command_tmp.q_target.at(LeftAnkleRoll) = L_R_des;
motor_command_tmp.q_target.at(RightAnklePitch) = R_P_des;
motor_command_tmp.q_target.at(RightAnkleRoll) = R_R_des;
} else {
// [Stage 3]: swing ankle using AB mode
mode_pr_ = Mode::AB;
double max_A = M_PI * 30.0 / 180.0;
double max_B = M_PI * 10.0 / 180.0;
double t = time_ - duration_ * 2;
double L_A_des = +max_A * std::sin(M_PI * t);
double L_B_des = +max_B * std::sin(M_PI * t + M_PI);
double R_A_des = -max_A * std::sin(M_PI * t);
double R_B_des = -max_B * std::sin(M_PI * t + M_PI);
motor_command_tmp.q_target.at(LeftAnkleA) = L_A_des;
motor_command_tmp.q_target.at(LeftAnkleB) = L_B_des;
motor_command_tmp.q_target.at(RightAnkleA) = R_A_des;
motor_command_tmp.q_target.at(RightAnkleB) = R_B_des;
}
motor_command_buffer_.SetData(motor_command_tmp);
}
}
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: g1_ankle_swing_example network_interface" << std::endl;
exit(0);
}
std::string networkInterface = argv[1];
G1Example custom(networkInterface);
while (true) sleep(10);
return 0;
}

View File

@ -0,0 +1,407 @@
#include <yaml-cpp/yaml.h>
#include <cmath>
#include <memory>
#include <mutex>
#include <shared_mutex>
// DDS
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
// IDL
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
using namespace unitree::robot::b2;
static const std::string HG_CMD_TOPIC = "rt/lowcmd";
static const std::string HG_STATE_TOPIC = "rt/lowstate";
using namespace unitree::common;
using namespace unitree::robot;
const int G1_NUM_MOTOR = 29;
template <typename T>
class DataBuffer {
public:
void SetData(const T &newData) {
std::unique_lock<std::shared_mutex> lock(mutex);
data = std::make_shared<T>(newData);
}
std::shared_ptr<const T> GetData() {
std::shared_lock<std::shared_mutex> lock(mutex);
return data ? data : nullptr;
}
void Clear() {
std::unique_lock<std::shared_mutex> lock(mutex);
data = nullptr;
}
private:
std::shared_ptr<T> data;
std::shared_mutex mutex;
};
struct ImuState {
std::array<float, 3> rpy = {};
std::array<float, 3> omega = {};
};
struct MotorCommand {
std::array<float, G1_NUM_MOTOR> q_target = {};
std::array<float, G1_NUM_MOTOR> dq_target = {};
std::array<float, G1_NUM_MOTOR> kp = {};
std::array<float, G1_NUM_MOTOR> kd = {};
std::array<float, G1_NUM_MOTOR> tau_ff = {};
};
struct MotorState {
std::array<float, G1_NUM_MOTOR> q = {};
std::array<float, G1_NUM_MOTOR> dq = {};
};
enum MotorType { GearboxS = 0, GearboxM = 1, GearboxL = 2 };
std::array<MotorType, G1_NUM_MOTOR> G1MotorType{
// clang-format off
// legs
GearboxM, GearboxM, GearboxM, GearboxL, GearboxS, GearboxS,
GearboxM, GearboxM, GearboxM, GearboxL, GearboxS, GearboxS,
// waist
GearboxM, GearboxS, GearboxS,
// arms
GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS,
GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS
// clang-format on
};
enum PRorAB { PR = 0, AB = 1 };
enum G1JointValidIndex {
LeftShoulderPitch = 15,
LeftShoulderRoll = 16,
LeftShoulderYaw = 17,
LeftElbow = 18,
LeftWristRoll = 19,
LeftWristPitch = 20,
LeftWristYaw = 21,
RightShoulderPitch = 22,
RightShoulderRoll = 23,
RightShoulderYaw = 24,
RightElbow = 25,
RightWristRoll = 26,
RightWristPitch = 27,
RightWristYaw = 28
};
inline uint32_t Crc32Core(uint32_t *ptr, uint32_t len) {
uint32_t xbit = 0;
uint32_t data = 0;
uint32_t CRC32 = 0xFFFFFFFF;
const uint32_t dwPolynomial = 0x04c11db7;
for (uint32_t i = 0; i < len; i++) {
xbit = 1 << 31;
data = ptr[i];
for (uint32_t bits = 0; bits < 32; bits++) {
if (CRC32 & 0x80000000) {
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
} else
CRC32 <<= 1;
if (data & xbit) CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
};
float GetMotorKp(MotorType type) {
switch (type) {
case GearboxS:
return 40;
case GearboxM:
return 40;
case GearboxL:
return 100;
default:
return 0;
}
}
float GetMotorKd(MotorType type) {
switch (type) {
case GearboxS:
return 1;
case GearboxM:
return 1;
case GearboxL:
return 1;
default:
return 0;
}
}
class G1Example {
private:
double time_;
double control_dt_; // [2ms]
double duration_; // [3 s]
PRorAB mode_;
uint8_t mode_machine_;
std::vector<std::vector<double>> frames_data_;
DataBuffer<MotorState> motor_state_buffer_;
DataBuffer<MotorCommand> motor_command_buffer_;
DataBuffer<ImuState> imu_state_buffer_;
ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_> lowcmd_publisher_;
ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_> lowstate_subscriber_;
ThreadPtr command_writer_ptr_, control_thread_ptr_;
std::shared_ptr<MotionSwitcherClient> msc;
public:
G1Example(std::string networkInterface)
: time_(0.0),
control_dt_(0.002),
duration_(3.0),
mode_(PR),
mode_machine_(0) {
ChannelFactory::Instance()->Init(0, networkInterface);
msc.reset(new MotionSwitcherClient());
msc->SetTimeout(5.0F);
msc->Init();
/*Shut down motion control-related service*/
while(queryMotionStatus())
{
std::cout << "Try to deactivate the motion control-related service." << std::endl;
int32_t ret = msc->ReleaseMode();
if (ret == 0) {
std::cout << "ReleaseMode succeeded." << std::endl;
} else {
std::cout << "ReleaseMode failed. Error code: " << ret << std::endl;
}
sleep(5);
}
loadBehaviorLibrary("motion");
// create publisher
lowcmd_publisher_.reset(
new ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(HG_CMD_TOPIC));
lowcmd_publisher_->InitChannel();
// create subscriber
lowstate_subscriber_.reset(
new ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
HG_STATE_TOPIC));
lowstate_subscriber_->InitChannel(
std::bind(&G1Example::LowStateHandler, this, std::placeholders::_1), 1);
// create threads
command_writer_ptr_ =
CreateRecurrentThreadEx("command_writer", UT_CPU_ID_NONE, 2000,
&G1Example::LowCommandWriter, this);
control_thread_ptr_ = CreateRecurrentThreadEx(
"control", UT_CPU_ID_NONE, 2000, &G1Example::Control, this);
}
void loadBehaviorLibrary(std::string behavior_name) {
std::string resource_dir = BLIB_DIR;
YAML::Node motion = YAML::LoadFile(resource_dir + behavior_name + ".seq");
std::string content = motion["components"][1]["content"].as<std::string>();
int num_parts = motion["components"][1]["num_parts"].as<int>();
std::cout << "BehaviorName: " << behavior_name + ".seq\n";
std::cout << content << " with " << num_parts << "\n";
auto frames = motion["components"][1]["frames"];
for (const auto &frame : frames) {
std::vector<double> frame_data;
for (const auto &element : frame) {
frame_data.push_back(element.as<double>());
}
frames_data_.push_back(frame_data);
}
std::cout << frames_data_.size() << " knots with " << frames_data_[0].size()
<< " DOF\n";
}
void ReportRPY() {
const std::shared_ptr<const ImuState> imu_tmp_ptr =
imu_state_buffer_.GetData();
if (imu_tmp_ptr) {
std::cout << "rpy: [" << imu_tmp_ptr->rpy.at(0) << ", "
<< imu_tmp_ptr->rpy.at(1) << ", " << imu_tmp_ptr->rpy.at(2)
<< "]" << std::endl;
}
}
void LowStateHandler(const void *message) {
unitree_hg::msg::dds_::LowState_ low_state =
*(const unitree_hg::msg::dds_::LowState_ *)message;
if (low_state.crc() !=
Crc32Core((uint32_t *)&low_state,
(sizeof(unitree_hg::msg::dds_::LowState_) >> 2) - 1)) {
std::cout << "low_state CRC Error" << std::endl;
return;
}
// get motor state
MotorState ms_tmp;
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
ms_tmp.q.at(i) = low_state.motor_state()[i].q();
ms_tmp.dq.at(i) = low_state.motor_state()[i].dq();
}
motor_state_buffer_.SetData(ms_tmp);
// get imu state
ImuState imu_tmp;
imu_tmp.omega = low_state.imu_state().gyroscope();
imu_tmp.rpy = low_state.imu_state().rpy();
imu_state_buffer_.SetData(imu_tmp);
// update mode machine
if (mode_machine_ != low_state.mode_machine()) {
if (mode_machine_ == 0)
std::cout << "G1 type: " << unsigned(low_state.mode_machine())
<< std::endl;
mode_machine_ = low_state.mode_machine();
}
}
void LowCommandWriter() {
unitree_hg::msg::dds_::LowCmd_ dds_low_command;
dds_low_command.mode_pr() = mode_;
dds_low_command.mode_machine() = mode_machine_;
const std::shared_ptr<const MotorCommand> mc =
motor_command_buffer_.GetData();
if (mc) {
for (size_t i = 0; i < G1_NUM_MOTOR; i++) {
dds_low_command.motor_cmd().at(i).mode() = 1; // 1:Enable, 0:Disable
dds_low_command.motor_cmd().at(i).tau() = mc->tau_ff.at(i);
dds_low_command.motor_cmd().at(i).q() = mc->q_target.at(i);
dds_low_command.motor_cmd().at(i).dq() = mc->dq_target.at(i);
dds_low_command.motor_cmd().at(i).kp() = mc->kp.at(i);
dds_low_command.motor_cmd().at(i).kd() = mc->kd.at(i);
}
dds_low_command.crc() = Crc32Core((uint32_t *)&dds_low_command,
(sizeof(dds_low_command) >> 2) - 1);
lowcmd_publisher_->Write(dds_low_command);
}
}
void Control() {
MotorCommand motor_command_tmp;
const std::shared_ptr<const MotorState> ms = motor_state_buffer_.GetData();
if (ms) {
time_ += control_dt_;
if (time_ < duration_) {
// [Stage 1]: set robot to zero posture
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
double ratio = std::clamp(time_ / duration_, 0.0, 1.0);
double q_des = 0;
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.q_target.at(i) =
(q_des - ms->q.at(i)) * ratio + ms->q.at(i);
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.kp.at(i) = GetMotorKp(G1MotorType[i]);
motor_command_tmp.kd.at(i) = GetMotorKd(G1MotorType[i]);
}
} else {
// [Stage 2]: tracking the offline trajectory
size_t frame_index = (size_t)((time_ - duration_) / control_dt_);
if (frame_index >= frames_data_.size()) {
frame_index = frames_data_.size() - 1;
time_ = 0.0; // RESET
}
if (frame_index % 100 == 0)
std::cout << "Frame Index: " << frame_index << std::endl;
for (int i = 0; i < G1_NUM_MOTOR; ++i) {
size_t index_in_frame = i - LeftShoulderPitch;
motor_command_tmp.q_target.at(i) =
(i >= LeftShoulderPitch)
? frames_data_[frame_index][index_in_frame]
: 0.0;
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.kp.at(i) = GetMotorKp(G1MotorType[i]);
motor_command_tmp.kd.at(i) = GetMotorKd(G1MotorType[i]);
}
}
motor_command_buffer_.SetData(motor_command_tmp);
}
}
std::string queryServiceName(std::string form,std::string name)
{
if(form == "0")
{
if(name == "normal" ) return "sport_mode";
if(name == "ai" ) return "ai_sport";
if(name == "advanced" ) return "advanced_sport";
}
else
{
if(name == "ai-w" ) return "wheeled_sport(go2W)";
if(name == "normal-w" ) return "wheeled_sport(b2W)";
}
return "";
}
int queryMotionStatus()
{
std::string robotForm,motionName;
int motionStatus;
int32_t ret = msc->CheckMode(robotForm,motionName);
if (ret == 0) {
std::cout << "CheckMode succeeded." << std::endl;
} else {
std::cout << "CheckMode failed. Error code: " << ret << std::endl;
}
if(motionName.empty())
{
std::cout << "The motion control-related service is deactivated." << std::endl;
motionStatus = 0;
}
else
{
std::string serviceName = queryServiceName(robotForm,motionName);
std::cout << "Service: "<< serviceName<< " is activate" << std::endl;
motionStatus = 1;
}
return motionStatus;
}
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: g1_dual_arm_example network_interface_name"
<< std::endl;
exit(0);
}
std::string networkInterface = argv[1];
G1Example custom(networkInterface);
while (true) sleep(10);
return 0;
}

View File

@ -0,0 +1,128 @@
#pragma once
#include <cmath>
namespace unitree::common
{
// bytecode mapping for raw joystick data
// 16b
typedef union
{
struct
{
uint8_t R1 : 1;
uint8_t L1 : 1;
uint8_t start : 1;
uint8_t select : 1;
uint8_t R2 : 1;
uint8_t L2 : 1;
uint8_t F1 : 1;
uint8_t F2 : 1;
uint8_t A : 1;
uint8_t B : 1;
uint8_t X : 1;
uint8_t Y : 1;
uint8_t up : 1;
uint8_t right : 1;
uint8_t down : 1;
uint8_t left : 1;
} components;
uint16_t value;
} xKeySwitchUnion;
// 40 Byte (now used 24B)
typedef struct
{
uint8_t head[2];
xKeySwitchUnion btn;
float lx;
float rx;
float ry;
float L2;
float ly;
uint8_t idle[16];
} xRockerBtnDataStruct;
typedef union
{
xRockerBtnDataStruct RF_RX;
uint8_t buff[40];
} REMOTE_DATA_RX;
class Button
{
public:
Button() {}
void update(bool state)
{
on_press = state ? state != pressed : false;
on_release = state ? false : state != pressed;
pressed = state;
}
bool pressed = false;
bool on_press = false;
bool on_release = false;
};
class Gamepad
{
public:
Gamepad() {}
void update(xRockerBtnDataStruct &key_data)
{
lx = lx * (1 - smooth) + (std::fabs(key_data.lx) < dead_zone ? 0.0 : key_data.lx) * smooth;
rx = rx * (1 - smooth) + (std::fabs(key_data.rx) < dead_zone ? 0.0 : key_data.rx) * smooth;
ry = ry * (1 - smooth) + (std::fabs(key_data.ry) < dead_zone ? 0.0 : key_data.ry) * smooth;
l2 = l2 * (1 - smooth) + (std::fabs(key_data.L2) < dead_zone ? 0.0 : key_data.L2) * smooth;
ly = ly * (1 - smooth) + (std::fabs(key_data.ly) < dead_zone ? 0.0 : key_data.ly) * smooth;
R1.update(key_data.btn.components.R1);
L1.update(key_data.btn.components.L1);
start.update(key_data.btn.components.start);
select.update(key_data.btn.components.select);
R2.update(key_data.btn.components.R2);
L2.update(key_data.btn.components.L2);
F1.update(key_data.btn.components.F1);
F2.update(key_data.btn.components.F2);
A.update(key_data.btn.components.A);
B.update(key_data.btn.components.B);
X.update(key_data.btn.components.X);
Y.update(key_data.btn.components.Y);
up.update(key_data.btn.components.up);
right.update(key_data.btn.components.right);
down.update(key_data.btn.components.down);
left.update(key_data.btn.components.left);
}
float lx = 0.;
float rx = 0.;
float ry = 0.;
float l2 = 0.;
float ly = 0.;
float smooth = 0.03;
float dead_zone = 0.01;
Button R1;
Button L1;
Button start;
Button select;
Button R2;
Button L2;
Button F1;
Button F2;
Button A;
Button B;
Button X;
Button Y;
Button up;
Button right;
Button down;
Button left;
};
} // namespace unitree::common

View File

@ -0,0 +1,46 @@
#include <unitree/robot/g1/common/terminations.hpp>
#include <boost/program_options.hpp>
#include <thread>
namespace po = boost::program_options;
using namespace unitree::robot;
using namespace unitree_hg::msg::dds_;
int main(int argc, char** argv)
{
// Parse command line arguments
po::options_description desc("Unitree G1 termination functions testing.");
desc.add_options()
("network,n", po::value<std::string>()->default_value(""), "dds network interface")
;
po::variables_map vm;
po::store(po::parse_command_line(argc, argv, desc), vm);
po::notify(vm);
std::cout << desc << std::endl;
// DDS Init
ChannelFactory::Instance()->Init(0, vm["network"].as<std::string>());
auto lowstate_subscriber = std::make_shared<ChannelSubscriber<LowState_>>("rt/lowstate");
LowState_ lowstate;
lowstate_subscriber->InitChannel([&lowstate](const void* message) {
lowstate = *(const LowState_*)message;
});
std::cout << "Checking terminations..." << std::endl;
while (true)
{
if (g1::bad_orientation(lowstate, 1.0f)) { // Tip the robot over to test bad orientation
std::cout << "Bad orientation detected!" << std::endl;
}
if (g1::lost_connection(lowstate_subscriber, 1000)) { // Unplug the network cable to test lost connection
std::cout << "Lost connection!" << std::endl;
}
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}
return 0;
}

View File

@ -0,0 +1,21 @@
# add_executable(go2_trajectory_follow go2_trajectory_follow.cpp)
# target_link_libraries(go2_trajectory_follow unitree_sdk2)
add_executable(go2_sport_client go2_sport_client.cpp)
target_link_libraries(go2_sport_client unitree_sdk2)
add_executable(go2_low_level go2_low_level.cpp)
target_link_libraries(go2_low_level unitree_sdk2)
add_executable(go2_stand_example go2_stand_example.cpp)
target_link_libraries(go2_stand_example unitree_sdk2)
add_executable(go2_robot_state_client go2_robot_state_client.cpp)
target_link_libraries(go2_robot_state_client unitree_sdk2)
add_executable(go2_video_client go2_video_client.cpp)
target_link_libraries(go2_video_client unitree_sdk2)
add_executable(go2_vui_client go2_vui_client.cpp)
target_link_libraries(go2_vui_client unitree_sdk2)

View File

@ -0,0 +1,215 @@
#include <iostream>
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/LowState_.hpp>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/common/thread/thread.hpp>
using namespace unitree::common;
using namespace unitree::robot;
#define TOPIC_LOWCMD "rt/lowcmd"
#define TOPIC_LOWSTATE "rt/lowstate"
constexpr double PosStopF = (2.146E+9f);
constexpr double VelStopF = (16000.0f);
class Custom
{
public:
explicit Custom()
{}
~Custom()
{}
void Init();
private:
void InitLowCmd();
void LowStateMessageHandler(const void* messages);
void LowCmdWrite();
private:
float qInit[3] = {0};
float qDes[3] = {0};
float sin_mid_q[3] = {0.0, 1.2, -2.0};
float Kp[3] = {0};
float Kd[3] = {0};
double time_consume = 0;
int rate_count = 0;
int sin_count = 0;
int motiontime = 0;
float dt = 0.002; // 0.001~0.01
unitree_go::msg::dds_::LowCmd_ low_cmd{}; // default init
unitree_go::msg::dds_::LowState_ low_state{}; // default init
/*publisher*/
ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_> lowcmd_publisher;
/*subscriber*/
ChannelSubscriberPtr<unitree_go::msg::dds_::LowState_> lowstate_subscriber;
/*LowCmd write thread*/
ThreadPtr lowCmdWriteThreadPtr;
};
uint32_t crc32_core(uint32_t* ptr, uint32_t len)
{
unsigned int xbit = 0;
unsigned int data = 0;
unsigned int CRC32 = 0xFFFFFFFF;
const unsigned int dwPolynomial = 0x04c11db7;
for (unsigned int i = 0; i < len; i++)
{
xbit = 1 << 31;
data = ptr[i];
for (unsigned int bits = 0; bits < 32; bits++)
{
if (CRC32 & 0x80000000)
{
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
}
else
{
CRC32 <<= 1;
}
if (data & xbit)
CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
}
void Custom::Init()
{
InitLowCmd();
/*create publisher*/
lowcmd_publisher.reset(new ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(TOPIC_LOWCMD));
lowcmd_publisher->InitChannel();
/*create subscriber*/
lowstate_subscriber.reset(new ChannelSubscriber<unitree_go::msg::dds_::LowState_>(TOPIC_LOWSTATE));
lowstate_subscriber->InitChannel(std::bind(&Custom::LowStateMessageHandler, this, std::placeholders::_1), 1);
/*loop publishing thread*/
lowCmdWriteThreadPtr = CreateRecurrentThreadEx("writebasiccmd", UT_CPU_ID_NONE, 2000, &Custom::LowCmdWrite, this);
}
void Custom::InitLowCmd()
{
low_cmd.head()[0] = 0xFE;
low_cmd.head()[1] = 0xEF;
low_cmd.level_flag() = 0xFF;
low_cmd.gpio() = 0;
for(int i=0; i<20; i++)
{
low_cmd.motor_cmd()[i].mode() = (0x01); // motor switch to servo (PMSM) mode
low_cmd.motor_cmd()[i].q() = (PosStopF);
low_cmd.motor_cmd()[i].kp() = (0);
low_cmd.motor_cmd()[i].dq() = (VelStopF);
low_cmd.motor_cmd()[i].kd() = (0);
low_cmd.motor_cmd()[i].tau() = (0);
}
}
void Custom::LowStateMessageHandler(const void* message)
{
low_state = *(unitree_go::msg::dds_::LowState_*)message;
}
double jointLinearInterpolation(double initPos, double targetPos, double rate)
{
double p;
rate = std::min(std::max(rate, 0.0), 1.0);
p = initPos * (1 - rate) + targetPos * rate;
return p;
}
void Custom::LowCmdWrite()
{
motiontime++;
if (motiontime >= 0)
{
// first, get record initial position
if (motiontime >= 0 && motiontime < 20)
{
qInit[0] = low_state.motor_state()[0].q();
qInit[1] = low_state.motor_state()[1].q();
qInit[2] = low_state.motor_state()[2].q();
}
// second, move to the origin point of a sine movement with Kp Kd
if (motiontime >= 10 && motiontime < 400)
{
rate_count++;
double rate = rate_count / 200.0; // needs count to 200
Kp[0] = 5.0; Kp[1] = 5.0; Kp[2] = 5.0;
Kd[0] = 1.0; Kd[1] = 1.0; Kd[2] = 1.0;
qDes[0] = jointLinearInterpolation(qInit[0], sin_mid_q[0], rate);
qDes[1] = jointLinearInterpolation(qInit[1], sin_mid_q[1], rate);
qDes[2] = jointLinearInterpolation(qInit[2], sin_mid_q[2], rate);
}
double sin_joint1, sin_joint2;
// last, do sine wave
float freq_Hz = 1;
// float freq_Hz = 5;
float freq_rad = freq_Hz * 2 * M_PI;
float t = dt * sin_count;
if (motiontime >= 400)
{
sin_count++;
sin_joint1 = 0.6 * sin(t * freq_rad);
sin_joint2 = -0.9 * sin(t * freq_rad);
qDes[0] = sin_mid_q[0];
qDes[1] = sin_mid_q[1] + sin_joint1;
qDes[2] = sin_mid_q[2] + sin_joint2;
}
low_cmd.motor_cmd()[2].q() = qDes[2];
low_cmd.motor_cmd()[2].dq() = 0;
low_cmd.motor_cmd()[2].kp() = Kp[2];
low_cmd.motor_cmd()[2].kd() = Kd[2];
low_cmd.motor_cmd()[2].tau() = 0;
}
low_cmd.crc() = crc32_core((uint32_t *)&low_cmd, (sizeof(unitree_go::msg::dds_::LowCmd_)>>2)-1);
lowcmd_publisher->Write(low_cmd);
}
int main(int argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
custom.Init();
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,82 @@
#include <unitree/robot/go2/robot_state/robot_state_client.hpp>
#include <unitree/common/time/time_tool.hpp>
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree::robot::go2;
int main(int32_t argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: robot_state_client_example [NetWorkInterface(eth0)] [ServiceName(sport_mode)]" << std::endl;
exit(0);
}
std::string networkInterface = "eth0", serviceName = "sport_mode";
if (argc > 1)
{
networkInterface = argv[1];
}
if (argc > 2)
{
serviceName = argv[2];
}
std::cout << "NetWorkInterface:" << networkInterface << std::endl;
std::cout << "Switch ServiceName:" << serviceName << std::endl;
ChannelFactory::Instance()->Init(0, networkInterface);
RobotStateClient rsc;
rsc.SetTimeout(10.0f);
rsc.Init();
std::string clientApiVersion = rsc.GetApiVersion();
std::string serverApiVersion = rsc.GetServerApiVersion();
if (clientApiVersion != serverApiVersion)
{
std::cout << "client and server api versions are not equal." << std::endl;
}
Timer timer;
int32_t status;
int32_t ret = rsc.SetReportFreq(3, 30);
std::cout << "Call SetReportFreq[3,30] ret:" << ret << ", cost:" << timer.Stop() << " (us)" << std::endl;
sleep(5);
timer.Restart();
ret = rsc.ServiceSwitch(serviceName, 0, status);
std::cout << "Call ServiceSwitch[" << serviceName << ",0] ret:" << ret << ", cost:" << timer.Stop() << " (us)" << std::endl;
sleep(5);
timer.Restart();
ret = rsc.ServiceSwitch(serviceName, 1, status);
std::cout << "Call ServiceSwitch[" << serviceName << ",1] ret:" << ret << ", cost:" << timer.Stop() << " (us)" << std::endl;
sleep(5);
timer.Restart();
std::vector<ServiceState> serviceStateList;
ret = rsc.ServiceList(serviceStateList);
std::cout << "Call ServiceList ret:" << ret << ", cost:" << timer.Stop() << " (us)" << std::endl;
size_t i, count=serviceStateList.size();
std::cout << "serviceStateList size:" << count << std::endl;
for (i=0; i<count; i++)
{
const ServiceState& serviceState = serviceStateList[i];
std::cout << "name:" << serviceState.name << ", status:" << serviceState.status << ", protect:" << serviceState.protect << std::endl;
}
ChannelFactory::Instance()->Release();
return 0;
}

View File

@ -0,0 +1,162 @@
/**********************************************************************
Copyright (c) 2020-2023, Unitree Robotics.Co.Ltd. All rights reserved.
***********************************************************************/
#include <cmath>
#include <unitree/robot/go2/sport/sport_client.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/SportModeState_.hpp>
#define TOPIC_HIGHSTATE "rt/sportmodestate"
using namespace unitree::common;
enum test_mode
{
/*---Basic motion---*/
normal_stand,
balance_stand,
velocity_move,
stand_down,
stand_up,
damp,
recovery_stand,
/*---Special motion ---*/
sit,
rise_sit,
stop_move = 99
};
const int TEST_MODE = stand_down;
class Custom
{
public:
Custom()
{
sport_client.SetTimeout(10.0f);
sport_client.Init();
suber.reset(new unitree::robot::ChannelSubscriber<unitree_go::msg::dds_::SportModeState_>(TOPIC_HIGHSTATE));
suber->InitChannel(std::bind(&Custom::HighStateHandler, this, std::placeholders::_1), 1);
};
void RobotControl()
{
ct += dt;
double px_local, py_local, yaw_local;
double vx_local, vy_local, vyaw_local;
double px_err, py_err, yaw_err;
double time_seg, time_temp;
unitree::robot::go2::PathPoint path_point_tmp;
std::vector<unitree::robot::go2::PathPoint> path;
switch (TEST_MODE)
{
case normal_stand: // 0. idle, default stand
// sport_client.SwitchGait(0); // 0:idle; 1:tort; 2:tort running; 3:climb stair; 4:tort obstacle
sport_client.StandUp();
break;
case balance_stand: // 1. Balance stand (controlled by dBodyHeight + rpy)
// sport_client.Euler(0.1, 0.2, 0.3); // roll, pitch, yaw
// sport_client.BodyHeight(0.0); // relative height [-0.18~0.03]
sport_client.BalanceStand();
break;
case velocity_move: // 2. target velocity walking (controlled by velocity + yawSpeed)
sport_client.Move(0.3, 0, 0.3);
break;
case stand_down: // 4. position stand down.
sport_client.StandDown();
break;
case stand_up: // 5. position stand up
sport_client.StandUp();
break;
case damp: // 6. damping mode
sport_client.Damp();
break;
case recovery_stand: // 7. recovery stand
sport_client.RecoveryStand();
break;
case sit:
if (flag == 0)
{
sport_client.Sit();
flag = 1;
}
break;
case rise_sit:
if (flag == 0)
{
sport_client.RiseSit();
flag = 1;
}
break;
case stop_move: // stop move
sport_client.StopMove();
break;
default:
sport_client.StopMove();
}
};
// Get initial position
void GetInitState()
{
px0 = state.position()[0];
py0 = state.position()[1];
yaw0 = state.imu_state().rpy()[2];
std::cout << "initial position: x0: " << px0 << ", y0: " << py0 << ", yaw0: " << yaw0 << std::endl;
};
void HighStateHandler(const void *message)
{
state = *(unitree_go::msg::dds_::SportModeState_ *)message;
// std::cout << "Position: " << state.position()[0] << ", " << state.position()[1] << ", " << state.position()[2] << std::endl;
// std::cout << "IMU rpy: " << state.imu_state().rpy()[0] << ", " << state.imu_state().rpy()[1] << ", " << state.imu_state().rpy()[2] << std::endl;
};
unitree_go::msg::dds_::SportModeState_ state;
unitree::robot::go2::SportClient sport_client;
unitree::robot::ChannelSubscriberPtr<unitree_go::msg::dds_::SportModeState_> suber;
double px0, py0, yaw0; // 初始状态的位置和偏航
double ct = 0; // 运行时间
int flag = 0; // 特殊动作执行标志
float dt = 0.005; // 控制步长0.001~0.01
};
int main(int argc, char **argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
sleep(1); // Wait for 1 second to obtain a stable state
custom.GetInitState(); // Get initial position
unitree::common::ThreadPtr threadPtr = unitree::common::CreateRecurrentThread(custom.dt * 1000000, std::bind(&Custom::RobotControl, &custom));
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,330 @@
#include <iostream>
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/LowState_.hpp>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/common/thread/thread.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree::robot::b2;
#define TOPIC_LOWCMD "rt/lowcmd"
#define TOPIC_LOWSTATE "rt/lowstate"
constexpr double PosStopF = (2.146E+9f);
constexpr double VelStopF = (16000.0f);
class Custom
{
public:
explicit Custom(){}
~Custom(){}
void Init();
void Start();
private:
void InitLowCmd();
void LowStateMessageHandler(const void* messages);
void LowCmdWrite();
int queryMotionStatus();
std::string queryServiceName(std::string form,std::string name);
private:
float Kp = 60.0;
float Kd = 5.0;
double time_consume = 0;
int rate_count = 0;
int sin_count = 0;
int motiontime = 0;
float dt = 0.002; // 0.001~0.01
MotionSwitcherClient msc;
unitree_go::msg::dds_::LowCmd_ low_cmd{}; // default init
unitree_go::msg::dds_::LowState_ low_state{}; // default init
/*publisher*/
ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_> lowcmd_publisher;
/*subscriber*/
ChannelSubscriberPtr<unitree_go::msg::dds_::LowState_> lowstate_subscriber;
/*LowCmd write thread*/
ThreadPtr lowCmdWriteThreadPtr;
float _targetPos_1[12] = {0.0, 1.36, -2.65, 0.0, 1.36, -2.65,
-0.2, 1.36, -2.65, 0.2, 1.36, -2.65};
float _targetPos_2[12] = {0.0, 0.67, -1.3, 0.0, 0.67, -1.3,
0.0, 0.67, -1.3, 0.0, 0.67, -1.3};
float _targetPos_3[12] = {-0.35, 1.36, -2.65, 0.35, 1.36, -2.65,
-0.5, 1.36, -2.65, 0.5, 1.36, -2.65};
float _startPos[12];
float _duration_1 = 500;
float _duration_2 = 500;
float _duration_3 = 1000;
float _duration_4 = 900;
float _percent_1 = 0;
float _percent_2 = 0;
float _percent_3 = 0;
float _percent_4 = 0;
bool firstRun = true;
bool done = false;
};
uint32_t crc32_core(uint32_t* ptr, uint32_t len)
{
unsigned int xbit = 0;
unsigned int data = 0;
unsigned int CRC32 = 0xFFFFFFFF;
const unsigned int dwPolynomial = 0x04c11db7;
for (unsigned int i = 0; i < len; i++)
{
xbit = 1 << 31;
data = ptr[i];
for (unsigned int bits = 0; bits < 32; bits++)
{
if (CRC32 & 0x80000000)
{
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
}
else
{
CRC32 <<= 1;
}
if (data & xbit)
CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
}
void Custom::Init()
{
InitLowCmd();
/*create publisher*/
lowcmd_publisher.reset(new ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(TOPIC_LOWCMD));
lowcmd_publisher->InitChannel();
/*create subscriber*/
lowstate_subscriber.reset(new ChannelSubscriber<unitree_go::msg::dds_::LowState_>(TOPIC_LOWSTATE));
lowstate_subscriber->InitChannel(std::bind(&Custom::LowStateMessageHandler, this, std::placeholders::_1), 1);
/*init MotionSwitcherClient*/
msc.SetTimeout(10.0f);
msc.Init();
/*Shut down motion control-related service*/
while(queryMotionStatus())
{
std::cout << "Try to deactivate the motion control-related service." << std::endl;
int32_t ret = msc.ReleaseMode();
if (ret == 0) {
std::cout << "ReleaseMode succeeded." << std::endl;
} else {
std::cout << "ReleaseMode failed. Error code: " << ret << std::endl;
}
sleep(5);
}
}
void Custom::InitLowCmd()
{
low_cmd.head()[0] = 0xFE;
low_cmd.head()[1] = 0xEF;
low_cmd.level_flag() = 0xFF;
low_cmd.gpio() = 0;
for(int i=0; i<20; i++)
{
low_cmd.motor_cmd()[i].mode() = (0x01); // motor switch to servo (PMSM) mode
low_cmd.motor_cmd()[i].q() = (PosStopF);
low_cmd.motor_cmd()[i].kp() = (0);
low_cmd.motor_cmd()[i].dq() = (VelStopF);
low_cmd.motor_cmd()[i].kd() = (0);
low_cmd.motor_cmd()[i].tau() = (0);
}
}
int Custom::queryMotionStatus()
{
std::string robotForm,motionName;
int motionStatus;
int32_t ret = msc.CheckMode(robotForm,motionName);
if (ret == 0) {
std::cout << "CheckMode succeeded." << std::endl;
} else {
std::cout << "CheckMode failed. Error code: " << ret << std::endl;
}
if(motionName.empty())
{
std::cout << "The motion control-related service is deactivated." << std::endl;
motionStatus = 0;
}
else
{
std::string serviceName = queryServiceName(robotForm,motionName);
std::cout << "Service: "<< serviceName<< " is activate" << std::endl;
motionStatus = 1;
}
return motionStatus;
}
std::string Custom::queryServiceName(std::string form,std::string name)
{
if(form == "0")
{
if(name == "normal" ) return "sport_mode";
if(name == "ai" ) return "ai_sport";
if(name == "advanced" ) return "advanced_sport";
}
else
{
if(name == "ai-w" ) return "wheeled_sport(go2W)";
if(name == "normal-w" ) return "wheeled_sport(b2W)";
}
return "";
}
void Custom::Start()
{
/*loop publishing thread*/
lowCmdWriteThreadPtr = CreateRecurrentThreadEx("writebasiccmd", UT_CPU_ID_NONE, 2000, &Custom::LowCmdWrite, this);
}
void Custom::LowStateMessageHandler(const void* message)
{
low_state = *(unitree_go::msg::dds_::LowState_*)message;
}
void Custom::LowCmdWrite()
{
if(_percent_4<1)
{
std::cout<<"Read sensor data example: "<<std::endl;
std::cout<<"Joint 0 pos: "<<low_state.motor_state()[0].q()<<std::endl;
std::cout<<"Imu accelerometer : "<<"x: "<<low_state.imu_state().accelerometer()[0]<<" y: "<<low_state.imu_state().accelerometer()[1]<<" z: "<<low_state.imu_state().accelerometer()[2]<<std::endl;
std::cout<<"Foot force "<<low_state.foot_force()[0]<<std::endl;
std::cout<<std::endl;
}
if((_percent_4 == 1) && ( done == false))
{
std::cout<<"The example is done! "<<std::endl;
std::cout<<std::endl;
done = true;
}
motiontime++;
if(motiontime>=500)
{
if(firstRun)
{
for(int i = 0; i < 12; i++)
{
_startPos[i] = low_state.motor_state()[i].q();
}
firstRun = false;
}
_percent_1 += (float)1 / _duration_1;
_percent_1 = _percent_1 > 1 ? 1 : _percent_1;
if (_percent_1 < 1)
{
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_1) * _startPos[j] + _percent_1 * _targetPos_1[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 < 1))
{
_percent_2 += (float)1 / _duration_2;
_percent_2 = _percent_2 > 1 ? 1 : _percent_2;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_2) * _targetPos_1[j] + _percent_2 * _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3<1))
{
_percent_3 += (float)1 / _duration_3;
_percent_3 = _percent_3 > 1 ? 1 : _percent_3;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3==1)&&((_percent_4<=1)))
{
_percent_4 += (float)1 / _duration_4;
_percent_4 = _percent_4 > 1 ? 1 : _percent_4;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_4) * _targetPos_2[j] + _percent_4 * _targetPos_3[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
low_cmd.crc() = crc32_core((uint32_t *)&low_cmd, (sizeof(unitree_go::msg::dds_::LowCmd_)>>2)-1);
lowcmd_publisher->Write(low_cmd);
}
}
int main(int argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
std::cout << "WARNING: Make sure the robot is hung up or lying on the ground." << std::endl
<< "Press Enter to continue..." << std::endl;
std::cin.ignore();
ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
custom.Init();
custom.Start();
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,65 @@
#include <unitree/robot/go2/sport/sport_client.hpp>
#include <unitree/common/thread/recurrent_thread.hpp>
#include <math.h>
class Custom
{
public:
Custom() {}
void control();
unitree::robot::go2::SportClient tc;
int c = 0;
float dt = 0.002; // 0.001~0.01
};
void Custom::control()
{
c++;
int32_t ret;
float vx = 0.3;
float delta = 0.06;
static float count = 0;
count += dt;
std::vector<unitree::robot::go2::PathPoint> path;
for (int i=0; i<30; i++) {
unitree::robot::go2::PathPoint p;
float var = (count + i * delta);
p.timeFromStart = i * delta;
p.x = vx * var;
p.y = 0.6 * sin(M_PI * vx * var);
p.yaw = 2*0.6 * vx * M_PI * cos(M_PI * vx * var);
p.vx = vx;
p.vy = M_PI * vx * (0.6 * cos(M_PI * vx * var));
p.vyaw = - M_PI * vx*2*0.6 * vx * M_PI * sin(M_PI * vx * var);
path.push_back(p);
}
ret = tc.TrajectoryFollow(path);
if(ret != 0){
std::cout << "Call TrajectoryFollow: " << ret << std::endl;
}
std::cout << c << std::endl;
}
int main(int argc, char** argv)
{
unitree::robot::ChannelFactory::Instance()->Init(0);
Custom custom;
custom.tc.SetTimeout(10.0f);
custom.tc.Init();
unitree::common::ThreadPtr threadPtr = unitree::common::CreateRecurrentThread(custom.dt * 1000000, std::bind(&Custom::control, &custom));
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,55 @@
#include <unitree/robot/go2/video/video_client.hpp>
#include <iostream>
#include <fstream>
#include <ctime>
int main()
{
/*
* Initilaize ChannelFactory
*/
unitree::robot::ChannelFactory::Instance()->Init(0);
unitree::robot::go2::VideoClient video_client;
/*
* Set request timeout 1.0s
*/
video_client.SetTimeout(1.0f);
video_client.Init();
//Test Api
std::vector<uint8_t> image_sample;
int ret;
while (true)
{
ret = video_client.GetImageSample(image_sample);
if (ret == 0) {
time_t rawtime;
struct tm *timeinfo;
char buffer[80];
time(&rawtime);
timeinfo = localtime(&rawtime);
strftime(buffer, sizeof(buffer), "%Y%m%d%H%M%S.jpg", timeinfo);
std::string image_name(buffer);
std::ofstream image_file(image_name, std::ios::binary);
if (image_file.is_open()) {
image_file.write(reinterpret_cast<const char*>(image_sample.data()), image_sample.size());
image_file.close();
std::cout << "Image saved successfully as " << image_name << std::endl;
} else {
std::cerr << "Error: Failed to save image." << std::endl;
}
}
sleep(3);
}
return 0;
}

View File

@ -0,0 +1,40 @@
#include <unitree/robot/go2/vui/vui_client.hpp>
int main(int32_t argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: vui_client_example network_interface_name" << std::endl;
exit(0);
}
/*
* Initilaize ChannelFactory
*/
std::string networkInterface = argv[1];
unitree::robot::ChannelFactory::Instance()->Init(0, networkInterface);
unitree::robot::go2::VuiClient vc;
/*
* Set request timeout 1.0s
*/
vc.SetTimeout(1.0f);
vc.Init();
//Test Api
int level = 0, value = 0;
int ret;
while (true)
{
ret = vc.SetBrightness(level);
std::cout << "SetBrightness level=" << level << ", api return:" << ret << std::endl;
++level %= 11;
sleep(1);
ret = vc.GetBrightness(value);
std::cout << "GetBrightness value=" << value << ", api return:" << ret << std::endl;
sleep(1);
}
return 0;
}

View File

@ -0,0 +1,5 @@
add_executable(go2w_sport_client go2w_sport_client.cpp)
target_link_libraries(go2w_sport_client unitree_sdk2)
add_executable(go2w_stand_example go2w_stand_example.cpp)
target_link_libraries(go2w_stand_example unitree_sdk2)

View File

@ -0,0 +1,194 @@
#include <iostream>
#include <string>
#include <chrono>
#include <mutex>
#include <thread>
#include <pthread.h>
#include <stdexcept>
#include <unitree/robot/go2/sport/sport_client.hpp>
#include <unitree/idl/go2/SportModeState_.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#define TOPIC_HIGHSTATE "rt/lf/sportmodestate"
using namespace std;
// 测试选项
struct TestOption
{
std::string name; // 名称
int id; // id
};
const vector<TestOption> option_list =
{{"damp", 0}, // 阻尼
{"stand_up", 1}, // 站立锁定
{"stand_down", 2}, // 趴下
{"move", 3}, // 速度控制
{"stop_move", 4}, // 停止运动
{"speed_level", 5}, // 速度档位
{"switch_gait", 6}, // 步态切换
{"get_state", 7}, // 获取状态
{"recovery", 8}, // 恢复站立
{"balance", 9}}; // 平衡站立
int ConvertToInt(const std::string &str)
{
try
{
std::stoi(str); // 尝试转换字符串为整数
return std::stoi(str);
}
catch (const std::invalid_argument &)
{
return -1; // 字符串包含非数字字符
}
catch (const std::out_of_range &)
{
return -1; // 字符串表示的数字超出int范围
}
}
class UserInterface
{
public:
UserInterface(){};
~UserInterface(){};
void terminalHandle()
{
std::string input;
std::getline(std::cin, input);
// 如果输入的是 list 则输出所有的测试选项名称和id
if (input.compare("list") == 0)
{
for (TestOption option : option_list)
{
std::cout << option.name << ", id: " << option.id << std::endl;
}
}
// 如果输入的名名称或id在枚举的测试选项中则记录测试选项名称和id
for (TestOption option : option_list)
{
if (input.compare(option.name) == 0 || ConvertToInt(input) == option.id)
{
test_option_->id = option.id;
test_option_->name = option.name;
std::cout << "Test: " << test_option_->name << ", test_id: " << test_option_->id << std::endl;
}
}
};
// 待测试的功能的指针
TestOption *test_option_;
};
void HighStateHandler(const void *message)
{
unitree_go::msg::dds_::SportModeState_ hs = *(unitree_go::msg::dds_::SportModeState_ *)message;
// std::cout << "mode: " << (int)hs.mode() << ", "
// << "gait: " << (int)hs.gait_type() << ", "
// << "progress: " << hs.progress() << std::endl;
}
int main(int argc, char **argv)
{
// 初始化 dds
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelSubscriber<unitree_go::msg::dds_::SportModeState_> suber(TOPIC_HIGHSTATE);
suber.InitChannel(HighStateHandler);
// 待测试的选项
TestOption test_option;
test_option.id = 1;
// 初始化sportclient
unitree::robot::go2::SportClient sport_client;
sport_client.SetTimeout(20.0f);
sport_client.Init();
// 初始化用户终端
UserInterface user_interface;
// 将user_interface.test_option_ 指向 test_option用于传递终端输入的结果
user_interface.test_option_ = &test_option;
std::cout << "Input \"list \" to list all test option ..." << std::endl;
long res_count = 0;
while (1)
{
auto time_start_trick = std::chrono::high_resolution_clock::now();
static const constexpr auto dt = std::chrono::microseconds(20000); // 50Hz
// 等待终端输入,并解析
user_interface.terminalHandle();
int res = 1;
if (test_option.id == 0)
{
res = sport_client.Damp();
}
else if (test_option.id == 1)
{
res = sport_client.StandUp();
}
else if (test_option.id == 2)
{
res = sport_client.StandDown();
}
else if (test_option.id == 3)
{
// 此处为调用一次 Move 指令机器人会移动1s后停下
// 如果循环调用 Move 则可以持续移动1s 中内无Move请求机器人会自动停下。
res = sport_client.Move(0.5, 0, 0);
}
else if (test_option.id == 4)
{
res = sport_client.StopMove();
}
else if (test_option.id == 5)
{
res = sport_client.SpeedLevel(1);
}
else if (test_option.id == 6)
{
// res = sport_client.SwitchGait(1);
}
else if (test_option.id == 7)
{
// std::map<std::string, std::string> state_map;
// std::vector<std::string> state_name = {"speedLevel", "gait "};
// res = sport_client.GetState(state_name, state_map);
// std::cout << "Speed level: " << state_map["speedLevel"] << ", Gait: " << state_map["gait"] << std::endl;
}
else if (test_option.id == 8)
{
res = sport_client.RecoveryStand();
}
else if (test_option.id == 9)
{
res = sport_client.BalanceStand();
}
if (res < 0)
{
res_count += 1;
std::cout << "Request error for: " << option_list[test_option.id].name << ", code: " << res << ", count: " << res_count << std::endl;
}
else
{
res_count = 0;
std::cout << "Request successed: " << option_list[test_option.id].name << ", code: " << res << std::endl;
}
std::this_thread::sleep_until(time_start_trick + dt);
}
return 0;
}

View File

@ -0,0 +1,370 @@
#include <iostream>
#include <stdio.h>
#include <stdint.h>
#include <math.h>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
#include <unitree/idl/go2/LowState_.hpp>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/common/time/time_tool.hpp>
#include <unitree/common/thread/thread.hpp>
#include <unitree/robot/b2/motion_switcher/motion_switcher_client.hpp>
using namespace unitree::common;
using namespace unitree::robot;
using namespace unitree::robot::b2;
#define TOPIC_LOWCMD "rt/lowcmd"
#define TOPIC_LOWSTATE "rt/lowstate"
constexpr double PosStopF = (2.146E+9f);
constexpr double VelStopF = (16000.0f);
class Custom
{
public:
explicit Custom(){}
~Custom(){}
void Init();
void Start();
private:
void InitLowCmd();
void LowStateMessageHandler(const void* messages);
void LowCmdWrite();
int queryMotionStatus();
std::string queryServiceName(std::string form,std::string name);
private:
float Kp = 70.0;
float Kd = 5.0;
double time_consume = 0;
int rate_count = 0;
int sin_count = 0;
int motiontime = 0;
float dt = 0.002; // 0.001~0.01
MotionSwitcherClient msc;
unitree_go::msg::dds_::LowCmd_ low_cmd{}; // default init
unitree_go::msg::dds_::LowState_ low_state{}; // default init
/*publisher*/
ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_> lowcmd_publisher;
/*subscriber*/
ChannelSubscriberPtr<unitree_go::msg::dds_::LowState_> lowstate_subscriber;
/*LowCmd write thread*/
ThreadPtr lowCmdWriteThreadPtr;
float _targetPos_1[12] = {0.0, 1.36, -2.65, 0.0, 1.36, -2.65,
-0.2, 1.36, -2.65, 0.2, 1.36, -2.65};
float _targetPos_2[12] = {0.0, 0.67, -1.3, 0.0, 0.67, -1.3,
0.0, 0.67, -1.3, 0.0, 0.67, -1.3};
float _targetPos_3[12] = {-0.35, 1.36, -2.65, 0.35, 1.36, -2.65,
-0.5, 1.36, -2.65, 0.5, 1.36, -2.65};
float _startPos[12];
float _duration_1 = 500;
float _duration_2 = 500;
float _duration_3 = 2000;
float _duration_4 = 900;
float _percent_1 = 0;
float _percent_2 = 0;
float _percent_3 = 0;
float _percent_4 = 0;
bool firstRun = true;
bool done = false;
};
uint32_t crc32_core(uint32_t* ptr, uint32_t len)
{
unsigned int xbit = 0;
unsigned int data = 0;
unsigned int CRC32 = 0xFFFFFFFF;
const unsigned int dwPolynomial = 0x04c11db7;
for (unsigned int i = 0; i < len; i++)
{
xbit = 1 << 31;
data = ptr[i];
for (unsigned int bits = 0; bits < 32; bits++)
{
if (CRC32 & 0x80000000)
{
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
}
else
{
CRC32 <<= 1;
}
if (data & xbit)
CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
}
void Custom::Init()
{
InitLowCmd();
/*create publisher*/
lowcmd_publisher.reset(new ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(TOPIC_LOWCMD));
lowcmd_publisher->InitChannel();
/*create subscriber*/
lowstate_subscriber.reset(new ChannelSubscriber<unitree_go::msg::dds_::LowState_>(TOPIC_LOWSTATE));
lowstate_subscriber->InitChannel(std::bind(&Custom::LowStateMessageHandler, this, std::placeholders::_1), 1);
/*init MotionSwitcherClient*/
msc.SetTimeout(10.0f);
msc.Init();
/*Shut down motion control-related service*/
while(queryMotionStatus())
{
std::cout << "Try to deactivate the motion control-related service." << std::endl;
int32_t ret = msc.ReleaseMode();
if (ret == 0) {
std::cout << "ReleaseMode succeeded." << std::endl;
} else {
std::cout << "ReleaseMode failed. Error code: " << ret << std::endl;
}
sleep(5);
}
}
void Custom::InitLowCmd()
{
low_cmd.head()[0] = 0xFE;
low_cmd.head()[1] = 0xEF;
low_cmd.level_flag() = 0xFF;
low_cmd.gpio() = 0;
for(int i=0; i<20; i++)
{
low_cmd.motor_cmd()[i].mode() = (0x01); // motor switch to servo (PMSM) mode
low_cmd.motor_cmd()[i].q() = (PosStopF);
low_cmd.motor_cmd()[i].kp() = (0);
low_cmd.motor_cmd()[i].dq() = (VelStopF);
low_cmd.motor_cmd()[i].kd() = (0);
low_cmd.motor_cmd()[i].tau() = (0);
}
}
int Custom::queryMotionStatus()
{
std::string robotForm,motionName;
int motionStatus;
int32_t ret = msc.CheckMode(robotForm,motionName);
if (ret == 0) {
std::cout << "CheckMode succeeded." << std::endl;
} else {
std::cout << "CheckMode failed. Error code: " << ret << std::endl;
}
if(motionName.empty())
{
std::cout << "The motion control-related service is deactivated." << std::endl;
motionStatus = 0;
}
else
{
std::string serviceName = queryServiceName(robotForm,motionName);
std::cout << "Service: "<< serviceName<< " is activate" << std::endl;
motionStatus = 1;
}
return motionStatus;
}
std::string Custom::queryServiceName(std::string form,std::string name)
{
if(form == "0")
{
if(name == "normal" ) return "sport_mode";
if(name == "ai" ) return "ai_sport";
if(name == "advanced" ) return "advanced_sport";
}
else
{
if(name == "ai-w" ) return "wheeled_sport(go2W)";
if(name == "normal-w" ) return "wheeled_sport(b2W)";
}
return "";
}
void Custom::Start()
{
/*loop publishing thread*/
lowCmdWriteThreadPtr = CreateRecurrentThreadEx("writebasiccmd", UT_CPU_ID_NONE, 2000, &Custom::LowCmdWrite, this);
}
void Custom::LowStateMessageHandler(const void* message)
{
low_state = *(unitree_go::msg::dds_::LowState_*)message;
}
void Custom::LowCmdWrite()
{
if(_percent_4<1)
{
std::cout<<"Read sensor data example: "<<std::endl;
std::cout<<"Joint 0 pos: "<<low_state.motor_state()[0].q()<<std::endl;
std::cout<<"Imu accelerometer : "<<"x: "<<low_state.imu_state().accelerometer()[0]<<" y: "<<low_state.imu_state().accelerometer()[1]<<" z: "<<low_state.imu_state().accelerometer()[2]<<std::endl;
std::cout<<"Foot force "<<low_state.foot_force()[0]<<std::endl;
std::cout<<std::endl;
}
if((_percent_4 == 1) && ( done == false))
{
std::cout<<"The example is done! "<<std::endl;
std::cout<<std::endl;
done = true;
}
motiontime++;
if(motiontime>=500)
{
if(firstRun)
{
for(int i = 0; i < 12; i++)
{
_startPos[i] = low_state.motor_state()[i].q();
}
firstRun = false;
}
_percent_1 += (float)1 / _duration_1;
_percent_1 = _percent_1 > 1 ? 1 : _percent_1;
if (_percent_1 < 1)
{
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_1) * _startPos[j] + _percent_1 * _targetPos_1[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 < 1))
{
_percent_2 += (float)1 / _duration_2;
_percent_2 = _percent_2 > 1 ? 1 : _percent_2;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_2) * _targetPos_1[j] + _percent_2 * _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3<1))
{
_percent_3 += (float)1 / _duration_3;
_percent_3 = _percent_3 > 1 ? 1 : _percent_3;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = _targetPos_2[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
if(_percent_3<0.4)
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = 3;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
else if((_percent_3>=0.4)&&(_percent_3<0.8))
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = -3;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
else if(_percent_3>=0.8)
{
for (int j = 12; j < 16; j++)
{
low_cmd.motor_cmd()[j].q() = 0;
low_cmd.motor_cmd()[j].kp() = 0;
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
}
if ((_percent_1 == 1)&&(_percent_2 == 1)&&(_percent_3==1)&&((_percent_4<=1)))
{
_percent_4 += (float)1 / _duration_4;
_percent_4 = _percent_4 > 1 ? 1 : _percent_4;
for (int j = 0; j < 12; j++)
{
low_cmd.motor_cmd()[j].q() = (1 - _percent_4) * _targetPos_2[j] + _percent_4 * _targetPos_3[j];
low_cmd.motor_cmd()[j].dq() = 0;
low_cmd.motor_cmd()[j].kp() = Kp;
low_cmd.motor_cmd()[j].kd() = Kd;
low_cmd.motor_cmd()[j].tau() = 0;
}
}
low_cmd.crc() = crc32_core((uint32_t *)&low_cmd, (sizeof(unitree_go::msg::dds_::LowCmd_)>>2)-1);
lowcmd_publisher->Write(low_cmd);
}
}
int main(int argc, const char** argv)
{
if (argc < 2)
{
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
std::cout << "WARNING: Make sure the robot is hung up or lying on the ground." << std::endl
<< "Press Enter to continue..." << std::endl;
std::cin.ignore();
ChannelFactory::Instance()->Init(0, argv[1]);
Custom custom;
custom.Init();
custom.Start();
while (1)
{
sleep(10);
}
return 0;
}

View File

@ -0,0 +1,18 @@
add_executable(h1_loco_client high_level/h1_loco_client_example.cpp)
target_link_libraries(h1_loco_client unitree_sdk2)
add_executable(h1_low_level_example low_level/humanoid.cpp)
target_link_libraries(h1_low_level_example unitree_sdk2)
add_executable(h1_27dof_example low_level/h1_27dof_example.cpp)
target_link_libraries(h1_27dof_example unitree_sdk2)
add_executable(h1_2_ankle_track low_level/h1_2_ankle_track.cpp)
target_link_libraries(h1_2_ankle_track unitree_sdk2)
add_executable(h1_arm_sdk_dds_example high_level/h1_arm_sdk_dds_example.cpp)
target_link_libraries(h1_arm_sdk_dds_example unitree_sdk2)
add_executable(h1_2_arm_sdk_dds_example high_level/h1_2_arm_sdk_dds_example.cpp)
target_link_libraries(h1_2_arm_sdk_dds_example unitree_sdk2)

111
deps/unitree_sdk2/example/h1/README.md vendored Normal file
View File

@ -0,0 +1,111 @@
# Unitree H1_2 Parallel Mechanism Control
English | [简体中文](README_zh.md)
## Parallel Mechanism Control Interface
The Unitree H1_2 robot's parallel mechanism involves the ankle joints of its left and right legs. Since the left and right ankle joints are symmetrical, the following explanation will use the H1_2 left ankle joint as an example:
<p align="center"><img src="doc/images/ankle.png" width="30%"/></p>
On the hardware side, the H1_2 left ankle joint uses a parallel mechanism consisting of four joints:
* Parallel joints: Joint A, Joint B
* Serial joints: Pitch joint (P joint), Roll joint (R joint)
Only the A and B joints can be directly driven by motors, while the P and R joints cannot be directly controlled. The robot's URDF model and motion control algorithms typically only consider the serial P and R joints. To control these joints, we control the A and B joints indirectly, which allows us to achieve control over the P and R joints. On the software side, we provide an equivalent serial joint control interface, called `PR Mode`, enabling users to directly control the P and R joints. Similar to the typical joint control method, in `PR Mode`, each serial joint receives the following commands:
| Command Name | Variable |
| ----------------------- | -------- |
| Feedforward Torque | `tau` |
| Target Angle | `q` |
| Target Angular Velocity | `dq` |
| Joint Stiffness | `kp` |
| Joint Damping | `kd` |
The total torque applied to the serial joint is calculated as `T = kp * (q - q_m) + kd * (dq - dq_m) + tau`. To improve the control precision of the serial joints, the H1_2 robot internally converts the feedforward torque, target angle, target angular velocity, joint stiffness, and joint damping commands for the P and R joints into actual commands for the A and B joints based on kinematic and dynamic relationships.
## Serial Joint Tracking Experiment
To test the performance of the H1_2 ankle in `PR Mode`, we have the P and R joints track a sinusoidal curve. You can refer to the [example](https://github.com/unitreerobotics/unitree_sdk2/blob/main/example/h1/low_level/h1_2_ankle_track.cpp). The core code is as follows:
**Enabling PR Mode and Generating Sinusoidal Curve**
```c++
// [Stage 2]: swing ankle's PR
mode_ = PR; // Enable PR mode
// generate sin/cos trajectory
double max_P = 0.25; // [rad]
double max_R = 0.25; // [rad]
double t = time_ - duration_;
double L_P_des = max_P * std::cos(2.0 * M_PI * t);
double L_R_des = max_R * std::sin(2.0 * M_PI * t);
double R_P_des = max_P * std::cos(2.0 * M_PI * t);
double R_R_des = -max_R * std::sin(2.0 * M_PI * t);
```
**Setting Ankle Joint Commands**
```c++
// update ankle joint position targets
float Kp_Pitch = 80;
float Kd_Pitch = 1;
float Kp_Roll = 80;
float Kd_Roll = 1;
dds_low_command.motor_cmd().at(4).q() = L_P_des; // 4: LeftAnklePitch
dds_low_command.motor_cmd().at(4).dq() = 0;
dds_low_command.motor_cmd().at(4).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(4).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(4).tau() = 0;
dds_low_command.motor_cmd().at(5).q() = L_R_des; // 5: LeftAnkleRoll
dds_low_command.motor_cmd().at(5).dq() = 0;
dds_low_command.motor_cmd().at(5).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(5).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(5).tau() = 0;
dds_low_command.motor_cmd().at(10).q() = R_P_des; // 10: RightAnklePitch
dds_low_command.motor_cmd().at(10).dq() = 0;
dds_low_command.motor_cmd().at(10).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(10).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(10).tau() = 0;
dds_low_command.motor_cmd().at(11).q() = R_R_des; // 11: RightAnkleRoll
dds_low_command.motor_cmd().at(11).dq() = 0;
dds_low_command.motor_cmd().at(11).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(11).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(11).tau() = 0;
```
**Printing Desired and Measured Values to Terminal**
```c++
float L_P_m = low_state_.motor_state().at(4).q();
float L_R_m = low_state_.motor_state().at(5).q();
float R_P_m = low_state_.motor_state().at(10).q();
float R_R_m = low_state_.motor_state().at(11).q();
printf("%f,%f,%f,%f,%f,%f,%f,%f\n", L_P_des, L_P_m, L_R_des, L_R_m, R_P_des, R_P_m, R_R_des, R_R_m);
```
| L_P_des | L_P_m | L_R_des | L_R_m | R_P_des | R_P_m | R_R_des | R_R_m |
| ------------------ | ------------------- | ----------------- | ------------------ | ------------------- | -------------------- | ------------------ | ------------------- |
| Left Pitch Desired | Left Pitch Measured | Left Roll Desired | Left Roll Measured | Right Pitch Desired | Right Pitch Measured | Right Roll Desired | Right Roll Measured |
To install and compile [unitree_sdk2](https://github.com/unitreerobotics/unitree_sdk2), ensure that the robot is **suspended first**, then run the test routine in the terminal:
```bash
h1_2_ankle_track network_interface
```
Once started, the robot will first reset to the zero position, then periodically swing its ankles while printing the desired and measured values for both ankle joints. The position tracking results are shown below:
<p float="middle">
<img src="doc/images/tracking.png" width="49%"/>
<img src="doc/images/tracking_circle.png" width="49%"/>
</p>
Definitions of the symbols in the figures:
* `L_Pitch_d`: Desired value of the left ankle's P joint
* `L_Pitch_m`: Measured value of the left ankle's P joint
* `L_Roll_d`: Desired value of the left ankle's R joint
* `L_Roll_m`: Measured value of the left ankle's R joint
The left graph shows that the serial Pitch and Roll joints can accurately track the sinusoidal target position commands, while the right graph illustrates the tracking performance of the serial joints in phase space.

View File

@ -0,0 +1,111 @@
# Unitree H1_2 并联机构控制
[English](README.md) | 简体中文
## 并联机构控制接口
Unitree H1_2 机器人并联机构涉及机器人的左右腿的脚踝。因左右脚踝对称,故下面以 H1_2 左脚踝关节为例:
<p align="center"><img src="doc/images/ankle.png" width="30%"/></p>
硬件上H1_2 左脚踝关节采用并联机构,包括四个关节:
* 并联关节A 关节、B 关节
* 串联关节Pitch 关节 (简称 P 关节)、Roll 关节 (简称 R 关)
其中只有 A、B 关节是可被电机直接驱动的关节P、R 关节不能被直接控制。而机器人 URDF 模型和运动控制算法通常只考虑 P、R 串联关节。为了实现对 P、R 关节的控制,我们通过控制 A、B 关节从而间接实现对 P、R 关节的控制。具体到软件上,我们为用户提供了等价的串联关节控制接口,即 `PR 模式`,让用户能直接控制 P、R 关节。与普通关节控制方法一样,`PR 模式` 下每个串联关节接收以下指令:
| 指令名称 | 变量 |
| ---------- | ----- |
| 前馈力矩 | `tau` |
| 目标角度 | `q` |
| 目标角速度 | `dq` |
| 关节刚度 | `kp` |
| 关节阻尼 | `kd` |
最终串联关节执行总的力矩为 `T = kp * (q - q_m) + kd * (dq - dq_m) + tau`。为了提高串联关节控制精度H1_2 机器人内部根据运动学和动力学关系,把 P、R 关节的前馈力矩、目标角度、目标角速度、关节刚度和关节阻尼指令转换为 A、B 实际关节执行单元。
## 串联关节跟踪实验
为测试 H1_2 脚踝 `PR 模式` 控制效果,我们让脚踝 P、R 关节跟踪正弦曲线,参考[测试例程](https://github.com/unitreerobotics/unitree_sdk2/blob/main/example/h1/low_level/h1_2_ankle_track.cpp)。核心代码段如下:
**启用 PR 模式并生成正弦曲线**
```c++
// [Stage 2]: swing ankle's PR
mode_ = PR; // Enable PR mode
// generate sin/cos trajectory
double max_P = 0.25; // [rad]
double max_R = 0.25; // [rad]
double t = time_ - duration_;
double L_P_des = max_P * std::cos(2.0 * M_PI * t);
double L_R_des = max_R * std::sin(2.0 * M_PI * t);
double R_P_des = max_P * std::cos(2.0 * M_PI * t);
double R_R_des = -max_R * std::sin(2.0 * M_PI * t);
```
**设置踝关节指令**
```c++
// update ankle joint position targets
float Kp_Pitch = 80;
float Kd_Pitch = 1;
float Kp_Roll = 80;
float Kd_Roll = 1;
dds_low_command.motor_cmd().at(4).q() = L_P_des; // 4: LeftAnklePitch
dds_low_command.motor_cmd().at(4).dq() = 0;
dds_low_command.motor_cmd().at(4).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(4).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(4).tau() = 0;
dds_low_command.motor_cmd().at(5).q() = L_R_des; // 5: LeftAnkleRoll
dds_low_command.motor_cmd().at(5).dq() = 0;
dds_low_command.motor_cmd().at(5).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(5).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(5).tau() = 0;
dds_low_command.motor_cmd().at(10).q() = R_P_des; // 10: RightAnklePitch
dds_low_command.motor_cmd().at(10).dq() = 0;
dds_low_command.motor_cmd().at(10).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(10).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(10).tau() = 0;
dds_low_command.motor_cmd().at(11).q() = R_R_des; // 11: RightAnkleRoll
dds_low_command.motor_cmd().at(11).dq() = 0;
dds_low_command.motor_cmd().at(11).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(11).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(11).tau() = 0;
```
**打印期望值和测量值到终端**
```c++
float L_P_m = low_state_.motor_state().at(4).q();
float L_R_m = low_state_.motor_state().at(5).q();
float R_P_m = low_state_.motor_state().at(10).q();
float R_R_m = low_state_.motor_state().at(11).q();
printf("%f,%f,%f,%f,%f,%f,%f,%f\n", L_P_des, L_P_m, L_R_des, L_R_m, R_P_des, R_P_m, R_R_des, R_R_m);
```
| L_P_des | L_P_m | L_R_des | L_R_m | R_P_des | R_P_m | R_R_des | R_R_m |
| ----------------- | ----------------- | ---------------- | ---------------- | ----------------- | ----------------- | ---------------- | ---------------- |
| 左脚 Pitch 期望值 | 左脚 Pitch 测量值 | 左脚 Roll 期望值 | 左脚 Roll 测量值 | 右脚 Pitch 期望值 | 右脚 Pitch 测量值 | 右脚 Roll 期望值 | 右脚 Roll 测量值 |
安装并编译 [unitree_sdk2](https://github.com/unitreerobotics/unitree_sdk2),务必先把机器人**悬挂起来**,然后终端运行测试例程:
```bash
h1_2_ankle_track network_interface
```
启动后,机器人会先恢复到零位,然后周期性摆动脚踝,并打印左右踝关节期望值和测量值,其位置跟踪效果如图:
<p float="middle">
<img src="doc/images/tracking.png" width="49%"/>
<img src="doc/images/tracking_circle.png" width="49%"/>
</p>
图中符号定义:
* `L_Pitch_d`:左脚踝 P 关节期望值
* `L_Pitch_m`:左脚踝 P 关节测量值
* `L_Roll_d`:左脚踝 R 关节期望值
* `L_Roll_m`:左脚踝 R 关节测量值
左图表示串联 Pitch、Roll 关节能较准确地跟踪正弦曲线目标位置指令;右图表示串联关节在相空间中的跟踪效果。

Binary file not shown.

After

Width:  |  Height:  |  Size: 239 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 126 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 66 KiB

View File

@ -0,0 +1,259 @@
#include <array>
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
static const std::string kTopicArmSDK = "rt/arm_sdk";
static const std::string kTopicState = "rt/lowstate";
constexpr float kPi = 3.141592654;
constexpr float kPi_2 = 1.57079632;
enum JointIndex {
// Left leg
kLeftHipYaw = 0,
kLeftHipPitch = 1,
kLeftHipRoll = 2,
kLeftKnee = 3,
kLeftAnkle = 4,
kLeftAnkleRoll = 5,
// Right leg
kRightHipYaw = 6,
kRightHipPitch = 7,
kRightHipRoll = 8,
kRightKnee = 9,
kRightAnkle = 10,
kRightAnkleRoll = 11,
kWaistYaw = 12,
// Left arm
kLeftShoulderPitch = 13,
kLeftShoulderRoll = 14,
kLeftShoulderYaw = 15,
kLeftElbow = 16,
kLeftWristRoll = 17,
kLeftWristPitch = 18,
kLeftWristYaw = 19,
// Right arm
kRightShoulderPitch = 20,
kRightShoulderRoll = 21,
kRightShoulderYaw = 22,
kRightElbow = 23,
kRightWristRoll = 24,
kRightWristPitch = 25,
kRightWristYaw = 26,
kNotUsedJoint = 27,
kNotUsedJoint1 = 28,
kNotUsedJoint2 = 29,
kNotUsedJoint3 = 30,
kNotUsedJoint4 = 31,
kNotUsedJoint5 = 32,
kNotUsedJoint6 = 33,
kNotUsedJoint7 = 34
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_>
arm_sdk_publisher;
unitree_hg::msg::dds_::LowCmd_ msg;
arm_sdk_publisher.reset(
new unitree::robot::ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(
kTopicArmSDK));
arm_sdk_publisher->InitChannel();
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_>
low_state_subscriber;
// create subscriber
unitree_hg::msg::dds_::LowState_ state_msg;
low_state_subscriber.reset(
new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
kTopicState));
low_state_subscriber->InitChannel([&](const void *msg) {
auto s = ( const unitree_hg::msg::dds_::LowState_* )msg;
memcpy( &state_msg, s, sizeof( unitree_hg::msg::dds_::LowState_ ) );
}, 1);
std::array<JointIndex, 15> arm_joints = {
JointIndex::kLeftShoulderPitch, JointIndex::kLeftShoulderRoll,
JointIndex::kLeftShoulderYaw, JointIndex::kLeftElbow,
JointIndex::kLeftWristRoll, JointIndex::kLeftWristPitch, JointIndex::kLeftWristYaw,
JointIndex::kRightShoulderPitch, JointIndex::kRightShoulderRoll,
JointIndex::kRightShoulderYaw, JointIndex::kRightElbow,
JointIndex::kRightWristRoll, JointIndex::kRightWristPitch, JointIndex::kRightWristYaw,
JointIndex::kWaistYaw};
float weight = 0.f;
float weight_rate = 0.2f;
std::array<float, 15> kp_array = { 120, 120, 80, 50, 50, 50, 50,
120, 120, 80, 50, 50, 50, 50,
200 };
std::array<float, 15> kd_array = { 2.0, 2.0, 1.5, 1.0, 1.0, 1.0, 1.0,
2.0, 2.0, 1.5, 1.0, 1.0, 1.0, 1.0,
2.0 };
float dq = 0.f;
float tau_ff = 0.f;
float control_dt = 0.02f;
float max_joint_velocity = 0.5f;
float delta_weight = weight_rate * control_dt;
float max_joint_delta = max_joint_velocity * control_dt;
auto sleep_time =
std::chrono::milliseconds(static_cast<int>(control_dt / 0.001f));
// modify the initial position to avoid collision
std::array<float, 15> init_pos{0.f, 0.3, 0.f, 0, 0, 0, 0,
0.f, -0.3, 0.f, 0, 0, 0, 0,
0.f};
std::array<float, 15> target_pos = {0.f, kPi_2, 0.f, kPi_2, 0, 0, 0,
0.f, -kPi_2, 0.f, kPi_2, 0, 0, 0,
0.f};
// wait for init
std::cout << "Press ENTER to init arms ...";
std::cin.get();
// get current joint position
std::array<float, 15> current_jpos{};
std::cout<<"Current joint position: ";
for (int i = 0; i < arm_joints.size(); ++i) {
current_jpos.at(i) = state_msg.motor_state().at(arm_joints.at(i)).q();
std::cout << current_jpos.at(i) << " ";
}
std::cout << std::endl;
// set init pos
std::cout << "Initailizing arms ...";
float init_time = 2.0f;
int init_time_steps = static_cast<int>(init_time / control_dt);
for (int i = 0; i < init_time_steps; ++i) {
// set weight
weight = 1.0;
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
float phase = 1.0 * i / init_time_steps;
std::cout << "Phase: " << phase << std::endl;
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(init_pos.at(j) * phase + current_jpos.at(j) * (1 - phase));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).kd(kd_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
// wait for control
std::cout << "Press ENTER to start arm ctrl ..." << std::endl;
std::cin.get();
// start control
std::cout << "Start arm ctrl!" << std::endl;
float period = 5.f;
int num_time_steps = static_cast<int>(period / control_dt);
std::array<float, 15> current_jpos_des{0.f, 0.3, 0.f, 0, 0, 0, 0,
0.f, -0.3, 0.f, 0, 0, 0, 0,
0.f};
// lift arms up
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(target_pos.at(j) - current_jpos_des.at(j),
-max_joint_delta, max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).kd(kd_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// put arms down
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(init_pos.at(j) - current_jpos_des.at(j), -max_joint_delta,
max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).kd(kd_array.at(j));
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// stop control
std::cout << "Stoping arm ctrl ...";
float stop_time = 2.0f;
int stop_time_steps = static_cast<int>(stop_time / control_dt);
for (int i = 0; i < stop_time_steps; ++i) {
// increase weight
weight -= delta_weight;
weight = std::clamp(weight, 0.f, 1.f);
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
return 0;
}

View File

@ -0,0 +1,234 @@
#include <array>
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/idl/go2/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
static const std::string kTopicArmSDK = "rt/arm_sdk";
static const std::string kTopicState = "rt/lowstate";
constexpr float kPi = 3.141592654;
constexpr float kPi_2 = 1.57079632;
enum JointIndex {
// Right leg
kRightHipYaw = 8,
kRightHipRoll = 0,
kRightHipPitch = 1,
kRightKnee = 2,
kRightAnkle = 11,
// Left leg
kLeftHipYaw = 7,
kLeftHipRoll = 3,
kLeftHipPitch = 4,
kLeftKnee = 5,
kLeftAnkle = 10,
kWaistYaw = 6,
kNotUsedJoint = 9,
// Right arm
kRightShoulderPitch = 12,
kRightShoulderRoll = 13,
kRightShoulderYaw = 14,
kRightElbow = 15,
// Left arm
kLeftShoulderPitch = 16,
kLeftShoulderRoll = 17,
kLeftShoulderYaw = 18,
kLeftElbow = 19,
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: " << argv[0] << " networkInterface" << std::endl;
exit(-1);
}
unitree::robot::ChannelFactory::Instance()->Init(0, argv[1]);
unitree::robot::ChannelPublisherPtr<unitree_go::msg::dds_::LowCmd_>
arm_sdk_publisher;
unitree_go::msg::dds_::LowCmd_ msg;
arm_sdk_publisher.reset(
new unitree::robot::ChannelPublisher<unitree_go::msg::dds_::LowCmd_>(
kTopicArmSDK));
arm_sdk_publisher->InitChannel();
unitree::robot::ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_>
low_state_subscriber;
// create subscriber
unitree_hg::msg::dds_::LowState_ state_msg;
low_state_subscriber.reset(
new unitree::robot::ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
kTopicState));
low_state_subscriber->InitChannel([&](const void *msg) {
auto s = ( const unitree_hg::msg::dds_::LowState_* )msg;
memcpy( &state_msg, s, sizeof( unitree_hg::msg::dds_::LowState_ ) );
}, 1);
std::array<JointIndex, 9> arm_joints = {
JointIndex::kLeftShoulderPitch, JointIndex::kLeftShoulderRoll,
JointIndex::kLeftShoulderYaw, JointIndex::kLeftElbow,
JointIndex::kRightShoulderPitch, JointIndex::kRightShoulderRoll,
JointIndex::kRightShoulderYaw, JointIndex::kRightElbow, JointIndex::kWaistYaw};
float weight = 0.f;
float weight_rate = 0.2f;
float kp = 60.f;
float kd = 1.5f;
float dq = 0.f;
float tau_ff = 0.f;
float control_dt = 0.02f;
float max_joint_velocity = 0.5f;
float delta_weight = weight_rate * control_dt;
float max_joint_delta = max_joint_velocity * control_dt;
auto sleep_time =
std::chrono::milliseconds(static_cast<int>(control_dt / 0.001f));
std::array<float, 9> init_pos{0, 0, 0, 0,
0, 0, 0, 0,
0};
std::array<float, 9> target_pos = {0.f, kPi_2, 0.f, kPi_2,
0.f, -kPi_2, 0.f, kPi_2,
0.f};
// wait for init
std::cout << "Press ENTER to init arms ...";
std::cin.get();
// get current joint position
std::array<float, 9> current_jpos{};
std::cout<<"Current joint position: ";
for (int i = 0; i < arm_joints.size(); ++i) {
current_jpos.at(i) = state_msg.motor_state().at(arm_joints.at(i)).q();
std::cout << current_jpos.at(i) << " ";
}
std::cout << std::endl;
// set init pos
std::cout << "Initailizing arms ...";
float init_time = 2.0f;
int init_time_steps = static_cast<int>(init_time / control_dt);
for (int i = 0; i < init_time_steps; ++i) {
// set weight
weight = 1.0;
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
float phase = 1.0 * i / init_time_steps;
std::cout << "Phase: " << phase << std::endl;
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(init_pos.at(j) * phase + current_jpos.at(j) * (1 - phase));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
// wait for control
std::cout << "Press ENTER to start arm ctrl ..." << std::endl;
std::cin.get();
// start control
std::cout << "Start arm ctrl!" << std::endl;
float period = 5.f;
int num_time_steps = static_cast<int>(period / control_dt);
std::array<float, 9> current_jpos_des{};
// lift arms up
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(target_pos.at(j) - current_jpos_des.at(j),
-max_joint_delta, max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// put arms down
for (int i = 0; i < num_time_steps; ++i) {
// update jpos des
for (int j = 0; j < init_pos.size(); ++j) {
current_jpos_des.at(j) +=
std::clamp(init_pos.at(j) - current_jpos_des.at(j), -max_joint_delta,
max_joint_delta);
}
// set control joints
for (int j = 0; j < init_pos.size(); ++j) {
msg.motor_cmd().at(arm_joints.at(j)).q(current_jpos_des.at(j));
msg.motor_cmd().at(arm_joints.at(j)).dq(dq);
msg.motor_cmd().at(arm_joints.at(j)).kp(kp);
msg.motor_cmd().at(arm_joints.at(j)).kd(kd);
msg.motor_cmd().at(arm_joints.at(j)).tau(tau_ff);
}
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
// stop control
std::cout << "Stoping arm ctrl ...";
float stop_time = 2.0f;
int stop_time_steps = static_cast<int>(stop_time / control_dt);
for (int i = 0; i < stop_time_steps; ++i) {
// increase weight
weight -= delta_weight;
weight = std::clamp(weight, 0.f, 1.f);
// set weight
msg.motor_cmd().at(JointIndex::kNotUsedJoint).q(weight);
// send dds msg
arm_sdk_publisher->Write(msg);
// sleep
std::this_thread::sleep_for(sleep_time);
}
std::cout << "Done!" << std::endl;
return 0;
}

View File

@ -0,0 +1,300 @@
#include <chrono>
#include <iostream>
#include <thread>
#include <unitree/robot/h1/loco/h1_loco_api.hpp>
#include <unitree/robot/h1/loco/h1_loco_client.hpp>
std::vector<float> stringToFloatVector(const std::string &str) {
std::vector<float> result;
std::stringstream ss(str);
float num;
while (ss >> num) {
result.push_back(num);
// ignore any trailing whitespace
ss.ignore();
}
return result;
}
int main(int argc, char const *argv[]) {
std::map<std::string, std::string> args = {{"network_interface", "lo"}};
std::map<std::string, std::string> values;
for (int i = 1; i < argc; ++i) {
std::string arg = argv[i];
if (arg.substr(0, 2) == "--") {
size_t pos = arg.find("=");
std::string key, value;
if (pos != std::string::npos) {
key = arg.substr(2, pos - 2);
value = arg.substr(pos + 1);
if (value.front() == '"' && value.back() == '"') {
value = value.substr(1, value.length() - 2);
}
} else {
key = arg.substr(2);
value = "";
}
if (args.find(key) != args.end()) {
args[key] = value;
} else {
args.insert({{key, value}});
}
}
}
unitree::robot::ChannelFactory::Instance()->Init(0, args["network_interface"]);
unitree::robot::h1::LocoClient client;
client.Init();
client.SetTimeout(10.f);
for (const auto &arg_pair : args) {
std::cout << "Processing command: [" << arg_pair.first << "] with param: [" << arg_pair.second << "] ..."
<< std::endl;
if (arg_pair.first == "network_interface") {
continue;
}
if (arg_pair.first == "get_fsm_id") {
int fsm_id;
client.GetFsmId(fsm_id);
std::cout << "current fsm_id: " << fsm_id << std::endl;
}
if (arg_pair.first == "get_fsm_mode") {
int fsm_mode;
client.GetFsmMode(fsm_mode);
std::cout << "current fsm_mode: " << fsm_mode << std::endl;
}
if (arg_pair.first == "get_balance_mode") {
int balance_mode;
client.GetBalanceMode(balance_mode);
std::cout << "current balance_mode: " << balance_mode << std::endl;
}
if (arg_pair.first == "get_swing_height") {
float swing_height;
client.GetSwingHeight(swing_height);
std::cout << "current swing_height: " << swing_height << std::endl;
}
if (arg_pair.first == "get_stand_height") {
float stand_height;
client.GetStandHeight(stand_height);
std::cout << "current stand_height: " << stand_height << std::endl;
}
if (arg_pair.first == "get_phase") {
std::vector<float> phase;
client.GetPhase(phase);
std::cout << "current phase: (";
for (const auto &p : phase) {
std::cout << p << ", ";
}
std::cout << ")" << std::endl;
}
if (arg_pair.first == "enable_odom") {
float x, y, yaw;
client.EnableOdom();
std::cout << "Send enable odom signal" << std::endl;
}
if (arg_pair.first == "disable_odom") {
float x, y, yaw;
client.DisableOdom();
std::cout << "Send disable odom signal" << std::endl;
}
if (arg_pair.first == "get_odom") {
float x, y, yaw;
client.GetOdom(x, y, yaw);
std::cout << "Get Odom: (" << x << ", " << y << ", " << yaw << ")" << std::endl;
}
if (arg_pair.first == "set_fsm_id") {
int fsm_id = std::stoi(arg_pair.second);
client.SetFsmId(fsm_id);
std::cout << "set fsm_id to " << fsm_id << std::endl;
}
if (arg_pair.first == "set_balance_mode") {
int balance_mode = std::stoi(arg_pair.second);
client.SetBalanceMode(balance_mode);
std::cout << "set balance_mode to " << balance_mode << std::endl;
}
if (arg_pair.first == "set_swing_height") {
float swing_height = std::stof(arg_pair.second);
client.SetSwingHeight(swing_height);
std::cout << "set swing_height to " << swing_height << std::endl;
}
if (arg_pair.first == "set_stand_height") {
float stand_height = std::stof(arg_pair.second);
client.SetStandHeight(stand_height);
std::cout << "set stand_height to " << stand_height << std::endl;
}
if (arg_pair.first == "set_velocity") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
auto param_size = param.size();
float vx, vy, omega, duration;
if (param_size == 3) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
duration = 1.f;
} else if (param_size == 4) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
duration = param.at(3);
} else {
std::cerr << "Invalid param size for method SetVelocity: " << param_size << std::endl;
return 1;
}
client.SetVelocity(vx, vy, omega, duration);
std::cout << "set velocity to " << arg_pair.second << std::endl;
}
if (arg_pair.first == "set_phase") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
auto param_size = param.size();
if (param_size == 2) {
client.SetPhase(param);
std::cout << "set phase to " << arg_pair.second << std::endl;
} else {
std::cerr << "Invalid param size for method SetPhase: " << param_size << std::endl;
return 1;
}
}
if (arg_pair.first == "set_target_pos") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
client.SetTargetPos(param.at(0), param.at(1), param.at(2), false);
std::cout << "set_target_pos: " << arg_pair.second << std::endl;
}
if (arg_pair.first == "set_target_pos_relative") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
client.SetTargetPos(param.at(0), param.at(1), param.at(2));
std::cout << "set_target_pos: " << arg_pair.second << std::endl;
}
if (arg_pair.first == "damp") {
client.Damp();
}
if (arg_pair.first == "start") {
client.Start();
}
if (arg_pair.first == "stand_up") {
client.StandUp();
}
if (arg_pair.first == "zero_torque") {
client.ZeroTorque();
}
if (arg_pair.first == "stop_move") {
client.StopMove();
}
if (arg_pair.first == "high_stand") {
client.HighStand();
}
if (arg_pair.first == "low_stand") {
client.LowStand();
}
if (arg_pair.first == "balance_stand") {
client.BalanceStand();
}
if (arg_pair.first == "continous_gait") {
bool flag;
if (arg_pair.second == "true") {
flag = true;
} else if (arg_pair.second == "false") {
flag = false;
} else {
std::cerr << "invalid argument: " << arg_pair.second << std::endl;
return 1;
}
client.ContinuousGait(flag);
}
if (arg_pair.first == "switch_move_mode") {
bool flag;
if (arg_pair.second == "true") {
flag = true;
} else if (arg_pair.second == "false") {
flag = false;
} else {
std::cerr << "invalid argument: " << arg_pair.second << std::endl;
return 1;
}
client.SwitchMoveMode(flag);
}
if (arg_pair.first == "move") {
std::vector<float> param = stringToFloatVector(arg_pair.second);
auto param_size = param.size();
float vx, vy, omega;
if (param_size == 3) {
vx = param.at(0);
vy = param.at(1);
omega = param.at(2);
} else {
std::cerr << "Invalid param size for method SetVelocity: " << param_size << std::endl;
return 1;
}
client.Move(vx, vy, omega);
}
if (arg_pair.first == "set_next_foot") {
bool flag;
if (arg_pair.second == "0") {
flag = true;
} else if (arg_pair.second == "1") {
flag = false;
} else {
std::cerr << "invalid argument: " << arg_pair.second << std::endl;
return 1;
}
client.SetNextFoot(flag);
}
if (arg_pair.first == "set_task_id") {
int task_id = std::stoi(arg_pair.second);
client.SetTaskId(task_id);
std::cout << "set task_id to " << task_id << std::endl;
}
if (arg_pair.first == "shake_hand") {
client.ShakeHand(0);
std::cout << "Shake hand starts! Waiting for 10 s for ending" << std::endl;
std::this_thread::sleep_for(std::chrono::seconds(10));
std::cout << "Shake hand ends!" << std::endl;
client.ShakeHand(1);
}
if (arg_pair.first == "wave_hand") {
client.WaveHand();
std::cout << "wave hand" << std::endl;
}
std::cout << "Done!" << std::endl;
}
return 0;
}

View File

@ -0,0 +1,8 @@
#pragma once
#include <array>
struct BaseState {
std::array<float, 3> rpy = {};
std::array<float, 3> omega = {};
};

View File

@ -0,0 +1,28 @@
#pragma once
#include <deque>
#include <memory>
#include <mutex>
#include <shared_mutex>
template <typename T> class DataBuffer {
public:
void SetData(const T &newData) {
std::unique_lock<std::shared_mutex> lock(mutex);
data = std::make_shared<T>(newData);
}
std::shared_ptr<const T> GetData() {
std::shared_lock<std::shared_mutex> lock(mutex);
return data ? data : nullptr;
}
void Clear() {
std::unique_lock<std::shared_mutex> lock(mutex);
data = nullptr;
}
private:
std::shared_ptr<T> data;
std::shared_mutex mutex;
};

View File

@ -0,0 +1,367 @@
#include <algorithm>
#include <cmath>
#include <memory>
#include <mutex>
#include <shared_mutex>
// DDS
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
// IDL
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
static const std::string HG_CMD_TOPIC = "rt/lowcmd";
static const std::string HG_STATE_TOPIC = "rt/lowstate";
using namespace unitree::common;
using namespace unitree::robot;
const int H1_NUM_MOTOR = 27;
template <typename T>
class DataBuffer {
public:
void SetData(const T &newData) {
std::unique_lock<std::shared_mutex> lock(mutex);
data = std::make_shared<T>(newData);
}
std::shared_ptr<const T> GetData() {
std::shared_lock<std::shared_mutex> lock(mutex);
return data ? data : nullptr;
}
void Clear() {
std::unique_lock<std::shared_mutex> lock(mutex);
data = nullptr;
}
private:
std::shared_ptr<T> data;
std::shared_mutex mutex;
};
struct ImuState {
std::array<float, 3> rpy = {};
std::array<float, 3> omega = {};
};
struct MotorCommand {
std::array<float, H1_NUM_MOTOR> q_target = {};
std::array<float, H1_NUM_MOTOR> dq_target = {};
std::array<float, H1_NUM_MOTOR> kp = {};
std::array<float, H1_NUM_MOTOR> kd = {};
std::array<float, H1_NUM_MOTOR> tau_ff = {};
};
struct MotorState {
std::array<float, H1_NUM_MOTOR> q = {};
std::array<float, H1_NUM_MOTOR> dq = {};
};
enum MotorType { GearboxS = 0, GearboxM = 1, GearboxL = 2 };
std::array<MotorType, H1_NUM_MOTOR> H1MotorType{
// clang-format off
// legs
GearboxM, GearboxM, GearboxM, GearboxL, GearboxS, GearboxS,
GearboxM, GearboxM, GearboxM, GearboxL, GearboxS, GearboxS,
// waist
GearboxM,
// arms
GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS,
GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS, GearboxS
// clang-format on
};
enum PRorAB { PR = 0, AB = 1 };
enum H1JointIndex {
// legs
LeftHipYaw = 0,
LeftHipPitch = 1,
LeftHipRoll = 2,
LeftKnee = 3,
LeftAnklePitch = 4,
LeftAnkleB = 4,
LeftAnkleRoll = 5,
LeftAnkleA = 5,
RightHipYaw = 6,
RightHipPitch = 7,
RightHipRoll = 8,
RightKnee = 9,
RightAnklePitch = 10,
RightAnkleB = 10,
RightAnkleRoll = 11,
RightAnkleA = 11,
// torso
WaistYaw = 12,
// arms
LeftShoulderPitch = 13,
LeftShoulderRoll = 14,
LeftShoulderYaw = 15,
LeftElbow = 16,
LeftWristRoll = 17,
LeftWristPitch = 18,
LeftWristYaw = 19,
RightShoulderPitch = 20,
RightShoulderRoll = 21,
RightShoulderYaw = 22,
RightElbow = 23,
RightWristRoll = 24,
RightWristPitch = 25,
RightWristYaw = 26
};
inline uint32_t Crc32Core(uint32_t *ptr, uint32_t len) {
uint32_t xbit = 0;
uint32_t data = 0;
uint32_t CRC32 = 0xFFFFFFFF;
const uint32_t dwPolynomial = 0x04c11db7;
for (uint32_t i = 0; i < len; i++) {
xbit = 1 << 31;
data = ptr[i];
for (uint32_t bits = 0; bits < 32; bits++) {
if (CRC32 & 0x80000000) {
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
} else
CRC32 <<= 1;
if (data & xbit) CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
};
float GetMotorKp(MotorType type) {
switch (type) {
case GearboxS:
return 80;
case GearboxM:
return 100;
case GearboxL:
return 200;
default:
return 0;
}
}
float GetMotorKd(MotorType type) {
switch (type) {
case GearboxS:
return 2;
case GearboxM:
return 3;
case GearboxL:
return 5;
default:
return 0;
}
}
class H1Example {
private:
double time_;
double control_dt_; // [2ms]
double duration_; // [3 s]
PRorAB mode_;
uint8_t mode_machine_;
DataBuffer<MotorState> motor_state_buffer_;
DataBuffer<MotorCommand> motor_command_buffer_;
DataBuffer<ImuState> imu_state_buffer_;
ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_> lowcmd_publisher_;
ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_> lowstate_subscriber_;
ThreadPtr command_writer_ptr_, control_thread_ptr_;
public:
H1Example(std::string networkInterface)
: time_(0.0),
control_dt_(0.002),
duration_(3.0),
mode_(PR),
mode_machine_(0) {
ChannelFactory::Instance()->Init(0, networkInterface);
// create publisher
lowcmd_publisher_.reset(
new ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(HG_CMD_TOPIC));
lowcmd_publisher_->InitChannel();
// create subscriber
lowstate_subscriber_.reset(
new ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
HG_STATE_TOPIC));
lowstate_subscriber_->InitChannel(
std::bind(&H1Example::LowStateHandler, this, std::placeholders::_1), 1);
// create threads
command_writer_ptr_ =
CreateRecurrentThreadEx("command_writer", UT_CPU_ID_NONE, 2000,
&H1Example::LowCommandWriter, this);
control_thread_ptr_ = CreateRecurrentThreadEx(
"control", UT_CPU_ID_NONE, 2000, &H1Example::Control, this);
}
void ReportRPY() {
const std::shared_ptr<const ImuState> imu_tmp_ptr =
imu_state_buffer_.GetData();
if (imu_tmp_ptr) {
std::cout << "rpy: [" << imu_tmp_ptr->rpy.at(0) << ", "
<< imu_tmp_ptr->rpy.at(1) << ", " << imu_tmp_ptr->rpy.at(2)
<< "]" << std::endl;
}
}
void LowStateHandler(const void *message) {
unitree_hg::msg::dds_::LowState_ low_state =
*(const unitree_hg::msg::dds_::LowState_ *)message;
if (low_state.crc() !=
Crc32Core((uint32_t *)&low_state,
(sizeof(unitree_hg::msg::dds_::LowState_) >> 2) - 1)) {
std::cout << "low_state CRC Error" << std::endl;
return;
}
// get motor state
MotorState ms_tmp;
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
ms_tmp.q.at(i) = low_state.motor_state()[i].q();
ms_tmp.dq.at(i) = low_state.motor_state()[i].dq();
if (low_state.motor_state()[i].motorstate())
std::cout << "[ERROR] motor " << i << " with code "
<< low_state.motor_state()[i].motorstate() << "\n";
}
motor_state_buffer_.SetData(ms_tmp);
// get imu state
ImuState imu_tmp;
imu_tmp.omega = low_state.imu_state().gyroscope();
imu_tmp.rpy = low_state.imu_state().rpy();
imu_state_buffer_.SetData(imu_tmp);
// update mode machine
if (mode_machine_ != low_state.mode_machine()) {
if (mode_machine_ == 0)
std::cout << "G1 type: " << unsigned(low_state.mode_machine())
<< std::endl;
mode_machine_ = low_state.mode_machine();
}
}
void LowCommandWriter() {
unitree_hg::msg::dds_::LowCmd_ dds_low_command;
dds_low_command.mode_pr() = mode_;
dds_low_command.mode_machine() = mode_machine_;
const std::shared_ptr<const MotorCommand> mc =
motor_command_buffer_.GetData();
if (mc) {
for (size_t i = 0; i < H1_NUM_MOTOR; i++) {
dds_low_command.motor_cmd().at(i).mode() = 1; // 1:Enable, 0:Disable
dds_low_command.motor_cmd().at(i).tau() = mc->tau_ff.at(i);
dds_low_command.motor_cmd().at(i).q() = mc->q_target.at(i);
dds_low_command.motor_cmd().at(i).dq() = mc->dq_target.at(i);
dds_low_command.motor_cmd().at(i).kp() = mc->kp.at(i);
dds_low_command.motor_cmd().at(i).kd() = mc->kd.at(i);
}
dds_low_command.crc() = Crc32Core((uint32_t *)&dds_low_command,
(sizeof(dds_low_command) >> 2) - 1);
lowcmd_publisher_->Write(dds_low_command);
}
}
void Control() {
ReportRPY();
MotorCommand motor_command_tmp;
const std::shared_ptr<const MotorState> ms = motor_state_buffer_.GetData();
if (ms) {
time_ += control_dt_;
if (time_ < duration_ * 1) {
// [Stage 1]: set robot to zero posture
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
double ratio = std::clamp(time_ / duration_, 0.0, 1.0);
double q_des = 0;
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.q_target.at(i) =
(q_des - ms->q.at(i)) * ratio + ms->q.at(i);
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.kp.at(i) = GetMotorKp(H1MotorType[i]);
motor_command_tmp.kd.at(i) = GetMotorKd(H1MotorType[i]);
}
} else if (time_ < duration_ * 2) {
// [Stage 2]: swing ankle's PR
mode_ = PR;
double max_P = M_PI * 30.0 / 180.0;
double max_R = M_PI * 10.0 / 180.0;
double t = time_ - duration_ * 1;
double L_P_des = +max_P * std::sin(2.0 * M_PI * t);
double L_R_des = +max_R * std::sin(2.0 * M_PI * t);
double R_P_des = +max_P * std::sin(2.0 * M_PI * t);
double R_R_des = -max_R * std::sin(2.0 * M_PI * t);
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.q_target.at(i) = 0.0;
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.kp.at(i) = GetMotorKp(H1MotorType[i]);
motor_command_tmp.kd.at(i) = GetMotorKd(H1MotorType[i]);
}
motor_command_tmp.q_target.at(LeftAnklePitch) = L_P_des;
motor_command_tmp.q_target.at(LeftAnkleRoll) = L_R_des;
motor_command_tmp.q_target.at(RightAnklePitch) = R_P_des;
motor_command_tmp.q_target.at(RightAnkleRoll) = R_R_des;
} else {
// [Stage 3]: swing ankle's AB
mode_ = AB;
double max_A = M_PI * 30.0 / 180.0;
double max_B = M_PI * 10.0 / 180.0;
double t = time_ - duration_ * 2;
double L_A_des = +max_A * std::sin(M_PI * t);
double L_B_des = +max_B * std::sin(M_PI * t + M_PI);
double R_A_des = -max_A * std::sin(M_PI * t);
double R_B_des = -max_B * std::sin(M_PI * t + M_PI);
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
motor_command_tmp.tau_ff.at(i) = 0.0;
motor_command_tmp.q_target.at(i) = 0.0;
motor_command_tmp.dq_target.at(i) = 0.0;
motor_command_tmp.kp.at(i) = GetMotorKp(H1MotorType[i]);
motor_command_tmp.kd.at(i) = GetMotorKd(H1MotorType[i]);
}
motor_command_tmp.q_target.at(LeftAnkleA) = L_A_des;
motor_command_tmp.q_target.at(LeftAnkleB) = L_B_des;
motor_command_tmp.q_target.at(RightAnkleA) = R_A_des;
motor_command_tmp.q_target.at(RightAnkleB) = R_B_des;
}
motor_command_buffer_.SetData(motor_command_tmp);
}
}
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: h1_27dof_example network_interface_name" << std::endl;
exit(0);
}
std::string networkInterface = argv[1];
H1Example custom(networkInterface);
while (true) sleep(10);
return 0;
}

View File

@ -0,0 +1,175 @@
#include <cmath>
// DDS
#include <unitree/robot/channel/channel_publisher.hpp>
#include <unitree/robot/channel/channel_subscriber.hpp>
// IDL
#include <unitree/idl/hg/LowCmd_.hpp>
#include <unitree/idl/hg/LowState_.hpp>
static const std::string HG_CMD_TOPIC = "rt/lowcmd";
static const std::string HG_STATE_TOPIC = "rt/lowstate";
using namespace unitree::common;
using namespace unitree::robot;
const int H1_NUM_MOTOR = 27;
enum PRorAB { PR = 0, AB = 1 };
inline uint32_t Crc32Core(uint32_t *ptr, uint32_t len) {
uint32_t xbit = 0;
uint32_t data = 0;
uint32_t CRC32 = 0xFFFFFFFF;
const uint32_t dwPolynomial = 0x04c11db7;
for (uint32_t i = 0; i < len; i++) {
xbit = 1 << 31;
data = ptr[i];
for (uint32_t bits = 0; bits < 32; bits++) {
if (CRC32 & 0x80000000) {
CRC32 <<= 1;
CRC32 ^= dwPolynomial;
} else
CRC32 <<= 1;
if (data & xbit) CRC32 ^= dwPolynomial;
xbit >>= 1;
}
}
return CRC32;
};
class H1Example {
private:
double time_;
double control_dt_; // [2ms]
double duration_; // [3 s]
PRorAB mode_;
unitree_hg::msg::dds_::LowState_ low_state_;
ChannelPublisherPtr<unitree_hg::msg::dds_::LowCmd_> lowcmd_publisher_;
ChannelSubscriberPtr<unitree_hg::msg::dds_::LowState_> lowstate_subscriber_;
ThreadPtr command_writer_ptr_, control_thread_ptr_;
public:
H1Example(std::string networkInterface)
: time_(0.0), control_dt_(0.002), duration_(3.0), mode_(PR) {
ChannelFactory::Instance()->Init(0, networkInterface);
// create publisher
lowcmd_publisher_.reset(
new ChannelPublisher<unitree_hg::msg::dds_::LowCmd_>(HG_CMD_TOPIC));
lowcmd_publisher_->InitChannel();
// create subscriber
lowstate_subscriber_.reset(
new ChannelSubscriber<unitree_hg::msg::dds_::LowState_>(
HG_STATE_TOPIC));
lowstate_subscriber_->InitChannel(
std::bind(&H1Example::LowStateHandler, this, std::placeholders::_1), 1);
// create threads
control_thread_ptr_ = CreateRecurrentThreadEx(
"control", UT_CPU_ID_NONE, 2000, &H1Example::Control, this);
}
void LowStateHandler(const void *message) {
low_state_ = *(const unitree_hg::msg::dds_::LowState_ *)message;
if (low_state_.crc() !=
Crc32Core((uint32_t *)&low_state_,
(sizeof(unitree_hg::msg::dds_::LowState_) >> 2) - 1)) {
std::cout << "low_state CRC Error" << std::endl;
return;
}
}
void Control() {
unitree_hg::msg::dds_::LowCmd_ dds_low_command;
dds_low_command.mode_pr() = mode_;
dds_low_command.mode_machine() = low_state_.mode_machine();
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
dds_low_command.motor_cmd().at(i).mode() = 1; // 1:Enable, 0:Disable
dds_low_command.motor_cmd().at(i).tau() = 0.0;
dds_low_command.motor_cmd().at(i).q() = 0.0;
dds_low_command.motor_cmd().at(i).dq() = 0.0;
dds_low_command.motor_cmd().at(i).kp() = (i < 13) ? 100.0 : 50.0;
dds_low_command.motor_cmd().at(i).kd() = 1.0;
}
time_ += control_dt_;
if (time_ < duration_) {
// [Stage 1]: set robot to zero posture
for (int i = 0; i < H1_NUM_MOTOR; ++i) {
double ratio = std::clamp(time_ / duration_, 0.0, 1.0);
dds_low_command.motor_cmd().at(i).q() =
(1. - ratio) * low_state_.motor_state().at(i).q();
}
} else {
// [Stage 2]: swing ankle's PR
mode_ = PR; // Enable PR mode
// generate sin/cos trajectory
double max_P = 0.25; // [rad]
double max_R = 0.25; // [rad]
double t = time_ - duration_;
double L_P_des = max_P * std::cos(2.0 * M_PI * t);
double L_R_des = max_R * std::sin(2.0 * M_PI * t);
double R_P_des = max_P * std::cos(2.0 * M_PI * t);
double R_R_des = -max_R * std::sin(2.0 * M_PI * t);
// update ankle joint position targets
float Kp_Pitch = 80;
float Kd_Pitch = 1;
float Kp_Roll = 80;
float Kd_Roll = 1;
dds_low_command.motor_cmd().at(4).q() = L_P_des; // 4: LeftAnklePitch
dds_low_command.motor_cmd().at(4).dq() = 0;
dds_low_command.motor_cmd().at(4).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(4).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(4).tau() = 0;
dds_low_command.motor_cmd().at(5).q() = L_R_des; // 5: LeftAnkleRoll
dds_low_command.motor_cmd().at(5).dq() = 0;
dds_low_command.motor_cmd().at(5).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(5).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(5).tau() = 0;
dds_low_command.motor_cmd().at(10).q() = R_P_des; // 10: RightAnklePitch
dds_low_command.motor_cmd().at(10).dq() = 0;
dds_low_command.motor_cmd().at(10).kp() = Kp_Pitch;
dds_low_command.motor_cmd().at(10).kd() = Kd_Pitch;
dds_low_command.motor_cmd().at(10).tau() = 0;
dds_low_command.motor_cmd().at(11).q() = R_R_des; // 11: RightAnkleRoll
dds_low_command.motor_cmd().at(11).dq() = 0;
dds_low_command.motor_cmd().at(11).kp() = Kp_Roll;
dds_low_command.motor_cmd().at(11).kd() = Kd_Roll;
dds_low_command.motor_cmd().at(11).tau() = 0;
float L_P_m = low_state_.motor_state().at(4).q();
float L_R_m = low_state_.motor_state().at(5).q();
float R_P_m = low_state_.motor_state().at(10).q();
float R_R_m = low_state_.motor_state().at(11).q();
// clang-format off
printf("%f,%f,%f,%f,%f,%f,%f,%f\n",
L_P_des, L_P_m, L_R_des, L_R_m,
R_P_des, R_P_m, R_R_des, R_R_m);
// clang-format on
}
dds_low_command.crc() = Crc32Core((uint32_t *)&dds_low_command,
(sizeof(dds_low_command) >> 2) - 1);
lowcmd_publisher_->Write(dds_low_command);
}
};
int main(int argc, char const *argv[]) {
if (argc < 2) {
std::cout << "Usage: h1_2_ankle_track network_interface_name" << std::endl;
exit(0);
}
std::string networkInterface = argv[1];
H1Example custom(networkInterface);
while (true) sleep(10);
return 0;
}

Some files were not shown because too many files have changed in this diff Show More