29.6. 수동 모드 간 상태 전이(State Transition) 메커니즘 소스 분석

29.6. 수동 모드 간 상태 전이(State Transition) 메커니즘 소스 분석

1. 개요 및 상태 전이(State Transition)의 필요성

멀티로터 비행 중 조종자는 지형지물, 풍향, 비행 목적의 변화에 따라 조종기의 특정 스위치를 조작하여 비행 모드를 수시로 변경한다. 예를 들어, 순수한 각속도 비행인 아크로(Acro) 모드에서 수평 복원 기능이 켜진 안정화(Stabilized) 모드로, 또는 완전히 제한이 해제된 매뉴얼(Manual) 모드로 전환할 수 있다.

이때 펌웨어 내부적으로는 단순히 계산 알고리즘(제어 루프)만 스왑(Swap)되는 것이 아니라, 센서의 유효성을 검증하고 이전 모드의 제어기 상태(누적 오차, 목표값 등)를 초기화해야 하는 복잡한 문제들이 발생한다. 최신 PX4-Autopilot(v1.14 이상)에서는 이러한 일련의 과정을 안전하게 통제하기 위해 중앙 집중식 상태 머신(Finite State Machine, FSM)인 Commander 모듈과 하위 Flight Mode Manager를 연동하여 ‘자연스럽고 매끄러운’ 수동 모드 간 상태 전이 메커니즘을 구현하고 있다.

2. 상태 전이 컨트롤 아키텍처

수동 모드 간의 전환이 요구될 때, PX4 펌웨어는 크게 세 가지 단계를 거쳐 상태 전환 트랜잭션(Transaction)을 완료한다.

  1. 의도 파악 및 사전 검증(Pre-condition Check): 조종기의 RC 채널 입력 또는 MAVLink 명령이 Commander 모듈에 도달하면, 기체의 센서 건강 상태(Health), 무장(Arming) 여부, 배터리 상태 등을 종합하여 전환이 허용되는지(Valid) 결정한다.
  2. 모듈 라우팅(Module Routing): 상태 전환이 최종 승인되면, Flight Mode Manager는 기존에 활성화된 수동 모드 태스크(Task)를 비활성화하고 새로운 수동 모드 태스크를 백그라운드 스레드에서 전경으로 끌어올린다.
  3. 범플리스 트랜스퍼(Bumpless Transfer): 갑작스러운 모드 변경으로 인한 목표값(Setpoint) 점프 및 액추에이터의 순간적 튐(Jerking) 현상을 방지하기 위해 새로운 제어기의 파라미터가 기체의 현재 물리적 상태로 초기화된다.

3. 상태 전이 흐름도 (Mermaid 설계도)

조종기의 스위치 입력으로부터 시작하여 제어 루프가 스왑되기까지의 시스템 처리 파이프라인은 다음과 같다.

graph TD
    A[조종기 RC Mode Switch 변경] --> B[RC Input / Manual Control 모듈]
    B --> C(Mode Change Request 생성)
    
    C --> D[Commander 모듈<br>State Machine Helper]
    
    D --> E{센서 및 상태 검증<br>전환 허가 통과?}
    E -- 거부 (Deny) --> F[거부 경고음 / 기존 모드 유지]
    E -- 승인 (Accept) --> G[Flight Mode Manager 트리거]
    
    G --> H[기존 모드 Task 비활성화<br>예: Acro Mode 중지]
    G --> I[신규 모드 Task 활성화<br>예: Stabilized Mode 시작]
    
    I --> J[Bumpless Transfer 로직 수행<br>현재 역학 상태로 Setpoint 동기화]
    J --> K[신규 PID 제어 루프 정상 구동]
    K --> L[안정적인 구동기 제어]

4. 소스 코드 깊은 분석 (src/modules/commander)

PX4 소스 코드 내에서 상태 전환 로직은 주로 src/modules/commander/state_machine_helper.cpp 및 관련된 모드 태스크 C++ 클래스들에 분산되어 구현된다.

4.1 모드 전환 검증 (State Machine Helper)

Commander 모듈 내의 전환 결정 함수(예: set_nav_state)는 목표 모드가 활성화될 수 있는지 철저히 검증한다.

// 수동 안정화 제어(Stabilized) 모드로 전이 가능한지 검증하는 의사 코드(Pseudo Code)
bool MainStateTransition::check_manual_stabilized_conditions() {
    // 1. 센서 융합기(EKF)로부터 현재 자세 방향(Attitude) 데이터를 획득 가능한가?
    if (!_status.condition_attitude_valid) {
        return false; // AHRS 실패 시 전환 불가
    }
    
    // 2. 조종자의 유효한 수동 조이스틱 입력이 존재하는가?
    if (!_status.rc_signal_found_once && !_status.data_link_lost) {
        // MAVLink 수동 제어도 허용될 수 있으나 기본적으로 조종기 연결성이 필요함
        return false;
    }

    return true; // 전환 허용
}

안정화(Stabilized) 모드와 달리 순수 수동(Manual/Acro) 모드는 자세 정보의 품질이 약간 저하되더라도 각속도 자이로(Gyro) 센서의 신뢰성만 유지된다면 전환을 허가할 수 있도록 조건 분기가 달리 설계되어 있다.

4.2 범플리스 트랜스퍼 (Bumpless Transfer) 구현

모드 전환 시 가장 핵심적인 제어 기술은 드론이 튕기거나 갑자기 곤두박질치는 현상을 막는 범플리스 트랜스퍼 알고리즘이다. 아크로 모드에서 안정화 모드로 전환하는 순간, 조종기의 피치 스틱이 0(중앙)에 있더라도 드론이 즉시 수평을 맞추기 위해 급격히 기동하는 것을 막기 위하여 FlightTaskManualAltitude 또는 각속도 제어기의 초기화 코드에서 다음과 같은 로직이 수행된다.

// 새로운 수동 제어 모드가 처음 활성화(onActivate) 될 때
void RateControl::reset() {
    // 1. 누적 오차 제거 (Integral Windup 발생분 소거)
    _torque_int.zero();

    // 2. 미분기(Derivative)의 노이즈 필터링 상태 초기화
    _angular_accel.zero();
}

void FlightTaskManualStabilized::activate() {
    // 활성화 순간의 현재 오일러 각도를 초기 목표 자세(Target Attitude)로 매핑하여
    // 자세 제어 루프의 초기 P-Error를 0으로 강제 편향(Zeroing)시킴 (선택적 구현)
    // 조종자가 스틱을 중립으로 가져갈 때까지 부드러운 감쇠 곡선(Easing)을 적용
}

이와 같이 모드 변경 이벤트 엣지(Edge)에서 내부 메모리 변수들을 초기화(reset())하고, 전환 시점의 동적 관성을 수용하는 것이 PX4 특유의 매끄러운 비행 감각에 직결된다.

5. Ardupilot 대비 관제 및 알고리즘 차이

수동 모드 간 전환에 관하여 두 시스템 모두 상태 머신을 바탕으로 안전성을 꾀하고 있으나 체계 구조가 상이하다.

  • PX4-Autopilot:
    uORB 메시징 구조를 기반으로 한 완전한 마이크로커널형(Microkernel-like) 컴포넌트 아키텍처를 가진다. Commander 모듈은 전역 상태 머신으로서 vehicle_status uORB 토픽을 Publish하며, 하위의 Flight Mode Managermc_att_control 앱들이 이 상태값 구독(Subscribe)을 통해 각자 자신의 모드를 활성화 또는 비활성화 한다. 컴포넌트 간 결합도가 낮아 사용자 정의 비행 모드를 끼워넣기 매우 편리하다.
  • Ardupilot:
    Ardupilot은 전통적으로 모놀리식(Monolithic) 아키텍처에 가까운 Copter.cpp 내 전역 루프 구조 속에서 set_mode() 함수를 호출하여 모드를 덮어쓰는 방식을 취한다. set_mode() 내부 안에 각 모드별 _init() 함수가 묶여있어 상태 변화로직과 제어 초기화 로직이 매우 직관적이고 밀집되어 있다. 따라서 디버깅 통제(Step-in)는 쉽지만, 새로운 아키텍처 형태의 모드를 스택 중간에 삽입하기는 PX4에 비해 복잡한 경향이 있다.

요약하자면, PX4의 수동 모드 간 전이 메커니즘은 Commander 모듈의 통제 아래 분산된 모듈들이 범플리스 트랜스퍼를 능동적으로 수행함으로써, 다양한 비행 시나리오에서도 치명적인 비행 궤적의 튐이나 통제 불능을 철저히 방지하는 데 그 목적이 있다.