| Both sides previous revisionPrevious revisionNext revision | Previous revision |
| en:multiasm:papc:chapter_6_8 [2026/02/27 01:48] – [Callig Windows system functions] jtokarz | en:multiasm:papc:chapter_6_8 [2026/05/27 10:04] (current) – [Syscall mechanism] ktokarz |
|---|
| </code> | </code> |
| |
| The Microsoft Windows x64 calling convention requires that even when the parameters are passed through registers, a 32-byte space for them should be reserved on the stack. It is referred to as a shadow space or home space. The shadow space size can be increased to store local variables of the procedure. Why does the x64 calling convention require the shadow space to be explained in the Microsoft blog article((https://devblogs.microsoft.com/oldnewthing/20160623-00/?p=93735)).\\ | The Microsoft Windows x64 calling convention requires that, even when parameters are passed in registers, a 32-byte space for them be reserved on the stack. It is referred to as a shadow space or home space. Reservation of a shadow space for arguments is the caller's responsibility. The shadow space size can be increased to store local variables of the procedure. Why does the x64 calling convention require the shadow space to be explained in the Microsoft blog article((https://devblogs.microsoft.com/oldnewthing/20160623-00/?p=93735)).\\ |
| Some registers are considered non-volatile. It means that they must be saved and restored by a function that uses them. They are RBX, RBP, RDI, RSI, RSP, R12, R13, R14, R15, and XMM6-XMM15.\\ | Some registers are considered non-volatile. It means that they must be saved and restored by a function that uses them. They are RBX, RBP, RDI, RSI, RSP, R12, R13, R14, R15, and XMM6-XMM15.\\ |
| |
| |
| ===== Callig Linux system functions ===== | ===== Callig Linux system functions ===== |
| The Linux operating system still supports the traditional calling of system functions using software interrupts. It is based on the **int 0x80** interrupt, which recognises the number of the function in the EAX register and up to six arguments in EBX, ECX, EDX, ESI, EDI, and EBP. | The Linux-based operating systems still support the traditional calling of system functions using software interrupts. It is based on the **int 0x80** interrupt, which recognises the number of the function in the EAX register and up to six arguments in EBX, ECX, EDX, ESI, EDI, and EBP. |
| The example of the Hello World program in Linux interrupt-based system call is shown in the following code. | The example of the Hello World program in Linux interrupt-based system call is shown in the following code. |
| |
| |
| ===== Syscall mechanism ===== | ===== Syscall mechanism ===== |
| Modern processors have a new instruction especially designed for calling system functions. | Modern processors have a new instruction especially designed for calling system functions. They are **syscall**, originally introduced by AMD and used in 64-bit mode, and **sysenter**, proposed by Intel for 32-bit processors. They enable transition from user mode to kernel mode and call system functions. |
| The **syscall** instruction doesn't use the interrupt mechanism, nor the stack for storing the returning address. It uses registers only to provide the address of the function, store the return address and flags register, and load the instruction pointer. The RIP is stored in RCX, and RFLAGS is stored in R11. The RIP is loaded with the content of the special register IA32_LSTAR MSR, which is an element of Architectural Model-Specific Registers, implemented starting from certain models of 32-bit processors. This makes the **syscall** instruction execution significantly faster than other mechanisms. | The **syscall** instruction doesn't use the interrupt mechanism, nor the stack for storing the returning address. It uses registers only to provide the address of the function, store the return address and flags register, and load the instruction pointer. The RIP is stored in RCX, and RFLAGS is stored in R11. The RIP is loaded with the content of the special register IA32_LSTAR MSR, which is an element of Architectural Model-Specific Registers, implemented starting from certain models of 32-bit processors. This makes the **syscall** instruction execution significantly faster than other mechanisms. |
| |
| The **syscall** instruction is supported in both Windows and Linux operating systems. It replaces Linux **int 80h**, and is the preferred mechanism for system calls in the 64-bit version of this system. The Linux system sets this register, and the programmer selects the function using the RAX register, as in the previous model of system calls. | The **syscall** instruction is supported in both Windows and Linux-based operating systems. It replaces Linux **int 80h**, and is the preferred mechanism for system calls in the 64-bit version of this system. Linux sets this register, and the programmer selects the function using the RAX register, as in the previous system-call model. |
| |
| <code asm> | <code asm> |
| </code> | </code> |
| |
| In Windows, low-level system functions are gathered in the ntdll.dll library. While using a high-level Windows API function, it results in calling a corresponding syscall. Although it is possible to call the low-level system function with syscall, API calls are preferred for user software. | In Windows, low-level system functions are gathered in libraries, including the ntdll.dll library. While using a high-level Windows API function, it results in calling a corresponding syscall. Although it is possible to call the low-level system function with syscall, API calls are preferred for user software. |