uORB Messaging
소개
uORB는 thread간/프로세스간 통신을 위해서 비동기 publish()
/ subscribe()
을 사용합니다.
C++로 사용 방법을 익히려면 튜토리얼을 참고하세요.
uORB는 많은 어플리케이션이 의존하므로 자동으로 부팅시에 일찍이 구동됩니다. uorb start
로 구동시킵니다. 단위테스트는 uorb_tests
로 구동시킬 수 있습니다.
새로운 topic 추가하기
새로운 topic을 추가하기 위해서 msg/
디렉토리에 새로운 .msg
파일을 생성하고 파일 이름을 msg/CMakeLists.txt
목록에 추가합니다. 이렇게 하면 필요한 C/C++ 코드가 자동으로 생성됩니다.
지원하는 타입을 참고하려면 기존 msg
파일을 살펴보세요. 메시지는 달느 메시지의 nest로 사용할 수 있습니다.
각 생성된 C/C++ 구조체에는 uint64_t timestamp
필드가 추가되어 있을 것입니다. 이는 logger를 위해 사용되므로 메시지를 publish할 때 값을 넣도록 합니다.
topic을 코드에서 사용하려면 헤더를 포함합니다 :
#include <uORB/topics/topic_name.h>
.msg
파일에 다음과 같은 라인을 추가하면 단일 메시지 정의가 여러 독립적인 topic 인스턴스에서 사용할 수 있습니다. :
# TOPICS mission offboard_mission onboard_mission
다음으로 코드에서 이를 topic id로 사용 : ORB_ID(offboard_mission)
.
Publishing
topic을 publish하는 것은 시스템 어디서든 가능합니다. 인터럽트 컨텍스트(hrt call
API에서 호출하는 함수)에서도 가능합니다. 그러나 topic을 advertising은 인터럽트 컨텍스트의 외부에서만 가능합니다. topic은 추후 publish되므로 동일한 프로세스에서 advertise해야만 합니다.
Topics 목록 및 Listening in
listener
명령은 Pixracer (FMUv4)와 Linux / OS X에서만 가능합니다.
모든 topic의 목록을 보기 위해 파일 핸들 목록 보기:
ls /obj
5개 메시지에 대해서 한 개 topic의 컨텐트를 liste하기 위해서 listener 실행 :
listener sensor_accel 5
출력은 n 번 topic 콘텐츠입니다. :
TOPIC: sensor_accel #3
timestamp: 84978861
integral_dt: 4044
error_count: 0
x: -1
y: 2
z: 100
x_integral: -0
y_integral: 0
z_integral: 0
temperature: 46
range_m_s2: 78
scaling: 0
TOPIC: sensor_accel #4
timestamp: 85010833
integral_dt: 3980
error_count: 0
x: -1
y: 2
z: 100
x_integral: -0
y_integral: 0
z_integral: 0
temperature: 46
range_m_s2: 78
scaling: 0
NuttX-기반 시스템 (Pixhawk, Pixracer 등)에서
listener
명령은 QGroundControl MAVLink 콘솔내에서 센서의 값이나 다른 topic을 조사하기 위해서 호출할 수 있습니다. QGC가 무선으로 연결되어 있는 경우에도(비행체가 비행 중인 경우) 사용할 수 있으므로 강력한 디버깅 도구가 됩니다. 추가 정보는 Sensor/Topic Debugging을 참고하세요.
urb top 명령
uorb top
명령은 실시간으로 각 topic의 publish 주기를 보여줍니다.:
update: 1s, num topics: 77
TOPIC NAME INST #SUB #MSG #LOST #QSIZE
actuator_armed 0 6 4 0 1
actuator_controls_0 0 7 242 1044 1
battery_status 0 6 500 2694 1
commander_state 0 1 98 89 1
control_state 0 4 242 433 1
ekf2_innovations 0 1 242 223 1
ekf2_timestamps 0 1 242 23 1
estimator_status 0 3 242 488 1
mc_att_ctrl_status 0 0 242 0 1
sensor_accel 0 1 242 0 1
sensor_accel 1 1 249 43 1
sensor_baro 0 1 42 0 1
sensor_combined 0 6 242 636 1
컬럼은 : topic 이름, 다중-인스턴스 인덱스, subscriber의 수, Hz 단위 publishing 주기, 손실 메시지 수(모두 합친 subscriber), queue 크기
다중-인스턴스
uORB는 orb_advertise_multi
를 통해 동일한 topic의 다중 독립 인스턴스를 publish하는 매커니즘을 제공합니다. publisher에게 인스턴스 인덱스를 반환합니다. subscriber는 orb_subscribe_multi
를(orb_subscribe
는 첫번째 인스턴스를 subscribe) 이용해서 어떤 인스턴스를 선택해야만 합니다.
다중 인스턴스를 가지면 시스템이 동일한 타입의 여러 센서를 가지고 있는 경우 유용합니다.
동일 topic에 대해서 orb_advertise_multi
와 orb_advertise
를 섞지 않도록 합니다.
전체 API는 src/modules/uORB/uORBManager.hpp를 참고하세요.
문제해결 및 일반적인 실수
다음에서는 일반적인 실수나 비정상적인 상황에 대해서 설명합니다 :
- topic이 publish되지 않아요 : 각 호출에서
ORB_ID()
가 맞는지 확인.orb_subscribe
와orb_unsubscribe
가orb_publish
로서 동일한 태스크에서 호출 되었는지가 중요합니다. 이것은px4_task_spawn_cmd()
에 적용되지만 work queue(work_queue()
)를 사용하는 경우에도 적용됩니다. - 정리(clean up) 하기 :
orb_unsubscribe
와orb_unadvertise
를 사용하세요. - 성공적으로
orb_check()
나px4_poll
호출은orb_copy()
가 필요하고 다음 poll에서 즉시 반환됩니다. - topic을 advertise하기 전에
orb_subscribe
를 호출해도 아무 문제 없습니다. orb_check()
와px4_poll()
은orb_subscribe()
후에 완료되는 publication에 대해서만 true를 반환합니다. topic이 일정하게 publish되지 않는다는 점이 중요합니다. 만약 subscriber가 이전 데이터를 원하는 경우orb_subscribe()
이후에 바로 조건없이orb_copy()
를 하면 됩니다.(advertiser가 없는 경우라면orb_copy()
는 실패하게 됩니다.)