summaryrefslogtreecommitdiff
path: root/lib/libc
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libc')
-rw-r--r--lib/libc/Kbuild4
-rw-r--r--lib/libc/devctl/posix_devctl.c6
-rw-r--r--lib/libc/errno/errno.c8
-rw-r--r--lib/libc/include/libc.h25
-rw-r--r--lib/libc/include/syscall.h59
-rw-r--r--lib/libc/internal/Kbuild4
-rw-r--r--lib/libc/internal/arch/Kbuild (renamed from lib/libc/arch/Kbuild)0
-rw-r--r--lib/libc/internal/arch/x86_64/Kbuild (renamed from lib/libc/arch/x86_64/Kbuild)0
-rw-r--r--lib/libc/internal/arch/x86_64/_start.c (renamed from lib/libc/arch/x86_64/_start.c)0
-rw-r--r--lib/libc/internal/arch/x86_64/fenv.s (renamed from lib/libc/arch/x86_64/fenv.s)0
-rw-r--r--lib/libc/internal/arch/x86_64/longjmp.c (renamed from lib/libc/arch/x86_64/longjmp.c)0
-rw-r--r--lib/libc/internal/arch/x86_64/setjmp.c (renamed from lib/libc/arch/x86_64/setjmp.c)0
-rw-r--r--lib/libc/internal/arch/x86_64/sigsetjmp.c (renamed from lib/libc/arch/x86_64/sigsetjmp.c)0
-rw-r--r--lib/libc/internal/deinit/tls.c13
-rw-r--r--lib/libc/internal/include/__aio.h (renamed from lib/libc/include/__aio.h)0
-rw-r--r--lib/libc/internal/include/__dirent.h (renamed from lib/libc/include/__dirent.h)0
-rw-r--r--lib/libc/internal/include/__select.h (renamed from lib/libc/include/__select.h)0
-rw-r--r--lib/libc/internal/include/__signal.h (renamed from lib/libc/include/__signal.h)0
-rw-r--r--lib/libc/internal/include/__statvfs.h (renamed from lib/libc/include/__statvfs.h)0
-rw-r--r--lib/libc/internal/include/__stdio.h (renamed from lib/libc/include/__stdio.h)0
-rw-r--r--lib/libc/internal/include/__thread.h (renamed from lib/libc/include/__thread.h)1
-rw-r--r--lib/libc/internal/include/atomic.h (renamed from lib/libc/include/atomic.h)0
-rw-r--r--lib/libc/internal/include/byteswap.h (renamed from lib/libc/include/byteswap.h)0
-rw-r--r--lib/libc/internal/include/internal/io_uring.h (renamed from lib/libc/include/internal/io_uring.h)0
-rw-r--r--lib/libc/internal/include/io_uring.h (renamed from lib/libc/include/io_uring.h)0
-rw-r--r--lib/libc/internal/include/libc.h48
-rw-r--r--lib/libc/internal/include/libc/dirent.h (renamed from lib/libc/include/libc/dirent.h)0
-rw-r--r--lib/libc/internal/include/malloc.h (renamed from lib/libc/include/malloc.h)0
-rw-r--r--lib/libc/internal/include/syscall.h44
-rw-r--r--lib/libc/internal/init/Kbuild1
-rw-r--r--lib/libc/internal/init/init.c6
-rw-r--r--lib/libc/internal/init/tls.c76
-rw-r--r--lib/libc/internal/panic.c29
-rw-r--r--lib/libc/internal/syscall.c12
-rw-r--r--lib/libc/mman/mmap.c2
-rw-r--r--lib/libc/mqueue/mq_notify.c4
-rw-r--r--lib/libc/mqueue/mq_unlink.c2
-rw-r--r--lib/libc/sys/getauxval.c2
-rw-r--r--lib/libc/thread/thrd_current.c9
39 files changed, 246 insertions, 109 deletions
diff --git a/lib/libc/Kbuild b/lib/libc/Kbuild
index 76e05807..8a52fdb3 100644
--- a/lib/libc/Kbuild
+++ b/lib/libc/Kbuild
@@ -1,10 +1,9 @@
lib-y := libc.a
install-y := lib/libc.a
-cflags-y += -I $(src)/include
+cflags-y += -I $(src)/internal/include
obj-y += aio/
-obj-y += arch/
obj-y += arpa/
obj-y += assert/
obj-y += ctype/
@@ -49,4 +48,3 @@ obj-y += utsname/
obj-y += wait/
obj-y += wchar/
obj-y += wctype/
-
diff --git a/lib/libc/devctl/posix_devctl.c b/lib/libc/devctl/posix_devctl.c
index 59497833..01af3111 100644
--- a/lib/libc/devctl/posix_devctl.c
+++ b/lib/libc/devctl/posix_devctl.c
@@ -1,13 +1,13 @@
#include <devctl.h>
+#include <errno.h>
#include <sys/cdefs.h>
#include <syscall.h>
int posix_devctl(int fildes, int dcmd, void *restrict dev_data_ptr, size_t __unused nbyte, int *restrict dev_info_ptr)
{
- int r;
+ int r = syscall(ioctl, fildes, dcmd, dev_data_ptr);
- r = syscall(ioctl, fildes, dcmd, dev_data_ptr);
- if (r < 0)
+ if (__predict_false(r < 0))
return errno;
*dev_info_ptr = r;
diff --git a/lib/libc/errno/errno.c b/lib/libc/errno/errno.c
index 09b22f4d..fc7c99bb 100644
--- a/lib/libc/errno/errno.c
+++ b/lib/libc/errno/errno.c
@@ -1,7 +1 @@
-#include <__thread.h>
-#include <threads.h>
-
-int *__errno(void)
-{
- return &thrd_current()->terrno;
-}
+_Thread_local int errno;
diff --git a/lib/libc/include/libc.h b/lib/libc/include/libc.h
deleted file mode 100644
index 87d4e88f..00000000
--- a/lib/libc/include/libc.h
+++ /dev/null
@@ -1,25 +0,0 @@
-#ifndef __LIBC_LIBC_H
-#define __LIBC_LIBC_H
-
-#include <stddef.h>
-#include <stdatomic.h>
-
-#define weak_reference(old, new) extern __typeof(old)((new)) __attribute__((__weak__, __alias__(#old)))
-
-struct libc {
- size_t auxv[32];
-
- enum {
- LIBC_ENVP_TOUCHED = 1 << 0,
- } flags;
-
- struct {
- volatile atomic_flag abort;
- volatile atomic_flag malloc;
- volatile atomic_flag environ;
- } lock;
-};
-
-extern struct libc __libc;
-
-#endif
diff --git a/lib/libc/include/syscall.h b/lib/libc/include/syscall.h
deleted file mode 100644
index 645c4bcd..00000000
--- a/lib/libc/include/syscall.h
+++ /dev/null
@@ -1,59 +0,0 @@
-#ifndef __LIBC_SYSCALL_H
-#define __LIBC_SYSCALL_H
-
-#include <asm/syscall.h>
-#include <asm/unistd_64.h>
-#include <errno.h>
-
-typedef long syscall_arg_t;
-
-#define __SYSCALL_NARGS_(a, b, c, d, e, f, g, h, n, ...) n
-#define __SYSCALL_NARGS(...) \
- __SYSCALL_NARGS_(__VA_ARGS__, 7, 6, 5, 4, 3, 2, 1, 0, )
-
-#define __SYSCALL_CONCAT_(a, b) a##b
-#define __SYSCALL_CONCAT(a, b) __SYSCALL_CONCAT_(a, b)
-
-#define __SYSCALL_(b, ...) \
- __SYSCALL_CONCAT(b, __SYSCALL_NARGS(__VA_ARGS__))(__VA_ARGS__)
-
-#define __syscall(...) __SYSCALL_(__syscall_, __VA_ARGS__)
-#define syscall(...) __syscall_ret(__syscall(__VA_ARGS__))
-
-#define __sa(x) ((syscall_arg_t)(x))
-
-#define __syscall_0(n) __syscall0(__NR_##n)
-#define __syscall_1(n, a) __syscall1(__NR_##n, __sa(a))
-#define __syscall_2(n, a, b) __syscall2(__NR_##n, __sa(a), __sa(b))
-#define __syscall_3(n, a, b, c) __syscall3(__NR_##n, __sa(a), __sa(b), __sa(c))
-#define __syscall_4(n, a, b, c, d) \
- __syscall4(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d))
-#define __syscall_5(n, a, b, c, d, e) \
- __syscall5(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e))
-#define __syscall_6(n, a, b, c, d, e, f) \
- __syscall6(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e), \
- __sa(f))
-#define __syscall_7(n, a, b, c, d, e, f, g) \
- __syscall7(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e), \
- __sa(f), __sa(g))
-
-static __inline long __syscall_ret(long ret)
-{
- if (ret > -4096 && ret < 0) {
- errno = -ret;
- ret = -1;
- }
- return ret;
-}
-
-#ifdef __NR_pread64
-#undef __NR_pread
-#define __NR_pread __NR_pread64
-#endif
-
-#ifdef __NR_pwrite64
-#undef __NR_pwrite
-#define __NR_pwrite __NR_pwrite64
-#endif
-
-#endif
diff --git a/lib/libc/internal/Kbuild b/lib/libc/internal/Kbuild
index 01daa04b..d391eaa8 100644
--- a/lib/libc/internal/Kbuild
+++ b/lib/libc/internal/Kbuild
@@ -1 +1,5 @@
obj-y += init/
+obj-y += arch/
+
+obj-y += panic.o
+obj-y += syscall.o
diff --git a/lib/libc/arch/Kbuild b/lib/libc/internal/arch/Kbuild
index ad3a7486..ad3a7486 100644
--- a/lib/libc/arch/Kbuild
+++ b/lib/libc/internal/arch/Kbuild
diff --git a/lib/libc/arch/x86_64/Kbuild b/lib/libc/internal/arch/x86_64/Kbuild
index 830a1c5b..830a1c5b 100644
--- a/lib/libc/arch/x86_64/Kbuild
+++ b/lib/libc/internal/arch/x86_64/Kbuild
diff --git a/lib/libc/arch/x86_64/_start.c b/lib/libc/internal/arch/x86_64/_start.c
index f3f4fef2..f3f4fef2 100644
--- a/lib/libc/arch/x86_64/_start.c
+++ b/lib/libc/internal/arch/x86_64/_start.c
diff --git a/lib/libc/arch/x86_64/fenv.s b/lib/libc/internal/arch/x86_64/fenv.s
index b9a46581..b9a46581 100644
--- a/lib/libc/arch/x86_64/fenv.s
+++ b/lib/libc/internal/arch/x86_64/fenv.s
diff --git a/lib/libc/arch/x86_64/longjmp.c b/lib/libc/internal/arch/x86_64/longjmp.c
index dbd18632..dbd18632 100644
--- a/lib/libc/arch/x86_64/longjmp.c
+++ b/lib/libc/internal/arch/x86_64/longjmp.c
diff --git a/lib/libc/arch/x86_64/setjmp.c b/lib/libc/internal/arch/x86_64/setjmp.c
index ea205e16..ea205e16 100644
--- a/lib/libc/arch/x86_64/setjmp.c
+++ b/lib/libc/internal/arch/x86_64/setjmp.c
diff --git a/lib/libc/arch/x86_64/sigsetjmp.c b/lib/libc/internal/arch/x86_64/sigsetjmp.c
index 2d900ce7..2d900ce7 100644
--- a/lib/libc/arch/x86_64/sigsetjmp.c
+++ b/lib/libc/internal/arch/x86_64/sigsetjmp.c
diff --git a/lib/libc/internal/deinit/tls.c b/lib/libc/internal/deinit/tls.c
new file mode 100644
index 00000000..438f0122
--- /dev/null
+++ b/lib/libc/internal/deinit/tls.c
@@ -0,0 +1,13 @@
+#include <libc.h>
+#include <sys/mman.h>
+
+void __deinit_tls(void)
+{
+ int r;
+
+ if (__libc.tls.base == NULL)
+ return;
+
+ r = munmap(__libc.tls.base, __libc.tls.size);
+ panic_if(__predict_false(r < 0), "munmap(tls) failed");
+}
diff --git a/lib/libc/include/__aio.h b/lib/libc/internal/include/__aio.h
index 93cb1f79..93cb1f79 100644
--- a/lib/libc/include/__aio.h
+++ b/lib/libc/internal/include/__aio.h
diff --git a/lib/libc/include/__dirent.h b/lib/libc/internal/include/__dirent.h
index 4f9ead80..4f9ead80 100644
--- a/lib/libc/include/__dirent.h
+++ b/lib/libc/internal/include/__dirent.h
diff --git a/lib/libc/include/__select.h b/lib/libc/internal/include/__select.h
index a38bbdce..a38bbdce 100644
--- a/lib/libc/include/__select.h
+++ b/lib/libc/internal/include/__select.h
diff --git a/lib/libc/include/__signal.h b/lib/libc/internal/include/__signal.h
index 6b762dee..6b762dee 100644
--- a/lib/libc/include/__signal.h
+++ b/lib/libc/internal/include/__signal.h
diff --git a/lib/libc/include/__statvfs.h b/lib/libc/internal/include/__statvfs.h
index c8a746d4..c8a746d4 100644
--- a/lib/libc/include/__statvfs.h
+++ b/lib/libc/internal/include/__statvfs.h
diff --git a/lib/libc/include/__stdio.h b/lib/libc/internal/include/__stdio.h
index 487a0382..487a0382 100644
--- a/lib/libc/include/__stdio.h
+++ b/lib/libc/internal/include/__stdio.h
diff --git a/lib/libc/include/__thread.h b/lib/libc/internal/include/__thread.h
index f978d018..7639707a 100644
--- a/lib/libc/include/__thread.h
+++ b/lib/libc/internal/include/__thread.h
@@ -3,7 +3,6 @@
struct __thread_self {
int tid;
- int terrno;
};
#endif
diff --git a/lib/libc/include/atomic.h b/lib/libc/internal/include/atomic.h
index e0593021..e0593021 100644
--- a/lib/libc/include/atomic.h
+++ b/lib/libc/internal/include/atomic.h
diff --git a/lib/libc/include/byteswap.h b/lib/libc/internal/include/byteswap.h
index 9dfe6520..9dfe6520 100644
--- a/lib/libc/include/byteswap.h
+++ b/lib/libc/internal/include/byteswap.h
diff --git a/lib/libc/include/internal/io_uring.h b/lib/libc/internal/include/internal/io_uring.h
index e7369146..e7369146 100644
--- a/lib/libc/include/internal/io_uring.h
+++ b/lib/libc/internal/include/internal/io_uring.h
diff --git a/lib/libc/include/io_uring.h b/lib/libc/internal/include/io_uring.h
index 4dac4583..4dac4583 100644
--- a/lib/libc/include/io_uring.h
+++ b/lib/libc/internal/include/io_uring.h
diff --git a/lib/libc/internal/include/libc.h b/lib/libc/internal/include/libc.h
new file mode 100644
index 00000000..f06fa6d8
--- /dev/null
+++ b/lib/libc/internal/include/libc.h
@@ -0,0 +1,48 @@
+#ifndef __LIBC_LIBC_H
+#define __LIBC_LIBC_H
+
+#include <stdatomic.h>
+#include <stddef.h>
+#include <sys/cdefs.h>
+
+#define weak_reference(old, new) extern __typeof(old)((new)) __attribute__((__weak__, __alias__(#old)))
+
+struct tls {
+ struct tls *next;
+ void *data;
+ size_t size;
+ size_t align;
+ size_t length;
+ size_t offset;
+};
+
+struct libc {
+ size_t auxv[32];
+ struct {
+ void *base;
+ size_t size;
+ } tls;
+
+ enum {
+ LIBC_ENVP_TOUCHED = 1 << 0,
+ } flags;
+
+ struct {
+ volatile atomic_flag abort;
+ volatile atomic_flag malloc;
+ volatile atomic_flag environ;
+ } lock;
+};
+
+extern struct libc __libc;
+
+#define panic(__errmsg) __libc_panic(__FILE__ ":" __STRING(__LINE__) ": ", __PRETTY_FUNCTION__, ": " __STRING(__errmsg))
+
+#define panic_if(__cond, __errmsg) \
+ do { \
+ if (__predict_false(__cond)) \
+ panic(__errmsg); \
+ } while (0)
+
+__dead void __libc_panic(const char *, const char *, const char *);
+#endif
diff --git a/lib/libc/include/libc/dirent.h b/lib/libc/internal/include/libc/dirent.h
index 296cc91e..296cc91e 100644
--- a/lib/libc/include/libc/dirent.h
+++ b/lib/libc/internal/include/libc/dirent.h
diff --git a/lib/libc/include/malloc.h b/lib/libc/internal/include/malloc.h
index b7cb0093..b7cb0093 100644
--- a/lib/libc/include/malloc.h
+++ b/lib/libc/internal/include/malloc.h
diff --git a/lib/libc/internal/include/syscall.h b/lib/libc/internal/include/syscall.h
new file mode 100644
index 00000000..ea72ece4
--- /dev/null
+++ b/lib/libc/internal/include/syscall.h
@@ -0,0 +1,44 @@
+#ifndef __LIBC_SYSCALL_H
+#define __LIBC_SYSCALL_H
+
+#include <asm/syscall.h>
+#include <asm/unistd_64.h>
+
+typedef long syscall_arg_t;
+
+#define __SYSCALL_NARGS_(a, b, c, d, e, f, g, h, n, ...) n
+#define __SYSCALL_NARGS(...) __SYSCALL_NARGS_(__VA_ARGS__, 7, 6, 5, 4, 3, 2, 1, 0, )
+
+#define __SYSCALL_CONCAT_(a, b) a##b
+#define __SYSCALL_CONCAT(a, b) __SYSCALL_CONCAT_(a, b)
+
+#define __SYSCALL_(b, ...) __SYSCALL_CONCAT(b, __SYSCALL_NARGS(__VA_ARGS__))(__VA_ARGS__)
+
+#define __syscall(...) __SYSCALL_(__syscall_, __VA_ARGS__)
+#define syscall(...) __syscall_ret(__syscall(__VA_ARGS__))
+
+#define __sa(x) ((syscall_arg_t)(x))
+
+#define __syscall_0(n) __syscall0(__NR_##n)
+#define __syscall_1(n, a) __syscall1(__NR_##n, __sa(a))
+#define __syscall_2(n, a, b) __syscall2(__NR_##n, __sa(a), __sa(b))
+#define __syscall_3(n, a, b, c) __syscall3(__NR_##n, __sa(a), __sa(b), __sa(c))
+#define __syscall_4(n, a, b, c, d) __syscall4(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d))
+#define __syscall_5(n, a, b, c, d, e) __syscall5(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e))
+#define __syscall_6(n, a, b, c, d, e, f) __syscall6(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e), __sa(f))
+#define __syscall_7(n, a, b, c, d, e, f, g) \
+ __syscall7(__NR_##n, __sa(a), __sa(b), __sa(c), __sa(d), __sa(e), __sa(f), __sa(g))
+
+#ifdef __NR_pread64
+#undef __NR_pread
+#define __NR_pread __NR_pread64
+#endif
+
+#ifdef __NR_pwrite64
+#undef __NR_pwrite
+#define __NR_pwrite __NR_pwrite64
+#endif
+
+extern long __syscall_ret(long ret);
+
+#endif
diff --git a/lib/libc/internal/init/Kbuild b/lib/libc/internal/init/Kbuild
index 7941a53c..361f220a 100644
--- a/lib/libc/internal/init/Kbuild
+++ b/lib/libc/internal/init/Kbuild
@@ -1,2 +1,3 @@
obj-y += init.o
+obj-y += tls.o
obj-y += vdso.o
diff --git a/lib/libc/internal/init/init.c b/lib/libc/internal/init/init.c
index 36e66ee4..b2dd8487 100644
--- a/lib/libc/internal/init/init.c
+++ b/lib/libc/internal/init/init.c
@@ -5,13 +5,14 @@
#include <sys/cdefs.h>
extern void __init_vdso(void);
+extern void __init_tls(void);
+
+extern int main(int, char **, char **);
struct libc __libc = { 0 };
char **environ;
char *__progname;
-extern int main(int, char **, char **);
-
__used void __init(uintptr_t *rsp)
{
char **argv;
@@ -34,6 +35,7 @@ __used void __init(uintptr_t *rsp)
for (size_t i = 0; auxv[i]; i += 2)
__libc.auxv[auxv[i]] = auxv[i + 1];
+ __init_tls();
__init_vdso();
exit(main(argc, argv, environ));
diff --git a/lib/libc/internal/init/tls.c b/lib/libc/internal/init/tls.c
new file mode 100644
index 00000000..f6ccde35
--- /dev/null
+++ b/lib/libc/internal/init/tls.c
@@ -0,0 +1,76 @@
+#include <__thread.h>
+#include <asm/prctl.h>
+#include <elf.h>
+#include <libc.h>
+#include <string.h>
+#include <sys/mman.h>
+#include <syscall.h>
+
+#define ALIGN_DOWN(x, a) ((x) & ~((a) - 1))
+#define ALIGN_UP(x, a) (((x) + (a) - 1) & ~((a) - 1))
+
+static struct tls __libc_tls = { 0 };
+static struct __thread_self __libc_thread;
+volatile int __libc_tid;
+
+void __init_tls(void)
+{
+ int r;
+ void *mem;
+ size_t base;
+ unsigned char *p;
+ Elf64_Phdr *tls_phdr;
+ struct __thread_self *thrd;
+
+ base = 0;
+ tls_phdr = 0;
+ p = (void *)__libc.auxv[AT_PHDR];
+ for (size_t n = __libc.auxv[AT_PHNUM]; n > 0; n--, p += __libc.auxv[AT_PHENT]) {
+ Elf64_Phdr *phdr = (Elf64_Phdr *)p;
+
+ if (phdr->p_type == PT_PHDR) {
+ base = __libc.auxv[AT_PHDR] - phdr->p_vaddr;
+ } else if (phdr->p_type == PT_TLS) {
+ tls_phdr = phdr;
+ }
+ }
+
+ if (tls_phdr) {
+ __libc_tls.data = (void *)(base + tls_phdr->p_vaddr);
+ __libc_tls.length = tls_phdr->p_filesz;
+ __libc_tls.size = tls_phdr->p_memsz;
+ __libc_tls.align = tls_phdr->p_align;
+ }
+
+ if (__libc_tls.size != 0) {
+ void *tls_mem;
+ size_t tls_size = __libc_tls.size + sizeof(struct __thread_self);
+ tls_size = (tls_size + __libc_tls.align - 1) & ~(__libc_tls.align - 1);
+
+ mem = mmap(0, tls_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
+ panic_if(mem == MAP_FAILED, "mmap failed");
+
+ __libc.tls.base = mem;
+ __libc.tls.size = tls_size;
+
+ thrd = (struct __thread_self *)mem;
+ tls_mem = (unsigned char *)mem + sizeof(struct __thread_self);
+
+ if (tls_phdr->p_filesz > 0) {
+ memcpy(tls_mem, (void *)tls_phdr->p_vaddr, tls_phdr->p_filesz);
+ memset(tls_mem + tls_phdr->p_filesz, 0, tls_phdr->p_memsz - tls_phdr->p_filesz);
+ } else {
+ memset(tls_mem, 0, tls_phdr->p_memsz);
+ }
+
+ r = syscall(arch_prctl, ARCH_SET_FS, mem + sizeof(struct __thread_self));
+ panic_if(r < 0, "arch_prctl(SET_FS) failed");
+ } else {
+ __libc.tls.base = NULL;
+ thrd = &__libc_thread;
+ }
+
+ r = syscall(set_tid_address, &__libc_tid);
+ panic_if(r < 0, "set_tid_address failed");
+ thrd->tid = r;
+}
diff --git a/lib/libc/internal/panic.c b/lib/libc/internal/panic.c
new file mode 100644
index 00000000..1af6d6cf
--- /dev/null
+++ b/lib/libc/internal/panic.c
@@ -0,0 +1,29 @@
+#include <string.h>
+#include <sys/cdefs.h>
+#include <sys/uio.h>
+#include <unistd.h>
+
+__dead void __libc_panic(const char *prefix, const char *f, const char *errmsg)
+{
+ struct iovec iovec[5];
+ const char *e = "libc panic: ";
+
+ iovec[0].iov_base = (char *)e;
+ iovec[0].iov_len = sizeof("libc panic: ") - 1;
+
+ iovec[1].iov_base = (char *)prefix;
+ iovec[1].iov_len = strlen(prefix);
+
+ iovec[2].iov_base = (char *)f;
+ iovec[2].iov_len = strlen(f);
+
+ iovec[3].iov_base = (char *)errmsg;
+ iovec[3].iov_len = strlen(errmsg);
+
+ iovec[4].iov_base = "\n";
+ iovec[4].iov_len = 1;
+
+ writev(STDERR_FILENO, iovec, 5);
+
+ __builtin_trap();
+}
diff --git a/lib/libc/internal/syscall.c b/lib/libc/internal/syscall.c
new file mode 100644
index 00000000..f7fd3c4b
--- /dev/null
+++ b/lib/libc/internal/syscall.c
@@ -0,0 +1,12 @@
+#include <errno.h>
+#include <sys/cdefs.h>
+
+long __syscall_ret(long ret)
+{
+ if (__predict_false(ret > -4096 && ret < 0)) {
+ errno = (int)-ret;
+ ret = -1;
+ }
+
+ return ret;
+}
diff --git a/lib/libc/mman/mmap.c b/lib/libc/mman/mmap.c
index d43ed686..b3ebdbbd 100644
--- a/lib/libc/mman/mmap.c
+++ b/lib/libc/mman/mmap.c
@@ -1,5 +1,3 @@
-
-
#include <stddef.h> // for size_t
#include <syscall.h> // for __syscall_6, syscall
diff --git a/lib/libc/mqueue/mq_notify.c b/lib/libc/mqueue/mq_notify.c
index a7617375..6011f567 100644
--- a/lib/libc/mqueue/mq_notify.c
+++ b/lib/libc/mqueue/mq_notify.c
@@ -1,11 +1,11 @@
+#include <errno.h>
#include <mqueue.h>
#include <signal.h>
#include <syscall.h>
int mq_notify(mqd_t mqdes, const struct sigevent *notification)
{
- if (notification == NULL ||
- notification->sigev_notify != SIGEV_THREAD) {
+ if (notification == NULL || notification->sigev_notify != SIGEV_THREAD) {
return syscall(mq_notify, mqdes, notification);
}
diff --git a/lib/libc/mqueue/mq_unlink.c b/lib/libc/mqueue/mq_unlink.c
index d136f109..da16f030 100644
--- a/lib/libc/mqueue/mq_unlink.c
+++ b/lib/libc/mqueue/mq_unlink.c
@@ -1,3 +1,4 @@
+#include <errno.h>
#include <mqueue.h>
#include <syscall.h>
@@ -11,7 +12,6 @@ int mq_unlink(const char *name)
r = __syscall(mq_unlink, name);
if (r < 0) {
- // Correct errno for POSIX compliance
if (r == -EPERM)
r = -EACCES;
errno = -r;
diff --git a/lib/libc/sys/getauxval.c b/lib/libc/sys/getauxval.c
index 155d4258..c9a2bf66 100644
--- a/lib/libc/sys/getauxval.c
+++ b/lib/libc/sys/getauxval.c
@@ -1,6 +1,8 @@
#include <errno.h>
#include <libc.h>
+#include <stdio.h>
+
unsigned long getauxval(unsigned long type)
{
size_t *auxv = __libc.auxv;
diff --git a/lib/libc/thread/thrd_current.c b/lib/libc/thread/thrd_current.c
index 69a99723..b588cc27 100644
--- a/lib/libc/thread/thrd_current.c
+++ b/lib/libc/thread/thrd_current.c
@@ -1,8 +1,9 @@
-#include <__thread.h> // for __thread_self
-#include <threads.h> // for thrd_current, thrd_t
+#include <__thread.h>
+#include <threads.h>
+
+thread_local struct __thread_self __thread_self;
thrd_t thrd_current(void)
{
- static struct __thread_self self = { 0 };
- return &self;
+ return &__thread_self;
}