shithub: scc

Download patch

ref: 297c3c7dfa958231abe140ee00d38b0e684ad48c
parent: 2bee5e38261775e54c94508a6955f0bbfa28e51c
author: Roberto E. Vargas Caballero <k0ga@shike2.com>
date: Fri Oct 1 17:27:43 EDT 2021

libc/linux: Add _sigaction() wrapper

Linux sigaction() syscall does not have the same prototype
than the POSIX version. For this reason is needed a wrapper
to that is able to adapt the interface and set the expected
behaviour of signal() in linux systems.

--- /dev/null
+++ b/include/bits/linux/amd64/arch/sigaction.h
@@ -1,0 +1,10 @@
+#define SA_RESTORER   0x04000000
+
+struct sigaction {
+        void (*sa_handler)(int);
+        unsigned long sa_flags;
+        void (*sa_restorer)(void);
+        unsigned sa_mask[2];
+};
+
+extern int __sigaction(int, struct sigaction *, struct sigaction *, size_t);
--- a/include/bits/linux/sys.h
+++ b/include/bits/linux/sys.h
@@ -12,11 +12,7 @@
 
 typedef int pid_t;
 
-struct sigaction {
-	void (*sa_handler)(int);
-	int sa_mask;
-	int sa_flags;
-};
+struct sigaction;
 
 extern pid_t _getpid(void);
 extern int _kill(pid_t, int);
--- a/src/libc/arch/amd64/linux/.gitignore
+++ b/src/libc/arch/amd64/linux/.gitignore
@@ -1,3 +1,4 @@
+__sigaction.s
 _close.s
 _exit.s
 _getpid.s
@@ -7,7 +8,7 @@
 _lseek.s
 _open.s
 _read.s
-_sigaction.s
+_sigreturn.s
 _sys_brk.s
 _sys_errlist.c
 _unlink.s
--- a/src/libc/arch/amd64/linux/Makefile
+++ b/src/libc/arch/amd64/linux/Makefile
@@ -6,6 +6,7 @@
 include ../../../rules.mk
 
 GENOBJS =\
+	__sigaction.$O\
 	_close.$O\
 	_exit.$O\
 	_getpid.$O\
@@ -15,7 +16,7 @@
 	_lseek.$O\
 	_open.$O\
 	_read.$O\
-	_sigaction.$O\
+	_sigreturn.$O\
 	_sys_brk.$O\
 	_unlink.$O\
 	_write.$O\
--- a/src/libc/arch/amd64/linux/syscall.lst
+++ b/src/libc/arch/amd64/linux/syscall.lst
@@ -6,7 +6,8 @@
 3	_close	1
 8	_lseek	3
 12	_sys_brk	1
-13	_sigaction	3
+13	__sigaction	4
+15	_sigreturn	0
 39	_getpid	0
 60	_exit	1
 62	_kill	2
--- a/src/libc/arch/arm/linux/syscall.lst
+++ b/src/libc/arch/arm/linux/syscall.lst
@@ -8,4 +8,4 @@
 37	_kill
 19	_lseek
 45	_sys_brk
-134	_sigaction
+134	__sigaction
--- a/src/libc/arch/arm64/linux/syscall.lst
+++ b/src/libc/arch/arm64/linux/syscall.lst
@@ -6,6 +6,6 @@
 64	_write
 93	_Exit
 129	_kill
-134	_sigaction
+134	__sigaction
 172	_getpid
 214	_sys_brk
--- a/src/libc/arch/i386/linux/syscall.lst
+++ b/src/libc/arch/i386/linux/syscall.lst
@@ -7,5 +7,5 @@
 19	_lseek		3
 20	_getpid		0
 37	_kill		2
-45	_sys_brk		1
-67	_sigaction	3
+45	_sys_brk	1
+67	__sigaction	4
--- a/src/libc/arch/linux/Makefile
+++ b/src/libc/arch/linux/Makefile
@@ -6,6 +6,7 @@
 OBJS=\
 	_brk.$O\
 	_getheap.$O\
+	_sigaction.$O\
 
 all: $(OBJS)
 
--- /dev/null
+++ b/src/libc/arch/linux/_sigaction.c
@@ -1,0 +1,36 @@
+#include <string.h>
+
+#include <arch/sigaction.h>
+#include <sys.h>
+
+extern void _sigreturn(void);
+
+int _sigaction(int sig, struct sigaction *sa, struct sigaction *old)
+{
+	int r;
+	struct sigaction ksa, kold;
+
+	if (sa) {
+		ksa.sa_handler = sa->sa_handler;
+		ksa.sa_flags = sa->sa_flags | SA_RESTORER;
+		ksa.sa_restorer = _sigreturn;
+		memcpy(&ksa.sa_mask, &sa->sa_mask, sizeof(ksa.sa_mask));
+	}
+
+	r = __sigaction(sig,
+	                sa ? &ksa : NULL,
+	                old ? &kold : NULL,
+	                sizeof(ksa.sa_mask));
+
+	if (r != 0)
+		return -1;
+
+
+	if (old) {
+		old->sa_handler = kold.sa_handler;
+		old->sa_flags = kold.sa_flags;
+		memcpy(&old->sa_mask, &kold.sa_mask, sizeof kold.sa_mask);
+	}
+
+	return 0;
+}
--- a/src/libc/arch/posix/signal.c
+++ b/src/libc/arch/posix/signal.c
@@ -1,5 +1,7 @@
 #include <signal.h>
+#include <stddef.h>
 
+#include <arch/sigaction.h>
 #include <sys.h>
 
 #undef signal
--- a/src/libc/objs/amd64-linux.mk
+++ b/src/libc/objs/amd64-linux.mk
@@ -2,6 +2,7 @@
 
 OBJS =\
 	$(COMMON_OBJS)\
+	arch/amd64/linux/__sigaction.$O\
 	arch/amd64/linux/_cerrno.$O\
 	arch/amd64/linux/_close.$O\
 	arch/amd64/linux/_exit.$O\
@@ -12,7 +13,7 @@
 	arch/amd64/linux/_lseek.$O\
 	arch/amd64/linux/_open.$O\
 	arch/amd64/linux/_read.$O\
-	arch/amd64/linux/_sigaction.$O\
+	arch/amd64/linux/_sigreturn.$O\
 	arch/amd64/linux/_sys_brk.$O\
 	arch/amd64/linux/_sys_errlist.$O\
 	arch/amd64/linux/_unlink.$O\
@@ -30,6 +31,7 @@
 	arch/amd64/strcpy.$O\
 	arch/linux/_brk.$O\
 	arch/linux/_getheap.$O\
+	arch/linux/_sigaction.$O\
 	arch/posix/_getheap.$O\
 	arch/posix/_open.$O\
 	arch/posix/_systime.$O\