업데이트 관리자는 VM의 업데이트를 실행합니다. 업데이트 관리자는 시스템 통합업체가 제공하는 클라이언트와 협력합니다. 클라이언트는 업데이트 페이로드를 제공하고 전반적인 차량 업데이트를 조정합니다. 업데이트는 다음 단계로 구성됩니다.
- READY: 업데이트가 진행 중이 아닙니다.
- PREPARE: 업데이트 관리자는 업데이트를 디스크에 쓰지만 활성화하지는 않습니다.
- ACTIVATE: 업데이트 관리자는 준비된 업데이트를 활성화하여 재부팅 후 적용되도록 합니다.
- COMMIT: 업데이트 관리자는 업데이트를 영구적으로 만듭니다.
그림 1. 업데이트 관리자의 대략적인 작업입니다.
업데이트 관리자는 이 페이지에 설명된 시스템 업데이트와 서비스 번들 업데이트를 지원합니다.
시스템 업데이트
Android OS는 한 번에 하나의 슬롯 만 활성화된 슬롯이라는 두 개의 파티션 집합을 사용합니다. 시스템 업데이트는 비활성 슬롯에 새 파티션 집합을 쓰고 시스템은 다음 재부팅 시 활성 슬롯을 전환합니다. 시스템 업데이트 빌드에 관한 자세한 내용은 A/B 시스템 업데이트를 참고하세요.
서비스 번들 업데이트
AAOS SDV에서 서비스 번들은 APEX 내에서 서비스를 함께 패키징합니다. 서비스 번들 업데이트는 임시 세션에서 새 APEX 파일을 스테이징합니다. 시스템은 시스템 재부팅 후 이러한 업데이트된 번들을 활성화합니다. 서비스 번들 APEX 빌드에 관한 자세한 내용은 서비스 번들 업데이트를 참고하세요.
상태 머신
클라이언트의 요청과 시스템 서비스의 이벤트는 업데이트 관리자 상태 머신을 구동합니다. 업데이트 관리자는 예기치 않은 재부팅이나 비정상 종료 후에도 상태를 복구하고 업데이트 프로세스를 재개하는 등 복원력이 있도록 설계되었습니다.
그림 2. 업데이트 관리자 상태 머신입니다.
API
업데이트 관리자는 상태 머신을 통해 업데이트 프로세스를 구동하는 API를 제공합니다. API는 VSIDL을 사용합니다. VSIDL은 SDV Comms를 지원하는 모든 VM에 있는 클라이언트를 지원하고 요청 실패 알림을 제공합니다.
보안 및 액세스
시스템은 승인 정책을 사용하여 API 액세스를 제한합니다. 승인된 클라이언트만 업데이트 관리자를 호출할 수 있습니다.
상태 업데이트
업데이트 작업은 장기 실행될 수 있으므로 업데이트 관리자는 비동기 상태 업데이트를 제공합니다. 클라이언트는 상태 업데이트를 구독하여 상태를 모니터링해야 합니다.
구독 관리
구독: 클라이언트는
SubscribeToStatusUpdates()메서드를 호출하여 상태 업데이트를 구독합니다.rpc SubscribeToStatusUpdates(SubscribeToStatusUpdatesRequest) returns (SubscribeToStatusUpdatesResponse) {} message SubscribeToStatusUpdatesRequest {} message SubscribeToStatusUpdatesResponse {}클라이언트는
SubscribeToStatusUpdates()를 호출하기 전에UpdateManagerListenerService를 구현하는 RPC 인터페이스를 시작해야 합니다.구독 취소: 클라이언트는
UnsubscribeFromStatusUpdates()를 호출하여 상태 업데이트 수신을 중지할 수 있습니다.rpc UnsubscribeFromStatusUpdates(UnsubscribeFromStatusUpdatesRequest) returns (UnsubscribeFromStatusUpdatesResponse) {} message UnsubscribeFromStatusUpdatesRequest {} message UnsubscribeFromStatusUpdatesResponse {}
UpdateManagerListenerService
UpdateManagerService에서 SubscribeToStatusUpdates()를 호출하는 클라이언트는 상태 업데이트를 수신하기 위해 다음 서비스를 구현해야 합니다.
service UpdateManagerListenerService {
/* Called when there is a status update from the Update Manager. */
rpc OnStatusUpdate(OnStatusUpdateRequest) returns (OnStatusUpdateResponse) {}
}
message OnStatusUpdateRequest {
oneof status_update {
UpdateManagerStatus update_manager_status = 1;
UpdateProgress update_progress = 2;
}
}
message OnStatusUpdateResponse {}
OnStatusUpdateRequest 는 status_update 필드를 사용하여 가능한 두 메시지 중 하나를 전달합니다.
UpdateManagerStatus: 업데이트 관리자의 상태가 변경될 때 전송됩니다.UpdateProgress: 프로세스가 상당한 시간이 걸릴 수 있으므로PREPARE및ACTIVATE_PRE_REBOOT상태에서 업데이트 진행률을 나타내기 위해 전송됩니다.
상태 및 오류 메시지
상태 메시지에는 상태 및 오류에 관한 세부정보가 포함됩니다.
UpdateManagerStatus: 업데이트의 현재 단계와 오류의 이유를 보고합니다.message UpdateManagerStatus { /* The current state of the update */ UpdateState update_state = 1; /* The reason for the failure, if the update failed */ FailureReason failure_reason = 2; } enum UpdateState { /* The Update Manager is ready to accept a new update. */ READY = 0; /* An update is being prepared. */ PREPARE = 1; /* The update failed during the prepare step. Roll back the update to start a * new update. */ PREPARE_FAILURE = 2; /* The update was prepared successfully. */ PREPARE_COMPLETE = 3; /* A rollback has started from the prepare step. When complete, transitions * to READY. */ PREPARE_ROLLBACK = 4; /* The prepared update is being activated. */ ACTIVATE_PRE_REBOOT = 5; /* The update failed during the activate step before the reboot. Roll back the * update to start a new update. */ ACTIVATE_PRE_REBOOT_FAILURE = 6; /* The update was activated successfully. Reboot to complete activation. */ ACTIVATE_PRE_REBOOT_COMPLETE = 7; /* A rollback has started from the activate pre-reboot step. When complete, * transitions to READY. */ ACTIVATE_PRE_REBOOT_ROLLBACK = 8; /* An update was successfully activated after the reboot. The update needs to * be committed or rolled back to be completed. */ ACTIVATE_POST_REBOOT_COMPLETE = 9; /* A rollback has started from the activate post-reboot step. */ ACTIVATE_POST_REBOOT_ROLLBACK = 10; /* The rollback was completed successfully. Reboot to complete the * rollback. */ ACTIVATE_POST_REBOOT_ROLLBACK_COMPLETE = 11; /* The update is being committed. When complete, transitions to READY */ COMMIT = 12; /* The prepare request is being cancelled */ PREPARE_CANCEL = 13; /* The system update has started suspending */ PREPARE_SUSPEND = 14; /* The system update has finished suspending */ PREPARE_SUSPEND_COMPLETE = 15; } message FailureReason { /* The original error that triggered the failure */ ErrorCode error_code = 1; /* Binder error message for most ErrorCodes. */ string error_message = 2; } enum ErrorCode { Unspecified = 0; /* Error from UpdateEngine service */ UpdateEngineError = 1; // Error from the ApexService ApexServiceError = 2; // Error from the BootControlService BootControlServiceError = 3; // Error from the VoldService VoldServiceError = 4; }UpdateProgress: 시스템 업데이트 중에 업데이트 엔진의 현재 상태를 보고합니다.message UpdateProgress { /* Matches the enum UpdateStatus from the UpdateEngine service. */ int32 status_code = 1; /* A value ranging from 0.0 to 1.0, 1.0 representing the process is complete. */ float percentage = 2; }
즉시 상태 가져오기
GetStatus()를 호출하여 언제든지 현재 상태와 페이로드를 가져올 수 있습니다. SystemUpdatePayload 및 ServiceBundleUpdatePayload
메시지는 준비에 설명되어 있습니다.
rpc GetStatus(GetStatusRequest) returns (GetStatusResponse) {}
message GetStatusRequest {}
message GetStatusResponse {
/* The status of the Update Manager */
UpdateManagerStatus update_manager_status = 1;
/* The current update payload, if one has been set through the Prepare() request */
oneof payload {
SystemUpdatePayload system_update_payload = 2;
ServiceBundleUpdatePayload service_bundle_update_payload = 3;
}
}
준비
Prepare 요청은 페이로드를 스테이징하여 업데이트 프로세스를 시작하지만 시스템은 업데이트를 활성화할 때까지 기다립니다.
rpc Prepare(PrepareRequest) returns (PrepareResponse) {}
message PrepareRequest {
oneof payload {
SystemUpdatePayload system_update_payload = 1;
ServiceBundleUpdatePayload service_bundle_update_payload = 2;
}
}
message PrepareResponse {}
요청이 유효하면 상태가 PREPARE로 전환되고 업데이트 관리자가 업데이트를 시작합니다.
페이로드 유형에 따라 업데이트 유형이 결정됩니다.
시스템 업데이트 페이로드
시스템 업데이트는 무선 (OTA) 업데이트 이미지의 경로가 필요한 SystemUpdatePayload 데이터를 사용합니다. 다른 매개변수는 이미지에서 파싱되지만 파싱된 값을 재정의하도록 지정할 수 있습니다.
message SystemUpdatePayload {
/* Absolute path to the update image (e.g., /updates/ota_update.zip) */
string payload = 1;
/* Offset (in bytes) into the payload where the payload binary starts. */
optional int64 payload_offset = 2;
/* The amount of data (in bytes) to read from "payload" as the update payload. */
optional int64 payload_size = 3;
/* The header key value pairs to apply with the payload. */
map<string, string> header_key_value_pairs = 4;
}
업데이트 관리자는 설치 후 단계를 실행하기 위해 OTA 이미지 (/data/ota_package 디렉터리의 클라이언트에서 제공)를 처리하지만 활성 부팅 슬롯을 전환하지는 않습니다. 그런 다음 성공 시 PREPARE_COMPLETE 상태로 전환되고 실패 시 PREPARE_FAILURE 상태로 전환됩니다.
시스템 업데이트 일시중지
시스템 업데이트에 대해서만 업데이트 프로세스를 일시중지할 수 있습니다. 이 요청은 PREPARE 상태일 때만 유효합니다.
일시중지: 업데이트를 일시중지하고
PREPARE_SUSPEND를 통해 상태를 전환합니다.rpc Suspend(SuspendRequest) returns (SuspendResponse) {} message SuspendRequest {} message SuspendResponse {}성공 시 상태가
PREPARE_SUSPEND_COMPLETE로 전환됩니다. 실패 시 상태가PREPARE_FAILURE로 전환됩니다.재개: 일시중지된 업데이트를 계속합니다. 이는
PREPARE_SUSPEND_COMPLETE상태에서만 유효합니다.rpc Resume(ResumeRequest) returns (ResumeResponse) {} message ResumeRequest {} message ResumeResponse {}상태가
PREPARE상태로 다시 전환됩니다.
서비스 번들 업데이트 페이로드
서비스 번들 업데이트는 APEX 파일의 경로를 포함하고 활성화 시도 한도를 설정하는 ServiceBundleUpdatePayload를 사용합니다.
message ServiceBundleUpdatePayload {
/* Absolute path to an .apex file. Multiple .apex files can be included. */
repeated string apex_path = 1;
/* Number of boots to attempt activation before aborting. Must be > 0. */
int32 boot_attempts = 2;
}
업데이트 관리자는 APEX 파일이 올바르게 서명되었는지 확인하고 세션에서 스테이징합니다. 성공 시 상태가 PREPARE_COMPLETE로 전환됩니다. 실패 시 상태가 PREPARE_FAILURE로 전환됩니다.
활성화
Activate 요청은 다음 재부팅 시 준비된 업데이트를 활성화합니다.
rpc Activate(ActivateRequest) returns (ActivateResponse) {}
message ActivateRequest {}
message ActivateResponse {}
재부팅 전
업데이트 관리자는 업데이트를 활성화하는 동안 ACTIVATE_PRE_REBOOT 상태로 전환됩니다. 업데이트 관리자는 시스템이 재부팅될 때 적용되는 사용자 데이터
체크포인트도 만듭니다.
활성화 작업은 업데이트 유형에 따라 다릅니다.
- 시스템 업데이트: 시스템은 설치 후 단계를 실행하고 다음 재부팅 시 전환할 부팅 슬롯을 설정합니다.
- 서비스 번들 업데이트: 시스템은 스테이징된 APEX 세션을 활성화 준비 상태로 표시합니다.
시스템이 업데이트를 성공적으로 활성화하면 상태가 ACTIVATE_PRE_REBOOT_COMPLETE로 전환됩니다. 이는 VM이 재부팅할 준비가 되었음을 나타냅니다.
그렇지 않으면 상태가 ACTIVATE_PRE_REBOOT_FAILURE로 전환됩니다.
재부팅 후
재부팅 후 시스템은 체크포인트 모드로 시작됩니다. 이 모드에서 시스템은 사용자 데이터 파티션의 변경사항을 영구 저장소에 커밋하지 않습니다. 시스템이 업데이트를 성공적으로 커밋하지 않으면 이러한 변경사항을 초기 상태로 되돌립니다.
부팅 한도
시스템은 다음 조건 중 하나에서 사용자 데이터 파티션의 변경사항을 되돌립니다.
- 클라이언트가 명시적
Rollback()요청을 보내고 시스템을 재부팅합니다. - 클라이언트가
Commit()또는Rollback()을 호출하지 않고 시스템이 너무 많이 부팅됩니다. 부팅 한도는 업데이트 유형마다 다릅니다.- 시스템 업데이트:
BootControl구현에서 이를 설정합니다. 예를 들어 Cuttlefish 기기에서 사용하는 구현의 기본 한도는 7회 부팅입니다. - 서비스 번들 업데이트: 클라이언트에서 제공하는
ServiceBundleUpdatePayload의boot_attempts필드는Prepare()요청이 이루어질 때 이를 설정합니다.
- 시스템 업데이트:
인증
그런 다음 시스템은 업데이트를 인증합니다.
- 시스템 업데이트: dm-verity는 업데이트된 슬롯에 손상이 있는지 확인합니다.
- 서비스 번들 업데이트:
apexd는 각 APEX의 서명을 확인하고 APEX의 이미지를 파일 시스템에 마운트합니다.
인증에 성공하면 상태가 ACTIVATE_POST_REBOOT_COMPLETE로 전환됩니다. 업데이트 관리자는 Commit() 또는 Rollback()을 기다립니다.
인증에 실패하면 시스템이 재부팅됩니다. 시스템이 부팅 한도에 도달하면 시스템은 원래 상태로 되돌아갑니다.
- 시스템 업데이트: 시스템은 원래 슬롯으로 되돌아갑니다.
- 서비스 번들 업데이트: 업데이트된 APEX가 삭제되고 원래 APEX가 다시 활성화됩니다.
업데이트 유형에 대해 인증에 실패하면 원래 상태가 복원된 후 상태가 ACTIVATE_PRE_REBOOT_FAILURE로 전환됩니다.
롤백
Rollback 요청은 시스템을 업데이트 전 상태로 되돌리기 시작합니다.
rpc Rollback(RollbackRequest) returns (RollbackResponse) {}
message RollbackRequest {}
message RollbackResponse {}
여러 상태에서 Rollback() 요청을 할 수 있습니다. 초기 상태에 따라 시스템은 다른 작업을 실행하고 다른 상태가 이어집니다.
| 롤백이 실행될 때의 상태 | 상태 전환 | 시스템 작업 |
|---|---|---|
(시스템 업데이트만 해당) PREPARE, PREPARE_SUSPEND_COMPLETE |
→ PREPARE_CANCEL → PREPARE_ROLLBACK →
READY |
시스템 업데이트: 시스템 업데이트를 취소합니다. |
PREPARE_FAILURE, PREPARE_COMPLETE |
→ PREPARE_ROLLBACK → READY |
시스템 업데이트: 시스템 업데이트를 취소합니다. 서비스 번들 업데이트: 스테이징된 APEX 세션을 중단합니다. |
ACTIVATE_PRE_REBOOT_COMPLETE, ACTIVATE_PRE_REBOOT_FAILURE |
→ ACTIVATE_PRE_REBOOT_ROLLBACK → READY |
사용자 데이터
체크포인트를 사용 중지합니다. 시스템 업데이트: 부팅 슬롯 전환을 취소합니다. 서비스 번들 업데이트: 스테이징된 APEX를 삭제합니다. |
ACTIVATE_POST_REBOOT_COMPLETE |
→
ACTIVATE_POST_REBOOT_ROLLBACK → ACTIVATE_POST_REBOOT_ROLLBACK_COMPLETE |
사용자 데이터 체크포인트를 사용 중지합니다. 시스템 업데이트: 부팅 슬롯을 다시 전환합니다. 서비스 번들 업데이트: 활성 APEX 세션을 되돌립니다. 롤백이 적용되려면 최종 재부팅이 필요하며, 그 후 상태가 READY로 전환됩니다.
|
커밋
이 요청은 업데이트가 성공적으로 완료되었음을 나타내고 모든 변경사항을 영구적으로 적용합니다.
rpc Commit(CommitRequest) returns (CommitResponse) {}
message CommitRequest {}
message CommitResponse {}
커밋 작업을 실행하는 동안 상태가 COMMIT으로 전환됩니다.
- 시스템 업데이트: 업데이트 관리자는 부팅을 성공으로 표시합니다. 이렇게 하면 향후 롤백이 방지되고 후속 부팅 시 이 슬롯이 선택됩니다.
- 서비스 번들 업데이트: 업데이트 관리자는 스테이징된 APEX 세션을 성공으로 표시하여 업데이트 세션을 닫고 번들을 영구적으로 활성화합니다.
시스템이 업데이트를 커밋한 후 업데이트 관리자는 사용자 데이터 체크포인트를 커밋합니다. 시스템은 이 부팅 중에 작성된 모든 신규 사용자 데이터를 영구 저장소에 커밋합니다. 업데이트 관리자는 READY로 다시 전환되어 업데이트가 완료되었음을 나타냅니다.
APEX 제거
UninstallApex 요청은 서비스 번들의 /data 버전을 삭제합니다. 모든 상태에서 UninstallApex를 호출할 수 있지만 제거가 적용되려면 VM을 재부팅해야 합니다. 따라서 업데이트가 진행 중일 때는 UninstallApex를 호출하지 마세요. UninstallApex 는 사전 설치된 APEX를 삭제하거나 APEX 데이터를 삭제하거나 비활성 APEX 버전을 삭제하지 않습니다.
rpc UninstallApex(UninstallApexRequest) returns (UninstallApexResponse) {}
message UninstallApexRequest {
message ApexInfo {
string module_name = 1;
int64 version_code = 2;
}
repeated ApexInfo apexes = 1;
}
message UninstallApexResponse {}