Ricerca tra la vecchia roba

Compilare popcorn app da sorgenti

Posted: maggio 12th, 2014 | Author: | Filed under: General | Comments Off on Compilare popcorn app da sorgenti

Torno dopo due anni di assenza (ma non penso che a qualcuno io sia mancato più di tanto) per appuntare le istruzioni per compilare questa applicazione dai suoi sorgenti.

Questo programma permette di vedere in direttamente in streaming film e serie tv utilizzando come sistema la rete bittorrent; il tutto è implementato utilizzano nodejs ed è proprio la difficoltà a installare e mantenere questa tecnologia su una macchina Debian che mi spinge a scrivere questi appunti.

Dipendenze di sistema:

# apt-get install python-virtualenv ruby

ruby serve solo per compass e in caso non abbiato installato quest’ultimo è possibile sempre averlo in locale facendo

$ gem install compass --user-install
$ PATH=~/.gem/ruby/2.0.0/bin/:$PATH

Prima di tutto scarichiamo i sorgenti utilizzando git:

$ git clone https://github.com/popcorn-official/popcorn-app.git
$ cd popcorn-app
$ git checkout --track origin/dev-0.3
$ virtualenv --no-site-packages env
$ source env/bin/activate
$ pip install virtual-node
$ npm install bower grunt-cli
$ npm install

In questa maniera abbiamo installato in locale nodejs, dobbiamo solo inserire nel PATH i binari installati

$ PATH=node_modules/.bin/:$PATH

A questo punto un bel

$ grunt build
$ grunt exec:linux64

farà partire popcorn (cambiate linux64 con la vostra architettura).


Diaz

Posted: maggio 2nd, 2012 | Author: | Filed under: General | Tags: , , | Comments Off on Diaz

È uscito nella sale il film “Diaz: Don’t Clean Up This Blood”, opera che vuole descrivere quello che è stato più di dieci anni fa l’assalto della polizia italiano alla scuola Diaz al termine del G8 di genova del 2001. Un film che mancava, nonostante arrivi con un decennio di ritardo, e che mostra la vera faccia della polizia italiana (che chiunque sia andato ad una manifestazione conosce benissimo).

Siccome non sono un critico cinematografico linko qualche discussione trovata online

Come spesso succede, contenuti sugosi si possono trovare anche nei commenti. Vabbè, ACAB!


Compilare un kernel per il Samsung Galaxy S

Posted: ottobre 9th, 2011 | Author: | Filed under: Guide | Tags: , , , , | Comments Off on Compilare un kernel per il Samsung Galaxy S

Prima di tutto andare sul sito della samsung che mette a disposizione i sorgenti e selezionare il sorgente più ultimo che corrisponde al file GalaxyS_OpenSource_GB_Update2.zip (in realtà dipende da che versione di kernel avete sul cellulare e non ho un mapping fra archivi e versioni, nel caso scaricateveli ed informatemi).

All’interno dei sorgenti ci dovrebbe essere un file chiamato build_kernel.sh che dovrebbe buildare il tutto ma pare non scritto perfettamente bene. Alla fine la procedura da seguire è la seguente: prima di tutto

$ make ARCH=arm aries_eur_defconfig

vi genera il .config per l’hardware del vostro samsung. I passaggi successivi sono

$ make ARCH=arm CROSS_COMPILE=/opt/arm-sourcery-g++-lite/bin/arm-none-linux-gnueabi-
$ make ARCH=arm CROSS_COMPILE=/opt/arm-sourcery-g++-lite/bin/arm-none-linux-gnueabi- zImage
$ make ARCH=arm CROSS_COMPILE=/opt/arm-sourcery-g++-lite/bin/arm-none-linux-gnueabi- modules

Fate attenzione che la toolchain deve essere nel vostro PATH. Se invece dovete buildare un modulo che non è contenuto nel tree dei sorgenti il comando da dare è il seguente

$ make ARCH=arm CROSS_COMPILE=$TOOLCHAIN_PATH/$TOOLCHAIN_PREFIX -C /path/to/module/src

dall’interno del tree del kernel. Attenzione che per fare in modo che il modulo venga caricato senza problemi bisogna editare il config in modo che aggiunga un suffisso alla versione del  kernel che matchi quello che gira sul cellulare; per farlo dopo il primo step sopra descritto dare

$ make menuconfig ARCH=arm

ed editare

General setup  ---> Local version - append to kernel release

inserendo la stringa che trovate sotto la voce “Versione kernel” nella sezione “Info sul telefono” del vostro samsung. Senza questo sarebbe problematico riuscire a caricare i moduli compilati.

L’ultimo passaggio dovrebbe essere flashare il kernel usando heimdall. Saluti.


Buildare eseguibili per android

Posted: ottobre 9th, 2011 | Author: | Filed under: Guide | Tags: , , , , , , , , | Comments Off on Buildare eseguibili per android

Un mio progetto segreto (?) durante l’hackit è stato capire come eseguire il cross-compiling su android;  come argomento pare essere già stato affrontato da altri ma senza che nessuno abbia prodotto un tutorial completo. Dopo una prima occhiata sull’argomento parrebbero esserci almeno N metodologie per cross-compilare su android (per chi non lo sapesse apparecchi come i nostri smartphone hanno un processore ARM).

Quello che segue può sembrare un po’ roba sparsa ed in tal caso c’avete ragione.

LIBC

Prima di tutto bisogna sapere che la libreria standard utilizzata per i processi che vengono eseguiti su questo sistema non è la glibc ma è chiamata bionic; questa è stata pensata per girare su sistemi embedded e quindi non ha tutte le potenzialità/funzionalità delle più note omologhe librerie , in particolare c’è da tener presente che non è supportata la gestione dei locale(7) direttamente da C ma bisogna passare da Java (per esempio wget non compila proprio per questa problematica e anche lua ha lo stesso problema). Inoltre ha una gestione propria dei thread (quindi niente original linux threads/NPTL ).

LINKER

Il linker è il programma che si deve preoccupare in un sistema operativo di caricare le librerie necessarie ad un adeguato programma; in linux è chiamato linux-vdso.so.1 mentre in android si è scelto di usare il programma il cui path è /system/bin/linker. Al contrario dei linker UNIX che rispettano la variabile d’ambiente LD_LIBRARY_PATH esso cerca solamente le librerie in /system/lib/ e /lib/ e questo è un casino. Qualche info

  • http://www.koushikdutta.com/2009/05/androids-linker-makes-baby-jesus-cry.html
  • http://groups.google.com/group/android-developers/browse_thread/thread/a76d1822ed0021ac
  • http://android.git.kernel.org/?p=platform/bionic.git;a=blob;f=linker/linker.c;h=00f36c07a663c25219d8d963c2b753914383bc11;hb=HEAD

Un modo per evitare i casini è buildare gli eseguibili staticamente.

SISTEMA DI BUILD DI ANDROID

Il sistema android utilizza una versione moddata di Makefile che si preoccupano di ricostruire le dipendenze, buildare librerie ed eseguibili e copiarle nella immagine disco da flashare nell’apparecchio.

L”unico problema è che non si possono utilizzare gli autotools o cmake ma si deve scrivere un makefile apposito, chiamato Android.mk, tramite cui effettuare la compilazione. Si capisce subito che se abbiamo già un progetto avviato e di una certa complessità è molto difficile scrivere uno di questi file senza problemi (e non dimentichiamoci del suo mantenimento successivo).

Siccome per adesso sono interessato a compilare programmi che già utilizzano gli autotools mostrerò come compilare staticamente/dinamicamente passando parametri opportuni a configure.

Per chi è interessato a compilare roba per android utilizzando CMake è interessante utilizzare le istruzioni per il cross compiling di openCV.

COMPILATORE

Per compilare ovviamente serve un compilatore e tutta la toolchain ed una prima opzione è la toolchain arm sourcery con la quale è possibile compilare staticamente; opzioni simili sono la toolchain della SDK ed NDK scaricabili dal sito di android. Il problema con queste due soluzioni è il dover elencare a manina tutti i flags necessari per linkare correttamente il programma al sistema di android che non è proprio un cazzo facile per le questioni espresse più sopra.

Proprio per questo una valida alternativa è il progetto droid-wrapper, esso si propone di creare uno script che configuri gcc ed ld per compilare programmi utilizzando i normali autotools. Ci si deve solo premurare di aver prima compilato i sorgenti di android.

Una volta scaricato il progetto con git è possibile facilitarne l’uso creando uno script che imposti le variabili d’ambiente in maniera corretta (la directory in cui è stato scaricato nel nostro caso è /opt/droid-wrapper/ con i sorgenti di android in /opt/android-source/)

$ cat .bash_droid
export DROID_ROOT=/opt/android-source/
export DROID_TARGET=generic
export PATH=/opt/droid-wrapper/bin/:$PATH

echo "usa CC=droid-gcc LD=droid-ld ./configure --host=arm-linux-eabi"

Una cosa da tener presente quando si effettua il cross compiling (cioè il compilare del codice per piattaforma diversa rispetto a quella in cui gira il compilatore) è la naming convention usata dai compilatori: un compilatore di questo tipo ha un prefisso costruito usando il seguente schema

arch-vendor-(os-)abi

Per esempio la toolchain della sourcery citata poco più sopra ha un prefisso dato da arm-none-linux-gnueabi. Tenete presente che la toolchain che vorrete usare deve essere nel vostro PATH altrimenti nulla compilerà.

Vediamo adesso come compilare alcuni tools utili per i very hackerz.

BUSYBOX

Busybox è un singolo programma che racchiude internamente praticamente tutte le utility UNIX ri-implementandole e permettendo così di avere un sistema funzionante con un singolo eseguibile anche in sistemi embedded. Nel caso di android questo risulta molto utile proprio per evitare di dover compilare tutti gli eseguibili necessari uno per uno.

Per compilarlo staticamente usando la toolchain prescelta basta eseguire

$ make menuconfig

e nel menù che compare,  inserire in

Busybox Settings > Build options > Cross Compiler prefix

l’identificativo della toolchain prescelta! Un make builderà per voi tutte le utility in un singolo eseguibile chiamato busybox.

BASH

Fila tutto liscio usando

$ ./configure --host=arm-none-linux-gnueabi --enable-static-link --without-bash-malloc

VIM

Un primo esempio di programma che può tornare utile a voi hackerz è il mitico editor: a causa della sua complessità non è possibile compilarlo dinamicamente; usiamo la toolchain sourcery

export PATH=/opt/arm-sourcery-g++-lite/bin:$PATH

Prima di tutto si necessita delle librerie ncurses che possono essere compilate con un semplice

$ ./configure --host=arm-none-linux-gnueabi && make

Chiamando NCURSES_PATH la variabile dove si imposta il path per le librerie appena sopra compilate

vim_cv_memmove_handles_overlap=no \
 vim_cv_toupper_broken=set \
 vim_cv_memcpy_handles_overlap=no \
 vim_cv_bcopy_handles_overlap=no \
 vim_cv_stat_ignores_slash=no \
 vim_cv_getcwd_broken=no \
 vim_cv_tty_group=world \
 vim_cv_terminfo=yes \
 LDFLAGS="-L$NCURSES_PATH/lib/ -static" \
 CFLAGS=-I$NCURSES_PATH/include/ ./configure --host=arm-none-linux-gnueabi --with-tlib=ncurses

Potrebbe uscire un errore al check per int32: per risolverlo editate src/auto/configure eliminando il controllo che ha restituito l’errore. Ma non è finita qui: dando make vi uscirà un errore

auto/osdef.h:117: error: previous declaration of 'tgoto' was here

e per risolverlo dovete andare ad eliminare le funzioni di cui si lamenta il compilatore definite in src/auto/osdef.h; finito ridate make. Finito di compilare potete caricare nel device il programma

adb push src/vim /data/local/tmp/

e lanciarlo da una shell con

TERM=xterm-color vim

Ovviamente così molte cose non funzioneranno alla perfezione, per esempio l’help.

Tutto questo è una rielaborazione di questo post http://credentiality2.blogspot.com/2010/08/native-vim-for-android.html.

EMULATORE

Si possono installare i programmi anche sull’emulatore tenendo conto che

  1. se si vuole installare roba nella cartella di sistema, bisogna rimontare la partizione /system in read-write mode (mount -o rw,remount -t yaffs2 /dev/block/mtdblock0 /system)
  2. è probabile che la partizione /system non sia grande abbastanza quindi si deve far partire l’emulatore con una size adeguata (emulator -avd test2.3.3 -partition-size 1024)

ROBA IN GENERALE

Per qualche info in più leggere


Exploit: prevenire NON è meglio che curare

Posted: settembre 11th, 2011 | Author: | Filed under: Guide | Tags: , , , | Comments Off on Exploit: prevenire NON è meglio che curare

Eccoci alla seconda puntata di come capire il funzionamento degli exploit; l’ultima volta siamo rimasti alla potenziale modifica del flusso di un programma scritto male a nostro uso e consumo, oggi non andremo di molto avanti in quanto cercheremo di capire assieme come viene gestita la memoria relativa ad un processo in un OS moderno. Partire subito con esempi di exploit non sarebbe utile perché gli esempi semplici praticamente non esistono: il primo paper di Aleph1 risale al 1996 e da allora i sistemi informatici si sono evoluti con contromisure proprio atte a evitare il succedersi di intrusioni alzando sempre di più l’asticella della difficoltà insita nel deviare il $pc tanto agognato.

C’è da dire che benché molti sforzi siano stati fatti, la genialità degli exploiter è cresciuta altrettanto portando questa pratica ad uno stato quasi magico. Ma bando alle ciance e iniziamo ad analizzare come è strutturato un programma (mi limiterò al formato eseguibile ELF of course).

Teoria

Nella prima parte abbiamo visto come un programma funziona a livello di istruzioni, ma per eseguire istruzioni un programma ha prima di tutto bisogno di essere caricato in memoria; bisogna tenere conto che ci saranno zone di memoria apposite per ogni tipo di necessità, elenchiamole:

  • Stack: visto sempre nella puntata precedente, contiene le variabili locali del contesto di esecuzione più le variabili della funzione attualmente in esecuzione
  • File mappings: esiste la possibilità di mappare direttamente file in memoria ed è anche il metodo con cui vengono caricate le shared library (ne parlerò un po’ meglio dopo)
  • Heap: zone di memoria allocate dinamicamente (in pratica malloc() et familia)
  • BSS: variabili statiche non inizializzate
  • Data: variabili statiche inizializzate
  • Text: contiene il codice eseguibile

Ognuna di queste sezioni ha ovviamente delle proprietà sue proprie, in particolare può essere scrivili,leggibile ed eseguibile. Per avere un esempio pratico eseguiamo

$ cat /proc/self/maps
08048000-08052000 r-xp 00000000 08:21 8421442    /bin/cat
08052000-08053000 rw-p 0000a000 08:21 8421442    /bin/cat
0875a000-0877b000 rw-p 00000000 00:00 0          [heap]
b74bc000-b76bc000 r--p 00000000 08:21 1035297    /usr/lib/locale/locale-archive
b76bc000-b76bd000 rw-p 00000000 00:00 0
b76bd000-b7810000 r-xp 00000000 08:21 29540827   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7810000-b7811000 ---p 00153000 08:21 29540827   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7811000-b7813000 r--p 00153000 08:21 29540827   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7813000-b7814000 rw-p 00155000 08:21 29540827   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7814000-b7817000 rw-p 00000000 00:00 0
b784a000-b784c000 rw-p 00000000 00:00 0
b784c000-b784d000 r-xp 00000000 00:00 0          [vdso]
b784d000-b7868000 r-xp 00000000 08:21 29540776   /lib/i386-linux-gnu/ld-2.13.so
b7868000-b7869000 r--p 0001b000 08:21 29540776   /lib/i386-linux-gnu/ld-2.13.so
b7869000-b786a000 rw-p 0001c000 08:21 29540776   /lib/i386-linux-gnu/ld-2.13.so
bfb95000-bfbb6000 rw-p 00000000 00:00 0          [stack]

Come potete vedere vengono visualizzati i vari mappings che il programma ha nella sua esecuzione; per capire cosa significhi ‘sta roba ecco a voi la pagina di man

/proc/[pid]/maps
 A file containing the currently mapped memory regions and their access permissions.

 The format is:

 address           perms offset  dev   inode   pathname
 08048000-08056000 r-xp 00000000 03:0c 64593   /usr/sbin/gpm
 08056000-08058000 rw-p 0000d000 03:0c 64593   /usr/sbin/gpm
 08058000-0805b000 rwxp 00000000 00:00 0
 40000000-40013000 r-xp 00000000 03:0c 4165    /lib/ld-2.2.4.so
 40013000-40015000 rw-p 00012000 03:0c 4165    /lib/ld-2.2.4.so
 4001f000-40135000 r-xp 00000000 03:0c 45494   /lib/libc-2.2.4.so
 40135000-4013e000 rw-p 00115000 03:0c 45494   /lib/libc-2.2.4.so
 4013e000-40142000 rw-p 00000000 00:00 0
 bffff000-c0000000 rwxp 00000000 00:00 0

 where "address" is the address space in the process that it occupies, "perms" is a set of permissions:

 r = read
 w = write
 x = execute
 s = shared
 p = private (copy on write)

 "offset"  is  the  offset  into  the  file/whatever,  "dev" is the device (major:minor), and "inode" is the inode on that
 device.  0 indicates that no inode is associated with the memory region, as the case would  be  with  BSS  (uninitialized
 data).

 Under Linux 2.0 there is no field giving pathname.

Piccolo appunto: se controllate i mappings in vari programmi eseguiti contemporanemente potreste chiedervi come mai c’è un overlap fra le varie regioni di memoria fra programmi diversi e la spiegazione è semplice: ogni programma ha a disposizione virtualmente 3GB di memoria flat, è il sistema operativo che si preoccupa di eseguire i mappings virtuale/fisico in maniera corretta.

Tornando all’ouput di cui sopra potete vedere che tutte le zone di memoria elencate sono presenti con in più una zona chiamata vdso (Virtual Dynamic Shared Object) che si preoccupa di fare da trampolino per le syscall (invenzione di linus che dichiara “I’m a disgusting pig, and proud of it to boot.“)

Prendiamo il seguente programma

#include<stdio.h>
#include<string.h>

int main(int argc, char* argv[]) {
 char* unitialized;
 static char* s_unitialized;
 char initialized[] = "porcamadonna";
 static char s_initialized[] = "porcamadonna";

 printf("process %d \n"
  "\t       uninitialzed: 0x%08x\n"
  "\tstatic uninitialzed: 0x%08x\n"
  "\t       initialized:  0x%08x\n"
  "\tstatic initialized:  0x%08x\n",
  getpid(), &unitialized, &s_unitialized, &initialized, &s_initialized);

 int iMustWait = !(argc > 1 && ! strcmp(argv[1], "-go"));
 if (iMustWait)
  getchar();

 return 0;
}

e compiliamolo

$ gcc segment.c -o segment

Una volta lanciato si bloccherà mostrandoci gli indirizzi di memoria assegnati alle variabili

$ ./segment
process 11663
        uninitialzed: 0xbf9e3ad8
 static uninitialzed: 0x08049804
        initialized:  0xbf9e3acb
 static initialized:  0x080497ec

Se controlliamo il map del programma in esecuzione

$ cat /proc/11663/maps
08048000-08049000 r-xp 00000000 08:13 3556546    /home/packz/Programmazione/Ci/Exploit/Data segment/segment
08049000-0804a000 rw-p 00000000 08:13 3556546    /home/packz/Programmazione/Ci/Exploit/Data segment/segment
b76ad000-b76ae000 rw-p 00000000 00:00 0
b76ae000-b7801000 r-xp 00000000 08:21 29540770   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7801000-b7802000 ---p 00153000 08:21 29540770   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7802000-b7804000 r--p 00153000 08:21 29540770   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7804000-b7805000 rw-p 00155000 08:21 29540770   /lib/i386-linux-gnu/i686/cmov/libc-2.13.so
b7805000-b7808000 rw-p 00000000 00:00 0
b7839000-b783d000 rw-p 00000000 00:00 0
b783d000-b783e000 r-xp 00000000 00:00 0          [vdso]
b783e000-b7859000 r-xp 00000000 08:21 29540856   /lib/i386-linux-gnu/ld-2.13.so
b7859000-b785a000 r--p 0001b000 08:21 29540856   /lib/i386-linux-gnu/ld-2.13.so
b785a000-b785b000 rw-p 0001c000 08:21 29540856   /lib/i386-linux-gnu/ld-2.13.so
bf9c4000-bf9e5000 rw-p 00000000 00:00 0          [stack]

possiamo vedere che le variabili statiche (cioé globali all’interno del flusso del programma) sono nello spazio di memoria indicato nella seconda riga. Le altre sono nello spazio dello stack (ultima riga).

Tuttavia fra le due variabili statiche c’è una leggera differenza: se andiamo a vedere con readelf i section headers scopriamo che la variabile inizializzata punta alla sezione .data, mentre quella non inizializzata alla sezione .bss

$ readelf -S segment
There are 31 section headers, starting at offset 0x934:

Section Headers:
 [Nr] Name              Type            Addr     Off    Size   ES Flg Lk Inf Al
 [ 0]                   NULL            00000000 000000 000000 00      0   0  0
...
 [25] .data             PROGBITS        080497e4 0007e4 000018 00  WA  0   0  4
 [26] .bss              NOBITS          080497fc 0007fc 00000c 00  WA  0   0  4
...
 [30] .strtab           STRTAB          00000000 00126c 00024a 00      0   0  1
Key to Flags:
 W (write), A (alloc), X (execute), M (merge), S (strings)
 I (info), L (link order), G (group), T (TLS), E (exclude), x (unknown)
 O (extra OS processing required) o (OS specific), p (processor specific)

Un ulteriore segmento di memoria è quello denominato heap che è associato con l’allocazione dinamica di memoria (si pensi alle varie malloc(), calloc() e free()). A livello implementativo sono variazioni della chiamata di sistema brk() che per esempio nelle libc è eseguita tramite la Doug Lea’s malloc; se avrò tempo un giorno potrei scrivere come eseguire exploit dall’heap, pratica molto diffusa nei browser.

L’argomento che rimane da discutere è il caricamento delle librerie dinamiche che necessità l’eseguibile e ciò avviene tramite l’uso dell’interpreter (nei sistemi linux rappresentato da /lib/linux-so.2). In realtà quando un file eseguibile viene lanciato (funzione load_elf_binary in fs/binfmt.c), il kernel si preoccupa di leggere dall’apposita sezione del file ELF proprio quale è il suo interpreter  e dopo aver impostato opportunamente le zone di memoria carica le librerie necessarie al funzionamento del programma tramite esso. Se interessa il codice di ld.so si trova nella directory elf/ del tree delle libc; il suo punto di ingresso è la funzione dl_main in rtld.c.

Siccome le librerie vengono caricate a run-time esiste un processo chiamato di relocation che avviene all’interno di un processo ELF quando si necessità di eseguire una routine appartenente ad una libreria esterna: se disassembliamo il programma segment, possiamo vedere che alla riga in cui viene eseguita la call alla printf, la jump salta alla sezione .plt del nostro eseguibile

$gdb segment
Reading symbols from /home/packz/Programmazione/Ci/Exploit/Data segment/segment...(no debugging symbols found)...done.
(gdb)disassemble main
...
0x080484ad <+89>:    call   0x8048350 <printf@plt>
...

Se disassembliamo quella sezione otteniamo

$ objdump -j .plt -d segment

segment:     file format elf32-i386

Disassembly of section .plt:

08048340 <printf@plt-0x10>:
 8048340:       ff 35 c8 97 04 08       pushl  0x80497c8
 8048346:       ff 25 cc 97 04 08       jmp    *0x80497cc
 804834c:       00 00                   add    %al,(%eax)
 ...

08048350 <printf@plt>:
 8048350:       ff 25 d0 97 04 08       jmp    *0x80497d0
 8048356:       68 00 00 00 00          push   $0x0
 804835b:       e9 e0 ff ff ff          jmp    8048340 <_init+0x38>

Se in gdb andiamo a vedere che indirizzo c’è scritto alla cella di memoria 0x80497d0

(gdb) x/a 0x80497d0
0x80497d0 <printf@got.plt>:    0x8048356 <printf@plt+6>

con stupore scopriamo che punta alla istruzione successiva. Seguendo il flusso delle istruzioni vediamo che viene pushato un numero (l’indice della funzione da relocare) e avviene una jump all’inizio della sezione .plt; viene pushato un indirizzo (?) e si salta alla routine (call *0x80497cc) che andrà a risolvere la routine printf. L’indirizzo di quest’ultima jump è riempito dal linker all’avvio del programma.

Finita la routine all’indirizzo 0x80497d0 si ritroverà direttamente l’indirizzo della funzione in questione così da non aver più necessità di rieseguire tutto la relocazione alla prossima invocazione della printf. La Procedure Linkage Table e la Global Offset Table hanno un ruolo molto importante nella scrittura degli exploit avanzati, spero di poterlo spiegare in futuro.

Dopo tutta la teoria

Dopo tutto questo viaggio sulle varie zone di memoria possiamo passare al collegare questo con la sicurezza di un eseguibile: per prima cosa c’è da notare che se andiamo ad eseguire lo stesso programma due volte e controlliamo gli indirizzi assegnati alle varie aree di memoria scopriamo che tutti gli indirizzi tranne quelli per il codice e dei dati globali sono cambiati, in particolare sono randomizzati.

Questa è una delle prime contromisure sviluppate nel corso degli anni per prevenire i buffer overflow: se gli indirizzi cambiano ogni volta non è così facile scrivere un exploit che funzioni correttamente.

Per sapere come è implementata la randomizzazione leggetevi questo post: https://xorl.wordpress.com/2011/01/16/linux-kernel-aslr-implementation/.

Secondo step di protezione è lo stack non eseguibile (NX): siccome il codice per l’exploit viene posto (solitamente) nello stack e si cerca di eseguirlo da lì, rimuovendo dalle pagine di memoria dello stack il bit eseguibile provoca un segmentation fault quando l’istruction pointer viene dirottato in quelle zone. Come si nota l’unica zona eseguibile è quella text e le librerie condivise.

Terzo step di protezione è l’anteporre al frame dello stack dei valori random che vengono chiamati canary values da controllare al termine di una routine per la loro corruzione: siccome un buffer overflow dovrà per forza passare attraverso questi valori corrompendoli, la protezione dovrebbe essere effettiva.

L’ultimo livello di protezione è la cosiddetta ASCII-Armor, cioé caricare librerie  con indirizzi contenenti un byte nullo in maniera da rendere impossibile utilizzare tali indirizzi in un payload.

Purtroppo(?) tutte queste contromisure sono (per la maggior parte dei casi)  inutili, un eseguibile ha dentro di se abbastanza spazio di azione da rendere un overflow exploitabile nella maggioranza dei casi; nei post futuri spero di riuscire a spiegare come.


Exploit: intro

Posted: agosto 20th, 2011 | Author: | Filed under: Guide | Tags: , , , , | 2 Comments »

L’hacking da che mondo e mondo tratta l’usare uno strumento in un modo non concepito dal suo inventore; chi si occupa di programmazione e non solo si deve preoccupare in maniera critica di non esporre il proprio lavoro a mani poco scrupolose. Io non mi ritengo un esperto ma ci sono alcune cose che mi affascinano, tra queste la programmazione a basso livello e gli exploit (due cose molto legate tra loro).

Chi si fosse chiesto come sia possibile entrare in un computer altrui questo vuol essere un intro non esauriente (spero ulteriori posts seguiranno) che possa gettare luce.

Partiamo da un programma molto semplice

int bau(char* porcodio, int alpha) {
    return porcodio[0] + alpha;
}
 
int main(int argc, char* argv[]) {
    return bau("bastardo", 137);
}

Questo programma non fa niente di utile (se non un po’ di blasfemia spicciola) ma servirà a noi per capire come funziona sotto il cofano un programma per computer (quanto segue è tutto eseguito su sistemi x86).

Per prima cosa compiliamolo

$ gcc boh.c -o boh

e lanciamolo controllando il valore di ritorno

$ ./boh
$ echo $?
235

Entusiasmante vero (235 = ‘p’+ 137 dove il valore ASCII di “p” è 98)? ok, adesso proviamo a vedere passo passo cosa succede; utilizziamo il fido compagno di ogni programmatore, il prode gdb: lanciamolo e impostiamolo in maniera tale da fermarsi alla funzione main e mostrare le istruzioni a livello assembler

$ gdb -q ./boh
Reading symbols from /sti/cazzi/boh...(no debugging symbols found)...done.
(gdb) b main
Breakpoint 1 at 0x80483cb
(gdb) display /3i $pc

Piccolo appunto: il linguaggio assembler è il linguaggio a più basso livello con cui si può dialogare con un processore ed è ovviamente unico per ogni tipologia di architettura: l’assembler per x86 è diverso da quello per x86_64 e quello per ARM, ognuno ha le sue peculiarità ma la cosa più importante è capire che sono simili ma incompatibili.

Per chi non conoscesse il linguaggio assembler un piccolo riassunto: siccome parla con il processore le sue variabili possono essere solo i vari registri del processore stesso; in un sistema x86 si hanno i registri eax, ebx, ecx, edx che sono registri generici più dei registri più specifici come %ebp e %esp che gestiscono lo stack di cui parleremo più diffusamente subito dopo. Un registro molto importante è %eip che punta  all’indirizzo di memoria che contiene la prossima istruzione da eseguire (in gdb è $pc non so perché).

Lo stack è una parte fondamentale del sistema: è in pratica una area di memoria che contiene le variabili che una data routine deve gestire; infatti siccome i registri sono in numero limitato si ha bisogno di definire una area di memoria per gestire i dati. Lo stack permette di isolare le variabili locali proprie di una data routine definendo la base dello stack (puntata dal registro %ebp) e la cima dello stack (puntata dal registro %esp). Le istruzioni assembler per gestire lo stack sono push e pop, la prima inserisce nello stack il valore del registro indicato come argomento, il secondo invece fa l’opposto; la posizione nello stack è indicata da %esp che viene decrementato nel primo caso e incrementato nel secondo (nei sistemi x86 lo stack cresce verso il basso). In pratica lo stack è una coda LIFO (Last In First Out).

Facciamo girare il nostro programma e vediamo cosa succede in pratica

(gdb) r
Starting program: /sti/cazzi/boh 

Breakpoint 1, 0x080483cb in main ()
1: x/3i $pc
=> 0x80483cb <main+6>:    movl   $0x89,0x4(%esp)
 0x80483d3 <main+14>:    movl   $0x80484b0,(%esp)
 0x80483da <main+21>:    call   0x80483b4 <bau>

L’istruzione puntata dalla freccia muove nello stack il valore 137 mentre quella seguente mette la stringa “bastardo”

(gdb) x/s 0x80484b0
0x80484b0:     "bastardo"

Infine, l’ultima istruzione, chiama la funzione bau. Il perché di questa procedura consiste nel fatto che i parametri di una funzione devono essere passati nello stack in ordine inverso rispetto all’ordine nella definizione. Ultimo particolare da sapere è che l’istruzione call fa una push nello stack del registro %eip e salta all’indirizzo indicato come argomento.

Saltiamo alla funzione bau() eseguendo il comando si 3 volte così da ritrovarci in quello che viene chiamato prologo

0x080483b4 in bau ()
1: x/3i $pc
=> 0x80483b4 <bau>:    push   %ebp
 0x80483b5 <bau+1>:    mov    %esp,%ebp
 0x80483b7 <bau+3>:    mov    0x8(%ebp),%eax

Le prime due istruzioni sono chiamate in questo modo perché definiscono il frame per la funzione corrente, cioè il contesto in memoria dove collocare le variabili locali che saranno utilizzate da questa funzione; per farlo si imposta la base dello stack a coincidere con la cima dello stack. Tutto preceduto dal salvataggio del frame della precedente funzione.

In gdb è possibile ricavare questa info comodamente

(gdb) info frame
Stack level 0, frame at 0xbffff310:
 eip = 0x80483b7 in bau; saved eip 0x80483df
 called by frame at 0xbffff320
 Arglist at 0xbffff308, args:
 Locals at 0xbffff308, Previous frame's sp is 0xbffff310
 Saved registers:
 ebp at 0xbffff308, eip at 0xbffff30c

Quindi riassumendo, all’avvio di una nuova funzione nello stack saranno posizionate le seguenti variabili

secondo argomento
primo argomento
indirizzo di ritorno
vecchio ebp

una sopra l’altra. Sempre gdb ci aiuta

(gdb) x/4a $ebp
0xbffff308:    0xbffff318    0x80483df <main+26>    0x80484b0    0x89

Se analizziamo in toto la funzione bau, possiamo notare quello che si chiama epilogo nelle due ultime righe

(gdb) disassemble bau
Dump of assembler code for function bau:
 0x080483b4 <+0>:    push   %ebp
 0x080483b5 <+1>:    mov    %esp,%ebp
=> 0x080483b7 <+3>:    mov    0x8(%ebp),%eax
 0x080483ba <+6>:    movzbl (%eax),%eax
 0x080483bd <+9>:    movsbl %al,%eax
 0x080483c0 <+12>:    add    0xc(%ebp),%eax
 0x080483c3 <+15>:    pop    %ebp
 0x080483c4 <+16>:    ret   
End of assembler dump.

il cui scopo è ripristinare il frame precedente e riportare il flusso di esecuzione a dove era stata chiamata la funzione bau() recuperando dallo stack l’indirizzo di ritorno (ricordate cosa fa call? fa una push del registro %eip, ret lo recupera).

Bene, direte voi, ma chi se ne frega? vogliamo vedere la ciccia!!1!!!! Ok, state calmi, passiamo ad un altro programma tipo questo

int main(int argc, char* argv[]){
    char buffer[256];
    return strcpy(buffer, argv[1]);
}

Questo programma ha un difetto sostanziale, non controlla l’input dell’utente! abbiamo un buffer che può contenere 256 fucking char (grossi un byte) e ci copiamo dentro (senza fucking controllare) il primo argomento passato alla funzione. Quando non si controlla quello che si inserisce lato utente aspettatevi un problema, può essere un programma in C, in PHP o un controller di una view di una webapp.

Se proviamo a lanciare il programma passandogli 300 caratteri “A” cosa succede?

$ ./c `python -c 'print "A"*300'`
Errore di segmentazione (core dumped)

Oh, crasha! mio dio. Ma non finisce qui, se controlliamo con gdb il file core che ha creato scopriamo una cosa interessante

$ gdb -q ./c core
Reading symbols from /tmp/c...(no debugging symbols found)...done.
[New Thread 19714]

warning: Can't read pathname for load map: Errore di input/output.
Reading symbols from /lib/i386-linux-gnu/i686/cmov/libc.so.6...Reading symbols from /usr/lib/debug/lib/i386-linux-gnu/i686/cmov/libc-2.13.so...done.
done.
Loaded symbols for /lib/i386-linux-gnu/i686/cmov/libc.so.6
Reading symbols from /lib/ld-linux.so.2...(no debugging symbols found)...done.
Loaded symbols for /lib/ld-linux.so.2
Core was generated by `./c AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA'.
Program terminated with signal 11, Segmentation fault.
#0  0x41414141 in ?? ()

per capirci

(gdb) print $pc
$1 = (void (*)()) 0x41414141

Abbiamo sovrascritto il registro $pc, cioè (in teoria) abbiamo modificato il flusso del programma!!!Questo è successo semplicemente perché strcpy() è andata a copiare a partire dalla parte dello stack in cui era definita la variabile buffer andando a sbordare sopra il frame precedente e sovrascrivendo sia il vecchio %ebp che %eip. Infatti controllando i registri si conferma quanto detto

(gdb) info register
eax            0xbfce7c20    -1076986848
ecx            0x0    0
edx            0x12d    301
ebx            0xb76d3ff4    -1217576972
esp            0xbfce7d30    0xbfce7d30
ebp            0x41414141    0x41414141
esi            0x0    0
edi            0x0    0
eip            0x41414141    0x41414141
eflags         0x10246    [ PF ZF IF RF ]
cs             0x73    115
ss             0x7b    123
ds             0x7b    123
es             0x7b    123
fs             0x0    0
gs             0x33    51

Certo la strada è ancora lunga, ma in potenziale possiamo aprire una shell, ma questo è argomento di una prossima puntata.


Configurare Tor su un firefox > 3.x

Posted: agosto 4th, 2011 | Author: | Filed under: General | Tags: , , , | 2 Comments »

Siccome di questi tempi va di moda che i browsers si aggiornino e cambino numero di revisione come se piovesse, succede che Tor non mi parte su un firefox versione 5 (ma porcodio, prima per arrivare alla 3.6 sembrava che stesse cambiando il mondo e poi sono passati alla versione 4 e 5 di firefox praticamente nello stesso giorno).

Le istruzioni qua sotto le ho eseguite su una ubuntu: partiamo installando il software necessario

apt-get install tor polipo

scarichiamo il file di configurazione di polipo direttamente dal sito della torproject

# wget https://gitweb.torproject.org/torbrowser.git/blob_plain/HEAD:/build-scripts/config/polipo.conf -O /etc/polipo/config

ed installiamo l’estensione torbutton per firefox che funzioni: andiamo su questa pagina https://www.torproject.org/dist/torbutton/ e scarichiamo la versione 1.4.0 che al momento della scrittura di questo articolo è quella funzionante (dalla pagina delle “componenti aggiuntive” di firefix non lo trova). Comparirà un tasto

Controllare che funzioni effettivamente andando su https://check.torproject.org/. Fate i sovversivi.


Impostare certification authority per l’FTP di autistici

Posted: luglio 27th, 2011 | Author: | Filed under: Life, ssh | Comments Off on Impostare certification authority per l’FTP di autistici

Per motivi che non sto a spiegare dovevo entrare nel mio spazio webz, ma l’inganno sopraggiunge

$ lftp packz@ftp666.autistici.org
Password: 
lftp packz@ftp666.autistici.org:~> ls
ls: Errore fatale: Certificate verification: Not trusted
lftp packz@ftp5.autistici.org:~> exit

Non posso mica lasciare nell’incertezza la connessione, quindi scarico il certificato utile e lo piazzo dove il comando UNIX può trovarlo

$ wget -O ~/.ftp.pem http://ca.autistici.org/certs/ftp.pem

configurando opportunamente

$ cat ~/.lftprc
set ftp:ssl-force true
set ssl:ca-file ~/.ftp.pem

il tutto si risolve

$ lftp packz@ftp666.autistici.org
Password: 
lftp packz@ftp666.autistici.org:~> ls                                  
drwxrws---    2 236368   33           4096 Jun 01  2007 Image
drwxrws---   13 236368   33           4096 Aug 24  2010 html-packz
drwxr-s---    2 33       33           4096 Jun 18 04:26 logs
drwxr-s---    2 236368   33           4096 Jul 27 18:57 sessions
drwxr-s---    2 236368   33           4096 May 31 09:34 tmp
lftp packz@ftp666.autistici.org:/>

It’s a steal. From you.

Posted: luglio 22nd, 2011 | Author: | Filed under: General | Comments Off on It’s a steal. From you.

Riporto il testo di un hero allegato ad un torrent

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

  This archive contains 18,592 scientific publications totaling
33GiB, all from Philosophical Transactions of the Royal Society
and which should be  available to everyone at no cost, but most
have previously only been made available at high prices through
paywall gatekeepers like JSTOR.

Limited access to the  documents here is typically sold for $19
USD per article, though some of the older ones are available as
cheaply as $8. Purchasing access to this collection one article
at a time would cost hundreds of thousands of dollars.

Also included is the basic factual metadata allowing you to
locate works by title, author, or publication date, and a
checksum file to allow you to check for corruption.

ef8c02959e947d7f4e4699f399ade838431692d972661f145b782c2fa3ebcc6a sha256sum.txt

I've had these files for a long time, but I've been afraid that if I
published them I would be subject to unjust legal harassment by those who
profit from controlling access to these works.

I now feel that I've been making the wrong decision.

On July 19th 2011, Aaron Swartz was criminally charged by the US Attorney
General's office for, effectively, downloading too many academic papers
from JSTOR.

Academic publishing is an odd systemΓΓé¼ΓÇ¥the authors are not paid for their
writing, nor are the peer reviewers (they're just more unpaid academics),
and in some fields even the journal editors are unpaid. Sometimes the
authors must even pay the publishers.

And yet scientific publications are some of the most outrageously
expensive pieces of literature you can buy. In the past, the high access
fees supported the costly mechanical reproduction of niche paper journals,
but online distribution has mostly made this function obsolete.

As far as I can tell, the money paid for access today serves little
significant purpose except to perpetuate dead business models. The
"publish or perish" pressure in academia gives the authors an impossibly
weak negotiating position, and the existing system has enormous inertia.

Those with the most power to change the system--the long-tenured luminary
scholars whose works give legitimacy and prestige to the journals, rather
than the other way around--are the least impacted by its failures. They
are supported by institutions who invisibly provide access to all of the
resources they need. And as the journals depend on them, they may ask
for alterations to the standard contract without risking their career on
the loss of a publication offer. Many don't even realize the extent to
which academic work is inaccessible to the general public, nor do they
realize what sort of work is being done outside universities that would
benefit by it.

Large publishers are now able to purchase the political clout needed
to abuse the narrow commercial scope of copyright protection, extending
it to completely inapplicable areas: slavish reproductions of historic
documents and art, for example, and exploiting the labors of unpaid
scientists. They're even able to make the taxpayers pay for their
attacks on free society by pursuing criminal prosecution (copyright has
classically been a civil matter) and by burdening public institutions
with outrageous subscription fees.

Copyright is a legal fiction representing a narrow compromise: we give
up some of our natural right to exchange information in exchange for
creating an economic incentive to author, so that we may all enjoy more
works. When publishers abuse the system to prop up their existence,
when they misrepresent the extent of copyright coverage, when they use
threats of frivolous litigation to suppress the dissemination of publicly
owned works, they are stealing from everyone else.

Several years ago I came into possession, through rather boring and
lawful means, of a large collection of JSTOR documents.

These particular documents are the historic back archives of the
Philosophical Transactions of the Royal SocietyΓΓé¼ΓÇ¥a prestigious scientific
journal with a history extending back to the 1600s.

The portion of the collection included in this archive, ones published
prior to 1923 and therefore obviously in the public domain, total some
18,592 papers and 33 gigabytes of data.

The documents are part of the shared heritage of all mankind,
and are rightfully in the public domain, but they are not available
freely. Instead the articles are available at $19 each--for one month's
viewing, by one person, on one computer. It's a steal. From you.

When I received these documents I had grand plans of uploading them to
Wikipedia's sister site for reference works, WikisourceΓΓé¼ΓÇ¥ where they
could be tightly interlinked with Wikipedia, providing interesting
historical context to the encyclopedia articles. For example, Uranus
was discovered in 1781 by William Herschel; why not take a look at
the paper where he originally disclosed his discovery? (Or one of the
several follow on publications about its satellites, or the dozens of
other papers he authored?)

But I soon found the reality of the situation to be less than appealing:
publishing the documents freely was likely to bring frivolous litigation
from the publishers.

As in many other cases, I could expect them to claim that their slavish
reproductionΓΓé¼ΓÇ¥scanning the documentsΓΓé¼ΓÇ¥ created a new copyright
interest. Or that distributing the documents complete with the trivial
watermarks they added constituted unlawful copying of that mark. They
might even pursue strawman criminal charges claiming that whoever obtained
the files must have violated some kind of anti-hacking laws.

In my discreet inquiry, I was unable to find anyone willing to cover
the potentially unbounded legal costs I risked, even though the only
unlawful action here is the fraudulent misuse of copyright by JSTOR and
the Royal Society to withhold access from the public to that which is
legally and morally everyone's property.

In the meantime, and to great fanfare as part of their 350th anniversary,
the RSOL opened up "free" access to their historic archivesΓΓé¼ΓÇ¥but "free"
only meant "with many odious terms", and access was limited to about
100 articles.

All too often journals, galleries, and museums are becoming not
disseminators of knowledgeΓΓé¼ΓÇ¥as their lofty mission statements
suggestΓΓé¼ΓÇ¥but censors of knowledge, because censoring is the one thing
they do better than the Internet does. Stewardship and curation are
valuable functions, but their value is negative when there is only one
steward and one curator, whose judgment reigns supreme as the final word
on what everyone else sees and knows. If their recommendations have value
they can be heeded without the coercive abuse of copyright to silence
competition.

The liberal dissemination of knowledge is essential to scientific
inquiry. More than in any other area, the application of restrictive
copyright is inappropriate for academic works: there is no sticky question
of how to pay authors or reviewers, as the publishers are already not
paying them. And unlike 'mere' works of entertainment, liberal access
to scientific work impacts the well-being of all mankind. Our continued
survival may even depend on it.

If I can remove even one dollar of ill-gained income from a poisonous
industry which acts to suppress scientific and historic understanding,
then whatever personal cost I suffer will be justifiedΓΓé¼ΓÇ¥it will be one
less dollar spent in the war against knowledge. One less dollar spent
lobbying for laws that make downloading too many scientific papers
a crime.

I had considered releasing this collection anonymously, but others pointed
out that the obviously overzealous prosecutors of Aaron Swartz would
probably accuse him of it and add it to their growing list of ridiculous
charges. This didn't sit well with my conscience, and I generally believe
that anything worth doing is worth attaching your name to.

I'm interested in hearing about any enjoyable discoveries or even useful
applications which come of this archive.

- ----
Greg Maxwell - July 20th 2011
gmaxwell@gmail.com  Bitcoin: 14csFEJHk3SYbkBmajyJ3ktpsd2TmwDEBb

-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.11 (GNU/Linux)

iEYEARECAAYFAk4nlfwACgkQrIWTYrBBO/pK4QCfV/voN6IdZRU36Vy3xAedUMfz
rJcAoNF4/QTdxYscvF2nklJdMzXFDwtF
=YlVR
-----END PGP SIGNATURE-----

Sono tornato

Posted: giugno 29th, 2011 | Author: | Filed under: Life | Comments Off on Sono tornato

Nel frattempo che riorganizzo la mente e il codice, beccatevo questo articolo sull’hackmeeting.