House of Roman
Reading time: 5 minutes
tip
Aprenda e pratique Hacking AWS:
HackTricks Training AWS Red Team Expert (ARTE)
Aprenda e pratique Hacking GCP: 
HackTricks Training GCP Red Team Expert (GRTE)
Aprenda e pratique Hacking Azure: 
HackTricks Training Azure Red Team Expert (AzRTE)
Supporte o HackTricks
- Confira os planos de assinatura!
 - Junte-se ao 💬 grupo do Discord ou ao grupo do telegram ou siga-nos no Twitter 🐦 @hacktricks_live.
 - Compartilhe truques de hacking enviando PRs para o HackTricks e HackTricks Cloud repositórios do github.
 
Informações Básicas
Esta foi uma técnica muito interessante que permitiu RCE sem leaks através de fastbins falsos, o ataque unsorted_bin e sobrescritas relativas. No entanto, foi corrigido.
Código
- Você pode encontrar um exemplo em https://github.com/shellphish/how2heap/blob/master/glibc_2.23/house_of_roman.c
 
Objetivo
- RCE abusando de ponteiros relativos
 
Requisitos
- Editar ponteiros de fastbin e unsorted bin
 - 12 bits de aleatoriedade devem ser forçados por brute force (0,02% de chance) de funcionar
 
Etapas do Ataque
Parte 1: Fastbin Chunk aponta para __malloc_hook
Crie vários chunks:
fastbin_victim(0x60, offset 0): Chunk UAF que será editado para apontar para o valor da LibC.chunk2(0x80, offset 0x70): Para um bom alinhamentomain_arena_use(0x80, offset 0x100)relative_offset_heap(0x60, offset 0x190): offset relativo no chunk 'main_arena_use'
Então free(main_arena_use) que colocará este chunk na lista não ordenada e obterá um ponteiro para main_arena + 0x68 tanto nos ponteiros fd quanto bk.
Agora é alocado um novo chunk fake_libc_chunk(0x60) porque conterá os ponteiros para main_arena + 0x68 em fd e bk.
Então relative_offset_heap e fastbin_victim são liberados.
/*
Current heap layout:
0x0:   fastbin_victim       - size 0x70
0x70:  alignment_filler     - size 0x90
0x100: fake_libc_chunk      - size 0x70 (contains a fd ptr to main_arena + 0x68)
0x170: leftover_main        - size 0x20
0x190: relative_offset_heap - size 0x70
bin layout:
fastbin:  fastbin_victim -> relative_offset_heap
unsorted: leftover_main
*/
fastbin_victimtem umfdapontando pararelative_offset_heaprelative_offset_heapé um offset de distância defake_libc_chunk, que contém um ponteiro paramain_arena + 0x68- Apenas mudando o último byte de 
fastbin_victim.fdé possível fazerfastbin_victim pointsparamain_arena + 0x68 
Para as ações anteriores, o atacante precisa ser capaz de modificar o ponteiro fd de fastbin_victim.
Então, main_arena + 0x68 não é tão interessante, então vamos modificá-lo para que o ponteiro aponte para __malloc_hook.
Note que __memalign_hook geralmente começa com 0x7f e zeros antes dele, então é possível falsificá-lo como um valor no fast bin 0x70. Como os últimos 4 bits do endereço são aleatórios, há 2^4=16 possibilidades para o valor acabar apontando onde estamos interessados. Então, um ataque BF é realizado aqui para que o chunk termine como: 0x70: fastbin_victim -> fake_libc_chunk -> (__malloc_hook - 0x23).
(Para mais informações sobre os outros bytes, verifique a explicação no how2heap exemplo). Se o BF não funcionar, o programa simplesmente trava (então comece de novo até funcionar).
Então, 2 mallocs são realizados para remover os 2 chunks iniciais do fast bin e um terceiro é alocado para obter um chunk em __malloc_hook:
malloc(0x60);
malloc(0x60);
uint8_t* malloc_hook_chunk = malloc(0x60);
Parte 2: Ataque Unsorted_bin
Para mais informações, você pode verificar:
Mas basicamente, isso permite escrever main_arena + 0x68 em qualquer local especificado em chunk->bk. E para o ataque, escolhemos __malloc_hook. Então, após sobrescrevê-lo, usaremos uma sobrescrita relativa para apontar para um one_gadget.
Para isso, começamos obtendo um chunk e colocando-o no unsorted bin:
uint8_t* unsorted_bin_ptr = malloc(0x80);
malloc(0x30); // Don't want to consolidate
puts("Put chunk into unsorted_bin\n");
// Free the chunk to create the UAF
free(unsorted_bin_ptr);
Use um UAF neste chunk para apontar unsorted_bin_ptr->bk para o endereço de __malloc_hook (nós forçamos isso anteriormente).
caution
Note que este ataque corrompe o bin não ordenado (portanto, pequeno e grande também). Então, só podemos usar alocações do fast bin agora (um programa mais complexo pode fazer outras alocações e travar), e para acionar isso devemos alocar o mesmo tamanho ou o programa travará.
Então, para acionar a escrita de main_arena + 0x68 em __malloc_hook, após definir __malloc_hook em unsorted_bin_ptr->bk, só precisamos fazer: malloc(0x80)
Passo 3: Definir __malloc_hook para system
No primeiro passo, terminamos controlando um chunk contendo __malloc_hook (na variável malloc_hook_chunk) e no segundo passo conseguimos escrever main_arena + 0x68 aqui.
Agora, abusamos de uma sobrescrita parcial em malloc_hook_chunk para usar o endereço libc que escrevemos lá (main_arena + 0x68) para apontar um endereço one_gadget.
Aqui é onde é necessário forçar 12 bits de aleatoriedade (mais informações no how2heap exemplo).
Finalmente, uma vez que o endereço correto é sobrescrito, chame malloc e acione o one_gadget.
Referências
- https://github.com/shellphish/how2heap
 - https://github.com/shellphish/how2heap/blob/master/glibc_2.23/house_of_roman.c
 - https://ctf-wiki.mahaloz.re/pwn/linux/glibc-heap/house_of_roman/
 
tip
Aprenda e pratique Hacking AWS:
HackTricks Training AWS Red Team Expert (ARTE)
Aprenda e pratique Hacking GCP: 
HackTricks Training GCP Red Team Expert (GRTE)
Aprenda e pratique Hacking Azure: 
HackTricks Training Azure Red Team Expert (AzRTE)
Supporte o HackTricks
- Confira os planos de assinatura!
 - Junte-se ao 💬 grupo do Discord ou ao grupo do telegram ou siga-nos no Twitter 🐦 @hacktricks_live.
 - Compartilhe truques de hacking enviando PRs para o HackTricks e HackTricks Cloud repositórios do github.
 
HackTricks