Testamos internamente o SDV no hardware. Usamos o QVM no QNX para virtualização. Compartilhamos todos os destinos, documentação e configurações como exemplos.
Pré-requisitos
Esta página pressupõe um QNX pré-configurado e não inclui etapas para criar, configurar ou instalar o QNX no hardware.
Esta página pressupõe que você esteja executando o QNX no hardware arm64 e criando e usando os destinos _arm64 do SDV.
Componentes necessários
- Um blob da árvore de dispositivos (DTB, na sigla em inglês) para definir o hardware virtual
- Um kernel do Linux para usar
- Um ramdisk combinado que inclui todas as propriedades de inicialização do ramdisk
- Uma transferência de uma cadeia DICE para autenticação de VM do SDV
- Todas as partições de disco do sistema
- Uma configuração do QVM da VM
Blob da árvore de dispositivos (DTB)
O QVM gera a maior parte do blob da árvore de dispositivos (DTB) com base na configuração. Portanto, o DTB pode ser mínimo:
/*
* Copyright (C) 2026 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/dts-v1/;
/ {
model = "Virtual Machine";
#address-cells = <2>;
#size-cells = <2>;
// This reserved-memory node specifies for the open-dice driver which memory region(s) to
// expose as /dev/open-dice<n> device(s)
reserved-memory {
// The number of u32 cells to represent the address of a memory region
#address-cells = <2>;
// The number of u32 cells to represent the size of a memory region
#size-cells = <2>;
ranges;
// The unit address (after the @) must match the address in the reg property
dice@D1C30000 {
// The open-dice driver receives this device tree node based on this
// property.
compatible = "google,open-dice";
no-map;
// The address and the size of the memory region that is passed to the
// open-dice driver.
// First two hex numbers (cells) represent the address of the memory region,
// the last two represent its size (4K, in this case).
reg = <0x0 0xD1C30000 0x0 0x1000>;
};
};
};
Kernel
O SDV usa a imagem de kernel genérica (GKI, na sigla em inglês), e você pode usar a saída de uma build diretamente.
Ramdisk
As informações do ramdisk precisam incluir os diferentes ramdisks que o Android gera e as propriedades de inicialização. Como o QNX não oferece suporte a um bootloader por padrão, é necessário gerar um ramdisk com o formato de dados esperado.
Você pode fazer isso com o script Python a seguir, que concatena vários ramdisks e adiciona o bootconfig (que é o arquivo vendor-bootconfig.img) no formato esperado:
def create_qnx_ramdisk(output: io.BytesIO,
ramdisks: Sequence[io.BytesIO],
bootconfig: Optional[io.BytesIO]):
BUFFER_SIZE = 4096
for ramdisk in ramdisks:
while buf := ramdisk.read(BUFFER_SIZE):
output.write(buf)
# Kernel looks for bootconfig at the end of ramdisk.
if bootconfig:
bootconfig_checksum = 0
bootconfig_size = 0
while buf := bootconfig.read(BUFFER_SIZE):
bootconfig_checksum = (bootconfig_checksum + sum(buf)) & 0xFFFFFFFF
bootconfig_size += len(buf)
output.write(buf)
output.write(struct.pack('II', bootconfig_size, bootconfig_checksum))
output.write(b'#BOOTCONFIG\n')
Cadeia DICE
Em um sistema de produção, o sistema host e o bootloader constroem a cadeia DICE dinamicamente durante o processo de inicialização e fornecem uma cadeia DICE ao convidado para verificar se a imagem é confiável. Como esse requisito pode complicar os fluxos de teste e desenvolvimento, você carrega um snapshot da cadeia DICE.
Para gerar os arquivos dice_handover_instance*, use qualquer build do SDV Cuttlefish.
Exemplo:
lunch sdv_core_cf-trunk_staging-userdebug
m
cp $OUT/product/etc/dice_handover_instance* <GUEST>/test_dice_handover
Disco
O QVM oferece suporte a vários formatos para um disco virtual. Nossa configuração de referência usa um arquivo de imagem de disco que contém todas as partições. O bpttool pode gerar esses discos, mas não é desenvolvido ativamente no Android.
Configuração do QVM
A configuração do QVM define a configuração e aponta para os diferentes arquivos. Fornecemos as seguintes configurações de exemplo:
- Configuração da VM principal do SDV
- Configuração da VM de mídia do SDV
- VM IVI com integração do SDV
Perguntas frequentes
P: o adb não consegue se conectar à minha VM. O que posso fazer?
R: nessa configuração, o adb usa o Ethernet para se conectar à VM. Você precisa de uma configuração de encaminhamento de porta no QNX que encaminhe solicitações para convidados na porta 5555. É necessário se conectar ao sistema host. Como alternativa, também é possível configurar uma ponte para a VM e se conectar diretamente a ela.
P: o registro do sistema mostra que o IServiceRegistrationAgent está ausente. Por quê?
R: a descoberta de serviços depende de uma configuração de confiança e binder totalmente funcional. Verifique se o OpenDICE foi carregado corretamente e se o HwBinder não está mostrando erros durante a inicialização. Se esses itens não estiverem funcionando, será necessário corrigi-los primeiro.
P: init_open_dice falha. O que aconteceu?
R: os scripts de inicialização carregam as informações de confiança durante a inicialização e limpam o local da memória. Verifique na configuração do QVM se a configuração da linha de comando e os dados pessoais compartilhados no local da memória se encaixam. Verifique também se o local da memória no driver, na configuração do QVM e no DTB corresponde e se o local da memória é gravável.