Unitree SDK 분석해보기

목차

  1. 개요
  2. 시스템 아키텍처
  3. 보행 제어 방식
  4. 핵심 API 분석
  5. 코드 실행 흐름
  6. 주요 보행 기능
  7. 결론 및 시사점

개요

로보틱스 연구를 하다보면 특정 디바이스에 종속된 movement, locomotion, task를 수행해야 할 때가 있다. 최근들어 Unitree사의 Go2를 시뮬레이션상에서 연구 할 일이 많아 따로 작성해봄.

Unitree SDK2 Python은 Unitree 로봇(Go2, B2, G1, H1 등)을 제어하기 위한 공식 Python API임. 이 글은 Go2 로봇의 보행 로직을 중심으로 API의 작동 원리와 구현 방식을 분석해봄.

주요 특징

  • DDS(Data Distribution Service) 기반 통신: 실시간 분산 통신 프로토콜 사용
  • 계층적 제어 구조: High-level(Sport Mode)과 Low-level 제어 분리
  • RPC 기반 서비스 아키텍처: 모듈화된 서비스 구조

시스템 아키텍처

1. 디렉토리 구조

unitree_sdk2_python/
├── example/              # 예제 코드
│   └── go2/
│       ├── high_level/   # 고수준 제어 예제
│       └── low_level/    # 저수준 제어 예제
├── unitree_sdk2py/       # 핵심 라이브러리
│   ├── core/            # 통신 채널 및 설정
│   ├── go2/             # Go2 전용 모듈
│   │   ├── sport/       # Sport 모드 제어
│   │   └── robot_state/ # 로봇 상태 관리
│   ├── rpc/             # RPC 통신 모듈
│   └── idl/             # 데이터 타입 정의

2. 통신 아키텍처

┌─────────────────┐     RPC/DDS     ┌─────────────────┐
│  Python Client  │ ◄─────────────► │  Robot Service  │
│  (SDK)          │                  │  (내장 서비스)   │
└─────────────────┘                  └─────────────────┘
        │                                     │
        │                                     │
    ┌───▼───┐                           ┌────▼────┐
    │  High │                           │  Low    │
    │  Level│                           │  Level  │
    └───────┘                           └─────────┘

보행 제어 방식

1. High-Level 제어 (Sport Mode)

고수준 제어는 SportClient를 통해 이루어지며, 복잡한 동작을 간단한 명령으로 실행할 수 있습니다.

주요 특징:

  • 추상화된 명령: Move(vx, vy, vyaw) 같은 직관적인 인터페이스
  • 자동 균형 제어: 내부적으로 자세 제어 및 균형 유지
  • 사전 정의된 동작: 백플립, 춤, 계단 오르기 등

2. Low-Level 제어

저수준 제어는 개별 모터를 직접 제어하며, 정밀한 움직임 구현이 가능합니다.

주요 특징:

  • 모터 직접 제어: 위치(q), 속도(dq), 토크(tau) 제어
  • PD 제어기: Kp(비례 게인), Kd(미분 게인) 설정
  • 실시간 피드백: 2ms 주기로 제어 명령 전송

핵심 API 분석

1. SportClient 클래스 구조

class SportClient(Client):
    def __init__(self, enableLease: bool = False):
        super().__init__(SPORT_SERVICE_NAME, enableLease)

    def Init(self):
        # API 버전 설정
        self._SetApiVerson(SPORT_API_VERSION)

        # API 등록 (40개 이상의 API)
        self._RegistApi(SPORT_API_ID_DAMP, 0)
        self._RegistApi(SPORT_API_ID_MOVE, 0)
        # ...

2. 주요 보행 관련 메서드

기본 이동 제어

def Move(self, vx: float, vy: float, vyaw: float):
    """
    로봇 이동 제어
    - vx: 전진/후진 속도 (m/s)
    - vy: 좌우 이동 속도 (m/s)
    - vyaw: 회전 속도 (rad/s)
    """
    p = {"x": vx, "y": vy, "z": vyaw}
    parameter = json.dumps(p)
    code = self._CallNoReply(SPORT_API_ID_MOVE, parameter)
    return code

보행 모드 전환

def SwitchGait(self, t: int):
    """
    보행 패턴 변경
    - 0: 트로팅(Trotting) - 대각선 다리 동시 이동
    - 1: 기타 보행 패턴
    """
    p = {"data": t}
    parameter = json.dumps(p)
    code, data = self._Call(SPORT_API_ID_SWITCHGAIT, parameter)
    return code

고급 보행 기능

# 자유 보행 모드
def FreeWalk(self, flag: bool)

# 장애물 회피 보행
def FreeAvoid(self, flag: bool)

# 계단 오르기
def WalkStair(self, flag: bool)

# 직립 보행
def WalkUpright(self, flag: bool)

3. Low-Level 모터 제어

class MotorCmd_:
    mode: uint8      # 제어 모드 (0x01: PMSM 모드)
    q: float32       # 목표 위치 (라디안)
    dq: float32      # 목표 속도 (라디안/초)
    tau: float32     # 목표 토크 (Nm)
    kp: float32      # 위치 비례 게인
    kd: float32      # 속도 미분 게인

코드 실행 흐름

1. High-Level 보행 예제 실행 흐름

1. 초기화
   ├─ ChannelFactoryInitialize() - DDS 통신 채널 초기화
   ├─ SportClient 생성
   └─ client.Init() - API 등록

2. 명령 실행 루프
   ├─ 사용자 입력 대기
   ├─ 명령 선택 (예: Move, StandUp, BackFlip 등)
   ├─ RPC 호출 (_Call 또는 _CallNoReply)
   └─ 로봇 서비스에서 명령 실행

3. 내부 처리 과정
   ├─ JSON 파라미터 생성
   ├─ API ID와 함께 서비스 호출
   ├─ 서비스에서 명령 해석
   └─ 모터 제어 신호 생성 및 전송

2. Low-Level 제어 실행 흐름

1. 초기화
   ├─ 통신 채널 설정
   ├─ Publisher/Subscriber 생성
   └─ 초기 모터 위치 읽기

2. 제어 루프 (2ms 주기)
   ├─ 현재 상태 읽기 (LowState)
   ├─ 목표 위치 계산
   ├─ PD 제어기 파라미터 설정
   ├─ CRC 계산
   └─ 명령 전송 (LowCmd)

3. 보간 및 전환
   ├─ 시작 위치에서 목표 위치로 부드러운 전환
   ├─ 각 단계별 진행률 계산 (percent_1, percent_2...)
   └─ 선형 보간을 통한 관절 각도 계산

주요 보행 기능

1. 기본 보행 패턴

기능 API 설명
전진/후진 Move(vx, 0, 0) 직선 이동
좌우 이동 Move(0, vy, 0) 측면 이동 (크랩 워크)
제자리 회전 Move(0, 0, vyaw) Yaw 축 회전
트로팅 SwitchGait(0) 대각선 다리 동시 이동

2. 고급 보행 기능

기능 API 설명
자유 보행 FreeWalk() AI 기반 적응형 보행
장애물 회피 FreeAvoid() 센서 기반 자동 회피
계단 오르기 WalkStair() 계단 감지 및 적응
직립 보행 WalkUpright() 두 다리로 걷기
교차 보행 CrossStep() 다리 교차 패턴

3. 특수 동작

동작 API 설명
백플립 BackFlip() 후방 공중제비
좌측 플립 LeftFlip() 측면 공중제비
Dance1(), Dance2() 사전 정의된 춤 동작
점프 FreeJump() 자유 점프 동작

결론 및 시사점

1. 강화학습 적용을 위한 고려사항

장점:

  • High-Level API: 복잡한 동작을 간단히 실행 가능
  • Low-Level 접근: 정밀한 모터 제어로 커스텀 보행 패턴 구현 가능
  • 실시간 피드백: 2ms 주기의 빠른 제어 루프

도전 과제:

  • 제한된 중간 수준 제어: High-Level과 Low-Level 사이의 갭
  • 내부 알고리즘 불투명성: Sport 모드의 내부 구현 비공개
  • 센서 데이터 접근: IMU, 발 힘 센서 등의 제한적 접근

2. 권장 접근 방법

  1. 초기 단계: High-Level API로 기본 동작 학습
  2. 중급 단계: TrajectoryFollow API로 경로 기반 보행 구현
  3. 고급 단계: Low-Level 제어로 커스텀 보행 패턴 개발

3. 주요 인사이트

  • 계층적 제어의 중요성: 추상화 수준에 따른 적절한 API 선택
  • 실시간성 보장: DDS 통신으로 낮은 지연시간 달성
  • 모듈화된 구조: 각 기능이 독립적인 서비스로 구현