Comment by wahern
19 days ago
All true, but note that BSD introduced, and both Linux/glibc and Linux/musl support, a syscall(2) wrapper routine that takes a syscall number, a list of arguments (usually as long's), and performs the syscall magic. The syscall numbers are defined as macros beginning with SYS_. The Linux kernel headers export syscall numbers with macros using the prefix __NR_, but to match the BSD interface Linux libc headers usually translate or otherwise define them using a SYS_ prefix. Using the macros is much better because the numbers often vary by architecture for the same syscall.
Except with BSDs you are on your own if you go down that route, because there are no stability guarantees.
It is more of an implementation detail for the rest of the C APIs than anything else.
At least FreeBSD's syscall ABI is guaranteed to be stable, one can run ancient binaries on a modern kernel. I believe the same is not true of OpenBSD and maybe NetBSD however.
Indeed. Another reason to use the system's macros rather than hardcoding integer literals--the numbers can change between releases. Though that doesn't guarantee the syscall works the same way between releases wrt parameters and return value semantics, if it still exists at all. And I believe OpenBSD removed the syscall wrapper altogether after implementing the pinsyscalls feature.
Do you need a guarantee or is enough that it's painful enough for the BSD maintainers when they remove syscalls that they rarely do it? It's even worse if they renumber them so that really doesn't happen outside of syscalls that were only briefly available in a development branch.
Varies a bit by flavor: OpenBSD values security more than stability, so they are willing to break old binaries more often; FreeBSD does require compat modules/etc for some things, but those are available for a long time and sometimes something slips through.
If they break old syscalls, it breaks your code that skips libc, but it also breaks running an old userland with a new kernel and that needs to work for upgrade scenarios. It also breaks binaries that were statically linked with an older libc. When a new kernel breaks old binaries, people stop upgrading the kernel and that's not what maintainers want.