• Pavel Tatashin's avatar
    x86/pti/efi: broken conversion from efi to kernel page table · db297fe4
    Pavel Tatashin authored
    BugLink: http://bugs.launchpad.net/bugs/1745266
    
    In entry_64.S we have code like this:
    
        /* Unconditionally use kernel CR3 for do_nmi() */
        /* %rax is saved above, so OK to clobber here */
        ALTERNATIVE "jmp 2f", "movq %cr3, %rax", X86_FEATURE_KAISER
        /* If PCID enabled, NOFLUSH now and NOFLUSH on return */
        ALTERNATIVE "", "bts $63, %rax", X86_FEATURE_PCID
        pushq   %rax
        /* mask off "user" bit of pgd address and 12 PCID bits: */
        andq    $(~(X86_CR3_PCID_ASID_MASK | KAISER_SHADOW_PGD_OFFSET)), %rax
        movq    %rax, %cr3
    2:
    
        /* paranoidentry do_nmi, 0; without TRACE_IRQS_OFF */
        call    do_nmi
    
    With this instruction:
        andq    $(~(X86_CR3_PCID_ASID_MASK | KAISER_SHADOW_PGD_OFFSET)), %rax
    
    We unconditionally switch from whatever our CR3 was to kernel page table.
    But, in arch/x86/platform/efi/efi_64.c We temporarily set a different page
    table, that does not have the kernel page table with 0x1000 offset from it.
    
    Look in efi_thunk() and efi_thunk_set_virtual_address_map().
    
    So, while CR3 points to the other page table, we get an NMI interrupt,
    and clear 0x1000 from CR3, resulting in a bogus CR3 if the 0x1000 bit was
    set.
    
    The efi page table comes from realmode/rm/trampoline_64.S:
    
    arch/x86/realmode/rm/trampoline_64.S
    
    141 .bss
    142 .balign PAGE_SIZE
    143 GLOBAL(trampoline_pgd) .space PAGE_SIZE
    
    Notice: alignment is PAGE_SIZE, so after applying KAISER_SHADOW_PGD_OFFSET
    which equal to PAGE_SIZE, we can get a different page table.
    
    But, even if we fix alignment, here the trampoline binary is later copied
    into dynamically allocated memory in reserve_real_mode(), so we need to
    fix that place as well.
    
    Fixes: 8a43ddfb ("KAISER: Kernel Address Isolation")
    Signed-off-by: default avatarPavel Tatashin <pasha.tatashin@oracle.com>
    Reviewed-by: default avatarSteven Sistare <steven.sistare@oracle.com>
    Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
    Signed-off-by: default avatarKhalid Elmously <khalid.elmously@canonical.com>
    Signed-off-by: default avatarStefan Bader <stefan.bader@canonical.com>
    db297fe4
init.c 3.35 KB