# Trap in 1.9

**URL:** <https://www.ruby-forum.com/t/trap-in-1-9/105263>\
**Category:** Development\
**Created:** [May 28, 2007, 8:56am UTC](https://www.ruby-forum.com/t/trap-in-1-9/105263 "2007-05-28T08:56:36Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![nobu](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/e9c0ed/32.png) [@nobu](https://www.ruby-forum.com/u/nobu)\
**Post date:** [May 28, 2007, 8:56am UTC](https://www.ruby-forum.com/t/trap-in-1-9/105263/1 "2007-05-28T08:56:36Z")

</div>

e$B$J$+$@$G$9!#e(B

[ruby-dev:30820]e$B$r;n$7$F$$$F5$$E$$$?$N$G$9$,!"e(B1.9e$B$G0J2\<$N%3!\<%Ie(B  
e$B$,e(BSEGVe$B$7$^$9!#e(BQundefe$B$rJV$7$F$$$k$h$&$G$9!#e(B

p trap(:INT, trap(:INT, “EXIT”))

e$B$^$?!"e(Btrap(:EXIT)e$B$@$1$OG$0U$NJ8;zNs$rEO$;$k$^$^$K$J$C$F$$$^$9$,!"e(B  
e$B$d$O$je(BSEGVe$B$7$^$9!#e(B

trap(:EXIT, “p”)

e$B$D$$$G$K!"0z?t$N%A%’%C%/$r@h$K:Q$^$9$h$&$K$7$F$\_$^$7$?!#e(B

# Index: signal.c

— signal.c (revision 12396)  
+++ signal.c (working copy)  
@@ -375,5 +375,4 @@ rb\_f\_kill(int argc, VALUE \*argv)  
static struct {  
VALUE cmd;

- int safe;  
} trap\_list[NSIG];  
static rb\_atomic\_t trap\_pending\_list[NSIG];  
@@ -545,4 +544,13 @@ sigpipe(int sig)  
#endif

+static void  
+signal\_exec(VALUE cmd, int sig)  
+{

- rb\_proc\_t \*proc;
- VALUE signum = INT2FIX(sig);
- GetProcPtr(cmd, proc);
- th\_invoke\_proc(GET\_THREAD(), proc, proc-\>block.self, 1, &signum);  
+}
- 

void  
rb\_trap\_exit(void)  
@@ -553,5 +561,5 @@ rb\_trap\_exit(void)

trap\_list[0].cmd = 0;

- rb\_eval\_cmd(trap\_exit, rb\_ary\_new3(1, INT2FIX(0)),  
trap\_list[0].safe);

- signal\_exec(trap\_exit, 0);  
}  
#endif  
@@ -594,8 +602,5 @@ rb\_signal\_exec(rb\_thread\_t \*th, int sig)  
}  
else {

- rb\_proc\_t \*proc;
- VALUE signum = INT2FIX(sig);
- GetProcPtr(cmd, proc);
- th\_invoke\_proc(th, proc, proc-\>block.self, 1, &signum);

- signal\_exec(cmd, sig);  
}  
}  
@@ -625,21 +630,20 @@ struct trap\_arg {

# endif

#endif

- VALUE sig, cmd;

- int sig;
- sighandler\_t func;
- VALUE cmd;  
};

-static VALUE  
-trap(struct trap\_arg \*arg)  
+static sighandler\_t  
+trap\_handler(VALUE \*cmd)  
{

- sighandler\_t func, oldfunc;
- VALUE command, oldcmd;
- int sig = -1;
- const char \*s;

- sighandler\_t func = 0;
- VALUE command;

- func = sighandler;
- if (NIL\_P(arg-\>cmd)) {

- if (NIL\_P(\*cmd)) {  
func = SIG\_IGN;  
}  
else {

- command = rb\_check\_string\_type(arg-\>cmd);

- command = rb\_check\_string\_type(_cmd);  
if (!NIL\_P(command)) {  
SafeStringValue(command); /_ taint check \*/  
@@ -666,29 +670,47 @@ trap(struct trap\_arg \*arg)  
case 4:  
if (strncmp(RSTRING\_PTR(command), “EXIT”, 4) == 0) {

- 

```
   arg->cmd = Qundef;

```

- 

```
   func = sighandler;

```

- 

```
   *cmd = Qundef;

```

}  
break;  
}
- 

```
 if (!func) {

```

- rb\_raise(rb\_eArgError, “wrong trap - %s”, RSTRING\_PTR(command));
- 

```
 }

```

- }
- else {
- 

```
 rb_proc_t *proc;

```

- 

```
 GetProcPtr(*cmd, proc);

```

- 

```
 func = sighandler;

```

}  
}  
if (func == SIG\_IGN || func == SIG\_DFL) {

- command = 0;
- }
- else {
- command = arg-\>cmd;

- \*cmd = 0;  
}

- switch (TYPE(arg-\>sig)) {

- return func;  
+}
- 

+static int  
+trap\_signm(VALUE vsig)  
+{

- int sig = -1;
- const char \*s;
- 
- switch (TYPE(vsig)) {  
case T\_FIXNUM:

- sig = FIX2INT(arg-\>sig);

- sig = FIX2INT(vsig);

- if (sig \< 0 || sig \>= NSIG) {

- 

```
 rb_raise(rb_eArgError, "invalid signal number (%d)", sig);

```

- }  
break;

- s = rb\_id2name(SYM2ID(arg-\>sig));

- s = rb\_id2name(SYM2ID(vsig));  
if (!s) rb\_raise(rb\_eArgError, “bad signal”);  
goto str\_signal;

- 

```
 case T_STRING:

```

- s = RSTRING\_PTR(arg-\>sig);

- 

```
 default:

```

- s = StringValuePtr(vsig);

@@ -700,7 +722,4 @@ trap(struct trap\_arg \*arg)  
}

- if (sig \< 0 || sig \>= NSIG) {
- rb\_raise(rb\_eArgError, “invalid signal number (%d)”, sig);
- }  
#if defined(HAVE\_SETITIMER)  
if (sig == SIGVTALRM) {  
@@ -708,4 +727,10 @@ trap(struct trap\_arg \*arg)  
}  
#endif

- return sig;  
+}
- 

+static sighandler\_t  
+default\_handler(sighandler\_t func, int sig)  
+{  
if (func == SIG\_DFL) {  
switch (sig) {  
@@ -748,14 +773,29 @@ trap(struct trap\_arg \*arg)  
}  
}  
+

- return func;  
+}
- 

+static VALUE  
+trap(struct trap\_arg \*arg)  
+{

- sighandler\_t oldfunc, func = arg-\>func;
- VALUE oldcmd, command = arg-\>cmd;
- int sig = arg-\>sig;
- oldfunc = ruby\_signal(sig, func);  
oldcmd = trap\_list[sig].cmd;

- if (!oldcmd) {

- switch (oldcmd) {

- 

```
 case 0:

```

if (oldfunc == SIG\_IGN) oldcmd = rb\_str\_new2(“IGNORE”);  
else if (oldfunc == sighandler) oldcmd = rb\_str\_new2(“DEFAULT”);  
else oldcmd = Qnil;

- break;

- 

```
 case Qundef:

```

- oldcmd = rb\_str\_new2(“EXIT”);

- break;  
}

- trap\_list[sig].safe = rb\_safe\_level();  
/\* enable at least specified signal. \*/  
#ifndef \_WIN32  
@@ -834,10 +874,12 @@ sig\_trap(int argc, VALUE \*argv)  
}

- arg.sig = argv[0];

- arg.sig = trap\_signm(argv[0]);  
if (argc == 1) {  
arg.cmd = rb\_block\_proc();
- arg.func = sighandler;  
}  
else if (argc == 2) {  
arg.cmd = argv[1];
- arg.func = default\_handler(trap\_handler(&arg.cmd), arg.sig);  
}
