Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>At first I would like to provide some definition of system call. System call is a process of synchronous explicit requesting of the particular kernel service from the user space application. Synchronous mean that the act of system call is predetermined by executing instructions sequence. Interrupts is an example of asynchronous system service request, because they arrive to the kernel absolutely independently from the code executing on processor. Exceptions in the contrast to system calls are synchronous but implicit requests for the kernel services. </p> <p>System call consist from four stages:</p> <ol> <li>Passing control to the particular point in kernel with switching processor from user mode to kernel mode and returning it back with switching processor back to the user mode.</li> <li>Specifying of id of the requested kernel service.</li> <li>Passing of parameters for the requested service.</li> <li>Capturing the result of the service.</li> </ol> <p>In general, all these actions can be implemented as a part of one big library function which makes a number of auxiliary actions before and/or after actual system call. In this case we can say that the system call is embedded in this function, but the function in general isn't a system call. In another case we can have a tiny function which makes only this four steps and nothing more. In this case we can say that this function is a system call. Actually you can implement the system call itself by manual implementation of all four stages mentioned above. Note, that in this case you will be forced to use Assembler, because all this steps are entirely architecture-dependent.</p> <p>For example, Linux/i386 environment has next system call convention:</p> <ol> <li>Passing control from user mode to kernel mode can be done either by software interrupt with number 0x80 (assembly instruction INT 0x80) or by SYSCALL instruction (AMD) or by SYSENTER instruction (Intel)</li> <li>Id of the requested system service is specified by the integer value stored in EAX register during entering in the kernel mode. Kernel service id must be defined in the form _<em>NR</em>. You can find all system service ids in Linux source tree on path <code>include\uapi\asm-generic\unistd.h</code>.</li> <li>Up to 6 parameters can be passed through registers EBX(1) , ECX(2), EDX(3), ESI(4), EDI(5), EBP(6). The number in brackets is a sequential number of the parameter. </li> <li>Kernel returns the status of the service performed in the EAX register. This value usually used by glibc to setup errno variable. </li> </ol> <p>In modern versions of Linux there is no any _syscall macro (as far I know). Instead, glibc library, that is a main interface library of the Linux kernel, provides a special macro - <code>INTERNAL_SYSCALL</code>, which expands into a small piece of code populated by inline assembler instructions. This piece of code is targeted to a particular hardware platform and implements all stages of system call, and due to this, this macro represents a system call itself. There is also another macro - <code>INLINE_SYSCALL</code>. The last one macro provides glibc-like error handling, in accordance to which on failed system call -1 will be returned and the error number will be stored in <code>errno</code> variable. Both macros are defined in <code>sysdep.h</code> of glibc package.</p> <p>You can invoke a system call in the next way:</p> <pre><code>#include &lt;sysdep.h&gt; #define __NR_&lt;name&gt; &lt;id&gt; int my_syscall(void) { return INLINE_SYSCALL(&lt;name&gt;, &lt;argc&gt;, &lt;argv&gt;); } </code></pre> <p>where <code>&lt;name&gt;</code> must be replaced by the syscall name string, <code>&lt;id&gt;</code> - by the wanted system service number id, <code>&lt;argc&gt;</code> - by the actual number of parameters (from 0 to 6) and <code>&lt;argv&gt;</code> - by actual parameters separated by commas (and started by comma if parameters are present).</p> <p>For example:</p> <pre><code>#include &lt;sysdep.h&gt; #define __NR_exit 1 int _exit(int status) { return INLINE_SYSCALL(exit, 1, status); // takes 1 parameter "status" } </code></pre> <p>or another example:</p> <pre><code>#include &lt;sysdep.h&gt; #define __NR_fork 2 int _fork(void) { return INLINE_SYSCALL(fork, 0); // takes no parameters } </code></pre>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload