Isaac SimをDockerでインストールする
環境について
Dockerでisaac simをインストールします。
nvidia公式で配布されているnvcr.io/nvidia/isaac-sim:4.5.0
というイメージがありますが、以下2点が理由で別のベースイメージを使用します。
- Isaac Sim WebRTC Streaming ClientというVNCのようなかたちで操作しなければならない
- cudaバージョン等を自分で指定したものを使いたい
色々なインストール方法があるのですが、isaac labとしてはpip installの方法が紹介されているので、このやり方をベースとします。
Pythonのパッケージ管理はuvで、venv仮想環境上にisaac simをインストールします。
isaac simのインストール自体にはROSやcudaは必要ないはずですが、isaac labやpytorch等を用いたライブラリを後々使用したいので入れています。
- OS: Ubuntu 22.04
- GPU: Geforce RTX 3080 (10GB)
- GPU driver: 570.133.07
- Dockerベースイメージ:
nvidia/cuda:12.4.1-cudnn-devel-ubuntu22.04
- isaac sim: 4.5.0
- ROS: ROS2 humble
先にやっておくこと
GPUのdriverインストール
GPUのdriverをインストールします。
apt経由でもいいのですが、個人的にあまり上手くいったためしがないので.runファイル経由でインストールしました。
driver手動検索のページ
sudo sh NVIDIA-Linux-x86_64-570.133.07.run
だいたいよしなにYesを選択しておけば問題ないのですが、途中でUEFIのセキュアブートの箇所で引っ掛かります。
私の環境はWindows11とのデュアルブートとなっております。
Windows11は10からの移行時にUEFIを要求されてました。
そのため、Windows11とのデュアルブートをしている方は確実にこれが要求されるかと思います。
以下ページを参考にさせていただき、公開鍵を作ります。
参考: UEFI のセキュアブート機にNVIDIAのドライバを入れる話
そして、rebootする前に以下を実行してパスワードを設定します。
********
の箇所はtabで候補が出ると思います。
sudo mokutil --import /usr/share/nvidia/nvidia-modsign-crt-********.der
その後再起動するのですが、いつものubuntuの起動画面の前に1枚別の画面が挟まります。
一番上は普通に起動する選択肢ですが、私の場合は2つ目にenrollする選択肢が出たのでそちらを選びます。
そして、先ほど入力したパスワードをいれます。
この時点で、nvidia-smi
が通ると思います。
Docker関係のインストール
まずは公式ドキュメントの通り、dockerをインストールします。
以下はそのコピペです。
for pkg in docker.io docker-doc docker-compose docker-compose-v2 podman-docker containerd runc; do sudo apt remove $pkg; done
sudo apt update
sudo apt install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \
$(. /etc/os-release && echo "${UBUNTU_CODENAME:-$VERSION_CODENAME}") stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt update
sudo apt install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
さらに、nvidia-container-toolkitをインストールします。以下はそのコピペです。
curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey | sudo gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg \
&& curl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list | \
sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#g' | \
sudo tee /etc/apt/sources.list.d/nvidia-container-toolkit.list
sudo sed -i -e '/experimental/ s/^#//g' /etc/apt/sources.list.d/nvidia-container-toolkit.list
sudo apt update
sudo apt install -y nvidia-container-toolkit
sudo nvidia-ctk runtime configure --runtime=docker
sudo systemctl restart docker
Docker環境をつくる
Dockerイメージをビルドする
Docker composeを使用します。
ディレクトリ構成は好みですが、私は以下のようなかたちで作っていることが多いです。
.
├── docker
| ├── cpu
| | └── Dockerfile
| ├── gpu
| | └── Dockerfile
| ├── compose.yaml
| ├── entrypoint.sh
| └── .env
└── src
まずは、Docker内でローカルユーザをつくるために.envファイルをつくります。
以下のようにして現在ホスト側でログインしているユーザの情報をそのまま使います。手打ちしてもよいです。
echo UID=$(id -u) > .env
echo GID=$(id -g) >> .env
echo USERNAME=$(whoami) >> .env
.envはこうなります。
UID=1000
GID=1000
USERNAME=<usernameを書く>
次にcompose.yamlファイルを作成します。
docker-compose.yaml時代の書き方とかが混ざっていたり、port等は必要がないものがある気がしますが、気にしない方向でいきます。
services:
gpu:
build:
context: ../
dockerfile: docker/gpu/Dockerfile
args:
- UID=${UID}
- GID=${GID}
- USERNAME=${USERNAME}
env_file:
- .env
image: <イメージ名を入力する>
command: /bin/bash
ports:
- 8000:8000
working_dir: /home/${USERNAME}
tty: true
volumes:
- /tmp/.X11-unix:/tmp/.X11-unix
- /home/${USERNAME}/.Xauthority:/root/.Xauthority
runtime: nvidia
environment:
NVIDIA_VISIBLE_DEVICES: all
NVIDIA_DRIVER_CAPABILITIES: all
DISPLAY: $DISPLAY
QT_X11_NO_MITSHM: 1
privileged: true
shm_size: '16gb'
network_mode: "host"
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: 1
capabilities: [gpu]
恐らくポイントとしてあげられるのが以下項目で、これがないとDockerコンテナ内のnvidia-smiでGPUを見つけられていても、vulkaninfoで見つけられない場合があります。
runtime: nvidia
environment:
NVIDIA_VISIBLE_DEVICES: all
NVIDIA_DRIVER_CAPABILITIES: all
ないと下記のようなエラーが出てきます。
[Error] [gpu.foundation.plugin] No device could be created. Some known system issues:
- The driver is not installed properly and requires a clean re-install.
- Your GPUs do not support RayTracing: DXR or Vulkan ray_tracing, or hardware is excluded due to performance.
- The driver cannot enumerate any GPU: driver, display, TCC mode or a docker issue. For Vulkan, test it with Vulkaninfo tool from Vulkan SDK, instead of nvidia-smi.
- For Ubuntu, it requires server-xorg-core 1.20.7+ and a display to work without --no-window.
- For Linux dockers, the setup is not complete. Install the latest driver, xServer and NVIDIA container runtime.
Dockerfileはこんな感じです。
isaac sim側のインストールだとなぜかエラーが出たので、isaac lab側のインストールの方法を参考にしています。
(恐らく、pytorchをあらかじめインストールしておく必要があったのだと思います)
ちょこちょことUSERを切り替えて、isaac sim使用時をローカルユーザとなるようにしています。
一応isaacsim実行時に引数を指定することでrootでも実行できるようなのですが、ローカルユーザ使用が前提となっているようなのでこのようにしています。
rootのままuv pip install ~~~してしまうと、rootユーザでコンテナに入らないと実行できなくなります。
ARG BASE_IMAGE=nvidia/cuda:12.4.1-cudnn-devel-ubuntu22.04
FROM $BASE_IMAGE
ARG UID
ARG GID
ARG USERNAME
USER root
SHELL ["/bin/bash", "-c"]
ENV TZ=Asia/Tokyo
RUN export DEBIAN_FRONTEND=noninactive \
&& apt-get update && apt-get install -y --no-install-recommends \
tzdata \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
RUN apt-get update && apt-get install -y --no-install-recommends \
apt-transport-https \
build-essential \
bzip2 \
ca-certificates \
curl \
ffmpeg \
g++ \
git \
gnupg \
graphviz \
locales \
libgl1-mesa-dev \
libusb-1.0-0-dev \
lsb-release \
net-tools \
openssh-client \
software-properties-common \
sudo \
unzip \
vim \
wget \
xorg-dev \
zip \
emacs \
python3-dev \
python3-setuptools \
python3-pip \
python3-venv \
vulkan-tools \
usbutils \
x11-apps \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
RUN groupadd -g ${GID} ${USERNAME} && useradd -u ${UID} -g ${GID} -s /bin/bash -m ${USERNAME}
WORKDIR /home/$USERNAME/ws
# ROS2
ENV ROS_DISTRO=humble
RUN locale-gen ja_JP ja_JP.UTF-8 \
&& update-locale LC_ALL=ja_JP.UTF-8 LANG=ja_JP.UTF-8
ENV LANG=ja_JP.UTF-8
RUN add-apt-repository universe \
&& curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key -o /usr/share/keyrings/ros-archive-keyring.gpg \
&& echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/ros-archive-keyring.gpg] http://packages.ros.org/ros2/ubuntu $(. /etc/os-release && echo $UBUNTU_CODENAME) main" | sudo tee /etc/apt/sources.list.d/ros2.list > /dev/null \
&& apt-get update && apt-get install -y \
ros-$ROS_DISTRO-desktop \
ros-dev-tools \
ros-$ROS_DISTRO-xacro \
ros-$ROS_DISTRO-joint-state-publisher \
ros-$ROS_DISTRO-joint-state-publisher-gui \
ros-$ROS_DISTRO-moveit \
python3-rosdep \
python3-colcon-common-extensions \
python3-colcon-mixin \
python3-vcstool \
python3-argcomplete \
# for isaacsim bridge
ros-$ROS_DISTRO-vision-msgs \
ros-$ROS_DISTRO-ackermann-msgs \
python3-rosinstall \
python3-rosinstall-generator \
python3-wstool \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/* \
&& rosdep init \
&& rosdep update
# uv
COPY /uv /uvx /bin/
WORKDIR /home/$USERNAME/
USER $USERNAME
RUN mkdir isaacsim \
&& cd isaacsim \
&& uv venv --python 3.10 \
&& source .venv/bin/activate \
&& uv pip install --upgrade pip \
&& uv pip install torch==2.5.1 torchvision==0.20.1 --index-url https://download.pytorch.org/whl/cu124 \
&& uv pip install 'isaacsim[all,extscache]==4.5.0' --extra-index-url https://pypi.nvidia.com
USER root
RUN source /opt/ros/$ROS_DISTRO/setup.bash --extend \
&& cd ws \
&& git clone https://github.com/isaac-sim/IsaacSim-ros_workspaces.git \
&& cd IsaacSim-ros_workspaces/humble_ws \
&& rosdep update && apt-get update \
&& rosdep install -i --from-path src --rosdistro humble -y \
&& colcon build
# entrypoint
COPY docker/entrypoint.sh ./ws/entrypoint.sh
RUN chmod +x ./ws/entrypoint.sh
USER $USERNAME
ENTRYPOINT ["./ws/entrypoint.sh"]
enrtypoint.shはこんな感じです。
現状はROSのためだけにあります。
#!/bin/bash
set -e
source /opt/ros/$ROS_DISTRO/setup.bash --extend
source /home/$USERNAME/ws/IsaacSim-ros_workspaces/humble_ws/install/setup.bash --extend
exec "$@"
ビルドするときはdockerのディレクトリに移動してビルドします。
$ cd docker/
sudo docker compose build gpu
Dockerコンテナをrunする
実行するときは以下のようなかたちです。
sudo docker compose run --rm -u <usernameを書く> gpu
コンテナ内で以下をするとisaac simが実行できると思います。
実行後、GUIはすぐに立ち上がるのですが、諸々ロードするのに結構時間がかかり、GUI画面から応答待ちのダイアログが表示されるので待ちます。
cd isaacsim
source .venv/bin/activate
isaacsim
ROS2チュートリアルを実行してみる
基本的には公式のTurtlebotのチュートリアルに沿って実行します。
この前提となるROS and ROS 2 Installationについては、既にROS2:humbleと関連パッケージはDockerfile内でもう入っており、恐らくROS2 BridgeはONになっているはずなのでスキップします。
(Cyclone DDSを使う場合は戻ってくる必要があります)
コンテナをrunして、
sudo docker compose run --rm -u <usernameを書く> gpu
まず適当な場所に移動して、turtlebot3のrepositoryをcloneしておきます。
git clone -b humble-devel https://github.com/ROBOTIS-GIT/turtlebot3.git turtlebot3
そしてisaacsimを立ち上げます。
cd isaacsim
source .venv/bin/activate
isaacsim
ここからチュートリアルに沿っていきます。
isaacsimのGUI画面の、下のIsaac Sim AssetsタブからEnvironments->SIMPLE_ROOM->simple_roomを選択してロードします。
滑り台みたいなテーブル?が置いてあるシンプルな部屋がロードされたと思います。
File->Importから、先ほど別ターミナルでcloneしたTurtlebot3をインポートします。
場所は(cloneした場所)/turtlebot3/turtlebot3_description/urdf/turtlebot3_burger.urdf
です。
インポートするときに、Linksの部分だけチュートリアルの画像と違うので、Static BaseからMoveable Baseに変更にしておきます。
インポートしたTurtlebot3はテーブル?の上に乗ってしまうので、右サイドバーのturtlebot3_burgerをクリックして表示される矢印をドラッグし、適当に床面の近くに移動させます。
後に使うPlayボタンを押すと勝手に下に落ちるので、ちょっと床から浮かせておくくらいでいいそうです。
右サイドバーのturtlebot3_burger->joints->wheel_left_jointとwheel_right_jointをクリックし、その下に表示される諸々のPropertyの中からDumpingとStiffnessを探します。
そして両方ともDampingを10000000.0、Stiffnessを0.0としておきます。
そして、次のチュートリアルページを見ながらWindow->Graph Editors->Action Graphからグラフを作ります。今回はコツコツ写経をしました。
その中のMake Arrayはデフォルトは1入力ですが、右のPropertyからArray Sizeを手入力で変えるかプラスボタンを押して2入力とします。
グラフができた後は、各ノードをクリックして右サイドバーに表示されるPropertyに対して、以下を変更します。
- ROS2 Subscribe Twist Node: topic nameに
/cmd_vel
を入力します - Differential Controllerのノードで以下のようにPropertyを変更します
- Max Angular Speed: 1.0
- Max Linear Speed: 0.22
- Wheel Distance: 0.16
- Wheel Radius: 0.025
- Articulation Controller: targetPrimでturtlebot3_burger->base_footprintを選択する
- Constant Tokenのそれぞれのノードで以下のようにPropertyを変更します
- Value: wheel_left_joint
- Value: wheel_right_joint
上記が終われば、左側にある三角の再生マークのplayボタンをクリックすると動作可能の状態になります。
何らか失敗していると鬼のようなエラーと警告の嵐になるかと思いますので、直しましょう。
別ターミナルを立ち上げて、同じコンテナにexecで入ります。
sudo docker compose exec -u <usernameを書く> gpu bash
entrypoint.shを読み込んでないので中身に相当するものを読み込みます。
(source entrypoint.sh
でもよいです)
source /opt/ros/$ROS_DISTRO/setup.bash --extend
source /home/$USERNAME/ws/IsaacSim-ros_workspaces/humble_ws/install/setup.bash --extend
別ターミナルから以下を実行すると、壁にぶつかるまでTurtlebot3が直進します。
ros2 topic pub /cmd_vel geometry_msgs/Twist "{'linear': {'x': 0.2, 'y': 0.0, 'z': 0.0}, 'angular': {'x': 0.0, 'y': 0.0, 'z': 0.0}}"
壁にぶつかってもタイヤは動き続けます。
止めるには以下を実行します。
ros2 topic pub /cmd_vel geometry_msgs/Twist "{'linear': {'x': 0.0, 'y': 0.0, 'z': 0.0}, 'angular': {'x': 0.0, 'y': 0.0, 'z': 0.0}}"
Discussion