ROS2はUbuntuベースのミドルウェアです。
ラズパイではUbuntu Server 20.04.2 LTS(64bit)を使ってみます。
インストールに関してはこのページの前半をご参照ください。
環境はラズパイ4+コンテナ+ROS2(Foxy)です。
Jetsonで作成したROS2のドッカーイメージをDocker Hub にpushしておいたものを使います。同じUbuntuベースのarm64(aarch64)アーキテクチャなので可能ですが、X86-64 (amd64) のWindowsでは不可です。
また、イメージをtarボールアーカイブして移行する手もあるようですが今回はパス。
初期設定します
18.04用の記述ですが、20.04でも同様です。
ディレクトリ名などは適宜、置き換えてください。
必要なライブラリなどをインストールしておきます。
1 |
sudo apt install curl gnupg2 lsb-release |
Dockerをインストール
今回のラズパイはヘッドレスなのでWindowsからSSHで接続して使ってみます。
インストール
1 2 3 4 |
curl -sSL https://get.docker.com | sh //動作確認 sudo docker ps |
Jetsonで作成済のイメージを使います。
1 |
sudo docker pull wisteriahill/ros:foxy-ros-base-l4t-r32.4.4 |
シンプルにコンテナ作成
sudo docker create -it --name my_ros2 --network host wisteriahill/ros:foxy-ros-base-l4t-r32.4.4
USBカメラや作業ディレクトリを使う場合
sudo docker create -it --name my_ros2 --network host -e DISPLAY=$DISPLAY -v /tmp/.X11-unix/:/tmp/.X11-unix -v /home/ubuntu/work-ros2:/work wisteriahill/ros:foxy-ros-base-l4t-r32.4.4
起動
1 |
sudo docker start -i my_ros2 |
demo_nodes_cpp(demo_nodes_py)というパッケージを使って通信テスト
Nano(4GB)とラズパイの両方でコンテナ起動
1 |
sudo docker start -i my_ros2 |
両方で同じDOMAIN_IDを設定(0~65532、例えば10)
1 |
export ROS_DOMAIN_ID=10 |
ラズパイでtalkerを実行してみます。
1 |
ros2 run demo_nodes_cpp talker |
Nanoでlisten
1 |
ros2 run demo_nodes_cpp listener |
送受信が確認できました。
繋がらない?場合の確認
ROS2は同じネットワークセグメント内になければいけません。
IPアドレスをチェック。
有線接続か無線かの違いによっても繋がらないようです。
DOMAIN_IDも同じである必要があります。
Appendix
DOMAIN_ID無しで送受信してみます。
multicastを使います。
Jetson Nano 4GB と2GB でreceiveしておきます。
1 |
ros2 multicast receive |
ラズパイからsend
1 |
ros2 multicast send |
sendされた「Hello World !」をreceiveしています。
Jetson(4GB)
Jetson(2GB)
ただし、ラズパイでreceiveしようとすると受信時にエラーが発生しましたー>要調査
エラー箇所
/opt/ros/foxy/build/ros2multicast/ros2multicast/api/__init__.py の51行目
s.setsockopt(socket.IPPROTO_IP, socket.IP_DROP_MEMBERSHIP, mreq)
この行で、OSError: [Errno 99] Cannot assign requested addressが発生
対処
真の原因は不明ですが、対処としてこれをコメントアウトしてしまい、passにします。
こんな感じ
1 2 3 |
finally: pass #s.setsockopt(socket.IPPROTO_IP, socket.IP_DROP_MEMBERSHIP, mreq) |
これでエラー出力は、一応、回避されて「Hello World!」が標準出力されます。
でもfinally節に記述されているものなので、これでいいわけないですけど……。
ちなみに、メッセージを変更する場合
/opt/ros/foxy/build/ros2multicast/ros2multicast/verb/send.py
mainのsend関数内で変更
日本語を使う場合
sendではメッセージはbyte列で扱っているのでencodeする必要があります。
こんな感じ
1 2 3 4 5 |
def main(self, *, args): print('Sending one UDP multicast datagram...') j_dat = 'こんちわ' b_dat = j_dat.encode('utf-8') send(b_dat,ttl=args.ttl) |
そのままreceive
Appendix
ラズパイ3以降はUbuntuが使えますが、それ以前のラズパイのrasbian OS はDebianです。
実行してもexec format errorで実行できません。
ただZero(Raspberry Pi OS Lite 32bit)ではクロスコンパイルでROS2を使う方法があるようです。
Leave a Reply