Project

General

Profile

Bug #4765 » remove-signalmask-op.patch

kosaki (Motohiro KOSAKI), 06/12/2011 06:53 PM

View differences:

eval_intern.h (working copy)
212 212
void rb_thread_terminate_all(void);
213 213
VALUE rb_vm_top_self();
214 214
VALUE rb_vm_cbase(void);
215
void rb_trap_restore_mask(void);
216 215

  
217 216
#ifndef CharNext		/* defined as CharNext[AW] on Windows. */
218 217
#define CharNext(p) ((p) + mblen((p), RUBY_MBCHAR_MAXSIZE))
thread_pthread.c (working copy)
1029 1029
static void
1030 1030
rb_thread_create_timer_thread(void)
1031 1031
{
1032
    rb_enable_interrupt();
1033

  
1034 1032
    if (!timer_thread_id) {
1035 1033
	pthread_attr_t attr;
1036 1034
	int err;
......
1051 1049
	native_cond_wait(&timer_thread_cond, &timer_thread_lock);
1052 1050
	native_mutex_unlock(&timer_thread_lock);
1053 1051
    }
1054
    rb_disable_interrupt(); /* only timer thread recieve signal */
1055 1052
}
1056 1053

  
1057 1054
static int
vm_core.h (working copy)
640 640
#endif
641 641
VALUE rb_iseq_eval(VALUE iseqval);
642 642
VALUE rb_iseq_eval_main(VALUE iseqval);
643
void rb_enable_interrupt(void);
644
void rb_disable_interrupt(void);
645 643
#if defined __GNUC__ && __GNUC__ >= 4
646 644
#pragma GCC visibility pop
647 645
#endif
vm_eval.c (working copy)
1442 1442
	RB_GC_GUARD(desc);
1443 1443
	rb_raise(rb_eArgError, "uncaught throw %s", RSTRING_PTR(desc));
1444 1444
    }
1445
    rb_trap_restore_mask();
1446 1445
    th->errinfo = NEW_THROW_OBJECT(tag, 0, TAG_THROW);
1447 1446

  
1448 1447
    JUMP_TAG(TAG_THROW);
eval.c (working copy)
439 439
	JUMP_TAG(TAG_FATAL);
440 440
    }
441 441

  
442
    rb_trap_restore_mask();
443

  
444 442
    if (tag != TAG_FATAL) {
445 443
	EXEC_EVENT_HOOK(th, RUBY_EVENT_RAISE, th->cfp->self, 0, 0);
446 444
    }
process.c (working copy)
990 990

  
991 991
static void before_exec(void)
992 992
{
993
    /*
994
     * signalmask is inherited across exec() and almost system commands don't
995
     * work if signalmask is blocked.
996
     */
997
    rb_enable_interrupt();
998

  
999 993
#ifdef SIGPIPE
1000 994
    /*
1001 995
     * Some OS commands don't initialize signal handler properly. Thus we have
......
1026 1020
#endif
1027 1021

  
1028 1022
    forked_child = 0;
1029
    rb_disable_interrupt();
1030 1023
}
1031 1024

  
1032 1025
#define before_fork() before_exec()
......
2947 2940
void
2948 2941
rb_syswait(rb_pid_t pid)
2949 2942
{
2950
    static int overriding;
2951
#ifdef SIGHUP
2952
    RETSIGTYPE (*hfunc)(int) = 0;
2953
#endif
2954
#ifdef SIGQUIT
2955
    RETSIGTYPE (*qfunc)(int) = 0;
2956
#endif
2957
    RETSIGTYPE (*ifunc)(int) = 0;
2958 2943
    int status;
2959
    int i, hooked = FALSE;
2944
    int err;
2960 2945

  
2961
    if (!overriding) {
2962
#ifdef SIGHUP
2963
	hfunc = signal(SIGHUP, SIG_IGN);
2964
#endif
2965
#ifdef SIGQUIT
2966
	qfunc = signal(SIGQUIT, SIG_IGN);
2967
#endif
2968
	ifunc = signal(SIGINT, SIG_IGN);
2969
	overriding = TRUE;
2970
	hooked = TRUE;
2971
    }
2972

  
2973 2946
    do {
2974
	i = rb_waitpid(pid, &status, 0);
2975
    } while (i == -1 && errno == EINTR);
2947
	err = rb_waitpid(pid, &status, 0);
2948
    } while (err == -1 && errno == EINTR);
2976 2949

  
2977
    if (hooked) {
2978
#ifdef SIGHUP
2979
	signal(SIGHUP, hfunc);
2980
#endif
2981
#ifdef SIGQUIT
2982
	signal(SIGQUIT, qfunc);
2983
#endif
2984
	signal(SIGINT, ifunc);
2985
	overriding = FALSE;
2986
    }
2987 2950
}
2988 2951

  
2989 2952
static VALUE
signal.c (working copy)
517 517
    return signal_buff.size;
518 518
}
519 519

  
520
#if USE_TRAP_MASK
521
# ifdef HAVE_SIGPROCMASK
522
static sigset_t trap_last_mask;
523
# else
524
static int trap_last_mask;
525
# endif
526
#endif
527

  
528 520
#if HAVE_PTHREAD_H
529 521
#include <pthread.h>
530 522
#endif
531 523

  
532
void
524
static void
533 525
rb_disable_interrupt(void)
534 526
{
535 527
#if USE_TRAP_MASK
536 528
    sigset_t mask;
537 529
    sigfillset(&mask);
538
    sigdelset(&mask, SIGVTALRM);
539
    sigdelset(&mask, SIGSEGV);
540 530
    pthread_sigmask(SIG_SETMASK, &mask, NULL);
541 531
#endif
542 532
}
543 533

  
544
void
534
static void
545 535
rb_enable_interrupt(void)
546 536
{
547 537
#if USE_TRAP_MASK
......
867 857
{
868 858
    /* enable interrupt */
869 859
    pthread_sigmask(SIG_SETMASK, &arg->mask, NULL);
870
    trap_last_mask = arg->mask;
871 860
    return 0;
872 861
}
873 862
#endif
874 863

  
875
void
876
rb_trap_restore_mask(void)
877
{
878
#if USE_TRAP_MASK
879
    pthread_sigmask(SIG_SETMASK, &trap_last_mask, NULL);
880
#endif
881
}
882

  
883 864
/*
884 865
 * call-seq:
885 866
 *   Signal.trap( signal, command ) -> obj
......
986 967
init_sigchld(int sig)
987 968
{
988 969
    sighandler_t oldfunc;
989
#if USE_TRAP_MASK
990
# ifdef HAVE_SIGPROCMASK
991
    sigset_t mask;
992
    sigset_t fullmask;
993
# else
994
    int mask;
995
    int fullmask;
996
# endif
997
#endif
998 970

  
999
#if USE_TRAP_MASK
1000
    /* disable interrupt */
1001
    sigfillset(&fullmask);
1002
    pthread_sigmask(SIG_BLOCK, &fullmask, &mask);
1003
#endif
1004

  
1005 971
    oldfunc = ruby_signal(sig, SIG_DFL);
1006 972
    if (oldfunc != SIG_DFL && oldfunc != SIG_IGN) {
1007 973
	ruby_signal(sig, oldfunc);
1008 974
    } else {
1009 975
	GET_VM()->trap_list[sig].cmd = 0;
1010 976
    }
1011

  
1012
#if USE_TRAP_MASK
1013
    sigdelset(&mask, sig);
1014
    pthread_sigmask(SIG_SETMASK, &mask, NULL);
1015
    trap_last_mask = mask;
1016
#endif
1017 977
}
1018 978
#endif
1019 979