Mac OS X 10.0 (Cheetah) exécuté avec succès sur une Nintendo Wii
(bryankeller.github.io)- Un projet de portage a abouti à l’exécution native de Mac OS X 10.0 (Cheetah) sur le matériel PowerPC de la Wii
- Le noyau Darwin/XNU a été adapté à la Wii, avec écriture manuelle du bootloader, de l’arbre de périphériques et des pilotes, jusqu’au démarrage réussi de l’environnement graphique
- Des pilotes IOKit sur mesure prenant en charge la carte SD, le framebuffer et les périphériques d’entrée USB ont permis d’obtenir un système entièrement fonctionnel
- Le projet prend en compte les spécificités de la Wii, comme la correction des conflits de configuration BAT, la mise en place d’une couche de pilotes pour le SoC Hollywood et un framebuffer avec conversion RGB→YUV
- Après plus de dix ans de tentatives, il a permis un démarrage complet et une utilisation effective de Mac OS X sur Wii, démontrant l’intérêt de relever même les projets qui paraissent impossibles
Aperçu du projet d’exécution de Mac OS X sur Wii
- Un projet de portage a été mené pour exécuter nativement Mac OS X 10.0 (Cheetah) sur une Nintendo Wii
- La Wii avait déjà connu des portages de Linux, NetBSD et Windows NT ; Mac OS X s’ajoute désormais à cette liste
- En exploitant le matériel PowerPC de la Wii, le projet fait tourner le noyau Darwin/XNU et s’accompagne de l’écriture des pilotes et du bootloader nécessaires
- Résultat : démarrage complet de l’interface graphique de Mac OS X sur Wii, avec prise en charge du clavier et de la souris
Étude de faisabilité
- Le CPU PowerPC 750CL de la Wii succède au PowerPC 750CXe utilisé dans les G3 iMac/iBook, sans problème de compatibilité processeur
- Les 88 Mo de RAM de la Wii (MEM1 24 Mo + MEM2 64 Mo) sont inférieurs à la configuration requise officielle (128 Mo), mais des tests sous QEMU ont confirmé qu’un démarrage restait possible avec 64 Mo
- Le matériel pris en charge comprend USB Gecko (débogage série), la carte SD, le contrôleur d’interruptions, la sortie vidéo framebuffer et les ports USB
- En adaptant à la Wii le cœur open source de Mac OS X, Darwin (noyau XNU, IOKit), les couches graphiques supérieures peuvent elles aussi fonctionner
- La Wii permet l’exécution de code personnalisé via Homebrew Channel et BootMii, ce qui en fait une bonne plateforme pour ce type d’expérimentation
Approche de portage
- Trois stratégies de démarrage étaient envisageables :
- Portage d’Open Firmware
- Portage de BootX
- Écriture directe d’un bootloader personnalisé
- Un nouveau bootloader dédié à la Wii a été développé pour assurer l’initialisation matérielle, le chargement du noyau, la création de l’arbre de périphériques et le transfert du contrôle au noyau
- Une fois le noyau lancé, le code du bootloader n’était plus nécessaire, et la suite du travail s’est concentrée sur les patches noyau et l’écriture de pilotes
Écriture du bootloader
- Les fonctions d’initialisation de la Wii ainsi que la prise en charge de la carte SD, du framebuffer et du débogage USB ont été implémentées à partir de l’exemple ppcskel
- Le noyau XNU au format Mach-O est chargé en mémoire puis exécuté via le point d’entrée spécifié
- Pour vérifier l’exécution effective du noyau, un patch de clignotement de LED a été inséré afin de suivre l’étape d’entrée dans le noyau
- En retraçant le chemin d’exécution du noyau, une exception 300 a été identifiée à l’étape device_tree.c → d’où la nécessité de transmettre un arbre de périphériques
-
Création et transmission de l’arbre de périphériques
- Un arbre minimal codé en dur a été construit à partir de la structure matérielle fixe de la Wii (
/cpus,/memory) - Un pointeur vers l’arbre de périphériques a été inclus dans la structure
boot_argspuis transmis au noyau - Le noyau a ensuite reconnu correctement l’arbre et le démarrage a pu se poursuivre
- Un arbre minimal codé en dur a été construit à partir de la structure matérielle fixe de la Wii (
Patches noyau
- La configuration BAT (Block Address Translation) de XNU entrait en conflit avec la carte mémoire de la Wii, nécessitant une modification du code source du noyau
- L’environnement de build du noyau a été mis en place dans une machine invitée Mac OS X Cheetah (QEMU)
- La correction du BAT et l’ajout d’une redirection de la sortie console vers USB Gecko ont permis le débogage
- Par la suite, la mémoire virtuelle, IOKit et le sous-système BSD se sont initialisés correctement
- Le message de démarrage « Still waiting for root device » est alors apparu → confirmant la nécessité d’un pilote de carte SD
Écriture des pilotes
-
Compréhension de l’architecture IOKit
- IOKit est un framework d’extensions noyau en C++, qui représente les couches matérielles via une structure driver-nub
- Exemple :
IOPCIBridge→IOPCIDevice→SomeEthernetCard→IOEthernetInterface - La Wii n’utilise pas un bus PCI mais une architecture SoC (Hollywood), d’où la nécessité d’un pilote personnalisé remplaçant IOPCIFamily
-
Pilote Hollywood
- Un pilote
NintendoWiiHollywooda été écrit pour correspondre au nœud « hollywood » de l’arbre de périphériques - Il crée et enregistre des nub
NintendoWiiHollywoodDevicereprésentant le matériel sous-jacent - Cela permet ensuite aux pilotes des périphériques enfants, comme la carte SD, de s’y rattacher
- Un pilote
-
Pilote de carte SD
- L’accès à la carte SD de la Wii a été implémenté en héritant de
IOBlockStorageDevice - La communication avec la carte SD s’appuie sur les commandes IPC de MINI (coprocesseur Starlet) :
IPC_SDMMC_SIZE,READ,WRITE - Pour résoudre les problèmes liés à la mémoire cache, des buffers de mémoire non cacheable ont été utilisés
- Un nub
IOMediaa été créé avec succès, permettant la reconnaissance du système de fichiers racine et un démarrage complet - Le log de démarrage affiche
BSD root: disk0s4
- L’accès à la carte SD de la Wii a été implémenté en héritant de
-
Pilote framebuffer
- En héritant de
IOFramebuffer, la zone MEM1 (0x01700000) de la Wii a été définie comme framebuffer - Pour permettre la transition entre console texte initiale et interface graphique,
isConsoleDevice()renvoietrue - Le matériel vidéo de la Wii utilisant le format YUV, un double framebuffer avec conversion RGB→YUV a été implémenté
- Une boucle de conversion effectue cette transformation à 60 Hz → aboutissant à un affichage GUI aux couleurs correctes
- En héritant de
-
Prise en charge des entrées USB
- Une tentative a été faite avec
AppleUSBOHCIpour piloter le contrôleur USB 1.1 OHCI de la Wii - Problème 1 : absence des sources de IOUSBFamily, empêchant le débogage
- Problème 2 : dépendance à IOPCIDevice, contournée via l’écriture d’un faux
NintendoWiiHollywoodPCIDevicepour la Wii - Problème 3 : incohérence d’endianness (la Wii est en reversed-little-endian), nécessitant la suppression du byte swap logiciel
- Après obtention des sources de IOUSBFamily pour Mac OS X Cheetah via IRC, la modification et la compilation ont abouti
- Au final, le clavier et la souris USB fonctionnent, transformant la Wii en véritable système Mac OS X complet
- Une tentative a été faite avec
Améliorations du bootloader et du noyau
-
Améliorations du bootloader
- Ajout de la détection des partitions de carte SD et d’un menu de démarrage, avec implémentation du parsing de Apple Partition Map (APM)
- Les extensions noyau (kext) sont chargées par le bootloader puis enregistrées dans le nœud
/chosen/memory-map - Cela permet de démarrer à partir d’une image d’installation Mac OS X non modifiée
-
Simplification du noyau
- Les modifications spécifiques à la Wii ont été réduites au minimum :
- correction de la configuration BAT
- reconnaissance des adresses d’E/S à partir du nœud « hollywood »
- correction de la cohérence du cache du framebuffer
- externalisation des pilotes hors du noyau pour améliorer l’efficacité de build et la maintenabilité
Conclusion
- Un projet imaginé à l’université en 2013 a finalement été achevé plus de dix ans plus tard
- Le défi a été inspiré par un portage de Windows NT sur Wii
- Au final, le projet a permis un démarrage complet de Mac OS X 10.0 sur Wii et son utilisation en interface graphique
- Il souligne la leçon suivante : « plus un projet semble impossible, plus il vaut la peine d’être tenté »
Aucun commentaire pour le moment.