Agregar un nuevo dispositivo

Utilice la información de esta página para crear los archivos MAKE para su dispositivo y producto.

Cada nuevo módulo de Android debe tener un archivo de configuración para dirigir el sistema de compilación con metadatos del módulo, dependencias en tiempo de compilación e instrucciones de empaquetado. Android utiliza el sistema de compilación Soong . Consulte Compilación de Android para obtener más información sobre el sistema de compilación de Android.

Descripción de las capas de construcción

La jerarquía de compilación incluye las capas de abstracción que corresponden a la composición física de un dispositivo. Estas capas se describen en la siguiente tabla. Cada capa se relaciona con la anterior en una relación de uno a muchos. Por ejemplo, una arquitectura puede tener más de una placa y cada placa puede tener más de un producto. Puede definir un elemento en una capa dada como una especialización de un elemento en la misma capa, lo que elimina la copia y simplifica el mantenimiento.

Capa Ejemplo Descripción
Producto miProducto, miProducto_eu, miProducto_eu_fr, j2, sdk La capa del producto define la especificación de funciones de un producto de envío, como los módulos que se van a construir, las configuraciones regionales admitidas y la configuración para varias configuraciones regionales. En otras palabras, este es el nombre del producto en general. Las variables específicas del producto se definen en archivos MAKE de definición de producto. Un producto puede heredar de otras definiciones de productos, lo que simplifica el mantenimiento. Un método común es crear un producto base que contenga características que se apliquen a todos los productos y luego crear variantes de producto basadas en ese producto base. Por ejemplo, dos productos que se diferencian únicamente por sus radios (CDMA frente a GSM) pueden heredar del mismo producto base que no define una radio.
Tablero/dispositivo aguja, línea azul, coral La capa de placa/dispositivo representa la capa física de plástico en el dispositivo (es decir, el diseño industrial del dispositivo). Esta capa también representa los esquemas básicos de un producto. Estos incluyen los periféricos en la placa y su configuración. Los nombres utilizados son simplemente códigos para diferentes configuraciones de placa/dispositivo.
Arco brazo, x86, brazo64, x86_64 La capa de arquitectura describe la configuración del procesador y la interfaz binaria de la aplicación (ABI) que se ejecutan en la placa.

Uso de variantes de compilación

Al compilar para un producto en particular, es útil tener variaciones menores en la compilación de la versión final. En una definición de módulo, el módulo puede especificar etiquetas con LOCAL_MODULE_TAGS , que pueden ser uno o más valores optional (predeterminados), debug y eng .

Si un módulo no especifica una etiqueta (mediante LOCAL_MODULE_TAGS ), su etiqueta predeterminada es optional . Se instala un módulo opcional solo si lo requiere la configuración del producto con PRODUCT_PACKAGES .

Estas son las variantes de construcción definidas actualmente.

Variante Descripción
eng Este es el sabor predeterminado.
  • Instala módulos etiquetados con eng o debug .
  • Instala módulos según los archivos de definición del producto, además de los módulos etiquetados.
  • ro.secure=0
  • ro.debuggable=1
  • ro.kernel.android.checkjni=1
  • adb está habilitado de forma predeterminada.
user La variante destinada a ser los bits de lanzamiento final.
  • Instala módulos etiquetados con user .
  • Instala módulos según los archivos de definición del producto, además de los módulos etiquetados.
  • ro.secure=1
  • ro.debuggable=0
  • adb está deshabilitado de forma predeterminada.
userdebug Lo mismo que user , con estas excepciones:
  • También instala módulos etiquetados con debug .
  • ro.debuggable=1
  • adb está habilitado de forma predeterminada.

Directrices para la depuración de usuarios

La ejecución de compilaciones de depuración de usuarios en las pruebas ayuda a los desarrolladores de dispositivos a comprender el rendimiento y la potencia de las versiones en desarrollo. Para mantener la coherencia entre el usuario y las compilaciones de depuración de usuario, y para lograr métricas confiables en las compilaciones utilizadas para la depuración, los desarrolladores de dispositivos deben seguir estas pautas:

  • userdebug se define como una compilación de usuario con acceso raíz habilitado, excepto:
    • aplicaciones de depuración de usuario que se ejecutan solo bajo demanda por el usuario
    • Operaciones que se ejecutan solo durante el mantenimiento inactivo (en el cargador/totalmente cargado), como usar dex2oatd versus dex2oat para compilaciones en segundo plano
  • No incluya características que estén habilitadas o deshabilitadas de forma predeterminada según el tipo de compilación. Se desaconseja a los desarrolladores que utilicen cualquier forma de registro que afecte la duración de la batería, como el registro de depuración o el volcado de pilas.
  • Cualquier función de depuración que esté habilitada de forma predeterminada en userdebug debe definirse claramente y compartirse con todos los desarrolladores que trabajan en el proyecto. Debe habilitar las funciones de depuración solo por tiempo limitado hasta que se resuelva el problema que está tratando de depurar.

Personalización de la compilación con superposiciones de recursos

El sistema de compilación de Android utiliza superposiciones de recursos para personalizar un producto en el momento de la compilación. Las superposiciones de recursos especifican los archivos de recursos que se aplican sobre los valores predeterminados. Para usar superposiciones de recursos, modifique el archivo de compilación del proyecto para establecer PRODUCT_PACKAGE_OVERLAYS en una ruta relativa a su directorio de nivel superior. Esa ruta se convierte en una raíz oculta que se busca junto con la raíz actual cuando el sistema de compilación busca recursos.

La configuración personalizada más común se encuentra en el archivo frameworks/base/core/res/res/values/config.xml .

Para configurar una superposición de recursos en este archivo, agregue el directorio de superposición al archivo de compilación del proyecto usando uno de los siguientes:

PRODUCT_PACKAGE_OVERLAYS := device/device-implementer/device-name/overlay

o

PRODUCT_PACKAGE_OVERLAYS := vendor/vendor-name/overlay

Luego, agregue un archivo de superposición al directorio, por ejemplo:

vendor/foobar/overlay/frameworks/base/core/res/res/values/config.xml

Cualquier cadena o matriz de cadenas que se encuentre en el archivo superpuesto config.xml reemplaza a las que se encuentran en el archivo original.

construyendo un producto

Puede organizar los archivos de origen de su dispositivo de muchas maneras diferentes. Aquí hay una breve descripción de una forma de organizar una implementación de Pixel.

Pixel se implementa con una configuración de dispositivo principal denominada marlin . A partir de esta configuración de dispositivo, se crea un producto con un archivo MAKE de definición de producto que declara información específica del producto sobre el dispositivo, como el nombre y el modelo. Puede ver el directorio device/google/marlin para ver cómo se configura todo esto.

Escribir makefiles de productos

Los siguientes pasos describen cómo configurar archivos MAKE de productos de una manera similar a la de la línea de productos Pixel:

  1. Cree un directorio device/ <company-name> / <device-name> para su producto. Por ejemplo, device/google/marlin . Este directorio contendrá el código fuente de su dispositivo junto con los archivos MAKE para compilarlos.
  2. Cree un makefile device.mk que declare los archivos y módulos necesarios para el dispositivo. Para ver un ejemplo, consulte device/google/marlin/device-marlin.mk .
  3. Cree un archivo MAKE de definición de producto para crear un producto específico basado en el dispositivo. El siguiente archivo MAKE se toma de device/google/marlin/aosp_marlin.mk como ejemplo. Tenga en cuenta que el producto hereda de los archivos device/google/marlin/device-marlin.mk y vendor/google/marlin/device-vendor-marlin.mk a través del archivo MAKE al mismo tiempo que declara la información específica del producto, como nombre, marca, y modelo
    # Inherit from the common Open Source product configuration
    $(call inherit-product, $(SRC_TARGET_DIR)/product/core_64_bit.mk)
    $(call inherit-product, $(SRC_TARGET_DIR)/product/aosp_base_telephony.mk)
    
    PRODUCT_NAME := aosp_marlin
    PRODUCT_DEVICE := marlin
    PRODUCT_BRAND := Android
    PRODUCT_MODEL := AOSP on msm8996
    PRODUCT_MANUFACTURER := Google
    PRODUCT_RESTRICT_VENDOR_FILES := true
    
    PRODUCT_COPY_FILES += device/google/marlin/fstab.common:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.marlin
    
    $(call inherit-product, device/google/marlin/device-marlin.mk)
    $(call inherit-product-if-exists, vendor/google_devices/marlin/device-vendor-marlin.mk)
    
    PRODUCT_PACKAGES += \
        Launcher3QuickStep \
        WallpaperPicker
    

    Consulte Configuración de variables de definición de productos para conocer otras variables específicas del producto que puede agregar a sus archivos MAKE.

  4. Cree un archivo AndroidProducts.mk que apunte a los archivos MAKE del producto. En este ejemplo, solo se necesita el archivo MAKE de la definición del producto. El siguiente ejemplo es de device/google/marlin/AndroidProducts.mk (que contiene tanto marlin, Pixel, como pez vela, Pixel XL, que compartió la mayoría de las configuraciones):
    PRODUCT_MAKEFILES := \
    	$(LOCAL_DIR)/aosp_marlin.mk \
    	$(LOCAL_DIR)/aosp_sailfish.mk
    
    COMMON_LUNCH_CHOICES := \
    	aosp_marlin-userdebug \
    	aosp_sailfish-userdebug
    
  5. Cree un archivo MAKE BoardConfig.mk que contenga configuraciones específicas de la placa. Para ver un ejemplo, consulte device/google/marlin/BoardConfig.mk .
  6. Solo para Android 9 y versiones anteriores, cree un archivo vendorsetup.sh para agregar su producto (un "combo de almuerzo") a la compilación junto con una variante de compilación separada por un guión. Por ejemplo:
    add_lunch_combo <product-name>-userdebug
    
  7. En este punto, puede crear más variantes de productos basadas en el mismo dispositivo.

Configuración de variables de definición de productos

Las variables específicas del producto se definen en el archivo MAKE del producto. La tabla muestra algunas de las variables mantenidas en un archivo de definición de producto.

Variable Descripción Ejemplo
PRODUCT_AAPT_CONFIG Configuraciones de aapt para usar al crear paquetes.
PRODUCT_BRAND La marca (por ejemplo, operador) para la que se personaliza el software, si corresponde.
PRODUCT_CHARACTERISTICS Características aapt para permitir agregar recursos específicos de variantes a un paquete. tablet , nosdcard
PRODUCT_COPY_FILES Lista de palabras como source_path:destination_path . El archivo en la ruta de origen debe copiarse en la ruta de destino al compilar este producto. Las reglas para los pasos de copia se definen en config/makefile .
PRODUCT_DEVICE Nombre del diseño industrial. Este es también el nombre de la placa y el sistema de compilación lo usa para ubicar BoardConfig.mk . tuna
PRODUCT_LOCALES Una lista separada por espacios de códigos de idioma de dos letras, pares de códigos de país de dos letras que describen varias configuraciones para el usuario, como el idioma de la interfaz de usuario y el formato de hora, fecha y moneda. La primera configuración regional enumerada en PRODUCT_LOCALES se utiliza como configuración regional predeterminada del producto. en_GB , de_DE , es_ES , fr_CA
PRODUCT_MANUFACTURER Nombre del fabricante. acme
PRODUCT_MODEL Nombre visible para el usuario final del producto final.
PRODUCT_NAME Nombre visible para el usuario final para el producto general. Aparece en la pantalla Configuración > Acerca de.
PRODUCT_OTA_PUBLIC_KEYS Lista de claves públicas inalámbricas (OTA) para el producto.
PRODUCT_PACKAGES Lista de APKs y módulos a instalar. Contactos del calendario
PRODUCT_PACKAGE_OVERLAYS Indica si usar los recursos predeterminados o agregar superposiciones específicas del producto. vendor/acme/overlay
PRODUCT_SYSTEM_PROPERTIES Lista de las asignaciones de propiedades del sistema en el formato "key=value" para la partición del sistema. Las propiedades del sistema para otras particiones se pueden configurar a través de PRODUCT_<PARTITION>_PROPERTIES como en PRODUCT_VENDOR_PROPERTIES para la partición del proveedor. Nombres de partición compatibles: SYSTEM , VENDOR , ODM , SYSTEM_EXT y PRODUCT .

Configuración del idioma predeterminado del sistema y el filtro de configuración regional

Utilice esta información para configurar el idioma predeterminado y el filtro de configuración regional del sistema, luego habilite el filtro de configuración regional para un nuevo tipo de dispositivo.

Propiedades

Configure tanto el idioma predeterminado como el filtro de configuración regional del sistema utilizando las propiedades del sistema dedicadas:

  • ro.product.locale : para establecer la configuración regional predeterminada. Esto se establece inicialmente en la primera configuración regional en la variable PRODUCT_LOCALES ; puede anular ese valor. (Para obtener más información, consulte la tabla Configuración de variables de definición de productos ).
  • ro.localization.locale_filter : para establecer un filtro de configuración regional, utilizando una expresión regular aplicada a los nombres de configuración regional. Por ejemplo:
    • Filtro inclusivo: ^(de-AT|de-DE|en|uk).* - solo permite alemán (variantes de Austria y Alemania), todas las variantes de inglés y ucraniano
    • Filtro exclusivo: ^(?!de-IT|es).* - excluye alemán (variante de Italia) y todas las variantes de español.

Activación del filtro de configuración regional

Para habilitar el filtro, establezca el valor de cadena de la propiedad del sistema ro.localization.locale_filter .

Al configurar el valor de la propiedad del filtro y el idioma predeterminado a través de oem/oem.prop durante la calibración de fábrica, puede configurar restricciones sin hornear el filtro en la imagen del sistema. Asegúrese de que estas propiedades se recojan de la partición OEM agregándolas a la variable PRODUCT_OEM_PROPERTIES como se indica a continuación:

# Delegation for OEM customization
PRODUCT_OEM_PROPERTIES += \
    ro.product.locale \
    ro.localization.locale_filter

Luego, en producción, los valores reales se escriben en oem/oem.prop para reflejar los requisitos objetivo. Con este enfoque, los valores predeterminados se conservan durante el restablecimiento de fábrica, por lo que la configuración inicial se ve exactamente como una primera configuración para el usuario.

Configuración de ADB_VENDOR_KEYS para conectarse a través de USB

La variable de entorno ADB_VENDOR_KEYS permite a los fabricantes de dispositivos acceder a compilaciones depurables (-userdebug y -eng, pero no -user) sobre adb sin autorización manual. Normalmente, adb genera una clave de autenticación RSA única para cada computadora cliente, que enviará a cualquier dispositivo conectado. Esta es la clave RSA que se muestra en el cuadro de diálogo de autorización adb. Como alternativa, puede crear claves conocidas en la imagen del sistema y compartirlas con el cliente adb. Esto es útil para el desarrollo del sistema operativo y especialmente para las pruebas porque evita la necesidad de interactuar manualmente con el cuadro de diálogo de autorización de adb.

Para crear claves de proveedor, una persona (generalmente un administrador de versiones) debe:

  1. Genere un par de claves usando adb keygen . Para los dispositivos de Google, Google genera un nuevo par de claves para cada nueva versión del sistema operativo.
  2. Compruebe los pares de claves en algún lugar del árbol de fuentes. Google los almacena en vendor/google/security/adb/ , por ejemplo.
  3. Configure la variable de compilación PRODUCT_ADB_KEYS para que apunte a su directorio clave. Google hace esto agregando un archivo Android.mk en el directorio de claves que dice PRODUCT_ADB_KEYS := $(LOCAL_PATH)/$(PLATFORM_VERSION).adb_key.pub , lo que ayuda a garantizar que recordemos generar un nuevo par de claves para cada versión del sistema operativo.

Este es el archivo MAKE que usa Google en el directorio donde almacenamos nuestros pares de claves registrados para cada versión:

PRODUCT_ADB_KEYS := $(LOCAL_PATH)/$(PLATFORM_VERSION).adb_key.pub

ifeq ($(wildcard $(PRODUCT_ADB_KEYS)),)
  $(warning ========================)
  $(warning The adb key for this release)
  $(warning )
  $(warning   $(PRODUCT_ADB_KEYS))
  $(warning )
  $(warning does not exist. Most likely PLATFORM_VERSION in build/core/version_defaults.mk)
  $(warning has changed and a new adb key needs to be generated.)
  $(warning )
  $(warning Please run the following commands to create a new key:)
  $(warning )
  $(warning   make -j8 adb)
  $(warning   LOGNAME=android-eng HOSTNAME=google.com adb keygen $(patsubst %.pub,%,$(PRODUCT_ADB_KEYS)))
  $(warning )
  $(warning and upload/review/submit the changes)
  $(warning ========================)
  $(error done)
endif

Para usar estas claves de proveedores, un ingeniero solo necesita configurar la variable de entorno ADB_VENDOR_KEYS para que apunte al directorio en el que se almacenan los pares de claves. Esto le dice a adb que pruebe estas claves canónicas primero, antes de recurrir a la clave de host generada que requiere autorización manual. Cuando adb no puede conectarse a un dispositivo no autorizado, el mensaje de error le sugerirá que configure ADB_VENDOR_KEYS si aún no está configurado.