O Google tem o compromisso de promover a igualdade racial para as comunidades negras. Saiba como.
Esta página foi traduzida pela API Cloud Translation.
Switch to English

Memória apenas de execução (XOM) para binários AArch64

As seções de código executáveis ​​para binários do sistema AArch64 são, por padrão, marcadas como somente para execução (não legível) como uma atenuação de proteção contra ataques de reutilização de código just-in-time. O código que mistura dados e código e o código que inspeciona propositadamente essas seções (sem primeiro remapear os segmentos de memória como legíveis) não funcionam mais. Aplicativos com um SDK de destino de 10 (API de nível 29 ou superior) são afetados se o aplicativo tentar ler seções de código de bibliotecas de sistema habilitadas para memória somente para execução (XOM) sem primeiro marcar a seção como legível.

Para tirar o máximo proveito dessa atenuação, é necessário suporte de hardware e kernel. Sem esse suporte, a mitigação pode ser apenas parcialmente aplicada. O kernel comum do Android 4.9 contém os patches apropriados para fornecer suporte completo para isso em dispositivos ARMv8.2.

Implementação

Os binários AArch64 gerados pelo compilador assumem que o código e os dados não estão misturados. A ativação desse recurso não afeta negativamente o desempenho do dispositivo.

Para código que precisa realizar introspecção de memória intencional em seus segmentos executáveis, é aconselhável chamar mprotect nos segmentos de código que requerem inspeção para permitir que sejam legíveis e, em seguida, remover a legibilidade quando a inspeção for concluída.
Essa implementação faz com que as leituras nos segmentos de memória marcados como somente para execução resultem em uma falha de segmentação ( SEGFAULT ). Isso pode ocorrer como resultado de um bug, vulnerabilidade, dados misturados com código (literal pooling) ou introspecção intencional de memória.

Suporte e impacto do dispositivo

Dispositivos com hardware anterior ou kernels anteriores (inferiores a 4.9) sem os patches necessários podem não oferecer suporte completo ou se beneficiar deste recurso. Dispositivos sem suporte de kernel podem não forçar acessos de usuário de memória somente de execução, entretanto o código de kernel que verifica explicitamente se uma página é legível ainda pode impor esta propriedade, como process_vm_readv() .

O sinalizador do kernel CONFIG_ARM64_UAO deve ser definido no kernel para garantir que o kernel respeite as páginas de usuário marcadas como somente para execução. Dispositivos ARMv8 anteriores, ou dispositivos ARMv8.2 com User Access Override (UAO) desabilitado, podem não se beneficiar totalmente com isso e ainda podem ser capazes de ler páginas somente para execução usando syscalls.

Refatorando código existente

O código que foi transferido de AArch32 pode conter dados e código misturados, causando o surgimento de problemas. Em muitos casos, corrigir esses problemas é tão simples quanto mover as constantes para uma seção .data no arquivo de montagem.

O assembly escrito à mão pode precisar ser refatorado para separar constantes agrupadas localmente.

Exemplos:

Os binários gerados pelo compilador Clang não devem ter problemas com os dados sendo misturados no código. Se o código gerado da coleção do compilador GNU (GCC) for incluído (de uma biblioteca estática), inspecione o binário de saída para garantir que as constantes não foram agrupadas nas seções do código.

Se a introspecção do código for necessária nas seções do código executável, primeiro chame mprotect para marcar o código como legível. Depois que a operação for concluída, chame mprotect novamente para marcá-lo como ilegível.

Possibilitando

Somente execução é habilitado por padrão para todos os binários de 64 bits no sistema de compilação.

Desativando

Você pode desabilitar apenas a execução no nível do módulo, por uma árvore de subdiretório inteira ou globalmente para uma compilação inteira.

XOM pode ser desativado para os módulos individuais que não podem ser reformulado, ou necessidade de ler o seu código executável, definindo os LOCAL_XOM e xom variáveis para false .

// Android.mk
LOCAL_XOM := false

// Android.bp
cc_binary { // or other module types
   ...
   xom: false,
}

Se a memória somente de execução estiver desabilitada em uma biblioteca estática, o sistema de construção aplicará isso a todos os módulos dependentes dessa biblioteca estática. Você pode sobrescrever isso usando xom: true, ,.

Para desabilitar a memória somente de execução em um subdiretório específico (por exemplo, foo / bar /), passe o valor para XOM_EXCLUDE_PATHS .

make -j XOM_EXCLUDE_PATHS=foo/bar

Como alternativa, você pode definir a variável PRODUCT_XOM_EXCLUDE_PATHS na configuração do produto.

Você pode desabilitar binários somente de execução globalmente, passando ENABLE_XOM=false para seu comando make .

make -j ENABLE_XOM=false

Validação

Não há CTS ou testes de verificação disponíveis para memória somente de execução. Você pode verificar manualmente os binários usando readelf e verificando os sinalizadores de segmento.