For the English version of this alert, click here.
Allele Security Alert
ASA-2019-00083
Identificador(es)
ASA-2019-00083, A-120025196, CVE-2019-1999
Título
Binder use-after-free do VMA via race condition entre reclaim e munmap
Fabricante(s)
The Linux foundation
Google
Produto(s)
Linux
Android
Versão(ões) afetada(s)
Android Security Patch Level anteriores a February 2019
Versão(ões) corrigida(s)
Android Security Patch Level February 2019
Prova de conceito
Sim
Descrição
Existe um race condition entre o caminho direto de reclaim (entrar no Binder através de binder_shrinker) e a chamada de sistema munmap() (entrar no Binder através do handler ->close de binder_vm_ops).
Detalhes técnicos
Vindo da chamada de sistema munmap():
binder_vma_close() -> binder_alloc_vma_close() -> binder_alloc_set_vma() sets alloc->vma para NULL sem obter nenhum locks extra; binder_vma_close() é chamado de remove_vma() <- remove_vma_list() <- __do_munmap() <- __vm_munmap() <- sys_munmap() com somente o mmap_sem obtido para escrita.
Vindo através do caminho direto de reclaim:
binder_alloc_free_page() não obtém mmap_sem na entrada. Contém o seguinte código:
enum lru_status binder_alloc_free_page(struct list_head *item, struct list_lru_one *lru, spinlock_t *lock, void *cb_arg) { [...] alloc = page->alloc; if (!mutex_trylock(&alloc->mutex)) goto err_get_alloc_mutex_failed; if (!page->page_ptr) goto err_page_already_freed; index = page - alloc->pages; page_addr = (uintptr_t)alloc->buffer + index * PAGE_SIZE; // Leitura de ponteiro não proetgida! `vma` pode ser liberada imediatamente vma = binder_alloc_get_vma(alloc); if (vma) { if (!mmget_not_zero(alloc->vma_vm_mm)) goto err_mmget; mm = alloc->vma_vm_mm; if (!down_write_trylock(&mm->mmap_sem)) goto err_down_write_mmap_sem_failed; // mmap_sem é obtido neste pronto, mas o ponteiro vma foi lido // antes e pode estar dangling } list_lru_isolate(lru, item); spin_unlock(lock); if (vma) { trace_binder_unmap_user_start(alloc, index); // Ponteiro 'vma' dangling passado para zap_page_range zap_page_range(vma, page_addr + alloc->user_buffer_offset, PAGE_SIZE); trace_binder_unmap_user_end(alloc, index); up_write(&mm->mmap_sem); mmput(mm); }
Créditos
Jann Horn (Google Project Zero)
Referência(s)
1721 – Android: binder use-after-free of VMA via race between reclaim and munmap – project-zero – Monorail
https://bugs.chromium.org/p/project-zero/issues/detail?id=1721
Android Security Bulletin — February 2019
https://source.android.com/security/bulletin/2019-02-01.html
CVE-2019-1999
https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-1999
CVE-2019-1999
https://nvd.nist.gov/vuln/detail/CVE-2019-1999
Se encontrou algum erro neste alerta ou deseja uma análise compreensiva, entre em contato.
Última modificação: 19 fevereiro 2019