Ruby  2.4.2p198(2017-09-14revision59899)
signal.c
Go to the documentation of this file.
1 /**********************************************************************
2 
3  signal.c -
4 
5  $Author: nobu $
6  created at: Tue Dec 20 10:13:44 JST 1994
7 
8  Copyright (C) 1993-2007 Yukihiro Matsumoto
9  Copyright (C) 2000 Network Applied Communication Laboratory, Inc.
10  Copyright (C) 2000 Information-technology Promotion Agency, Japan
11 
12 **********************************************************************/
13 
14 #include "internal.h"
15 #include "vm_core.h"
16 #include <signal.h>
17 #include <stdio.h>
18 #include <errno.h>
19 #include "ruby_atomic.h"
20 #include "eval_intern.h"
21 #ifdef HAVE_UNISTD_H
22 # include <unistd.h>
23 #endif
24 #ifdef HAVE_SYS_UIO_H
25 #include <sys/uio.h>
26 #endif
27 #ifdef HAVE_UCONTEXT_H
28 #include <ucontext.h>
29 #endif
30 
31 #ifdef HAVE_VALGRIND_MEMCHECK_H
32 # include <valgrind/memcheck.h>
33 # ifndef VALGRIND_MAKE_MEM_DEFINED
34 # define VALGRIND_MAKE_MEM_DEFINED(p, n) VALGRIND_MAKE_READABLE((p), (n))
35 # endif
36 # ifndef VALGRIND_MAKE_MEM_UNDEFINED
37 # define VALGRIND_MAKE_MEM_UNDEFINED(p, n) VALGRIND_MAKE_WRITABLE((p), (n))
38 # endif
39 #else
40 # define VALGRIND_MAKE_MEM_DEFINED(p, n) 0
41 # define VALGRIND_MAKE_MEM_UNDEFINED(p, n) 0
42 #endif
43 
44 #if defined(__native_client__) && defined(NACL_NEWLIB)
45 # include "nacl/signal.h"
46 #endif
47 
49 #define id_signo ruby_static_id_signo
50 
51 #ifdef NEED_RUBY_ATOMIC_OPS
54 {
55  rb_atomic_t old = *ptr;
56  *ptr = val;
57  return old;
58 }
59 
62  rb_atomic_t newval)
63 {
64  rb_atomic_t old = *ptr;
65  if (old == cmp) {
66  *ptr = newval;
67  }
68  return old;
69 }
70 #endif
71 
72 #ifndef NSIG
73 # define NSIG (_SIGMAX + 1) /* For QNX */
74 #endif
75 
76 static const struct signals {
77  const char *signm;
78  int signo;
79 } siglist [] = {
80  {"EXIT", 0},
81 #ifdef SIGHUP
82  {"HUP", SIGHUP},
83 #endif
84  {"INT", SIGINT},
85 #ifdef SIGQUIT
86  {"QUIT", SIGQUIT},
87 #endif
88 #ifdef SIGILL
89  {"ILL", SIGILL},
90 #endif
91 #ifdef SIGTRAP
92  {"TRAP", SIGTRAP},
93 #endif
94 #ifdef SIGABRT
95  {"ABRT", SIGABRT},
96 #endif
97 #ifdef SIGIOT
98  {"IOT", SIGIOT},
99 #endif
100 #ifdef SIGEMT
101  {"EMT", SIGEMT},
102 #endif
103 #ifdef SIGFPE
104  {"FPE", SIGFPE},
105 #endif
106 #ifdef SIGKILL
107  {"KILL", SIGKILL},
108 #endif
109 #ifdef SIGBUS
110  {"BUS", SIGBUS},
111 #endif
112 #ifdef SIGSEGV
113  {"SEGV", SIGSEGV},
114 #endif
115 #ifdef SIGSYS
116  {"SYS", SIGSYS},
117 #endif
118 #ifdef SIGPIPE
119  {"PIPE", SIGPIPE},
120 #endif
121 #ifdef SIGALRM
122  {"ALRM", SIGALRM},
123 #endif
124 #ifdef SIGTERM
125  {"TERM", SIGTERM},
126 #endif
127 #ifdef SIGURG
128  {"URG", SIGURG},
129 #endif
130 #ifdef SIGSTOP
131  {"STOP", SIGSTOP},
132 #endif
133 #ifdef SIGTSTP
134  {"TSTP", SIGTSTP},
135 #endif
136 #ifdef SIGCONT
137  {"CONT", SIGCONT},
138 #endif
139 #ifdef SIGCHLD
140  {"CHLD", SIGCHLD},
141 #endif
142 #ifdef SIGCLD
143  {"CLD", SIGCLD},
144 #else
145 # ifdef SIGCHLD
146  {"CLD", SIGCHLD},
147 # endif
148 #endif
149 #ifdef SIGTTIN
150  {"TTIN", SIGTTIN},
151 #endif
152 #ifdef SIGTTOU
153  {"TTOU", SIGTTOU},
154 #endif
155 #ifdef SIGIO
156  {"IO", SIGIO},
157 #endif
158 #ifdef SIGXCPU
159  {"XCPU", SIGXCPU},
160 #endif
161 #ifdef SIGXFSZ
162  {"XFSZ", SIGXFSZ},
163 #endif
164 #ifdef SIGVTALRM
165  {"VTALRM", SIGVTALRM},
166 #endif
167 #ifdef SIGPROF
168  {"PROF", SIGPROF},
169 #endif
170 #ifdef SIGWINCH
171  {"WINCH", SIGWINCH},
172 #endif
173 #ifdef SIGUSR1
174  {"USR1", SIGUSR1},
175 #endif
176 #ifdef SIGUSR2
177  {"USR2", SIGUSR2},
178 #endif
179 #ifdef SIGLOST
180  {"LOST", SIGLOST},
181 #endif
182 #ifdef SIGMSG
183  {"MSG", SIGMSG},
184 #endif
185 #ifdef SIGPWR
186  {"PWR", SIGPWR},
187 #endif
188 #ifdef SIGPOLL
189  {"POLL", SIGPOLL},
190 #endif
191 #ifdef SIGDANGER
192  {"DANGER", SIGDANGER},
193 #endif
194 #ifdef SIGMIGRATE
195  {"MIGRATE", SIGMIGRATE},
196 #endif
197 #ifdef SIGPRE
198  {"PRE", SIGPRE},
199 #endif
200 #ifdef SIGGRANT
201  {"GRANT", SIGGRANT},
202 #endif
203 #ifdef SIGRETRACT
204  {"RETRACT", SIGRETRACT},
205 #endif
206 #ifdef SIGSOUND
207  {"SOUND", SIGSOUND},
208 #endif
209 #ifdef SIGINFO
210  {"INFO", SIGINFO},
211 #endif
212  {NULL, 0}
213 };
214 
215 static const char signame_prefix[3] = "SIG";
216 
217 static int
218 signm2signo(const char *nm)
219 {
220  const struct signals *sigs;
221 
222  for (sigs = siglist; sigs->signm; sigs++)
223  if (strcmp(sigs->signm, nm) == 0)
224  return sigs->signo;
225  return 0;
226 }
227 
228 static const char*
229 signo2signm(int no)
230 {
231  const struct signals *sigs;
232 
233  for (sigs = siglist; sigs->signm; sigs++)
234  if (sigs->signo == no)
235  return sigs->signm;
236  return 0;
237 }
238 
239 /*
240  * call-seq:
241  * Signal.signame(signo) -> string or nil
242  *
243  * Convert signal number to signal name.
244  * Returns +nil+ if the signo is an invalid signal number.
245  *
246  * Signal.trap("INT") { |signo| puts Signal.signame(signo) }
247  * Process.kill("INT", 0)
248  *
249  * <em>produces:</em>
250  *
251  * INT
252  */
253 static VALUE
255 {
256  const char *signame = signo2signm(NUM2INT(signo));
257  if (!signame) return Qnil;
258  return rb_str_new_cstr(signame);
259 }
260 
261 const char *
263 {
264  return signo2signm(no);
265 }
266 
267 static VALUE
269 {
270  const char *const signm = signo2signm(signo);
271  if (signm) {
272  return rb_sprintf("SIG%s", signm);
273  }
274  else {
275  return rb_sprintf("SIG%u", signo);
276  }
277 }
278 
279 /*
280  * call-seq:
281  * SignalException.new(sig_name) -> signal_exception
282  * SignalException.new(sig_number [, name]) -> signal_exception
283  *
284  * Construct a new SignalException object. +sig_name+ should be a known
285  * signal name.
286  */
287 
288 static VALUE
290 {
291  int argnum = 1;
292  VALUE sig = Qnil;
293  int signo;
294  const char *signm;
295 
296  if (argc > 0) {
297  sig = rb_check_to_integer(argv[0], "to_int");
298  if (!NIL_P(sig)) argnum = 2;
299  else sig = argv[0];
300  }
301  rb_check_arity(argc, 1, argnum);
302  if (argnum == 2) {
303  signo = NUM2INT(sig);
304  if (signo < 0 || signo > NSIG) {
305  rb_raise(rb_eArgError, "invalid signal number (%d)", signo);
306  }
307  if (argc > 1) {
308  sig = argv[1];
309  }
310  else {
311  sig = rb_signo2signm(signo);
312  }
313  }
314  else {
315  int len = sizeof(signame_prefix);
316  if (SYMBOL_P(sig)) sig = rb_sym2str(sig); else StringValue(sig);
317  signm = RSTRING_PTR(sig);
318  if (strncmp(signm, signame_prefix, len) == 0) {
319  signm += len;
320  len = 0;
321  }
322  signo = signm2signo(signm);
323  if (!signo) {
324  rb_raise(rb_eArgError, "unsupported name `%.*s%"PRIsVALUE"'",
325  len, signame_prefix, sig);
326  }
327  sig = rb_sprintf("SIG%s", signm);
328  }
329  rb_call_super(1, &sig);
330  rb_ivar_set(self, id_signo, INT2NUM(signo));
331 
332  return self;
333 }
334 
335 /*
336  * call-seq:
337  * signal_exception.signo -> num
338  *
339  * Returns a signal number.
340  */
341 
342 static VALUE
344 {
345  return rb_ivar_get(self, id_signo);
346 }
347 
348 /* :nodoc: */
349 static VALUE
351 {
352  VALUE args[2];
353 
354  args[0] = INT2FIX(SIGINT);
355  rb_scan_args(argc, argv, "01", &args[1]);
356  return rb_call_super(2, args);
357 }
358 
359 void
361 {
362  signal(sig, SIG_DFL);
363  raise(sig);
364 }
365 
366 static RETSIGTYPE sighandler(int sig);
367 static int signal_ignored(int sig);
368 static void signal_enque(int sig);
369 
370 /*
371  * call-seq:
372  * Process.kill(signal, pid, ...) -> integer
373  *
374  * Sends the given signal to the specified process id(s) if _pid_ is positive.
375  * If _pid_ is zero _signal_ is sent to all processes whose group ID is equal
376  * to the group ID of the process. _signal_ may be an integer signal number or
377  * a POSIX signal name (either with or without a +SIG+ prefix). If _signal_ is
378  * negative (or starts with a minus sign), kills process groups instead of
379  * processes. Not all signals are available on all platforms.
380  * The keys and values of +Signal.list+ are known signal names and numbers,
381  * respectively.
382  *
383  * pid = fork do
384  * Signal.trap("HUP") { puts "Ouch!"; exit }
385  * # ... do some work ...
386  * end
387  * # ...
388  * Process.kill("HUP", pid)
389  * Process.wait
390  *
391  * <em>produces:</em>
392  *
393  * Ouch!
394  *
395  * If _signal_ is an integer but wrong for signal,
396  * <code>Errno::EINVAL</code> or +RangeError+ will be raised.
397  * Otherwise unless _signal_ is a +String+ or a +Symbol+, and a known
398  * signal name, +ArgumentError+ will be raised.
399  *
400  * Also, <code>Errno::ESRCH</code> or +RangeError+ for invalid _pid_,
401  * <code>Errno::EPERM</code> when failed because of no privilege,
402  * will be raised. In these cases, signals may have been sent to
403  * preceding processes.
404  */
405 
406 VALUE
407 rb_f_kill(int argc, const VALUE *argv)
408 {
409 #ifndef HAVE_KILLPG
410 #define killpg(pg, sig) kill(-(pg), (sig))
411 #endif
412  int negative = 0;
413  int sig;
414  int i;
415  VALUE str;
416  const char *s;
417 
419 
420  switch (TYPE(argv[0])) {
421  case T_FIXNUM:
422  sig = FIX2INT(argv[0]);
423  break;
424 
425  case T_SYMBOL:
426  str = rb_sym2str(argv[0]);
427  goto str_signal;
428 
429  case T_STRING:
430  str = argv[0];
431  str_signal:
432  s = RSTRING_PTR(str);
433  if (s[0] == '-') {
434  negative++;
435  s++;
436  }
437  if (strncmp(signame_prefix, s, sizeof(signame_prefix)) == 0)
438  s += 3;
439  if ((sig = signm2signo(s)) == 0) {
440  long ofs = s - RSTRING_PTR(str);
441  if (ofs) str = rb_str_subseq(str, ofs, RSTRING_LEN(str)-ofs);
442  rb_raise(rb_eArgError, "unsupported name `SIG%"PRIsVALUE"'", str);
443  }
444 
445  if (negative)
446  sig = -sig;
447  break;
448 
449  default:
450  str = rb_check_string_type(argv[0]);
451  if (!NIL_P(str)) {
452  goto str_signal;
453  }
454  rb_raise(rb_eArgError, "bad signal type %s",
455  rb_obj_classname(argv[0]));
456  break;
457  }
458 
459  if (argc <= 1) return INT2FIX(0);
460 
461  if (sig < 0) {
462  sig = -sig;
463  for (i=1; i<argc; i++) {
464  if (killpg(NUM2PIDT(argv[i]), sig) < 0)
465  rb_sys_fail(0);
466  }
467  }
468  else {
469  const rb_pid_t self = (GET_THREAD() == GET_VM()->main_thread) ? getpid() : -1;
470  int wakeup = 0;
471 
472  for (i=1; i<argc; i++) {
473  rb_pid_t pid = NUM2PIDT(argv[i]);
474 
475  if ((sig != 0) && (self != -1) && (pid == self)) {
476  int t;
477  /*
478  * When target pid is self, many caller assume signal will be
479  * delivered immediately and synchronously.
480  */
481  switch (sig) {
482  case SIGSEGV:
483 #ifdef SIGBUS
484  case SIGBUS:
485 #endif
486 #ifdef SIGKILL
487  case SIGKILL:
488 #endif
489 #ifdef SIGILL
490  case SIGILL:
491 #endif
492 #ifdef SIGFPE
493  case SIGFPE:
494 #endif
495 #ifdef SIGSTOP
496  case SIGSTOP:
497 #endif
498  ruby_kill(pid, sig);
499  break;
500  default:
501  t = signal_ignored(sig);
502  if (t) {
503  if (t < 0 && kill(pid, sig))
504  rb_sys_fail(0);
505  break;
506  }
507  signal_enque(sig);
508  wakeup = 1;
509  }
510  }
511  else if (kill(pid, sig) < 0) {
512  rb_sys_fail(0);
513  }
514  }
515  if (wakeup) {
516  rb_threadptr_check_signal(GET_VM()->main_thread);
517  }
518  }
520 
521  return INT2FIX(i-1);
522 }
523 
524 static struct {
527 } signal_buff;
528 
529 #ifdef __dietlibc__
530 #define sighandler_t sh_t
531 #else
532 #define sighandler_t ruby_sighandler_t
533 #endif
534 
535 typedef RETSIGTYPE (*sighandler_t)(int);
536 #ifdef USE_SIGALTSTACK
537 typedef void ruby_sigaction_t(int, siginfo_t*, void*);
538 #define SIGINFO_ARG , siginfo_t *info, void *ctx
539 #define SIGINFO_CTX ctx
540 #else
541 typedef RETSIGTYPE ruby_sigaction_t(int);
542 #define SIGINFO_ARG
543 #define SIGINFO_CTX 0
544 #endif
545 
546 #ifdef USE_SIGALTSTACK
547 int
549 {
550  /* XXX: BSD_vfprintf() uses >1500KiB stack and x86-64 need >5KiB stack. */
551  int size = 16*1024;
552 
553 #ifdef MINSIGSTKSZ
554  if (size < MINSIGSTKSZ)
555  size = MINSIGSTKSZ;
556 #endif
557 #if defined(HAVE_SYSCONF) && defined(_SC_PAGE_SIZE)
558  {
559  int pagesize;
560  pagesize = (int)sysconf(_SC_PAGE_SIZE);
561  if (size < pagesize)
562  size = pagesize;
563  }
564 #endif
565 
566  return size;
567 }
568 
569 /* alternate stack for SIGSEGV */
570 void
571 rb_register_sigaltstack(rb_thread_t *th)
572 {
573  stack_t newSS, oldSS;
574 
575  if (!th->altstack)
576  rb_bug("rb_register_sigaltstack: th->altstack not initialized\n");
577 
578  newSS.ss_sp = th->altstack;
579  newSS.ss_size = rb_sigaltstack_size();
580  newSS.ss_flags = 0;
581 
582  sigaltstack(&newSS, &oldSS); /* ignore error. */
583 }
584 #endif /* USE_SIGALTSTACK */
585 
586 #ifdef POSIX_SIGNAL
587 static sighandler_t
588 ruby_signal(int signum, sighandler_t handler)
589 {
590  struct sigaction sigact, old;
591 
592 #if 0
593  rb_trap_accept_nativethreads[signum] = 0;
594 #endif
595 
596  sigemptyset(&sigact.sa_mask);
597 #ifdef USE_SIGALTSTACK
598  if (handler == SIG_IGN || handler == SIG_DFL) {
599  sigact.sa_handler = handler;
600  sigact.sa_flags = 0;
601  }
602  else {
603  sigact.sa_sigaction = (ruby_sigaction_t*)handler;
604  sigact.sa_flags = SA_SIGINFO;
605  }
606 #else
607  sigact.sa_handler = handler;
608  sigact.sa_flags = 0;
609 #endif
610 
611  switch (signum) {
612 #ifdef SA_NOCLDWAIT
613  case SIGCHLD:
614  if (handler == SIG_IGN)
615  sigact.sa_flags |= SA_NOCLDWAIT;
616  break;
617 #endif
618 #if defined(SA_ONSTACK) && defined(USE_SIGALTSTACK)
619  case SIGSEGV:
620 #ifdef SIGBUS
621  case SIGBUS:
622 #endif
623  sigact.sa_flags |= SA_ONSTACK;
624  break;
625 #endif
626  }
627  (void)VALGRIND_MAKE_MEM_DEFINED(&old, sizeof(old));
628  if (sigaction(signum, &sigact, &old) < 0) {
629  return SIG_ERR;
630  }
631  if (old.sa_flags & SA_SIGINFO)
632  return (sighandler_t)old.sa_sigaction;
633  else
634  return old.sa_handler;
635 }
636 
638 posix_signal(int signum, sighandler_t handler)
639 {
640  return ruby_signal(signum, handler);
641 }
642 
643 #elif defined _WIN32
644 static inline sighandler_t
645 ruby_signal(int signum, sighandler_t handler)
646 {
647  if (signum == SIGKILL) {
648  errno = EINVAL;
649  return SIG_ERR;
650  }
651  return signal(signum, handler);
652 }
653 
654 #else /* !POSIX_SIGNAL */
655 #define ruby_signal(sig,handler) (/* rb_trap_accept_nativethreads[(sig)] = 0,*/ signal((sig),(handler)))
656 #if 0 /* def HAVE_NATIVETHREAD */
657 static sighandler_t
658 ruby_nativethread_signal(int signum, sighandler_t handler)
659 {
660  sighandler_t old;
661 
662  old = signal(signum, handler);
663  rb_trap_accept_nativethreads[signum] = 1;
664  return old;
665 }
666 #endif
667 #endif
668 
669 static int
671 {
673 #ifdef POSIX_SIGNAL
674  struct sigaction old;
675  (void)VALGRIND_MAKE_MEM_DEFINED(&old, sizeof(old));
676  if (sigaction(sig, NULL, &old) < 0) return FALSE;
677  func = old.sa_handler;
678 #else
679  sighandler_t old = signal(sig, SIG_DFL);
680  signal(sig, old);
681  func = old;
682 #endif
683  if (func == SIG_IGN) return 1;
684  return func == sighandler ? 0 : -1;
685 }
686 
687 static void
688 signal_enque(int sig)
689 {
690  ATOMIC_INC(signal_buff.cnt[sig]);
691  ATOMIC_INC(signal_buff.size);
692 }
693 
694 static RETSIGTYPE
695 sighandler(int sig)
696 {
697  int old_errnum = errno;
698 
699  signal_enque(sig);
701 #if !defined(BSD_SIGNAL) && !defined(POSIX_SIGNAL)
702  ruby_signal(sig, sighandler);
703 #endif
704 
705  errno = old_errnum;
706 }
707 
708 int
710 {
711  return signal_buff.size;
712 }
713 
714 #if HAVE_PTHREAD_H
715 #include <pthread.h>
716 #endif
717 
718 static void
720 {
721 #ifdef HAVE_PTHREAD_SIGMASK
722  sigset_t mask;
723  sigfillset(&mask);
724  pthread_sigmask(SIG_SETMASK, &mask, NULL);
725 #endif
726 }
727 
728 static void
730 {
731 #ifdef HAVE_PTHREAD_SIGMASK
732  sigset_t mask;
733  sigemptyset(&mask);
734  pthread_sigmask(SIG_SETMASK, &mask, NULL);
735 #endif
736 }
737 
738 int
740 {
741  int i, sig = 0;
742 
743  if (signal_buff.size != 0) {
744  for (i=1; i<RUBY_NSIG; i++) {
745  if (signal_buff.cnt[i] > 0) {
746  ATOMIC_DEC(signal_buff.cnt[i]);
747  ATOMIC_DEC(signal_buff.size);
748  sig = i;
749  break;
750  }
751  }
752  }
753  return sig;
754 }
755 
756 #if defined SIGSEGV || defined SIGBUS || defined SIGILL || defined SIGFPE
757 static const char *received_signal;
758 # define clear_received_signal() (void)(ruby_disable_gc = 0, received_signal = 0)
759 #else
760 # define clear_received_signal() ((void)0)
761 #endif
762 
763 #if defined(USE_SIGALTSTACK) || defined(_WIN32)
765 # if defined __HAIKU__
766 # define USE_UCONTEXT_REG 1
767 # elif !(defined(HAVE_UCONTEXT_H) && (defined __i386__ || defined __x86_64__ || defined __amd64__))
768 # elif defined __linux__
769 # define USE_UCONTEXT_REG 1
770 # elif defined __APPLE__
771 # define USE_UCONTEXT_REG 1
772 # elif defined __FreeBSD__
773 # define USE_UCONTEXT_REG 1
774 # endif
775 # ifdef USE_UCONTEXT_REG
776 static void
777 check_stack_overflow(const uintptr_t addr, const ucontext_t *ctx)
778 {
779  const DEFINE_MCONTEXT_PTR(mctx, ctx);
780 # if defined __linux__
781 # if defined REG_RSP
782  const greg_t sp = mctx->gregs[REG_RSP];
783  const greg_t bp = mctx->gregs[REG_RBP];
784 # else
785  const greg_t sp = mctx->gregs[REG_ESP];
786  const greg_t bp = mctx->gregs[REG_EBP];
787 # endif
788 # elif defined __APPLE__
789 # if defined(__LP64__)
790  const uintptr_t sp = mctx->__ss.__rsp;
791  const uintptr_t bp = mctx->__ss.__rbp;
792 # else
793  const uintptr_t sp = mctx->__ss.__esp;
794  const uintptr_t bp = mctx->__ss.__ebp;
795 # endif
796 # elif defined __FreeBSD__
797 # if defined(__amd64__)
798  const __register_t sp = mctx->mc_rsp;
799  const __register_t bp = mctx->mc_rbp;
800 # else
801  const __register_t sp = mctx->mc_esp;
802  const __register_t bp = mctx->mc_ebp;
803 # endif
804 # elif defined __HAIKU__
805 # if defined(__amd64__)
806  const unsigned long sp = mctx->rsp;
807  const unsigned long bp = mctx->rbp;
808 # else
809  const unsigned long sp = mctx->esp;
810  const unsigned long bp = mctx->ebp;
811 # endif
812 # endif
813  enum {pagesize = 4096};
814  const uintptr_t sp_page = (uintptr_t)sp / pagesize;
815  const uintptr_t bp_page = (uintptr_t)bp / pagesize;
816  const uintptr_t fault_page = addr / pagesize;
817 
818  /* SP in ucontext is not decremented yet when `push` failed, so
819  * the fault page can be the next. */
820  if (sp_page == fault_page || sp_page == fault_page + 1 ||
821  sp_page <= fault_page && fault_page <= bp_page) {
823  if ((uintptr_t)th->tag->buf / pagesize == sp_page) {
824  /* drop the last tag if it is close to the fault,
825  * otherwise it can cause stack overflow again at the same
826  * place. */
827  th->tag = th->tag->prev;
828  }
831  }
832 }
833 # else
834 static void
835 check_stack_overflow(const void *addr)
836 {
837  int ruby_stack_overflowed_p(const rb_thread_t *, const void *);
839  if (ruby_stack_overflowed_p(th, addr)) {
842  }
843 }
844 # endif
845 # ifdef _WIN32
846 # define CHECK_STACK_OVERFLOW() check_stack_overflow(0)
847 # else
848 # define FAULT_ADDRESS info->si_addr
849 # ifdef USE_UCONTEXT_REG
850 # define CHECK_STACK_OVERFLOW() check_stack_overflow((uintptr_t)FAULT_ADDRESS, ctx)
851 # else
852 # define CHECK_STACK_OVERFLOW() check_stack_overflow(FAULT_ADDRESS)
853 # endif
854 # define MESSAGE_FAULT_ADDRESS " at %p", FAULT_ADDRESS
855 # endif
856 #else
857 # define CHECK_STACK_OVERFLOW() (void)0
858 #endif
859 #ifndef MESSAGE_FAULT_ADDRESS
860 # define MESSAGE_FAULT_ADDRESS
861 #endif
862 
863 #if defined SIGSEGV || defined SIGBUS || defined SIGILL || defined SIGFPE
864 NOINLINE(static void check_reserved_signal_(const char *name, size_t name_len));
865 /* noinine to reduce stack usage in signal handers */
866 
867 #define check_reserved_signal(name) check_reserved_signal_(name, sizeof(name)-1)
868 
869 #ifdef SIGBUS
870 static RETSIGTYPE
871 sigbus(int sig SIGINFO_ARG)
872 {
873  check_reserved_signal("BUS");
874 /*
875  * Mac OS X makes KERN_PROTECTION_FAILURE when thread touch guard page.
876  * and it's delivered as SIGBUS instead of SIGSEGV to userland. It's crazy
877  * wrong IMHO. but anyway we have to care it. Sigh.
878  */
879  /* Seems Linux also delivers SIGBUS. */
880 #if defined __APPLE__ || defined __linux__
882 #endif
884 }
885 #endif
886 
887 static void
888 ruby_abort(void)
889 {
890 #ifdef __sun
891  /* Solaris's abort() is async signal unsafe. Of course, it is not
892  * POSIX compliant.
893  */
894  raise(SIGABRT);
895 #else
896  abort();
897 #endif
898 
899 }
900 
901 #ifdef SIGSEGV
902 static RETSIGTYPE
903 sigsegv(int sig SIGINFO_ARG)
904 {
905  check_reserved_signal("SEGV");
907  rb_bug_context(SIGINFO_CTX, "Segmentation fault" MESSAGE_FAULT_ADDRESS);
908 }
909 #endif
910 
911 #ifdef SIGILL
912 static RETSIGTYPE
913 sigill(int sig SIGINFO_ARG)
914 {
915  check_reserved_signal("ILL");
916 #if defined __APPLE__
918 #endif
919  rb_bug_context(SIGINFO_CTX, "Illegal instruction" MESSAGE_FAULT_ADDRESS);
920 }
921 #endif
922 
923 static void
924 check_reserved_signal_(const char *name, size_t name_len)
925 {
926  const char *prev = ATOMIC_PTR_EXCHANGE(received_signal, name);
927 
928  if (prev) {
929  ssize_t RB_UNUSED_VAR(err);
930 #define NOZ(name, str) name[sizeof(str)-1] = str
931  static const char NOZ(msg1, " received in ");
932  static const char NOZ(msg2, " handler\n");
933 
934 #ifdef HAVE_WRITEV
935  struct iovec iov[4];
936 
937  iov[0].iov_base = (void *)name;
938  iov[0].iov_len = name_len;
939  iov[1].iov_base = (void *)msg1;
940  iov[1].iov_len = sizeof(msg1);
941  iov[2].iov_base = (void *)prev;
942  iov[2].iov_len = strlen(prev);
943  iov[3].iov_base = (void *)msg2;
944  iov[3].iov_len = sizeof(msg2);
945  err = writev(2, iov, 4);
946 #else
947  err = write(2, name, name_len);
948  err = write(2, msg1, sizeof(msg1));
949  err = write(2, prev, strlen(prev));
950  err = write(2, msg2, sizeof(msg2));
951 #endif
952  ruby_abort();
953  }
954 
955  ruby_disable_gc = 1;
956 }
957 #endif
958 
959 #if defined SIGPIPE || defined SIGSYS
960 static RETSIGTYPE
961 sig_do_nothing(int sig)
962 {
963 }
964 #endif
965 
966 static void
967 signal_exec(VALUE cmd, int safe, int sig)
968 {
969  rb_thread_t *cur_th = GET_THREAD();
970  volatile unsigned long old_interrupt_mask = cur_th->interrupt_mask;
971  int state;
972 
973  /*
974  * workaround the following race:
975  * 1. signal_enque queues signal for execution
976  * 2. user calls trap(sig, "IGNORE"), setting SIG_IGN
977  * 3. rb_signal_exec runs on queued signal
978  */
979  if (IMMEDIATE_P(cmd))
980  return;
981 
983  TH_PUSH_TAG(cur_th);
984  if ((state = EXEC_TAG()) == 0) {
985  VALUE signum = INT2NUM(sig);
986  rb_eval_cmd(cmd, rb_ary_new3(1, signum), safe);
987  }
988  TH_POP_TAG();
989  cur_th = GET_THREAD();
990  cur_th->interrupt_mask = old_interrupt_mask;
991 
992  if (state) {
993  /* XXX: should be replaced with rb_threadptr_pending_interrupt_enque() */
994  TH_JUMP_TAG(cur_th, state);
995  }
996 }
997 
998 void
1000 {
1001  rb_vm_t *vm = GET_VM();
1002  VALUE trap_exit = vm->trap_list[0].cmd;
1003 
1004  if (trap_exit) {
1005  vm->trap_list[0].cmd = 0;
1006  signal_exec(trap_exit, vm->trap_list[0].safe, 0);
1007  }
1008 }
1009 
1010 void
1012 {
1013  rb_vm_t *vm = GET_VM();
1014  VALUE cmd = vm->trap_list[sig].cmd;
1015  int safe = vm->trap_list[sig].safe;
1016 
1017  if (cmd == 0) {
1018  switch (sig) {
1019  case SIGINT:
1020  rb_interrupt();
1021  break;
1022 #ifdef SIGHUP
1023  case SIGHUP:
1024 #endif
1025 #ifdef SIGQUIT
1026  case SIGQUIT:
1027 #endif
1028 #ifdef SIGTERM
1029  case SIGTERM:
1030 #endif
1031 #ifdef SIGALRM
1032  case SIGALRM:
1033 #endif
1034 #ifdef SIGUSR1
1035  case SIGUSR1:
1036 #endif
1037 #ifdef SIGUSR2
1038  case SIGUSR2:
1039 #endif
1040  rb_threadptr_signal_raise(th, sig);
1041  break;
1042  }
1043  }
1044  else if (cmd == Qundef) {
1046  }
1047  else {
1048  signal_exec(cmd, safe, sig);
1049  }
1050 }
1051 
1052 static sighandler_t
1054 {
1056  switch (sig) {
1057  case SIGINT:
1058 #ifdef SIGHUP
1059  case SIGHUP:
1060 #endif
1061 #ifdef SIGQUIT
1062  case SIGQUIT:
1063 #endif
1064 #ifdef SIGTERM
1065  case SIGTERM:
1066 #endif
1067 #ifdef SIGALRM
1068  case SIGALRM:
1069 #endif
1070 #ifdef SIGUSR1
1071  case SIGUSR1:
1072 #endif
1073 #ifdef SIGUSR2
1074  case SIGUSR2:
1075 #endif
1076  func = sighandler;
1077  break;
1078 #ifdef SIGBUS
1079  case SIGBUS:
1080  func = (sighandler_t)sigbus;
1081  break;
1082 #endif
1083 #ifdef SIGSEGV
1084  case SIGSEGV:
1085  func = (sighandler_t)sigsegv;
1086  break;
1087 #endif
1088 #ifdef SIGPIPE
1089  case SIGPIPE:
1090  func = sig_do_nothing;
1091  break;
1092 #endif
1093 #ifdef SIGSYS
1094  case SIGSYS:
1095  func = sig_do_nothing;
1096  break;
1097 #endif
1098  default:
1099  func = SIG_DFL;
1100  break;
1101  }
1102 
1103  return func;
1104 }
1105 
1106 static sighandler_t
1107 trap_handler(VALUE *cmd, int sig)
1108 {
1110  VALUE command;
1111 
1112  if (NIL_P(*cmd)) {
1113  func = SIG_IGN;
1114  }
1115  else {
1116  command = rb_check_string_type(*cmd);
1117  if (NIL_P(command) && SYMBOL_P(*cmd)) {
1118  command = rb_sym2str(*cmd);
1119  if (!command) rb_raise(rb_eArgError, "bad handler");
1120  }
1121  if (!NIL_P(command)) {
1122  const char *cptr;
1123  long len;
1124  SafeStringValue(command); /* taint check */
1125  *cmd = command;
1126  RSTRING_GETMEM(command, cptr, len);
1127  switch (len) {
1128  case 0:
1129  goto sig_ign;
1130  break;
1131  case 14:
1132  if (memcmp(cptr, "SYSTEM_DEFAULT", 14) == 0) {
1133  func = SIG_DFL;
1134  *cmd = 0;
1135  }
1136  break;
1137  case 7:
1138  if (memcmp(cptr, "SIG_IGN", 7) == 0) {
1139 sig_ign:
1140  func = SIG_IGN;
1141  *cmd = Qtrue;
1142  }
1143  else if (memcmp(cptr, "SIG_DFL", 7) == 0) {
1144 sig_dfl:
1145  func = default_handler(sig);
1146  *cmd = 0;
1147  }
1148  else if (memcmp(cptr, "DEFAULT", 7) == 0) {
1149  goto sig_dfl;
1150  }
1151  break;
1152  case 6:
1153  if (memcmp(cptr, "IGNORE", 6) == 0) {
1154  goto sig_ign;
1155  }
1156  break;
1157  case 4:
1158  if (memcmp(cptr, "EXIT", 4) == 0) {
1159  *cmd = Qundef;
1160  }
1161  break;
1162  }
1163  }
1164  else {
1165  rb_proc_t *proc;
1166  GetProcPtr(*cmd, proc);
1167  (void)proc;
1168  }
1169  }
1170 
1171  return func;
1172 }
1173 
1174 static int
1176 {
1177  int sig = -1;
1178  const char *s;
1179 
1180  switch (TYPE(vsig)) {
1181  case T_FIXNUM:
1182  sig = FIX2INT(vsig);
1183  if (sig < 0 || sig >= NSIG) {
1184  rb_raise(rb_eArgError, "invalid signal number (%d)", sig);
1185  }
1186  break;
1187 
1188  case T_SYMBOL:
1189  vsig = rb_sym2str(vsig);
1190  s = RSTRING_PTR(vsig);
1191  goto str_signal;
1192 
1193  default:
1194  s = StringValuePtr(vsig);
1195 
1196  str_signal:
1197  if (strncmp(signame_prefix, s, sizeof(signame_prefix)) == 0)
1198  s += 3;
1199  sig = signm2signo(s);
1200  if (sig == 0 && strcmp(s, "EXIT") != 0) {
1201  long ofs = s - RSTRING_PTR(vsig);
1202  if (ofs) vsig = rb_str_subseq(vsig, ofs, RSTRING_LEN(vsig)-ofs);
1203  rb_raise(rb_eArgError, "unsupported signal SIG%"PRIsVALUE"", vsig);
1204  }
1205  }
1206  return sig;
1207 }
1208 
1209 static VALUE
1210 trap(int sig, sighandler_t func, VALUE command)
1211 {
1212  sighandler_t oldfunc;
1213  VALUE oldcmd;
1214  rb_vm_t *vm = GET_VM();
1215 
1216  /*
1217  * Be careful. ruby_signal() and trap_list[sig].cmd must be changed
1218  * atomically. In current implementation, we only need to don't call
1219  * RUBY_VM_CHECK_INTS().
1220  */
1221  if (sig == 0) {
1222  oldfunc = SIG_ERR;
1223  }
1224  else {
1225  oldfunc = ruby_signal(sig, func);
1226  if (oldfunc == SIG_ERR) rb_sys_fail_str(rb_signo2signm(sig));
1227  }
1228  oldcmd = vm->trap_list[sig].cmd;
1229  switch (oldcmd) {
1230  case 0:
1231  case Qtrue:
1232  if (oldfunc == SIG_IGN) oldcmd = rb_str_new2("IGNORE");
1233  else if (oldfunc == SIG_DFL) oldcmd = rb_str_new2("SYSTEM_DEFAULT");
1234  else if (oldfunc == sighandler) oldcmd = rb_str_new2("DEFAULT");
1235  else oldcmd = Qnil;
1236  break;
1237  case Qnil:
1238  break;
1239  case Qundef:
1240  oldcmd = rb_str_new2("EXIT");
1241  break;
1242  }
1243 
1244  vm->trap_list[sig].cmd = command;
1245  vm->trap_list[sig].safe = rb_safe_level();
1246 
1247  return oldcmd;
1248 }
1249 
1250 static int
1252 {
1253 /* Synchronous signal can't deliver to main thread */
1254 #ifdef SIGSEGV
1255  if (signo == SIGSEGV)
1256  return 1;
1257 #endif
1258 #ifdef SIGBUS
1259  if (signo == SIGBUS)
1260  return 1;
1261 #endif
1262 #ifdef SIGILL
1263  if (signo == SIGILL)
1264  return 1;
1265 #endif
1266 #ifdef SIGFPE
1267  if (signo == SIGFPE)
1268  return 1;
1269 #endif
1270 
1271 /* used ubf internal see thread_pthread.c. */
1272 #ifdef SIGVTALRM
1273  if (signo == SIGVTALRM)
1274  return 1;
1275 #endif
1276 
1277  return 0;
1278 }
1279 
1280 /*
1281  * call-seq:
1282  * Signal.trap( signal, command ) -> obj
1283  * Signal.trap( signal ) {| | block } -> obj
1284  *
1285  * Specifies the handling of signals. The first parameter is a signal
1286  * name (a string such as ``SIGALRM'', ``SIGUSR1'', and so on) or a
1287  * signal number. The characters ``SIG'' may be omitted from the
1288  * signal name. The command or block specifies code to be run when the
1289  * signal is raised.
1290  * If the command is the string ``IGNORE'' or ``SIG_IGN'', the signal
1291  * will be ignored.
1292  * If the command is ``DEFAULT'' or ``SIG_DFL'', the Ruby's default handler
1293  * will be invoked.
1294  * If the command is ``EXIT'', the script will be terminated by the signal.
1295  * If the command is ``SYSTEM_DEFAULT'', the operating system's default
1296  * handler will be invoked.
1297  * Otherwise, the given command or block will be run.
1298  * The special signal name ``EXIT'' or signal number zero will be
1299  * invoked just prior to program termination.
1300  * trap returns the previous handler for the given signal.
1301  *
1302  * Signal.trap(0, proc { puts "Terminating: #{$$}" })
1303  * Signal.trap("CLD") { puts "Child died" }
1304  * fork && Process.wait
1305  *
1306  * produces:
1307  * Terminating: 27461
1308  * Child died
1309  * Terminating: 27460
1310  */
1311 static VALUE
1313 {
1314  int sig;
1316  VALUE cmd;
1317 
1318  rb_check_arity(argc, 1, 2);
1319 
1320  sig = trap_signm(argv[0]);
1321  if (reserved_signal_p(sig)) {
1322  const char *name = signo2signm(sig);
1323  if (name)
1324  rb_raise(rb_eArgError, "can't trap reserved signal: SIG%s", name);
1325  else
1326  rb_raise(rb_eArgError, "can't trap reserved signal: %d", sig);
1327  }
1328 
1329  if (argc == 1) {
1330  cmd = rb_block_proc();
1331  func = sighandler;
1332  }
1333  else {
1334  cmd = argv[1];
1335  func = trap_handler(&cmd, sig);
1336  }
1337 
1338  if (OBJ_TAINTED(cmd)) {
1339  rb_raise(rb_eSecurityError, "Insecure: tainted signal trap");
1340  }
1341 
1342  return trap(sig, func, cmd);
1343 }
1344 
1345 /*
1346  * call-seq:
1347  * Signal.list -> a_hash
1348  *
1349  * Returns a list of signal names mapped to the corresponding
1350  * underlying signal numbers.
1351  *
1352  * Signal.list #=> {"EXIT"=>0, "HUP"=>1, "INT"=>2, "QUIT"=>3, "ILL"=>4, "TRAP"=>5, "IOT"=>6, "ABRT"=>6, "FPE"=>8, "KILL"=>9, "BUS"=>7, "SEGV"=>11, "SYS"=>31, "PIPE"=>13, "ALRM"=>14, "TERM"=>15, "URG"=>23, "STOP"=>19, "TSTP"=>20, "CONT"=>18, "CHLD"=>17, "CLD"=>17, "TTIN"=>21, "TTOU"=>22, "IO"=>29, "XCPU"=>24, "XFSZ"=>25, "VTALRM"=>26, "PROF"=>27, "WINCH"=>28, "USR1"=>10, "USR2"=>12, "PWR"=>30, "POLL"=>29}
1353  */
1354 static VALUE
1356 {
1357  VALUE h = rb_hash_new();
1358  const struct signals *sigs;
1359 
1360  for (sigs = siglist; sigs->signm; sigs++) {
1361  rb_hash_aset(h, rb_fstring_cstr(sigs->signm), INT2FIX(sigs->signo));
1362  }
1363  return h;
1364 }
1365 
1366 static int
1367 install_sighandler(int signum, sighandler_t handler)
1368 {
1369  sighandler_t old;
1370 
1371  old = ruby_signal(signum, handler);
1372  if (old == SIG_ERR) return -1;
1373  /* signal handler should be inherited during exec. */
1374  if (old != SIG_DFL) {
1375  ruby_signal(signum, old);
1376  }
1377  return 0;
1378 }
1379 #ifndef __native_client__
1380 # define install_sighandler(signum, handler) (install_sighandler(signum, handler) ? rb_bug(#signum) : (void)0)
1381 #endif
1382 
1383 #if defined(SIGCLD) || defined(SIGCHLD)
1384 static int
1385 init_sigchld(int sig)
1386 {
1387  sighandler_t oldfunc;
1388 
1389  oldfunc = ruby_signal(sig, SIG_DFL);
1390  if (oldfunc == SIG_ERR) return -1;
1391  if (oldfunc != SIG_DFL && oldfunc != SIG_IGN) {
1392  ruby_signal(sig, oldfunc);
1393  }
1394  else {
1395  GET_VM()->trap_list[sig].cmd = 0;
1396  }
1397  return 0;
1398 }
1399 # ifndef __native_client__
1400 # define init_sigchld(signum) (init_sigchld(signum) ? rb_bug(#signum) : (void)0)
1401 # endif
1402 #endif
1403 
1404 void
1406 {
1407  sighandler_t oldfunc;
1408 
1409  oldfunc = ruby_signal(SIGINT, SIG_IGN);
1410  if (oldfunc == sighandler) {
1411  ruby_signal(SIGINT, SIG_DFL);
1412  }
1413 }
1414 
1415 
1417 #ifndef RUBY_DEBUG_ENV
1418 #define ruby_enable_coredump 0
1419 #endif
1420 
1421 /*
1422  * Many operating systems allow signals to be sent to running
1423  * processes. Some signals have a defined effect on the process, while
1424  * others may be trapped at the code level and acted upon. For
1425  * example, your process may trap the USR1 signal and use it to toggle
1426  * debugging, and may use TERM to initiate a controlled shutdown.
1427  *
1428  * pid = fork do
1429  * Signal.trap("USR1") do
1430  * $debug = !$debug
1431  * puts "Debug now: #$debug"
1432  * end
1433  * Signal.trap("TERM") do
1434  * puts "Terminating..."
1435  * shutdown()
1436  * end
1437  * # . . . do some work . . .
1438  * end
1439  *
1440  * Process.detach(pid)
1441  *
1442  * # Controlling program:
1443  * Process.kill("USR1", pid)
1444  * # ...
1445  * Process.kill("USR1", pid)
1446  * # ...
1447  * Process.kill("TERM", pid)
1448  *
1449  * produces:
1450  * Debug now: true
1451  * Debug now: false
1452  * Terminating...
1453  *
1454  * The list of available signal names and their interpretation is
1455  * system dependent. Signal delivery semantics may also vary between
1456  * systems; in particular signal delivery may not always be reliable.
1457  */
1458 void
1460 {
1461  VALUE mSignal = rb_define_module("Signal");
1462 
1463  rb_define_global_function("trap", sig_trap, -1);
1464  rb_define_module_function(mSignal, "trap", sig_trap, -1);
1465  rb_define_module_function(mSignal, "list", sig_list, 0);
1466  rb_define_module_function(mSignal, "signame", sig_signame, 1);
1467 
1468  rb_define_method(rb_eSignal, "initialize", esignal_init, -1);
1470  rb_alias(rb_eSignal, rb_intern_const("signm"), rb_intern_const("message"));
1471  rb_define_method(rb_eInterrupt, "initialize", interrupt_init, -1);
1472 
1473  /* At this time, there is no subthread. Then sigmask guarantee atomics. */
1475 
1477 #ifdef SIGHUP
1478  install_sighandler(SIGHUP, sighandler);
1479 #endif
1480 #ifdef SIGQUIT
1481  install_sighandler(SIGQUIT, sighandler);
1482 #endif
1483 #ifdef SIGTERM
1484  install_sighandler(SIGTERM, sighandler);
1485 #endif
1486 #ifdef SIGALRM
1487  install_sighandler(SIGALRM, sighandler);
1488 #endif
1489 #ifdef SIGUSR1
1490  install_sighandler(SIGUSR1, sighandler);
1491 #endif
1492 #ifdef SIGUSR2
1493  install_sighandler(SIGUSR2, sighandler);
1494 #endif
1495 
1496  if (!ruby_enable_coredump) {
1497 #ifdef SIGBUS
1498  install_sighandler(SIGBUS, (sighandler_t)sigbus);
1499 #endif
1500 #ifdef SIGILL
1501  install_sighandler(SIGILL, (sighandler_t)sigill);
1502 #endif
1503 #ifdef SIGSEGV
1504 # ifdef USE_SIGALTSTACK
1505  rb_register_sigaltstack(GET_THREAD());
1506 # endif
1507  install_sighandler(SIGSEGV, (sighandler_t)sigsegv);
1508 #endif
1509  }
1510 #ifdef SIGPIPE
1511  install_sighandler(SIGPIPE, sig_do_nothing);
1512 #endif
1513 #ifdef SIGSYS
1514  install_sighandler(SIGSYS, sig_do_nothing);
1515 #endif
1516 
1517 #if defined(SIGCLD)
1518  init_sigchld(SIGCLD);
1519 #elif defined(SIGCHLD)
1520  init_sigchld(SIGCHLD);
1521 #endif
1522 
1524 }
static VALUE rb_signo2signm(int signo)
Definition: signal.c:268
#define T_SYMBOL
Definition: ruby.h:508
static VALUE sig_list(void)
Definition: signal.c:1355
static int cmp(VALUE x, VALUE y)
Definition: time.c:57
static void signal_exec(VALUE cmd, int safe, int sig)
Definition: signal.c:967
#define MESSAGE_FAULT_ADDRESS
Definition: signal.c:860
static void signal_enque(int sig)
Definition: signal.c:688
const char * ruby_signal_name(int no)
Definition: signal.c:262
void rb_interrupt(void)
Definition: eval.c:638
void ruby_thread_stack_overflow(rb_thread_t *th)
Definition: thread.c:2167
void rb_bug(const char *fmt,...)
Definition: error.c:482
#define FALSE
Definition: nkf.h:174
size_t strlen(const char *)
#define INT2NUM(x)
Definition: ruby.h:1538
static VALUE trap(int sig, sighandler_t func, VALUE command)
Definition: signal.c:1210
void * iov_base
Definition: win32.h:203
#define T_FIXNUM
Definition: ruby.h:503
VALUE cmd
Definition: vm_core.h:521
rb_atomic_t ruby_atomic_exchange(rb_atomic_t *ptr, rb_atomic_t val)
Definition: signal.c:53
VALUE rb_eSignal
Definition: error.c:758
const char * signm
Definition: signal.c:77
#define NUM2INT(x)
Definition: ruby.h:684
#define GetProcPtr(obj, ptr)
Definition: vm_core.h:863
#define NUM2PIDT(v)
Definition: ruby.h:326
VALUE rb_fstring_cstr(const char *str)
Definition: string.c:387
static int signal_ignored(int sig)
Definition: signal.c:670
#define SIGINFO_ARG
Definition: signal.c:542
static VALUE interrupt_init(int argc, VALUE *argv, VALUE self)
Definition: signal.c:350
#define Qtrue
Definition: ruby.h:437
static void rb_enable_interrupt(void)
Definition: signal.c:729
void rb_threadptr_signal_raise(rb_thread_t *th, int sig)
Definition: thread.c:2142
#define RUBY_NSIG
Definition: vm_core.h:98
#define TH_JUMP_TAG(th, st)
Definition: eval_intern.h:186
#define rb_check_arity
Definition: intern.h:303
SSL_METHOD *(* func)(void)
Definition: ossl_ssl.c:54
void rb_trap_exit(void)
Definition: signal.c:999
RETSIGTYPE ruby_sigaction_t(int)
Definition: signal.c:541
void rb_signal_exec(rb_thread_t *th, int sig)
Definition: signal.c:1011
#define ruby_enable_coredump
Definition: signal.c:1418
int kill(int, int)
Definition: win32.c:4724
void rb_raise(VALUE exc, const char *fmt,...)
Definition: error.c:2207
VALUE rb_ivar_get(VALUE, ID)
Definition: variable.c:1260
#define RSTRING_GETMEM(str, ptrvar, lenvar)
Definition: ruby.h:991
#define SIGKILL
Definition: win32.h:463
VALUE rb_eSecurityError
Definition: error.c:771
rb_atomic_t size
Definition: signal.c:526
void ruby_default_signal(int sig)
Definition: signal.c:360
int ruby_disable_gc
Definition: gc.c:814
#define ATOMIC_PTR_EXCHANGE(var, val)
Definition: ruby_atomic.h:177
static VALUE esignal_signo(VALUE self)
Definition: signal.c:343
void rb_define_global_function(const char *name, VALUE(*func)(ANYARGS), int argc)
Defines a global function.
Definition: class.c:1745
VALUE rb_check_to_integer(VALUE, const char *)
Definition: object.c:2673
#define sighandler_t
Definition: signal.c:532
static sighandler_t trap_handler(VALUE *cmd, int sig)
Definition: signal.c:1107
#define OBJ_TAINTED(x)
Definition: ruby.h:1298
#define NORETURN(x)
Definition: defines.h:34
const char * rb_obj_classname(VALUE)
Definition: variable.c:458
#define GET_THREAD()
Definition: vm_core.h:1513
static VALUE sig_signame(VALUE recv, VALUE signo)
Definition: signal.c:254
#define TH_POP_TAG()
Definition: eval_intern.h:137
#define install_sighandler(signum, handler)
Definition: signal.c:1380
static int reserved_signal_p(int signo)
Definition: signal.c:1251
#define ATOMIC_DEC(var)
Definition: ruby_atomic.h:129
void rb_thread_wakeup_timer_thread(void)
VALUE rb_hash_aset(VALUE hash, VALUE key, VALUE val)
Definition: hash.c:1576
#define EXEC_TAG()
Definition: eval_intern.h:183
#define val
int signo
Definition: signal.c:78
struct rb_vm_struct::@200 trap_list[RUBY_NSIG]
static RETSIGTYPE sighandler(int sig)
Definition: signal.c:695
VALUE rb_thread_current(void)
Definition: thread.c:2504
static const char signame_prefix[3]
Definition: signal.c:215
#define NIL_P(v)
Definition: ruby.h:451
Definition: signal.c:76
static const struct signals siglist[]
void rb_sys_fail_str(VALUE mesg)
Definition: error.c:2332
rb_atomic_t cnt[RUBY_NSIG]
Definition: signal.c:525
VALUE rb_f_kill(int argc, const VALUE *argv)
Definition: signal.c:407
void rb_threadptr_check_signal(rb_thread_t *mth)
Definition: thread.c:4032
#define TYPE(x)
Definition: ruby.h:521
int argc
Definition: ruby.c:183
#define rb_str_new2
Definition: intern.h:857
int err
Definition: win32.c:135
#define RB_UNUSED_VAR(x)
Definition: ruby.h:558
static sighandler_t default_handler(int sig)
Definition: signal.c:1053
#define NOINLINE(x)
Definition: defines.h:46
static VALUE sig_trap(int argc, VALUE *argv)
Definition: signal.c:1312
static int signm2signo(const char *nm)
Definition: signal.c:218
VALUE rb_str_subseq(VALUE, long, long)
Definition: string.c:2324
#define RSTRING_LEN(str)
Definition: ruby.h:978
void rb_define_module_function(VALUE module, const char *name, VALUE(*func)(ANYARGS), int argc)
Defines a module function for module.
Definition: class.c:1731
int errno
void Init_signal(void)
Definition: signal.c:1459
#define id_signo
Definition: signal.c:49
VALUE rb_sprintf(const char *format,...)
Definition: sprintf.c:1440
VALUE rb_hash_new(void)
Definition: hash.c:441
int rb_scan_args(int argc, const VALUE *argv, const char *fmt,...)
Definition: class.c:1919
void rb_thread_execute_interrupts(VALUE th)
Definition: thread.c:2098
VALUE rb_ivar_set(VALUE, ID, VALUE)
Definition: variable.c:1364
#define PRIsVALUE
Definition: ruby.h:135
VALUE rb_eInterrupt
Definition: error.c:757
unsigned long ID
Definition: ruby.h:86
#define Qnil
Definition: ruby.h:438
unsigned int uintptr_t
Definition: win32.h:106
unsigned long VALUE
Definition: ruby.h:85
static const char * signo2signm(int no)
Definition: signal.c:229
rb_thread_t * ruby_current_thread
Definition: vm.c:316
#define VALGRIND_MAKE_MEM_DEFINED(p, n)
Definition: signal.c:40
static void rb_disable_interrupt(void)
Definition: signal.c:719
#define FIX2INT(x)
Definition: ruby.h:686
Definition: win32.h:202
void rb_alias(VALUE, ID, ID)
Definition: vm_method.c:1526
#define rb_ary_new3
Definition: intern.h:91
#define TH_PUSH_TAG(th)
Definition: eval_intern.h:131
VALUE rb_call_super(int, const VALUE *)
Definition: vm_eval.c:287
VALUE rb_str_new_cstr(const char *)
Definition: string.c:770
int memcmp(const void *s1, const void *s2, size_t len)
Definition: memcmp.c:7
int rb_sigaltstack_size(void)
#define NSIG
Definition: vm_core.h:95
void rb_sys_fail(const char *mesg)
Definition: error.c:2326
static struct @173 signal_buff
#define ATOMIC_INC(var)
Definition: ruby_atomic.h:128
register unsigned int len
Definition: zonetab.h:51
#define IMMEDIATE_P(x)
Definition: ruby.h:371
int rb_get_next_signal(void)
Definition: signal.c:739
#define RSTRING_PTR(str)
Definition: ruby.h:982
rb_atomic_t ruby_atomic_compare_and_swap(rb_atomic_t *ptr, rb_atomic_t cmp, rb_atomic_t newval)
Definition: signal.c:61
#define CHECK_STACK_OVERFLOW()
Definition: signal.c:857
#define INT2FIX(i)
Definition: ruby.h:232
#define UNLIMITED_ARGUMENTS
Definition: intern.h:44
int rb_safe_level(void)
Definition: safe.c:35
unsigned long interrupt_mask
Definition: vm_core.h:762
VALUE rb_block_proc(void)
Definition: proc.c:787
void ruby_sig_finalize(void)
Definition: signal.c:1405
VALUE rb_check_string_type(VALUE)
Definition: string.c:2164
int rb_signal_buff_size(void)
Definition: signal.c:709
#define T_STRING
Definition: ruby.h:496
static VALUE esignal_init(int argc, VALUE *argv, VALUE self)
Definition: signal.c:289
VALUE rb_eval_cmd(VALUE, VALUE, int)
Definition: vm_eval.c:1558
#define SafeStringValue(v)
Definition: ruby.h:574
int rb_atomic_t
Definition: ruby_atomic.h:120
void ruby_kill(rb_pid_t pid, int sig)
Definition: thread.c:5048
const char * name
Definition: nkf.c:208
static int trap_signm(VALUE vsig)
Definition: signal.c:1175
rb_jmpbuf_t buf
Definition: vm_core.h:665
#define StringValuePtr(v)
Definition: ruby.h:570
ID ruby_static_id_signo
Definition: eval.c:27
struct rb_vm_tag * tag
Definition: vm_core.h:769
#define killpg(pg, sig)
#define ruby_signal(sig, handler)
Definition: signal.c:655
struct rb_vm_tag * prev
Definition: vm_core.h:666
#define rb_intern_const(str)
Definition: ruby.h:1756
void rb_bug_context(const void *ctx, const char *fmt,...)
Definition: error.c:497
VALUE rb_define_module(const char *name)
Definition: class.c:768
#define SYMBOL_P(x)
Definition: ruby.h:382
#define clear_received_signal()
Definition: signal.c:760
#define NULL
Definition: _sdbm.c:102
#define Qundef
Definition: ruby.h:439
void rb_define_method(VALUE klass, const char *name, VALUE(*func)(ANYARGS), int argc)
Definition: class.c:1515
#define SIGINFO_CTX
Definition: signal.c:543
#define bp()
Definition: vm_debug.h:25
VALUE rb_eArgError
Definition: error.c:763
void rb_threadptr_signal_exit(rb_thread_t *th)
Definition: thread.c:2152
char ** argv
Definition: ruby.c:184
#define StringValue(v)
Definition: ruby.h:569
#define rb_sym2str(sym)
Definition: console.c:107
#define SIGINT
Definition: win32.h:460
#define GET_VM()
Definition: vm_core.h:1507