À partir d'Android 11, pour les processus 64 bits, toutes les allocations de tas ont une balise définie par l'implémentation définie dans l'octet supérieur du pointeur sur les appareils prenant en charge le noyau pour ARM Top-byte Ignore (TBI). Toute application qui modifie cette balise est arrêtée lorsque la balise est vérifiée lors de la désallocation. Cela est nécessaire pour le matériel futur avec prise en charge de l'extension de marquage de mémoire ARM (MTE).
Ignorer l'octet supérieur
La fonction Top-byte Ignore d'ARM est disponible pour le code 64 bits dans tout le matériel Armv8 AArch64. Cette fonctionnalité signifie que le matériel ignore l'octet supérieur d'un pointeur lors de l'accès à la mémoire.
TBI nécessite unnoyau compatible qui gère correctement les pointeurs balisés transmis depuis l'espace utilisateur. Les noyaux communs Android à partir de la version 4.14 (Pixel 4) et des versions ultérieures comportent les correctifs TBI requis .
Les périphériques prenant en charge TBI dans le noyau sont détectés dynamiquement au démarrage du processus et une balise dépendante de l'implémentation est insérée dans l'octet supérieur du pointeur pour toutes les allocations de tas. Après cela, une vérification est effectuée pour s'assurer que la balise n'a pas été tronquée lors de la libération de la mémoire.
Préparation de l'extension de marquage de mémoire
L'extension d'étiquetage de mémoire (MTE) d'ARM aide à résoudre les problèmes de sécurité de la mémoire. MTE fonctionne en étiquetant les 56e à 59e bits d'adresse de chaque allocation de mémoire sur la pile, le tas et les globals. Le matériel et le jeu d'instructions vérifient automatiquement que la balise correcte est utilisée à chaque accès à la mémoire.
Les applications Android qui stockent de manière incorrecte des informations dans l'octet supérieur du pointeur sont garanties de se casser sur un appareil compatible MTE . Les pointeurs balisés facilitent la détection et le rejet des utilisations incorrectes de l'octet supérieur du pointeur avant que les périphériques MTE ne soient disponibles.
Assistance aux développeurs
Si votre application plante et que ce lien vous est demandé, cela peut signifier l'une des choses suivantes :
- L'application a tenté de libérer un pointeur qui n'était pas alloué par l'allocateur de tas du système.
- Quelque chose dans votre application a modifié l'octet supérieur d'un pointeur. L'octet supérieur du pointeur ne peut pas être modifié et votre code doit être modifié pour résoudre ce problème.
Exemples d'utilisation ou de modification incorrectes du pointeur d'octet supérieur.
- Les pointeurs vers un type particulier ont des métadonnées spécifiques à l'application stockées dans les 16 premiers bits d'adresse.
- Un pointeur converti en double puis en arrière, perdant les bits d'adresse inférieurs.
- Code calculant la différence entre les adresses des variables locales de différents cadres de pile comme moyen de mesurer la profondeur de récursivité.
Certaines applications peuvent dépendre de bibliothèques qui se comportent de manière incorrecte lorsque l'octet supérieur du pointeur est défini. Nous reconnaissons qu'il peut être non trivial de résoudre rapidement ces problèmes sous-jacents dans les bibliothèques. Ainsi, les applications qui utilisent targetSdkLevel < 30
n'auront pas le balisage de pointeur activé par défaut. Nous fournissons également une trappe d'évacuation pour les applications construites avec targetSdkLevel >= 30
afin de faciliter la période de transition.
La trappe d'évacuation est utilisée en ajoutant ce qui suit à votre fichier AndroidManifest.xml
:
<application android:allowNativeHeapPointerTagging="false"> ... </application>
Cela désactivera la fonctionnalité Pointer Tagging pour votre application. Veuillez noter que cela ne résout pas le problème d'intégrité du code sous-jacent. Cette trappe de secours disparaîtra dans les futures versions d'Android, car les problèmes de cette nature seront incompatibles avec MTE .