Implémentation de Bootconfig dans Android 12

Dans Android 12, la fonctionnalité bootconfig remplace les options de ligne de commande du noyau androidboot.* utilisées avec Android 11 et versions antérieures. La fonctionnalité bootconfig est un mécanisme permettant de transmettre les détails de configuration de la build et du chargeur de démarrage à Android 12.

Cette fonctionnalité permet de séparer les paramètres de configuration de l'espace utilisateur Android de ceux du noyau. Le déplacement des longs paramètres du noyau androidboot.* vers le fichier bootconfig crée de l'espace sur la ligne de commande du noyau et le rend disponible pour une expansion future facile.

Le noyau et l'espace utilisateur Android doivent prendre en charge bootconfig .

  • Première version bénéficiant de ce support : Android 12
  • Première version du noyau prenant en charge ce support : noyau 12-5.4.xx

Implémentez la fonctionnalité bootconfig pour les nouveaux appareils lancés avec une version du noyau 12-5.10.xx. Vous n'avez pas besoin de l'implémenter si vous mettez à niveau des appareils.

Exemples et source

Lorsque vous consultez les exemples et le code source de cette section, notez que le format du code bootconfig n'est que légèrement différent du format de la ligne de commande du noyau utilisée dans Android 11 et versions antérieures. Cependant, la différence suivante est importante pour votre utilisation :

  • Les paramètres doivent être séparés par la séquence d'échappement de nouvelle ligne \n , et non par des espaces.

Exemple de chargeur de démarrage

Pour un exemple de chargeur de démarrage, consultez l'implémentation du chargeur de démarrage de référence Cuttlefish U-boot. Deux commits dans la référence sont répertoriés ci-dessous. Le premier met à niveau la prise en charge de la version de l’en-tête de démarrage vers la dernière version. Dans l'exemple, le premier commit met à jour (ou uprev) la version prenant en charge la suivante, v4. Le second fait deux choses ; il ajoute la gestion du bootconfig et démontre l'ajout de paramètres au moment de l'exécution :

Exemple de construction

Pour un exemple de construction qui montre les modifications mkbootimg pour créer le vendor_boot.img avec l'en-tête de démarrage du fournisseur v4, consultez mkbootimg changes for bootconfig . Consultez les modifications apportées à la seiche pour effectuer les opérations suivantes :

Mise en œuvre

Les partenaires doivent ajouter la prise en charge de leurs chargeurs de démarrage et déplacer leurs paramètres androidboot.* au moment de la construction de la ligne de commande du noyau vers le fichier bootconfig. La meilleure façon de mettre en œuvre ce changement est de le faire progressivement ; voir la section Implémentation et validation incrémentielles pour plus d’informations sur le suivi d’un processus incrémentiel.

Si vous avez des modifications qui recherchent les paramètres androidboot.* dans le fichier /proc/cmdline, pointez-les plutôt vers le fichier /proc/bootconfig. Les propriétés ro.boot.* sont définies avec les nouvelles valeurs bootconfig , vous n'avez donc pas besoin de modifier le code à l'aide de ces propriétés.

Modifications de construction

Tout d’abord, augmentez la version de votre en-tête de démarrage vers la version 4 :

- BOARD_BOOT_HEADER_VERSION := 3

+ BOARD_BOOT_HEADER_VERSION := 4

Ajoutez le paramètre cmdline du noyau bootconfig . Cela oblige le noyau à rechercher la section bootconfig :

BOARD_KERNEL_CMDLINE += bootconfig

Les paramètres de bootconfig sont créés à partir des paramètres de la variable BOARD_BOOTCONFIG , tout comme la ligne de commande du noyau est créée à partir de BOARD\_KERNEL\_CMDLINE .

Tous les paramètres androidboot.* peuvent être déplacés tels quels, comme suit :

- BOARD_KERNEL_CMDLINE += androidboot..selinux=enforcing

+ BOARD_BOOTCONFIG += androidboot..selinux=enforcing

Modifications du chargeur de démarrage

Le chargeur de démarrage configure initramfs avant de passer au noyau. La configuration de démarrage du noyau recherche la section bootconfig et la trouve à la toute fin de initramfs, avec la fin attendue.

Le chargeur de démarrage obtient les informations de présentation vendor_boot.img à partir de l'en-tête de l'image de démarrage du fournisseur.

Diagram of bootconfig memory allocation layout

Figure 1. Allocation de mémoire bootconfig d'Android 12

Le chargeur de démarrage crée la section bootconfig en mémoire. La section bootconfig contient des allocations de mémoire pour les éléments suivants :

  • Paramètres
  • 4 parameters size de taille B
  • parameters checksum de taille 4 B
  • Chaîne magique bootconfig 12 B ( #BOOTCONFIG\n )

Les paramètres proviennent de deux sources : les paramètres connus au moment de la construction et les paramètres qui ne sont pas connus au moment de la construction. Des paramètres inconnus doivent être ajoutés.

Les paramètres connus au moment de la construction sont regroupés à la fin de l'image vendor_boot dans la section bootconfig. La taille de la section est stockée (en octets) dans le champ d'en-tête de démarrage du fournisseur vendor_bootconfig_size .

Les paramètres qui ne sont pas connus au moment de la construction ne le sont qu'au moment de l'exécution dans le chargeur de démarrage. Ceux-ci doivent être ajoutés à la fin de la section des paramètres de bootconfig avant que la bande-annonce de bootconfig ne soit appliquée.

Si vous devez ajouter des paramètres après l'application de la fin de bootconfig, écrasez la fin et réappliquez-la.

Implémentation et validation incrémentielles

Implémentez la fonctionnalité bootconfig de manière incrémentielle en suivant le processus indiqué dans cette section. Laissez les paramètres de ligne de commande du noyau intacts pendant que les paramètres de configuration de démarrage sont ajoutés.

Voici les étapes pour une mise en œuvre incrémentielle, avec validation :

  1. Apportez les modifications au chargeur de démarrage et à la build, puis procédez comme suit :
    1. Utilisez la variable BOARD_BOOTCONFIG pour ajouter un nouveau paramètre bootconfig.
    2. Conservez les paramètres de la ligne de commande du noyau tels qu'ils sont, afin que le périphérique puisse continuer à démarrer correctement. Cela rend le débogage et la validation beaucoup plus faciles.
  2. Vérifiez votre travail en vérifiant le contenu de /proc/bootconfig . Vérifiez que vous voyez le paramètre nouvellement ajouté après le démarrage du périphérique.
  3. Déplacez les paramètres androidboot.* de la ligne de commande du noyau vers bootconfig, à l'aide de la variable BOARD_BOOTCONFIG et du chargeur de démarrage.
  4. Vérifiez que chacun des paramètres existe dans /proc/bootconfig ET qu'ils ne sont pas dans /proc/cmdline . Si vous pouvez le vérifier, votre implémentation a réussi.

Considérations relatives à la mise à niveau et à la rétrogradation de l'OTA

Lorsque vous gérez les mises à niveau et les rétrogradations OTA entre différentes versions d'Android ou différentes versions du noyau, des précautions particulières doivent être prises.

Android 12 est la première version prenant en charge bootconfig. En cas de rétrogradation vers une version antérieure, les paramètres de ligne de commande du noyau doivent être utilisés à la place de bootconfig.

Les versions du noyau 12-5.4 et ultérieures prennent en charge bootconfig. En cas de rétrogradation vers une version antérieure (y compris 11-5.4), les paramètres de ligne de commande du noyau doivent être utilisés.

Les mises à niveau d’Android 11 et versions antérieures vers Android 12 et versions ultérieures peuvent continuer à utiliser les paramètres de ligne de commande du noyau. Il en va de même pour la mise à niveau des versions du noyau.

Dépannage

Lorsque vous effectuez l'étape de vérification , si vous ne voyez pas les paramètres attendus dans /proc/bootconfig , vérifiez les journaux du noyau dans logcat . Il y a toujours une entrée de journal présente pour bootconfig si le noyau le prend en charge.

Exemple de sortie de journal

$ adb logcat | grep bootconfig
02-24 17:00:07.610     0     0 I Load bootconfig: 128 bytes 9 nodes

Si un journal d'erreurs s'affiche, cela signifie qu'un problème est survenu lors du chargement de la configuration de démarrage. Pour voir différents types d'erreurs, consultez init/main.c .