Benvenuto su Inforge
Rimuovi la pubblicità e partecipa alla più grande comunità italiana sul mondo digitale presente sul web sin dal 2007.
Iscriviti
Android Application Penetration Testing - Concetti e Basi

Guida Android Application Penetration Testing - Concetti e Basi

Android-Penetration-Testing2.png

In questa guida andremo ad analizzare i concetti base (e non solo) del Penetration testing sui dispositivi Android.

Indice​



1    Introduzione alle piattaforme Mobile

Quando si esegue un penetration test su dispositivi mobile bisogna sempre fare distinzione tra due diverse categorie di dati con cui si avrà a che fare:​
  • Data in motion: sono quei dati "dinamici" che un'app si scambia continuamente con i server. La sicurezza di questi dati deve essere garantita non presupponendo che l'apparecchio sia sempre collegato a delle reti sicure (per esempio, dati sensibili trasmessi senza cifratura).​
  • Data at rest: sono i dati "statici" salvati lato client non in movimento. Si possono trovare all'interno di APK, Database, files, ecc. La sicurezza di questi dati deve essere garantita a riposo e non sulla base che il device non possa venir compromesso. (ad esempio, memorizzare o leakare involontariamente dati sensibili in modo che possano essere letti da altre applicazioni sul telefono o da altri utenti).​
Durante i test si dovrà verificare quindi, oltre alle tradizionali vulnerabilità, che entrambe le categorie di dati siano propriamente protette su ogni piattaforma e device. Per questo motivo è fondamentale utilizzare quanti più differenti OS possibili, in modo da avere una coverage adeguata alle criticità e vulnerabilità relative ai differenti OS sul mercato, nonché alle differenze di implementazione tra i diversi sistemi.

Un altro aspetto molto importante durante un penetration test mobile è quello di riconoscere la tipologia di applicazione che si andrà a testare. Le tipologie più diffuse sono principalmente tre:​
  • Native apps: Sono le applicazioni "tradizionali", sviluppate con linguaggi di programmazione lato client (es. Java, Swift, Objective-C, ecc.) e spesso sono specifiche per la piattaforma su cui devono girare, con lo scopo di sfruttare al massimo l'hardware e le API per cui sono state progettate.​
  • Mobile web apps: Sono applicazioni non native, scritte in linguaggi web (HTML, CSS, JavaScript, ecc.) e importate all'interno dell'app tramite specifiche componenti, come ad esempio le web-view. Il loro funzionamento è praticamente identico a quello di un tradizionale sito web, con la differenza che sono ottimizzate per funzionare su dispositivi mobile. Spesso lo stesso codice può essere importato su piattaforme differenti, rendendo così più semplice l'integrazione​
  • Hybrid apps: Come lascia intendere il nome, sono le applicazioni che uniscono le tue tipologie sopra citate.​
Identificare correttamente la tipologia di applicazione è importante poiché in fase di test si dovranno eseguire controlli differenti in base a cosa ci si troverà davanti.​

2    Il sistema Android

Attualmente l'ultima versione dell'OS di casa Google è la versione 11 (API 30), ciò però non comporta che sia il solo sistema su cui eseguire i test, anzi. Sono ancora abbastanza numerosi i device in circolazione che utilizzano versioni non recenti di Android, nonostante comunque piano piano stiano venendo abbandonate.

La API minime consigliate per fare test risultano essere quelle di Android 6.0 Marshmallow (API 23), mentre le più diffuse e usate attualmente sono quelle compresa tra Android 8.0 Oreo (API 26) e Android 10 (API 29). Una lista completa di tutte le versioni e le API esistenti è possibile leggerla qui.
android-feat.jpg

Altre importanti informazioni da conoscere:​
  • Android presenta numerosisime diverse implementazioni, basate su specifici requisiti hardware e software​
  • Il kernel è un fork della versione 2.6 / 3.0 del kernel Linux​
  • Il file system è Ext4
  • Il sistema operativo è basato su Linux
  • Gli eseguibili sono in formato ELF​
  • E' Open Source (Apache SW License 2.0 with GPL components)​

Dal punto di vista della sicurezza i punti fondamentali sono:​
  • La sicurezza low-level è delegata ai fornitori hardware
  • L'os presenta diverse feature per la mitigazione di exploit
  • Controlli basati sul filesystem Unix
  • File-base encryption (FBE) e full-disk encryption (FDE)​
  • Supporto SELinux
  • Possibilità di installare applicazioni self-signed
  • Verifica di Google per la pubblicazione delle app sullo store (non è così effettiva la verifica)​

2.1    Architettura di Android

Come accennato in precedenza, l'architettura del sistema Android è basata sul Kernel Linux 2.x e 3.x. Si estende però poi in altri 5 differenti layers, ottimizzati e integrati tra loro per fornire l'ambiente ideale per lo sviluppo e l'esecuzione di applicazioni per dispositivi mobile.
android-stack_2x.png
  1. Linux Kernel: Il primo livello, nonché la base dell'intera piattaforma Android, è il kernel Linux. Consente ad Android di sfruttare le principali caratteristiche di sicurezza e permette ai produttori di dispositivi di sviluppare driver hardware per un kernel ben noto.​
  2. Hardware Abstraction Layer (HAL): E' un livello di astrazione che fornisce interfacce standard per interagire con le componenti Hardware del sistema correttamente. A partire da Android 8.0 questo layer è stato completamente riscritto, perciò dando vita così a due diversi HAL: quello più recente e la rispettiva versione legacy.​
  3. Middleware: Il layer comunemente chiamato middleware è in verità composto da due sotto-elementi:​
    1. Native Libraries: Sono librerie native, scritte in C e C++, che permettono il corretto funzionamento di vari componenti quali ART e HAL. Posso venir richiamate dalle applicazioni tramite le Java API Frameworks o si può accedere a loro direttamente tramite codice nativo nel caso si utilizzino le Android NDK in fase di sviluppo.​
    2. Android Runtime (ART): è l'elemento chiave che gestisce l'esecuzione delle app all'interno del sistema. Fino ad Android 5.0 l'esecuzione del codice era gestita dalla Dalvik Virtual Machine (DVM), ora obsoleta. Fu rimpiazzata dall'Android Runtime (ART), scritta per eseguire più macchine virtuali su dispositivi low-memory, eseguendo file DEX, un formato byte code progettato appositamente per Android e ottimizzato per ridurre al minimo l'ingombro di memoria.​
      DVMvsART.png
      La differenza fondamentale tra Dalvik e ART è il modo in cui il byte code viene eseguito. In Dalvik, il byte code viene tradotto in codice macchina al momento dell'esecuzione, un processo noto come compilazione just-in-time (JIT). La compilazione JIT influisce negativamente sulle prestazioni poiché la deve essere eseguita ogni volta che l'applicazione viene eseguita. Per migliorare le prestazioni, ART ha introdotto la compilazione ahead-of-time (AOT). Come suggerisce il nome, le app vengono precompilate prima di essere eseguite per la prima volta. Il codice macchina precompilato viene poi utilizzato per tutte le esecuzioni successive, favorendone tempistiche e consumo di energia.​
  4. Application Framework: Sono tutte quelle API che consentono di interagire con le varie funzionalità messe a disposizione dal sistema operativo. Sono scritte in Java e assieme formano building blocks necessari per sviluppare applicazioni Android favorendo il riutilizzo dei componenti e dei servizi di sistema. Gli sviluppatori hanno pieno accesso alle stesse API usate anche dalle app di sistema Android.​
  5. Applications Layer: Sono le applicazioni finali, quelle installate sul device con cui interagiamo ogni giorno per inviare SMS, effettuare telefonate, navigare su internet ecc. Nota particolare per le app di sistema: funzionano sia come app per gli utenti finali sia come elemento per fornire funzionalità chiave a cui gli sviluppatori possono accedere dalla propria app. Ad esempio, se l'app desidera consegnare un messaggio SMS, non è necessario che venga costruita da zero quella funzionalità. E' possibile invece invocare una qualsiasi app di SMS già installata e consegnare il messaggio in questione tramite lei.​

2.2    APK e Android Application Components

I file installabili su Android sono chiamati Android application package, abbreviati in file APK. Questo è il formato che Google ha deciso di utilizzare per distribuire e permettere l'installazione delle applicazioni sui sistemi di loro invenzione. I file APK non sono nient'altro che degli archivi (come fossero dei file .zip), e come tali possono venir scompattati.

All'interno di un file APK gli elementi più comuni e importanti sono:​
  • /assets e /res: sono cartelle contenenti elementi utili all'app per funzionare, come ad esempio le diverse lingue, informazioni sulle dimensioni delle videate, ecc.​
  • /META-INF: E' la cartella che contiene i file .MF e i certificati usati dall'app​
  • AndroidManifest.xml: E' il file contenente tutti i dettagli sull'applicazione, le sue funzionalità e i permessi necessari per farla funzionare. Quando l'archivio APK viene scompattato, questo file non è leggibile poiché deve essere decompilato dal .jar.​
  • classes.dex: è il file eseguibile compilato in Delvik (Delvik executable file)​
  • resources.arsc: è il file contenente tutte le risorse precompilate necessarie dall'app, come per esempio i file xml necessari per la GUI​
  • /lib: è la cartella contenente tutto il codice compilato specifico per il processore​

2.2.1    AndroidManifest.xml

What is in the application = AndroidManifest.xml

Manifest.png


Questo file fornisce informazioni complete su un'applicazione Android. In parole povere, Android leggerà questo particolare file prima e dopo l'installazione di un'app per avviare l'applicazione correttamente e sapere come gestirla.

Il file ha diversi compiti:​
  • Determina il nome del package dell'applicazione​
  • Descrive i componenti presenti (vedremo a breve quali sono)​
  • Determina quale processo è associato a quale componente​
  • Dichiara i permessi dell'app
  • Elenca le librerie linkate all'app
  • Dichiara quali sono le API minime per eseguire l'app​
Per una spiegazione dettagliata del file e di tutti gli elementi disponibili, leggere la documentazione ufficiale di Google

2.2.2    Intent

Gli intents sono la chiave della comunicazione interna tra gli elementi che compongono un'applicazione. Sono descrizioni astratte contenenti informazioni riguardo l'operazione che deve essere eseguita.

Esistono due forme di intents:​
  • Espliciti: hanno specificato un componente che stabilisce quale esatta classe dovrà essere eseguita. Nella maggior parte dei casi sono intent che hanno il solo compito di avviare le varie activity interne dell'applicazione, senza interagire con applicazioni esterne.​
  • Impliciti: non hanno specificato un componente, ma devono invece includere sufficienti informazioni per il sistema in modo da determinare quale dei componenti disponibili è meglio utilizzare.​
Types-of-Intent-Implicit-and-Explicit-Intent-in-Android-example-1.jpg


[/SUBSECTION]Activity[/SUBSECTION]
Un'activity non è nient'altro che la rappresentazione di una singola schermata della GUI che un utente può vedere e con cui può interagire. Per esempio, un'activity di una rubrica potrebbe essere la schermata che ti mostra i dettagli di un numero, mentre una seconda activity potrebbe essere quella che ti permette di cercare un determinato contatto.

Le activity sono gestite tramite dal sistema tramite dei metodi specifici. Di seguito il flusso raffigurante il ciclo di vita di un'activity:​
Activity-Lifecycle-in-Android.jpg


2.2.3    Services

I services sono componenti di un'applicazione che possono eseguire operazione a lungo termine in background e possono essere avviati e stoppati senza l'interazione tramite GUI. Dei classici esempi sono gli alert del Wi-Fi, le notifiche SMS, ecc. Per comunicare con le app i services utilizzano gli intents.

Esistono due tipologie principali di service:​
  • Unbound: il processo viene lanciato da un componente e continua a girare in background pure dopo che il componente originale che l'ha eseguito viene distrutto.​
  • Bound: Il processo viene distrutto quando il componente abbinato cessa di esistere​
services.png


2.2.4    Broadcast receivers

Un broadcast receiver è un componente utilizzato per rispondere agli eventi di sistema o applicativi. Un esempio di broadcast receiver è il componente che ti avvisa quando il telefono viene collegato alla corrente elettrica.

I permessi impostati su questo componente limitano le app che possono inviargli intents.
Android-broadcast-receiver-tutorial.jpg

2.2.5    Content providers

I content providers sono componenti utilizzati per immagazzinare, gestire e condividere dati tra più applicazioni. Un esempio è WhatsApp che accedere ai dati della rubrica. A causa dell'isolamento tra le app, in teoria questa cosa non sarebbe possibile. Il content provider in questione però permette a un app di accedere ai dati dell'altra, permettendo così di comunicare e scambiarsi dati.
ContProv.jpg


2.3    Application sandboxing e Secure inter-process comunication

Una peculiarità molto importante e di cui bisogna essere per forza a conoscenza del sistema Android è la logica di isolamento delle app. Ogni applicazione, nel momento in cui deve essere eseguita, viene isolata dalle altre ottenendo un proprio id e un proprio processo, inaccessibile a chiunque altro al di fuori della stessa applicazione. Questo permette di aggiungere un livello di sicurezza in più al sistema e permette di renderlo anche più stabile: un'applicazione che va in crash o che va in freeze non intaccherà mai le altre applicazioni in esecuzione.
sandbox.png

A causa di questo isolamento, anche la comunicazione lecita tra app diventa impossibile. Per risolvere questo problema è stato implementato un framework, chiamato inter-process comunication (IPC), tramite l'utilizzo del Binder Framework. L'intera implementazione segue un approccio Client-Server e può essere illustrata col seguente schema:
binder.png
Maggiori dettagli sull'implementazione IPC possono essere approfonditi al seguente articolo.​

2.4    Android data directories

/system/bin contiene tutti i binari utilizzati per eseguire i principali comandi (es. ls, cd, ecc.)

/system/xbin ha la stessa funzione della directory sopra

/data/data contiene tutti i dati delle varie applicazioni installate sul device, suddivise per package

/data/apk contiene tutti i file APK originali delle app installate sul nostro device, suddivise per package​

3    Conclusioni

In questa prima guida abbiamo visto i concetti principali del sistema operativo Android, le basi del suo funzionamento, le implementazioni fondamentali di sicurezza e tutti i componenti delle applicazioni per questo sistema. Questi concetti sono fondamentali per poter comprendere al meglio la prossima guida, che sarà esclusivamente incentrata sulle tecniche di attacco e sull'analisi delle applicazioni. Poiché questa che avete appena letto non è una guida esaustiva sul mondo Android, invito chiunque ne sentisse il bisogno, volesse approfondire maggiormente le tematiche o volesse portarsi avanti con gli studi, a proseguire i suoi studi sui riferimenti qui sotto.

4    Internal References:


5    External References

Autore
0xbro
Visualizzazioni
729
Prima pubblicazione
Ultimo aggiornamento
Voto recensione
0.00 stelle/a 0 voti

Altre release di 0xbro