AEGLOSLAB ROS 2 Jazzy 대전

제3부 미들웨어: DDS·RTPS·RMW

3.10 rmw_zenoh — DDS 아닌 대안

3.10.1 이 장에서 배우는 것 / 선수 지식

제3부는 DDS의 강점과 한계를 함께 봤다. 강점은 성숙한 표준·QoS·브로커 부재였고, 한계는 $O(N^2)$ 디스커버리(3.3), 멀티캐스트 의존(3.9), LAN 전제였다. Discovery Server(3.4)는 그 한계를 DDS 안에서 완화하는 시도였다.

zenoh는 다른 답이다 — 미들웨어 자체를 바꾼다. 3.5에서 본 rmw 추상이 존재하는 이유가 여기서 실증된다. rmw_zenoh_cpp는 DDS가 아닌 프로토콜 위에 ROS 2를 구축한다.

배우는 것:

  • zenoh의 정체 — 무엇을 다르게 설계했는가.
  • 세 가지 모드 — peer·client·router와 각각의 배치.
  • DDS와의 구조적 차이 — 디스커버리·라우팅·QoS.
  • Jazzy에서의 사용법 — 설치·실행·설정.
  • 트레이드오프 — 얻는 것과 잃는 것.
  • 판단 기준 — 언제 검토할 가치가 있는가.

선수 지식: 3.3(디스커버리 비용), 3.4(Discovery Server), 3.5(RMW 교체), 3.9(네트워크 문제), 3.6(벤더 선택).

정직: 이 장은 이 책에서 가장 시점 의존적이다. zenoh와 rmw_zenoh_cpp는 빠르게 발전 중이다. 2026-08-16에 Jazzy에 실제로 설치해 통신·QoS·설정을 확인했고(실행 확인 — 3.10.12), 그 결과를 시점과 함께 적었다. 그 절 밖의 개념 서술은 공개 문서 기준이며 검증하지 않았다(목차 3). 성능 비교 수치는 인용하지 않는다(3.6.1의 방침).

3.10.2 zenoh는 무엇인가

Zenoh(Zero Overhead Network Protocol)는 Eclipse 재단의 프로토콜·미들웨어로, pub/sub · 질의(query) · 저장(storage) 을 하나의 프로토콜에 통합한다.

zenoh Pub/Sub (토픽과 유사) Query (질의·응답 · 분산 저장 조회) Storage (데이터 보관·복제)

DDS와의 설계 전제 차이가 핵심이다:

전제DDSzenoh
네트워크신뢰할 수 있는 LANLAN·WAN·무선·인터넷 전반
규모수십~수백 엔티티대규모 지향
토폴로지평면(flat) 피어peer·client·router 조합
디스커버리멀티캐스트 브로드캐스트라우터 경유 가능
이름토픽 이름키 표현식(계층·와일드카드)
저장없음(TRANSIENT_LOCAL 한정)1급 개념

"키 표현식"이 흥미롭다. zenoh의 이름 공간은 robot1/sensors/lidar 같은 계층이며 와일드카드 구독(robot1/**)이 프로토콜 수준에서 지원된다. DDS·ROS 2에는 없는 개념이다(확인 필요: rmw_zenoh가 이를 ROS 2 API로 노출하지는 않을 것이다 — ROS 2 API가 그런 개념을 갖지 않으므로).

3.10.3 세 가지 모드

peer 모드 client + router 노드 노드 노드 zenohd 라우터 노드 노드 노드
모드동작유사한 것
peer서로 직접 연결·디스커버리DDS 기본 디스커버리
client라우터에만 연결Discovery Server의 클라이언트(3.4)
router(zenohd)연결을 중계·라우팅DDS에 없는 것

router가 Discovery Server와 결정적으로 다른 점: 데이터도 중계할 수 있다.

축Discovery Serverzenoh router
디스커버리 중계✅✅
데이터 중계❌ (피어 투 피어 유지)✅ 가능
서브넷 경계라우팅되면 통과라우터가 이어 준다
라우터 연결(다단)—라우터끼리 연결 가능

데이터 중계가 왜 중요한가: NAT 뒤·다른 서브넷·인터넷 너머의 노드가 직접 연결 없이 통신할 수 있다. Discovery Server는 디스커버리만 도와주므로, 실제 데이터 경로가 막혀 있으면 여전히 통신이 안 된다(3.9.5의 Docker bridge 문제가 그 예다).

대가: 데이터가 라우터를 거치면 지연이 늘고 라우터가 병목·단일 장애점이 된다. 그래서 zenoh는 같은 서브넷 안에서는 직접 연결하고, 필요할 때만 라우터를 거치는 방식을 취한다(확인 필요: 정확한 최적화 동작).

라우터 다단 연결이 플릿 구조에 잘 맞는다:

로봇 1 온보드 라우터 중앙 라우터 로봇 2 온보드 라우터 관제 · 클라우드

3.4.5에서 "온보드 서버 + 중앙 서버의 계층 구조가 안전하다"고 했는데, zenoh는 그 구조를 프로토콜이 직접 지원한다.

3.10.4 Jazzy에서 사용하기

# 설치 (실행 확인)
sudo apt install ros-jazzy-rmw-zenoh-cpp

# 라우터 실행 — 사실상 필수다 (3.10.12.1)
ros2 run rmw_zenoh_cpp rmw_zenohd

# 노드 실행
export RMW_IMPLEMENTATION=rmw_zenoh_cpp
ros2 run demo_nodes_cpp talker

Jazzy에서 실제로 실행해 확인했다(3.10.12): 기본 세션 모드는 peer이지만, 그럼에도 라우터가 없으면 통신이 되지 않는다. 노드는 경고만 내고 정상 실행되므로 실패처럼 보이지 않는다는 점이 함정이다.

설정:

zenoh는 JSON5 형식의 설정 파일을 쓴다.

export ZENOH_SESSION_CONFIG_URI=/etc/robot/zenoh_session.json5
export ZENOH_ROUTER_CONFIG_URI=/etc/robot/zenoh_router.json5
# 이름은 실행 확인 — 전체 목록은 3.10.12.2
{
  mode: "peer",
  connect: {
    endpoints: ["tcp/192.168.1.100:7447"]
  },
  scouting: {
    multicast: { enabled: true },
    gossip: { enabled: true }
  }
}

gossip 디스커버리가 DDS와 다른 점이다 — 멀티캐스트가 없어도 이미 연결된 피어를 통해 다른 피어를 알아 간다. 이것이 3.9.2의 "멀티캐스트가 막힌 환경" 문제에 대한 구조적 답이다.

기본 전송이 TCP다(실행 확인 — 기본 세션 설정의 연결 엔드포인트가 tcp/localhost:7447이다). UDP·QUIC·시리얼·공유메모리 등도 지원한다. TCP 기반이라 방화벽·NAT 통과가 DDS보다 쉽다(3.9.6의 포트 문제가 크게 단순해진다 — 라우터 포트 하나면 되는 경우가 많다).

3.10.5 QoS는 어떻게 되는가

이것이 실무에서 가장 중요한 질문이다. ROS 2 코드는 QoS를 지정하는데(1.5), zenoh는 DDS QoS 체계를 갖지 않는다.

ROS 2 QoSzenoh에서
RELIABLE·BEST_EFFORT대응하는 개념 있음
HISTORY·depth대응 있음
TRANSIENT_LOCAL동작한다 — 늦게 기동된 구독자가 과거 메시지를 받는 것을 실측(3.10.12.3)
DEADLINE·LIFESPAN·LIVELINESS설정은 받아들이지만 감시 이벤트가 없다 — 위반을 알려 주지 않는다(3.10.12.3)

Jazzy 기준의 매핑 상태는 3.10.12.3에 실측으로 정리했다. 버전이 높아지면 달라질 수 있으므로 확인 방법도 함께 적어 둔다 — QoS 이벤트 콜백(1.4.6)을 등록해 보는 것이 가장 빠르다. DEADLINE·LIVELINESS에 의존해 장애를 감지하는 시스템이라면 이 부분이 곧 설계 제약이다(1.5.3.6).

3.5.5의 방어적 확인이 여기서 특히 중요하다:

RCLCPP_INFO(get_logger(), "RMW=%s, 실제 QoS reliability=%d durability=%d",
            rmw_get_implementation_identifier(),
            static_cast<int>(pub_->get_actual_qos().reliability()),
            static_cast<int>(pub_->get_actual_qos().durability()));

3.10.6 얻는 것과 잃는 것

얻는 것:

이득설명대응하는 DDS 문제
멀티캐스트 불필요gossip 디스커버리·라우터3.9.2·3.9.5
NAT·방화벽 통과TCP 기반·라우터 경유3.9.5·3.9.6
서브넷·WAN 확장라우터가 이어 준다3.9.7
디스커버리 확장성$O(N^2)$ 구조가 아님3.3.4
컨테이너 친화bridge 모드에서도 라우터로3.9.5
플릿 구조라우터 계층이 자연스럽다3.4.5
설정 단순성포트 계산·XML 프로파일 부담 감소3.2.6·3.7

잃는 것:

대가설명
생태계 성숙도DDS 대비 문서·질의응답·실전 사례가 얇다(확인 필요)
QoS 완전성일부 정책 매핑이 불완전할 수 있다(3.10.5)
DDS 상호운용 상실비ROS DDS 시스템과 연결되지 못한다(3.1.2)
벤더 도구 상실Wireshark RTPS 디섹터·DDS 모니터링 도구가 무용
표준 지위DDS는 OMG 표준, zenoh는 단일 프로젝트
인증 자료안전 인증 맥락의 축적이 얇다(14.10)
라우터 의존client 모드면 라우터가 단일 장애점
팀 지식 전환축적된 DDS 튜닝 노하우가 무효(3.5.6)

"Wireshark 디섹터 상실"이 과소평가된다. 3.2.8의 진단 기법이 대부분 쓸 수 없게 되고, 대신 zenoh 자체 도구·로그에 의존해야 한다. 진단 능력의 전환 비용이다.

견해: zenoh는 "DDS보다 좋다"가 아니라 "다른 전제 위에 서 있다"고 이해하는 것이 정확하다. 공장 LAN 안의 단일 로봇에서는 DDS의 성숙도가 우선한다. 무선 플릿·클라우드 연결·NAT 뒤 컨테이너에서는 zenoh의 전제가 맞는다. 문제가 무엇인지가 선택을 정한다.

3.10.7 언제 검토할 가치가 있는가

아니오 예 예 zenoh 검토? 무선 · WAN이 본질적 문제? ✅ 강력한 후보 멀티캐스트 불가 + 컨테이너 격리 필요? ✅ 검토 가치
아니오 아니오 예 예 아니오 멀티캐스트 불가 + 컨테이너 격리 필요? 노드 수백 개 이상 + Discovery Server로 부족? ✅ 검토 가치 안전 인증 · DDS 연동 필요? ❌ DDS 유지 기본 RMW 유지 3.6.6의 ①
(계속 — 멀티캐스트 불가 아닌 경우)

검토할 만한 경우:

상황이유
무선 로봇 플릿설계 전제가 맞는다
클라우드·원격 연동WAN·NAT 통과
Kubernetes 배포라우터를 Service로(3.9.5)
다중 사이트라우터 다단 연결
Discovery Server로도 부족한 규모구조가 다르다

검토하지 않는 편이 나은 경우:

상황이유
단일 로봇 + 유선 LANDDS로 충분, 성숙도가 우선한다
비ROS DDS 시스템과 연동상호운용 상실
안전 인증 프로젝트자료 축적이 얇다
DDS 튜닝이 이미 안정화됨전환 비용이 이득 초과
팀에 검증 여력이 없음새 미들웨어는 검증 부담

견해: "무선이 문제라서" 검토하는 것이 가장 정당한 이유다. 3.9.3에서 본 Wi-Fi와 DDS의 구조적 불화는 튜닝으로 완전히 풀리지 않는다. 반면 "최신 기술이라서"·"빠르다고 들어서"는 좋은 이유가 아니다 — 3.6.5의 절차로 자기 워크로드에서 측정하고, 3.5.6의 재검증 목록을 통과해야 한다.

3.10.8 전환 시 확인 목록

3.5.6의 일반 목록에 zenoh 특유 항목을 더한다.

  • [ ] QoS 매핑 검증 — 쓰는 정책이 실제로 동작하는가(topic info -v·이벤트 콜백).
  • [ ] TRANSIENT_LOCAL 동작 — /map·/tf_static·/robot_description이 늦은 구독자에게 가는가(1.6.3.3).
  • [ ] 서비스·액션 — 요청·응답 상관과 타임아웃이 정상인가(1.7·1.8).
  • [ ] 라우터 필요 여부와 배치 — peer만으로 되는가, 라우터를 어디 두는가.
  • [ ] 라우터 장애 시나리오 — 3.4.8과 같은 시험을 수행했는가.
  • [ ] 진단 수단 — RTPS 캡처 대신 무엇으로 진단할 것인가.
  • [ ] 성능 기준선 비교 — 종단 지연 p50·p99·max(2.7.8).
  • [ ] 대용량 토픽 — 이미지·포인트클라우드가 실제 링크에서 흐르는가.
  • [ ] Discovery Server 등 DDS 전용 구성 제거 — 대응 구성으로 대체했는가.
  • [ ] SROS2 보안 — 보안을 쓴다면 대응 수단이 있는가(13.2)(확인 필요).

견해: TRANSIENT_LOCAL 항목을 특히 강조한다. Nav2의 /map, robot_state_publisher의 /robot_description, /tf_static이 모두 이 정책에 의존하며(1.6.3.3), 여기가 어긋나면 시스템이 부팅은 되는데 간헐적으로 비정상적으로 동작한다. 전환 시 가장 먼저 시험할 항목이다.

3.10.9 제3부를 마치며 — 미들웨어 층의 지도

이 장은 제3부의 마지막이므로, 열 장을 하나의 판단 흐름으로 묶는다.

미들웨어 문제 발생 어느 층인가? 2.1.8 네트워크 층? 3.9 플레이북 멀티캐스트 · NIC · 방화벽 · MTU
어느 층인가? 2.1.8 디스커버리? 3.3 비용 구조 규모 · 멀티캐스트? 컴포지션 · 정적 피어 3.3.9 Discovery Server 3.4 zenoh 3.10
(계속 — 디스커버리 분기)
어느 층인가? 2.1.8 전송·QoS? 3.2 캡처 · 1.5 벤더 튜닝 3.7 · 3.8 적용 확인 필수
(계속 — 전송·QoS 분기)

제3부가 반복해 말한 세 가지:

  1. 층을 가려라. 문제가 rclcpp인지 rmw인지 DDS인지 네트워크인지 먼저 정한다(2.1.8·3.9.9). 이 판단만 정확해도 시간의 대부분을 아낀다.
  2. 설정했다고 믿지 말고 확인하라. XML은 조용히 무시되고(3.7.9), 기능은 조용히 fallback하며(3.5.5), 격리는 조용히 안 되며(3.3.7), 라우터 없는 zenoh 노드는 정상적으로 기동된 채로 아무도 못 받는다(3.10.12.1). ros2 topic info -v·패킷 캡처·ss가 정본이다.
  3. 가장 값싼 해법부터. 컴포지션 → 정적 피어 → Discovery Server → 미들웨어 교체 순으로 비용이 커진다(3.3.9·3.4.9). 아래로 내려갈수록 검증 부담이 급증한다.

3.10.12 Jazzy에서 실제로 실행해 본 결과 — 실측

이 장은 서두에서 "이 책에서 가장 시점 의존적"이라고 밝혔다. 그래서 Jazzy에 rmw_zenoh_cpp를 설치하고 통신까지 시켜 본 결과를 시점과 함께 남긴다(실행 확인, 2026-08-16 · ros-jazzy-rmw-zenoh-cpp).

3.10.12.1 라우터 없이도 노드는 기동된다 — 그리고 아무도 못 받는다

가장 중요한 실측 결과다. 라우터를 기동하지 않고 talker를 실행하면 이렇게 된다:

[WARN] [rmw_zenoh_cpp]: Unable to connect to a Zenoh router.
       Have you started a router with `ros2 run rmw_zenoh_cpp rmw_zenohd`?
[WARN] [rmw_zenoh_cpp]: Unable to connect to a Zenoh router after 1 attempt(s).
       ... Proceeding with initialization but other peers will not discover or
       receive data from peers in this session until a router is started.
[INFO] [talker]: Publishing: 'Hello World: 1'
[INFO] [talker]: Publishing: 'Hello World: 2'

노드는 정상 실행되고 발행도 계속한다. 로그를 보지 않으면 아무 문제가 없어 보인다. 그러나 경고가 말하는 그대로 — 다른 피어는 이 세션을 발견하지도, 데이터를 받지도 못한다.

라우터를 기동하면 달라진다(실행 확인):

ros2 run rmw_zenoh_cpp rmw_zenohd
# → Started Zenoh router with id d54672db4bbe...

이 상태에서 talker/listener를 실행하면 경고가 사라지고 정상 통신한다(구독자가 메시지를 받는 것까지 확인).

조건노드 실행통신
라우터 없음성공(경고 2줄)안 됨
라우터 있음성공(경고 없음)됨

함정: "노드가 떴으니 되는 줄 안다"가 이 미들웨어의 첫 함정이다. DDS에 익숙하면 더 그렇다 — DDS는 라우터라는 것이 없고 피어끼리 직접 연결되므로, "중앙 프로세스를 먼저 기동한다"는 습관 자체가 없다. rmw_zenoh_cpp로 바꾼 뒤 토픽이 안 보이면 라우터부터 확인하라.

기본 재시도는 1회다("after 1 attempt(s)"). 라우터와 노드를 함께 부팅시키는 구성에서는 노드가 먼저 기동돼서 실패하고 그대로 고립될 수 있다 — 경고 메시지가 안내하는 대로 ZENOH_ROUTER_CHECK_ATTEMPTS를 늘리거나, systemd 의존으로 순서를 강제해야 한다(14.8).

견해: 기본 모드가 peer인데도 라우터가 필요한 것이 혼동을 일으키는데, zenoh의 peer는 "라우터를 통해 서로를 알아 가는 피어"라고 읽는 편이 실제에 가깝다. 멀티캐스트 없이 동작하는 대가(3.10.4의 gossip 디스커버리)로 부트스트랩 지점이 하나 필요한 구조다. 이것이 3.9.2의 "멀티캐스트가 막힌 환경"에 대한 답이 되는 동시에, 단일 장애점을 하나 들여오는 거래이기도 하다.

3.10.12.2 설정 파일과 환경 변수

패키지가 배포하는 기본 설정은 두 개다:

파일용도
DEFAULT_RMW_ZENOH_SESSION_CONFIG.json5노드(세션) 쪽
DEFAULT_RMW_ZENOH_ROUTER_CONFIG.json5라우터 쪽

세션 설정에서 확인되는 기본값:

mode: "peer",
connect: {
  endpoints: [ "tcp/localhost:7447" ]
},
shared_memory: { /* 기본 true — 다만 양쪽이 켜야 실제로 쓰인다 */ }

기본 연결 대상이 tcp/localhost:7447이다. 즉 라우터가 같은 머신에 있다고 가정한다 — 라우터를 다른 호스트에 두려면 이 값을 바꿔야 한다.

환경 변수는 일곱 개다(실행 확인):

변수용도
ZENOH_SESSION_CONFIG_URI · ZENOH_ROUTER_CONFIG_URI설정 파일 경로
ZENOH_CONFIG_OVERRIDE설정 일부만 덮어쓰기
ZENOH_ROUTER_CHECK_ATTEMPTS라우터 연결 재시도 횟수(기본 1)
ZENOH_SHM_ALLOC_SIZE · ZENOH_SHM_MESSAGE_SIZE_THRESHOLD공유메모리
RMW_ZENOH_BUFFER_POOL_MAX_SIZE_BYTES버퍼 풀 상한

ZENOH_CONFIG_OVERRIDE가 실용적이다. 파일 전체를 복사해 고치는 대신 한 항목만 바꿀 수 있어, 컨테이너 배포에서 라우터 주소만 바꿔 넣기에 좋다.

3.10.12.3 QoS — 되는 것과 안 되는 것이 갈린다

3.10.5가 (확인 필요)로 남긴 두 줄을 실측으로 확정했다.

TRANSIENT_LOCAL은 동작한다. 발행자가 TRANSIENT_LOCAL로 세 건을 보내고 종료하지 않은 상태에서, 나중에 기동된 구독자가 세 건을 모두 받았다. DDS의 래치 동작과 같다.

DEADLINE·LIVELINESS는 "설정은 되고 감시는 안 된다". 두 단계로 나뉜다:

시도결과
QoS 프로파일에 deadline·lifespan·liveliness 지정성공 — 오류 없이 퍼블리셔가 만들어진다
그 이벤트 콜백 등록(deadline·liveliness)UnsupportedEventTypeError
incompatible_qos·matched 콜백 등록지원

오류 메시지는 이렇다:

UnsupportedEventTypeError: publisher event is unsupported:
provided event_type 7 is not supported by rmw_zenoh_cpp

설정을 받아들이는 것이 함정이다. deadline=200ms를 설정해 두면 코드는 통과하고 로그도 조용한데, 위반해도 아무 일이 일어나지 않는다. 감시를 담당할 이벤트가 없기 때문이다.

이 거동은 1.5.10에서 본 Cyclone DDS의 내용 필터와 성격이 다르다. 그쪽은 설정이 조용히 무시되어 알 방법이 없었지만, 여기서는 이벤트를 등록하려는 순간 예외가 난다. 즉 "감시가 필요한 코드"는 반드시 실패하므로, 조용한 사고로는 이어지지 않는다. 설계로 보면 나은 쪽이다.

함정: 그래도 QoS 설정만 하고 이벤트를 안 쓰는 코드는 통과한다. DEADLINE을 "선언해 두면 미들웨어가 지켜 주는 것"으로 오해하고 있었다면(1.5.3.4), zenoh에서는 그 오해가 드러나지 않는다. 감시가 필요하면 이벤트를 등록하라 — 등록해 보는 것이 지원 여부를 아는 유일한 방법이다.

3.10.12.4 보안 — SROS 2 정책을 재사용한다

3.10.8의 체크리스트가 (확인 필요)로 남긴 항목이다. 별도 패키지 ros-jazzy-zenoh-security-tools가 있고, 그 실행 파일이 정확히 이 일을 한다(실행 확인):

Usage: ros2 run zenoh_security_tools generate_configs [options]
Generate Zenoh session and router configs with security artifacts.
  -p,--policy TEXT REQUIRED   The path to the Access Control Policy file.
  -e,--enclaves TEXT          The directory with the security enclaves ...

입력이 SROS 2의 정책 파일과 enclave 디렉터리다(13.2.5·13.2.12). 즉 접근 제어 정책을 DDS 보안과 같은 형식으로 쓰고, 그것을 zenoh 설정으로 변환하는 구조다 — 미들웨어를 바꿔도 정책 자산은 이어 쓸 수 있다는 뜻이다.

정직: 변환이 된다는 것과 보호 수준이 같다는 것은 다른 말이다. DDS-Security의 거버넌스(암호화 방식·서명 요구)가 zenoh 설정에서 어떻게 대응되는지는 확인하지 않았다. 보안이 요건이라면 생성된 설정을 직접 읽고 검증해야 한다.

3.10.10 함정 카탈로그

#함정증상대처
1QoS가 DDS와 동일하게 동작할 것으로 가정조용한 동작 차이매핑 검증(3.10.5)
2TRANSIENT_LOCAL 동작 가정—동작한다(실측, 3.10.12.3)
3라우터를 안 띄움노드는 정상 실행되는데 아무도 못 받음rmw_zenohd 먼저 실행(3.10.12.1)
4라우터 장애 시나리오 미시험현장에서 처음 겪음사전 시험(3.4.8)
5RTPS 진단 기법 의존도구가 무용대체 진단 수단 확보
6비ROS DDS 연동 필요한데 전환상호운용 상실DDS 유지
7"최신이라서" 전환검증 부담만 증가측정 근거(3.6.5)
8DDS 전용 구성 잔존Discovery Server 설정 무효구성 정리
9성능 기준선 없이 전환개선 여부 불명사전 측정
10문서 확인 없이 이 책만 신뢰버전 차이로 실패현재 문서가 정본
11DEADLINE·LIVELINESS로 장애 감지 기대위반해도 아무 일 없음이벤트 콜백 등록해 지원 확인(3.10.12.3)
12라우터·노드 동시 부팅노드가 먼저 기동돼 고립ZENOH_ROUTER_CHECK_ATTEMPTS 상향·systemd 순서(3.10.12.1)

10번을 강조한다. 이 장은 이 책에서 가장 빨리 낡을 내용이다. zenoh 생태계는 활발히 변하고 있으므로, 도입한다면 반드시 현재 문서를 확인하기 바란다.

3.10.11 체크포인트

  • zenoh가 통합하는 세 가지 기능과, DDS와의 설계 전제 차이 여섯 가지를 말할 수 있는가.
  • peer·client·router 세 모드를 설명하고, router가 Discovery Server와 결정적으로 다른 점을 말할 수 있는가.
  • 데이터 중계가 가능하다는 것이 Docker bridge·NAT 문제에 어떤 답이 되는가. 그 대가는?
  • gossip 디스커버리가 3.9.2의 어떤 문제에 대한 구조적 답인가.
  • ROS 2 QoS가 zenoh에서 어떻게 되는가. 반드시 검증해야 할 정책은 무엇이며 왜인가.
  • zenoh로 얻는 것 일곱 가지와 잃는 것 여덟 가지를 들 수 있는가. 과소평가되는 손실은?
  • zenoh를 검토할 만한 상황 다섯 가지와 검토하지 않는 편이 나은 상황 다섯 가지를 구분할 수 있는가.
  • "무선이 문제라서"가 정당한 이유이고 "최신이라서"가 아닌 이유를 설명할 수 있는가.
  • 전환 확인 목록에서 가장 먼저 시험해야 할 항목은 무엇이며, 어긋나면 어떤 증상이 나타나는가.
  • 제3부가 반복한 세 가지 원칙을 말할 수 있는가.
  • rmw_zenoh_cpp에서 라우터를 안 기동하면 무슨 일이 생기는가. 노드는 기동되는가? TRANSIENT_LOCAL과 DEADLINE은 각각 어떻게 되는가(3.10.12).

여기까지가 제3부 미들웨어: DDS·RTPS·RMW다. 제1·2부가 한 프로세스 안의 이야기였다면, 제3부는 프로세스와 머신 사이를 다뤘다 — DDS 개념(3.1), 와이어 프로토콜(3.2), 디스커버리와 그 비용(3.3), 대규모 해법(3.4), rmw 계약(3.5), 벤더 선택(3.6), 튜닝(3.7·3.8), 네트워크(3.9), 그리고 다른 길(3.10).

이제 ROS 2가 어떻게 동작하는지는 다 봤다. 남은 질문은 어떻게 만들고 배포하는가다. 소스 코드가 패키지가 되고, 패키지가 워크스페이스가 되고, 워크스페이스가 로봇 위의 바이너리가 되기까지 — ament·colcon·rosdep·bloom·크로스 컴파일·CI가 제4부 빌드·패키징·배포(4.1~4.10) 의 주제다. 4.1에서 ament 빌드 시스템의 구조부터 시작한다.