Interfaces to C
The system call interfaces of modern operating systems are presented as an
API of C-language prototypes, regardless of the programmer's choice of
application language (C++, Java, Visual-Basic). This is a clear improvement
over earlier interfaces in assembly languages.
The technique used in most modern operating systems is to provide an
identically-named interface function in a standard C library or system's
library (for example
/lib/libc.so.6 on Linux and
/usr/lib/system/libsystem_kernel.dylib on macOS ).
An application program, written in any programming language, may invoke the
system calls provided that the language's run-time mechanisms support the
operating system's standard calling convention.
In the case of a programming language employing a different calling
convention, or requiring strong controls over programs (e.g. running them in
a sandbox environment, as does Java), direct access to system calls may be
limited.
As the context switch between application process and the kernel is
relatively expensive, most error checking of arguments is performed within
the library, avoiding a call of the kernel with incorrect parameters:
#include <syscall.h>
#include <unistd.h>
.....
int write(int fd, void *buf, size_t len)
{
if (any_errors_in_arguments) {
errno = EINVAL;
return (-1);
}
return syscall(SYS_write, fd, buf, len);
}
|
But also, system calls need to be ''paranoid'' to protect the kernel from
memory access violations!
They will check their arguments, too.
CITS2002 Systems Programming, Lecture 10, p2, 22nd August 2023.
|