SDK Guide#

What you’ll do

  • C++ SDK를 빌드하고 예제 코드를 실행하여 하드웨어 동작을 확인합니다.

  • Driver 클래스를 사용해 차량에 주행 명령(\(v, \omega\))을 전송하는 방법을 익힙니다.

  • 차량의 상태(속도, 배터리 등)를 수신하고 처리하는 구조를 이해합니다.

Prerequisites

Next


1. SDK 구성#

SDK는 사용 목적에 따라 두 가지 레벨의 인터페이스를 제공합니다. 대부분의 자율주행 알고리즘 개발에는 Driver 클래스 사용을 권장합니다.

  • Driver (Recommended)

    • 내부 스레드가 명령 입력, 속도 요청, 보조 명령을 주기적으로 처리합니다.

    • 수신 데이터는 메시지 큐로 전달됩니다.

  • UartClient (Advanced)

    • 사용자가 송수신 시점과 파싱을 직접 제어해야 하는 Low-Level 클래스입니다.

    • 통신 프로토콜 디버깅, 커스텀 스케줄링 구현, 또는 Driver 구조를 사용할 수 없는 특수한 환경.

    • DriverUartClient로 구현되어있습니다.

권장 사용 패턴

  • 기본: Driver (I/O 스레드, 수신 큐, 타임아웃 포함)

  • UartClient를 쓰는 경우: 프레임 단위 타이밍을 직접 제어하거나, 보조 명령 (0xAF)을 직접 실험 및 디버깅할 때


2. 빌드와 첫 동작 확인#

  • github repository에서 sdk를 clone합니다.

git clone https://github.com/Seo12044/KAIST_Mobility_Challenge_SDK.git
cd KAIST_Mobility_Challenge_SDK/

SDK 리포지토리 루트에서 빌드합니다.

2.1 Linux 빌드#

cmake -S . -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build -j

2.2 동작 테스트#

빌드가 완료되면 기본 예제인 driver_demo를 실행하여 연결을 확인합니다.

./build/driver_demo

주의

초기 테스트는 바퀴가 공중에 뜬 상태(또는 아주 낮은 속도)에서 진행하세요.

예제 구성:

  • 속도 읽기(속도 요청): read_speed

  • 배터리 전압/AllState(보조 명령): read_battery, read_allstate

  • Driver 큐 처리: driver_observe

  • 고속 성능 확인: high_rate_control


3. 명령 입력#

SDK는 선속도(\(v\))와 각속도(\(\omega\)) 를 입력받습니다.DriversetCommand(v, omega)를 호출하여 차량을 제어합니다.

  • \(v\) (velocity_mps): \(\mathrm{m/s}\)

  • \(\omega\) (omega_rps): \(\mathrm{rad/s}\), \(\omega>0\)이면 CCW, \(\omega<0\)이면 CW

Driver::setCommand(v, omega) 호출 시, SDK는 다음 수식을 통해 전송 패킷을 생성합니다.

\[\begin{split} \kappa = \begin{cases} \omega / v, & |v| > 10^{-3} \\ 0, & |v| \le 10^{-3} \end{cases} \end{split}\]

여기서 \(\kappa\)의 단위는 \(\mathrm{m}^{-1}\)입니다. 부호/기하 의미는 Vehicle Control Model에 정리되어 있습니다.


4. Timing & Safety#

안정적인 제어를 위해 하드웨어 송신 주기와 사용자 명령 업데이트 주기를 구분하여 이해해야 합니다.

4.1 주요 설정 파라미터 (Driver::Options)#

필드별 의미/기본값은 Driver::Options에 정리되어 있습니다.

파라미터

설명

권장 값

control_rate_hz

Driver가 하드웨어로 명령 패킷을 보내는 주기

\(200 \sim 400\,\mathrm{Hz}\)

vehicle_speed_rate_hz

Driver가 하드웨어에 현재 속도를 요청하는 주기

\(50\,\mathrm{Hz}\) (필요에 따라 조절)

command_timeout_ms

사용자 명령 업데이트가 끊길 경우 정지하는 시간

\(200\,\mathrm{ms}\)

\[ command\_timeout\_ms \approx \max(50,\ 2 \cdot \frac{1000}{command\_hz}) \]

예를 들어 \(command\_hz=50\,\mathrm{Hz}\)이면, \(command\_timeout\_ms \approx 200\,\mathrm{ms}\)가 됩니다.


5. 수신 데이터 처리#

5.1 Driver 큐 사용#

Driver는 수신된 UART 패킷을 파싱하여 메시지 큐에 저장합니다. 사용자는 메인 루프에서 이 큐를 비우며 데이터를 처리해야 합니다.

while (auto msg = drv.tryPopMessage()) {
  if (auto* vs = std::get_if<KMC_HARDWARE::VehicleSpeed>(&*msg)) {
    // vs->mps : 차량 속도 (m/s)
  } else if (auto* st = std::get_if<KMC_HARDWARE::AllState>(&*msg)) {
    // st->error_code : 에러 코드(bitmask)
  }
}

AllState.error_code의 비트 정의는 UART Protocol Reference의 AllState 섹션을 따릅니다.

5.2 UartClient 폴링 사용#

UartClient는 요청을 보낸 뒤 poll(timeout_ms)로 응답을 받아 처리하는 구조입니다. 명령 입력속도 요청, 보조 명령의 스케줄링을 직접 구현할 때 사용합니다.


6. 고속 제어#

\(1\,\mathrm{kHz}\) 수준의 고속 제어가 필요한 경우, 시스템 설정을 최적화해야 합니다.

  • Baud Rate 상향: \(921{,}600\,\mathrm{bps}\) 또는 \(1{,}000{,}000\,\mathrm{bps}\) 사용 권장.

  • Realtime Priority (Linux): 스레드 스케줄링 지연을 줄이기 위해 Driver 옵션에서 realtime_priority를 설정하십시오 (root 권한 필요 가능성 있음).


Troubleshooting#

UART Troubleshooting