Fix high interrupt ISRs
[viridis.git] / kernel / platforms / efi / efi_call.asm
1 .code64
2
3 // EFI: RCX RDX R8 R9 RSP+32 ...
4 // ELF: RDI RSI RDX RCX R8 R9 RSP+8 ...
5 //
6 // We're burning the first two arguments with a call address and a 0 so we can
7 // use RSI, so it actually looks like
8 //
9 // EFI: RCX RDX R8 R9 RSP+32 ...
10 // ELF: RDX RCX R8 R9 RSP+8 ...
11 //
12 // Then we pop rsi to keep it off the stack so then it's
13 //
14 // EFI: RCX RDX R8 R9 RSP+32 ...
15 // ELF: RDX RCX R8 R9 RSP+0 ...
16 //
17 // So all we need to do is swap RDX and RCX, and then sub 32 from the stack
18 // to perfectly line up our calling conventions.
19
20 .global efi_call
21
22 efi_call:           // Stack is 16 byte aligned at call, but
23     pop %rsi        // call pushed the return address, pop it into RSI
24                     // so it's 16 byte aligned again for the EFI ABI
25     push %rcx
26     mov %rdx, %rcx  // RSI is guaranteed to be preserved by the EFI ABI
27     pop %rdx        // and the standard ABI doesn't require it to be preserved
28                     // by the callee, so we don't violate either.
29
30     sub $32, %rsp
31     call *%rdi
32     add $32, %rsp
33
34     push %rsi
35     ret