martedì 22 ottobre 2013

Un viaggio attraverso il kernel - Parte 1




Benvenuti in questo viaggio in più puntate riguardo uno degli aspetti più importanti, ma anche più complessi, del mondo di Android, ossia il kernel.

Prima di iniziare l'argomento vero e proprio, diamo un'occhiata all'organizzazione del post:
  • In questa prima guida accennerò qualcosa sulla storia del kernel Linux e sulla divisione del ramo Android, facendo cenno ad alcuni parametri ed aspetti tecnici. 
  • Nella prossima parte, si parlerà di tweaks, ossia di modifiche che si possono compiere al kernel per renderlo più simile alle nostre esigenze e lo faremo tramite script.
  • Nell'ultima parte, invece, andremo ad analizzare le opzioni ed il funzionamento di Stweaks, l'app sviluppata da gokhanmoral, il creatore di uno dei migliori kernel esistenti per diversi device, il Siyah, dal quale ha tratto spunto Dorimanx per il suo omonimo kernel.
PARTE PRIMA

Il kernel è un software che costituisce il nucleo di qualunque sistema operativo, da quello mobile, a quello desktop e server, che si occupa della comunicazione tra l'hardware ed il software del sistema operativo stesso, detto shell. I programmi (invocati o meno dall'utente) richiedono delle risorse al kernel (processo chiamato system call), cosa che non possono fare direttamente i programmi ed il kernel accede direttamente all'hardware "smuovendo" uno o più componenti (processore, RAM, periferiche etc).

Schema di funzionamento del kernel Linux.


Esso comprende più driver che, nel caso del kernel Linux, quello che andremo ad analizzare, sono integrati in moduli, che possono essere accorpati o estromessi a piacere da una certa tipologia di utente (l'utente root o amministratore).
Il kernel Linux nacque nel 1991 ad opera dell'informatico finlandese Linus Torvalds (ecco da dove viene il nome Linux) che da solo, iniziò a scrivere il codice per il kernel e, attraverso un post (che potete trovare ritrascritto qui) lo pubblicò al mondo. In tanti si misero al lavoro assieme a Torvalds, compreso Richard Stallman che, in accoppiata col suo GNU (che originariamente montava il kernel Hurd), formano il sistema operativo GNU/Linux.
Ovviamente il tutto è open source, marcia in più che ha consentito al kernel di espandersi e di venire utilizzato in ogni dove (si stima che il 90% dei server monti sistemi operativi basati su Linux, più della metà dei device mobili montano Android e quindi Linux e solo l'1% dei desktop pc monta distro Linux).



L'open source è stata anche la molla che ha fatto scattare la nascita di Android.
Difatti Android nasce con kernel Linux 2.6, sviluppatosi, poi in 3.x (successivamente ad Ice Cream Sandwich 4.0.x).
Esso integra middleware, API e librerie (scritte in C, C++ e Java), con un software in esecuzione su un framework ed una macchina virtuale, chiamata Dalvik VM, che fa uso di un compilatore just-in-time che esegue il codice dalvix dex-code, che viene fornito dal codice bytecode Java. Un percorso complesso se pensiamo che il tutto viene eseguito su un device grande quanto un palmo della mano!
Verrebbe abbastanza semplice da pensare che sia i sistemi operativi desktop (quali Debian, Arch, Gentoo, Red Hat ed il più famoso Ubuntu) che quelli mobili, (Firefox OS, Ubuntu touch ed ovviamente Android) condividano lo stesso kernel. Diciamo che non è totalmente vero e non è totalmente falso. Difatti, sebbene entrambi i kernel siano Linux (anche se per Android parliamo di stampo Linuxiano), questi differiscono per tanti aspetti. 
Il primo, ovviamente, è la dimensione del kernel: difatti mentre per le versioni desktop si parla di 150~200MB (più di 18 milioni di righe di codice), per Android il peso del kernel si aggira dai 5 ai 10MB, una nullità in confronto!
Semplice presupporre il perché: il kernel Linux desktop integra, alla struttura primaria monolitica, diversi moduli per accorpare tutti i driver possibili (ovviamente open source) per avere una piena compatibilità con la maggior parte dei pc in commercio. 

Al contrario il kernel Android viene di volta in volta integrato e snellito per accorpare solo e soltanto i driver che necessitano al particolare dispositivo, motivo per il quale un kernel per Samsung Galaxy SII non funziona per Samsung Galaxy SIII (per citare un esempio dove compaiono due membri della stessa famiglia).
Qui di fianco potete vedere il funzionamento del sistema operativo Android. Alla base di esso risiede il kernel Linux che integra i driver dei vari componenti e la gestione energetica, indicati come "stanze a sé stanti", ossia i moduli. Ogni driver è univoco per il componente hardware assegnato, per cui, portando ancora l'esempio del device più usato dal team di AndroidMod, ossia il Galaxy SII, alla voce Display (che integra anche la GPU), ci saranno i driver Mali. Ovviamente il discorso è molto semplificato, ma in linea di massima è questo.
Andando veloce, come vedete sempre da immagine, vedete le librerie (tra le più conosciute, quelle relative a SQLite, ossia la gestione del database, e le OpenGL/ES, recentemente aggiornati alla versione 3.0 con Android 4.3), il Runtime Android, dove risiede la macchina virtuale che esegue il codice .dex, il framework delle applicazioni ed infine le applicazioni a diretto contatto con l'utente, quelle che volgarmente chiamiamo apk.

Possiamo trarre alcune conclusioni: il kernel è il nocciolo di un sistema operativo, parte fondamentale per il funzionamento della macchina stessa, dal quale dipendono le prestazioni che la macchina può offrire, nonché, per quanto riguarda Android (ma non solo), anche la gestione energetica della stessa macchina. Sta alla base di tutto e non è direttamente accessibile all'utente (per evitare che faccia danni), a meno che esso non sia un utente root, ossia un utente con i privilegi di amministratore del dispositivo.
Su Android, o almeno, sulla stragrande maggioranza dei device android, non si è in possesso inizialmente di questi privilegi, per cui l'utente può interfacciarsi solo e soltanto con le applicazioni, ma senza modificarle (non nel loro funzionamento almeno). Come detto prima, è stato deciso di non concedere i permessi di root per evitare, a chi non è avvezzo di sistemi Linux, di fare danni irreparabili al proprio device (basti pensare anche soltanto al processo dell'overvolt della gpu che può far scoppiare lo schermo, causando anche danni fisici).
Grazie al lavoro di tanti developer, uno su tutti Chainfire di XDA, è possibile ottenere questi permessi ed avere pieno controllo del dispositivo (perdendo la garanzia, come tutti sapranno ormai), per cui si ottengono anche i permessi per modificare il software al livello più basso, toccando il bootloader (ossia la partizione del device che carica il kernel), il kernel, le librerie, il framework e, ovviamente, le applicazioni.

Lo scopo del prossimo articolo sarà quello di guardare dentro al kernel e vedere come poter modificare, tramite dei tweaks, la gestione che lo stesso esegue sull'hardware.

Per adesso ci fermiamo qui, a questi concetti semplificati, per poi addentrarci, in maniera mai troppo complessa, nel fantastico mondo del modding puro.

Alla prossima!