1 #include <signal.h>
2 #include <printf.h>
3 #include <stddef.h>
4 #include <libsystem/syscall.h>
5 
6 #pragma GCC push_options
7 #pragma GCC optimize("O0")
__libc_sa_restorer()8 void __libc_sa_restorer()
9 {
10     // 在这里发起sigreturn,请注意,由于内核需要读取到原来的do_signal时保存的栈帧,因此这里不能发生函数调用(会导致函数压栈),只能够这样来完成sigreturn
11     __asm__ __volatile__("int $0x80   \n\t" ::"a"(SYS_RT_SIGRETURN) : "memory");
12 }
13 #pragma GCC pop_options
14 
15 /**
16  * @brief 设置信号处理动作(简单版本)
17  *
18  * @param signum
19  * @param handler
20  * @return int
21  */
signal(int signum,__sighandler_t handler)22 int signal(int signum, __sighandler_t handler)
23 {
24     struct sigaction sa = {0};
25     sa.sa_handler = handler;
26     // 由于DragonOS必须由用户程序指定一个sa_restorer,因此这里设置为libc的sa_restorer
27     sa.sa_restorer = &__libc_sa_restorer;
28     // printf("handler address: %#018lx\n", handler);
29     // printf("restorer address: %#018lx\n", &__libc_sa_restorer);
30     sigaction(signum, &sa, NULL);
31 }
32 
33 /**
34  * @brief 设置信号处理动作
35  *
36  * @param signum 信号
37  * @param act 处理动作(不可为NULL)
38  * @param oldact 返回的旧的处理动作(若为NULL,则不返回)
39  * @return int 错误码(遵循posix)
40  */
sigaction(int signum,const struct sigaction * act,struct sigaction * oldact)41 int sigaction(int signum, const struct sigaction *act, struct sigaction *oldact)
42 {
43     return syscall_invoke(SYS_SIGACTION, (uint64_t)signum, (uint64_t)act, (uint64_t)oldact, 0, 0, 0, 0, 0);
44 }
45 
46 /**
47  * @brief 向当前进程发送一个信号
48  *
49  * @param sig signal number
50  * @return int 错误码
51  */
raise(int sig)52 int raise(int sig)
53 {
54     return kill(getpid(), sig);
55 }
56 
57 /**
58  * @brief
59  *
60  * @param pid 进程的标识符
61  * @param sig signal number
62  * @return int 错误码
63  */
kill(pid_t pid,int sig)64 int kill(pid_t pid, int sig)
65 {
66     syscall_invoke(SYS_KILL, pid, sig, 0, 0, 0, 0, 0, 0);
67 }