Guida rapida: crea ed esegui pacchetti di servizi SDV

Questa pagina mostra come creare un bundle di servizi SDV, pacchettizzarlo nel formato file APEX ed eseguirlo su un dispositivo Cuttlefish virtuale. Le unità principali di esecuzione del codice nel sistema SDV sono i bundle di servizi. I bundle di servizi forniscono metodi del ciclo di vita che il sistema esegue quando lo stato del sistema cambia.

  1. Configura l'ambiente di build

    Dalla directory di lavoro, esegui lo script envsetup.sh per configurare l'ambiente di build, imposta Cuttlefish come target di build e crea il generatore di codice vsidlc:

    source build/envsetup.sh
    lunch sdv_core_cf-aosp_current-userdebug
    m vsidlc
    
  2. Definisci l'architettura creando una cartella denominata my_catalog con questi file:

    • tire.proto: definisce la struttura dei dati che stai inviando:

      syntax = "proto3";
      
      package com.android.sdv.sample.quickstart;
      
      import "google/protobuf/empty.proto";
      import "sdv/vsidl/v1/annotations.proto";
      
      message TirePressure {
        uint32 pressure = 1;
      }
      
      message TireInfoResponse {
        string serial_number = 1;
        uint32 max_pressure = 2;
      }
      
      service TireService {
        rpc GetTireInfo(google.protobuf.Empty) returns (TireInfoResponse);
      }
      
    • architecture.vsidl: definisce i bundle di servizi e la loro comunicazione (per l'evidenziazione della sintassi, la convalida e il completamento automatico in Android Studio for Platform, consulta Modifica i file VSIDL):

      package: "com.android.sdv.sample.quickstart"
      
      service_bundle {
        name: "Manager"
      
        publisher {
          message: "TirePressure"
          topic: "pressure"
          capacity: 8
        }
      
        server {
          service: "TireService"
          channel: "tire-service"
        }
      }
      
      service_bundle {
        name: "Monitor"
      
        subscriber {
          message: "TirePressure"
          topic: "pressure"
        }
      
        client {
          service: "TireService"
          channel: "tire-service"
        }
      }
      
    • Android.bp: definisce il processo di build:

      rust_protobuf {
          name: "libquickstart_sample_tire_proto",
          crate_name: "quickstart_sample_tire_proto",
          protos: [
              "tire.proto",
          ],
          source_stem: "quickstart_sample_tire_proto_source",
          rustlibs: [
              "libvsidl_v1_stdlib_proto_rs",
          ],
          proto_flags: [
              "-I external/protobuf/src",
          ],
          vendor_available: true,
          product_available: true,
          apex_available: [
              "//apex_available:platform",
              "//apex_available:anyapex",
          ],
          min_sdk_version: "35",
      }
      
      filegroup {
          name: "vsidl_quickstart_catalog",
          srcs: ["**/*"],
      }
      
  3. Genera un'implementazione di base e i file di configurazione eseguendo:

    vsidlc -c /path/to/catalog -o /path/to/output --services --apex
    
  4. Per ogni bundle di servizi, trova l'implementazione Rust in /path/to/output/services/ServiceBundleName/src/main.rs.

  5. Per impostazione predefinita, l'implementazione generata crea messaggi con valori predefiniti e li invia tra publisher e sottoscrittori o client e server RPC. Per modificare questo comportamento, cerca i commenti TODO in main.rs e modificali in base alle tue preferenze. Ad esempio:

    rust async fn handle_tire_pressure_pressure_publisher(publisher: sdv::mw::Publisher<TirePressure>) { loop { // TODO: Modify the frequency of publishing messages here. sleep(Duration::from_secs(1)).await; // TODO: Modify the message content here. let message = TirePressure::default(); info!("Publishing on TirePressure#PRESSURE"); publisher.publish(&message).unwrap(); } }

  6. Per includere il bundle nell'immagine di sistema, aggiungi il nome del modulo APEX generato al makefile del prodotto.

    1. Apri il makefile del prodotto (ad esempio, device/google/sdv/sdv_core_base/sdv_samples_core_services.mk).

    2. Aggiungi il modulo a PRODUCT_PACKAGES aggiungendo:

      PRODUCT_PACKAGES += com.android.sdv.sample.quickstart
      PRODUCT_PACKAGES += com_android_sdv_sample_quickstart_orchestration_configurations
      
  7. Crea l'immagine:

    m
    

    Dopo che l'immagine di sistema include l'APEX (o la chiave utilizzata per firmarlo), puoi anche creare ed eseguire il deployment di modifiche iterative direttamente dall'icona del margine apex/Android.bp in Android Studio for Platform. Per saperne di più, consulta Esegui il deployment dei bundle di servizi SDV.

  8. Esegui e verifica l'esecuzione del bundle di servizi:

    1. Avvia un dispositivo Cuttlefish virtuale:

      sdv-cf create --instance_name=instance1
      
    2. Esegui il bundle di servizi all'avvio del sistema:

      • Manualmente:

        adb wait-for-device
        adb root
        adb shell sdv_service_bundle start local-vm:com.android.sdv.sample.quickstart.Manager/instance
        adb shell sdv_service_bundle start local-vm:com.android.sdv.sample.quickstart.Monitor/instance
        
      • Utilizzo dell'orchestratore:

        adb wait-for-device
        adb root
        # Apply global orchestration configuration by setting system property
        adb shell setprop persist.sdv.orchestrator_config_path "etc/orch/vm_quickstart_orch_config.textproto"
        adb reboot
        
    3. Verifica l'esecuzione del bundle di servizi:

      adb logcat *:F com_android_sdv_sample_quickstart_Manager_instance:* com_android_sdv_sample_quickstart_Monitor_instance:*
      

      Questo comando mostra i log che indicano che i bundle di servizi si scambiano messaggi:

      03-30 13:41:31.505   967   976 I com_android_sdv_sample_quickstart_Manager_instance: sdv_lm_manager: Publishing on TirePressure#PRESSURE
      03-30 13:41:31.505   983   991 I com_android_sdv_sample_quickstart_Monitor_instance: sdv_lm_monitor: Received message on TirePressure#PRESSURE: [TirePressure { pressure: 0, special_fields: SpecialFields { unknown_fields: UnknownFields { fields: None }, cached_size: CachedSize { size: 0 } } }]
      03-30 13:41:31.626   983   991 I com_android_sdv_sample_quickstart_Monitor_instance: sdv_lm_monitor: Sending request on Monitor/TireService
      03-30 13:41:31.627   967   976 I com_android_sdv_sample_quickstart_Manager_instance: sdv_lm_manager: Received request on Manager/TireService: Empty { special_fields: SpecialFields { unknown_fields: UnknownFields { fields: None }, cached_size: CachedSize { size: 0 } } }
      03-30 13:41:31.627   983   991 I com_android_sdv_sample_quickstart_Monitor_instance: sdv_lm_monitor: Received response on Monitor/TireService: TireInfoResponse { serial_number: "", max_pressure: 0, special_fields: SpecialFields { unknown_fields: UnknownFields { fields: None }, cached_size: CachedSize { size: 0 } } }
      

Passaggi successivi

Scopri di più sul Vehicle Services Interface Definition Language (VSIDL) e su come definire i tuoi bundle di servizi da zero.