VirtualizationService

VirtualizationService administra varias VMs invitadas, protegidas o no, que se ejecutan en un sistema Android, principalmente mediante la administración de instancias de crosvm. VirtualizationService expone una API de AIDL que los servicios o las apps del sistema pueden usar para iniciar, supervisar y detener VMs. Para usar VirtualizationService, ejecuta virtmgr directamente o importa javalib o rustlib, que ejecuta virtmgr como un proceso secundario.

Ciclo de vida de las VMs

El acceso a una VM se realiza a través del objeto IVirtualMachine. Mientras haya al menos una referencia al objeto IVirtualMachine, la VM seguirá ejecutándose (a menos que falle o se cierre por sí sola). Si se quitan todas las referencias al objeto IVirtualMachine antes de que se cierre la VM, VirtualizationService la cerrará automáticamente. Este proceso implica que, si el cliente que inició la VM se apaga por el eliminador de memoria insuficiente, la VM también se apagará, lo que evitará pérdidas de recursos.

Cada VM se administra con su propia instancia de crosvm, que VirtualizationService administra en nombre del cliente. VirtualizationService en virtmgr inicia estos procesos secundarios de crosvm según sea necesario con los recursos globales asignados incluido el CID que otorga VirtualizationServiceInternal en virtualizationservice, y les pasa los descriptores de archivos para las imágenes que necesita la VM. Luego, VirtualizationService supervisa el proceso secundario para cuando finaliza, de modo que pueda notificar a los clientes restantes en consecuencia.

Paquetes de VM

crosvm admite dos formas diferentes de iniciar una VM: se proporciona un kernel y un initrd, o se proporciona un cargador de arranque. En cualquier caso, también se puede proporcionar una cantidad arbitraria de imágenes de disco, que pueden ser una imagen sin procesar o una composición de varias particiones. El cliente proporciona las distintas imágenes como descriptores de archivos.

VirtualizationService compila imágenes de disco compuestas a pedido. Este proceso es necesario porque el archivo de disco compuesto hace referencia internamente a los distintos archivos de imagen de partición que componen el disco, que pasa el cliente y que crosvm podría no poder acceder directamente. Para solucionar este problema, VirtualizationService garantiza que los números de descriptor de archivos heredados por crosvm sean los mismos que los números de descriptor de archivos que VirtualizationService usó para crear las imágenes compuestas. La imagen de disco compuesto usa nombres de archivo en el formato /proc/self/fd/N para representar cada archivo de partición.

Para las pVM de Microdroid, AVF incluye un cargador de arranque, que carga el kernel desde una partición de una imagen de disco compuesto, siguiendo el flujo estándar de inicio verificado de Android.

Sockets de VM (vsock)

La interfaz principal para la comunicación entre pVMs es vsock, una interfaz de socket virtio estándar. Cada VM se identifica con un identificador de contexto (CID) de 32 bits , que es análogo a una dirección IP, que VirtualizationServiceInternal asigna a la VM cuando VirtualizationService crea la VM, y puede exponer servicios en los números de puerto que elija la VM. El CID es único mientras se ejecuta la VM, pero el valor del CID se puede reciclar cuando finaliza la VM y se quitan todos los controladores de binder IVirtualMachine de la VM.

Interfaz de depuración

El comando vm se proporciona para fines de depuración. Este comando permite que un desarrollador inicie una VM desde el shell, vea sus registros y finalice la VM. Con el comando vm o las otras interfaces que proporciona AVF, una VM puede iniciarse en modo depurable (FULL) o no depurable (NONE). Con una VM depurable, puedes ver los registros a nivel del SO, acceder al shell de ADB y capturar el volcado de fallas o la carga útil de la app. Se recomienda usar una VM no depurable en producción. Para obtener más información sobre la herramienta de línea de comandos y otras interfaces de depuración que proporciona AVF, consulta debug/README.md.