diff options
author | johannst <johannes.stoelp@gmail.com> | 2021-04-28 23:08:45 +0200 |
---|---|---|
committer | johannst <johannes.stoelp@gmail.com> | 2021-04-28 23:08:45 +0200 |
commit | d367355eb4c3569d422034b69737d8dc7022e13e (patch) | |
tree | f9f6768228235f4712466d65edeb0b745d904833 /lib/src/syscalls.c | |
parent | cf97ecd5b52c2f7a8953fd1674742d46fd15418a (diff) | |
parent | fc137e7d0263a0fe908ca1a150e34a9c8b9902d4 (diff) | |
download | dynld-d367355eb4c3569d422034b69737d8dc7022e13e.tar.gz dynld-d367355eb4c3569d422034b69737d8dc7022e13e.zip |
Merge branch 'dev04'
Diffstat (limited to 'lib/src/syscalls.c')
-rw-r--r-- | lib/src/syscalls.c | 62 |
1 files changed, 62 insertions, 0 deletions
diff --git a/lib/src/syscalls.c b/lib/src/syscalls.c new file mode 100644 index 0000000..074fced --- /dev/null +++ b/lib/src/syscalls.c @@ -0,0 +1,62 @@ +// Copyright (c) 2021 Johannes Stoelp + +#include <asm/unistd.h> // __NR_* +#include <syscall.h> +#include <syscalls.h> + +// Storage for `dynld_errno`. +int dynld_errno; + +// Convert return value to errno/ret. +static long syscall_ret(unsigned long ret) { + if (ret > (unsigned long)-4096ul) { + dynld_errno = -ret; + return -1; + } + return ret; +} + +int open(const char* path, int flags) { + long ret = syscall2(__NR_open, path, flags); + return syscall_ret(ret); +} + +int close(int fd) { + long ret = syscall1(__NR_close, fd); + return syscall_ret(ret); +} + +int access(const char* path, int mode) { + long ret = syscall2(__NR_access, path, mode); + return syscall_ret(ret); +} + +ssize_t write(int fd, const void* buf, size_t count) { + long ret = syscall3(__NR_write, fd, buf, count); + return syscall_ret(ret); +} + +ssize_t read(int fd, void* buf, size_t count) { + long ret = syscall3(__NR_read, fd, buf, count); + return syscall_ret(ret); +} + +ssize_t pread(int fd, void* buf, size_t count, off_t offset) { + long ret = syscall4(__NR_read, fd, buf, count, offset); + return syscall_ret(ret); +} + +void* mmap(void* addr, size_t length, int prot, int flags, int fd, off_t offset) { + long ret = syscall6(__NR_mmap, addr, length, prot, flags, fd, offset); + return (void*)syscall_ret(ret); +} + +int munmap(void* addr, size_t length) { + long ret = syscall2(__NR_munmap, addr, length); + return syscall_ret(ret); +} + +void _exit(int status) { + syscall1(__NR_exit, status); + __builtin_unreachable(); +} |