Example #1
0
void *Test_Thread(void *arg)
{
  bool        blocked = *((bool *)arg);
  const char *name;
  int         sc;
  sigset_t    mask;
  sigset_t    wait_mask;
  siginfo_t   info;

  if ( blocked )
    name = "SignalBlocked";
  else
    name = "SignalNotBlocked";

  /* build unblocked mask */
  sc = sigemptyset( &mask );
  rtems_test_assert(  !sc );

  printf( "%s - Unblock %s\n", name, signal_name(SIGNAL_ONE) );
  sc = sigaddset( &mask, SIGNAL_ONE );
  rtems_test_assert(  !sc );

  if ( !blocked ) {
    printf( "%s - Unblock %s\n", name, signal_name(SIGNAL_TWO) );
    sc = sigaddset( &mask, SIGNAL_TWO );
    rtems_test_assert(  !sc );
  }

  /* unblocked signals */
  sc = pthread_sigmask( SIG_UNBLOCK, &mask, NULL );
  rtems_test_assert(  !sc );

  /* build wait mask */
  sc = sigemptyset( &wait_mask );
  rtems_test_assert(  !sc );

  sc = sigaddset( &wait_mask, SIGNAL_ONE );
  rtems_test_assert(  !sc );

  /* wait for a signal */
  memset( &info, 0, sizeof(info) );

  printf( "%s - Wait for %s unblocked\n", name, signal_name(SIGNAL_ONE) );
  sigwaitinfo( &wait_mask, &info );
  rtems_test_assert(  !sc );

  printf( "%s - siginfo.si_signo=%d\n", name, info.si_signo );
  printf( "%s - siginfo.si_code=%d\n", name, info.si_code );
  /* FIXME: Instead of casting to (uintptr_t) and using PRIxPTR, we
   * likely should use %p. However, this would render this test's
   * behavior non-deterministic, because %p's behavior is
   * "implementation defined" */
  printf( "%s - siginfo.si_value=0x%08" PRIxPTR "\n", name, (uintptr_t) info.si_value.sival_ptr );

  rtems_test_assert(  info.si_signo == SIGNAL_TWO );
  rtems_test_assert(  info.si_code == SI_USER );

  printf( "%s - exiting\n", name );
  return NULL;
}
Example #2
0
/* Given 'status', which is a process status in the form reported by waitpid(2)
 * and returned by process_status(), returns a string describing how the
 * process terminated.  The caller is responsible for freeing the string when
 * it is no longer needed. */
char *
process_status_msg(int status)
{
    struct ds ds = DS_EMPTY_INITIALIZER;
#ifndef _WIN32
    if (WIFEXITED(status)) {
        ds_put_format(&ds, "exit status %d", WEXITSTATUS(status));
    } else if (WIFSIGNALED(status)) {
        char namebuf[SIGNAL_NAME_BUFSIZE];

        ds_put_format(&ds, "killed (%s)",
                      signal_name(WTERMSIG(status), namebuf, sizeof namebuf));
    } else if (WIFSTOPPED(status)) {
        char namebuf[SIGNAL_NAME_BUFSIZE];

        ds_put_format(&ds, "stopped (%s)",
                      signal_name(WSTOPSIG(status), namebuf, sizeof namebuf));
    } else {
        ds_put_format(&ds, "terminated abnormally (%x)", status);
    }
    if (WCOREDUMP(status)) {
        ds_put_cstr(&ds, ", core dumped");
    }
#else
    ds_put_cstr(&ds, "function not supported.");
#endif
    return ds_cstr(&ds);
}
Example #3
0
/**
 * If a restart signal is received during exit-notification, reset the
 * signal and return true. If its a soft restart signal from the event loop
 * which implies the loop cannot continue, remap to SIGTERM to exit promptly.
 */
static bool
ignore_restart_signals(struct context *c)
{
    bool ret = false;
#ifdef ENABLE_OCC
    if ( (c->sig->signal_received == SIGUSR1 || c->sig->signal_received == SIGHUP)
         && event_timeout_defined(&c->c2.explicit_exit_notification_interval) )
    {
        if (c->sig->source == SIG_SOURCE_HARD)
        {
            msg(M_INFO, "Ignoring %s received during exit notification",
                signal_name(c->sig->signal_received, true));
            signal_reset(c->sig);
            ret = true;
        }
        else
        {
            msg(M_INFO, "Converting soft %s received during exit notification to SIGTERM",
                signal_name(c->sig->signal_received, true));
            register_signal(c, SIGTERM, "exit-with-notification");
            ret = false;
        }
    }
#endif
    return ret;
}
Example #4
0
void
print_signal (const struct signal_info *si, const char *title, int msglevel)
{
  if (si)
    {
      const char *hs = (si->hard ? "hard" : "soft");
      const char *type = (si->signal_text ? si->signal_text : "");
      const char *t = (title ? title : "process");

      switch (si->signal_received)
	{
	case SIGINT:
	case SIGTERM:
	  msg (msglevel, "%s[%s,%s] received, %s exiting",
	       signal_name (si->signal_received, true), hs, type, t);
	  break;
	case SIGHUP:
	case SIGUSR1:
	  msg (msglevel, "%s[%s,%s] received, %s restarting",
	       signal_name (si->signal_received, true), hs, type, t);
	  break;
	default:
	  msg (msglevel, "Unknown signal %d [%s,%s] received by %s", si->signal_received, hs, type, t);
	  break;
	}
    }
  else
    msg (msglevel, "Unknown signal received");
}
Example #5
0
void
print_signal(const struct signal_info *si, const char *title, int msglevel)
{
    if (si)
    {
        const char *type = (si->signal_text ? si->signal_text : "");
        const char *t = (title ? title : "process");
        const char *hs = NULL;
        switch (si->source)
        {
            case SIG_SOURCE_SOFT:
                hs = "soft";
                break;

            case SIG_SOURCE_HARD:
                hs = "hard";
                break;

            case SIG_SOURCE_CONNECTION_FAILED:
                hs = "connection failed(soft)";
                break;

            default:
                ASSERT(0);
        }

        switch (si->signal_received)
        {
            case SIGINT:
            case SIGTERM:
                msg(msglevel, "%s[%s,%s] received, %s exiting",
                    signal_name(si->signal_received, true), hs, type, t);
                break;

            case SIGHUP:
            case SIGUSR1:
                msg(msglevel, "%s[%s,%s] received, %s restarting",
                    signal_name(si->signal_received, true), hs, type, t);
                break;

            default:
                msg(msglevel, "Unknown signal %d [%s,%s] received by %s", si->signal_received, hs, type, t);
                break;
        }
    }
    else
    {
        msg(msglevel, "Unknown signal received");
    }
}
static void write_context_state(OutputStream * out, Context * ctx) {
    int fst = 1;
    assert(!ctx->exited);

    if (!ctx->intercepted) {
        write_stringz(out, "0");
        write_stringz(out, "null");
        write_stringz(out, "null");
        return;
    }

    /* Number: PC */
    json_write_ulong(out, get_regs_PC(ctx->regs));
    write_stream(out, 0);

    /* String: Reason */
    json_write_string(out, context_suspend_reason(ctx));
    write_stream(out, 0);

    /* Object: Additional context state info */
    write_stream(out, '{');
    if (ctx->signal) {
        json_write_string(out, "Signal");
        write_stream(out, ':');
        json_write_long(out, ctx->signal);
        if (signal_name(ctx->signal)) {
            write_stream(out, ',');
            json_write_string(out, "SignalName");
            write_stream(out, ':');
            json_write_string(out, signal_name(ctx->signal));
        }
        fst = 0;
    }
    if (ctx->stopped_by_bp && ctx->bp_ids != NULL && ctx->bp_ids[0] != NULL) {
        int i = 0;
        if (!fst) write_stream(out, ',');
        json_write_string(out, "BPs");
        write_stream(out, ':');
        write_stream(out, '[');
        while (ctx->bp_ids[i] != NULL) {
            if (i > 0) write_stream(out, ',');
            json_write_string(out, ctx->bp_ids[i++]);
        }
        write_stream(out, ']');
        fst = 0;
    }
    write_stream(out, '}');
    write_stream(out, 0);
}
Example #7
0
/* Check whether a fatal signal has occurred and, if so, call the fatal signal
 * hooks and exit.
 *
 * This function is called automatically by poll_block(), but specialized
 * programs that may not always call poll_block() on a regular basis should
 * also call it periodically.  (Therefore, any function with "block" in its
 * name should call fatal_signal_run() each time it is called, either directly
 * or through poll_block(), because such functions can only used by specialized
 * programs that can afford to block outside their main loop around
 * poll_block().)
 */
void
fatal_signal_run(void)
{
    sig_atomic_t sig_nr;

    fatal_signal_init();

    sig_nr = stored_sig_nr;
    if (sig_nr != SIG_ATOMIC_MAX) {
        char namebuf[SIGNAL_NAME_BUFSIZE];

        ovs_mutex_lock(&mutex);

        VLOG_WARN("terminating with signal %d (%s)",
                  (int)sig_nr, signal_name(sig_nr, namebuf, sizeof namebuf));
        call_hooks(sig_nr);

        /* Re-raise the signal with the default handling so that the program
         * termination status reflects that we were killed by this signal */
        signal(sig_nr, SIG_DFL);
        raise(sig_nr);

        ovs_mutex_unlock(&mutex);
        OVS_NOT_REACHED();
    }
}
Example #8
0
NOEXPORT void client_status(void) { /* dead children detected */
    int pid, status;
    char *sig_name;

#ifdef HAVE_WAIT_FOR_PID
    while((pid=wait_for_pid(-1, &status, WNOHANG))>0) {
#else
    if((pid=wait(&status))>0) {
#endif
#ifdef WIFSIGNALED
        if(WIFSIGNALED(status)) {
            sig_name=signal_name(WTERMSIG(status));
            s_log(LOG_DEBUG, "Process %d terminated on %s",
                pid, sig_name);
            str_free(sig_name);
        } else {
            s_log(LOG_DEBUG, "Process %d finished with code %d",
                pid, WEXITSTATUS(status));
        }
    }
#else
        s_log(LOG_DEBUG, "Process %d finished with code %d",
            pid, status);
    }
#endif
}
Example #9
0
/*
 * Call management interface with restart info
 */
void
signal_restart_status(const struct signal_info *si)
{
#ifdef ENABLE_MANAGEMENT
    if (management)
    {
        int state = -1;
        switch (si->signal_received)
        {
            case SIGINT:
            case SIGTERM:
                state = OPENVPN_STATE_EXITING;
                break;

            case SIGHUP:
            case SIGUSR1:
                state = OPENVPN_STATE_RECONNECTING;
                break;
        }

        if (state >= 0)
        {
            management_set_state(management,
                                 state,
                                 si->signal_text ? si->signal_text : signal_name(si->signal_received, true),
                                 NULL,
                                 NULL,
                                 NULL,
                                 NULL);
        }
    }
#endif /* ifdef ENABLE_MANAGEMENT */
}
Example #10
0
const char *
signal_description (const int signum, const char *sigtext)
{
  if (sigtext)
    return sigtext;
  else
    return signal_name (signum, false);
}
static void command_get_signal_list(char * token, Channel * c) {
    int err = 0;
    char id[256];
    pid_t pid;

    json_read_string(&c->inp, id, sizeof(id));
    if (read_stream(&c->inp) != 0) exception(ERR_JSON_SYNTAX);
    if (read_stream(&c->inp) != MARKER_EOM) exception(ERR_JSON_SYNTAX);

    pid = id2pid(id, NULL);
    write_stringz(&c->out, "R");
    write_stringz(&c->out, token);
    /* pid is ignored, same signal list for all */

    write_errno(&c->out, err);
    if (err) {
        write_stringz(&c->out, "null");
    }
    else {
        int i = 0;
        int n = 0;
        write_stream(&c->out, '[');
        for (i = 0; i < 32; i++) {
            char * name = signal_name(i);
            char * desc = signal_description(i);
            if (name != NULL || desc != NULL) {
                if (n > 0) write_stream(&c->out, ',');
                write_stream(&c->out, '{');
                json_write_string(&c->out, "Index");
                write_stream(&c->out, ':');
                json_write_long(&c->out, i);
                if (name != NULL) {
                    write_stream(&c->out, ',');
                    json_write_string(&c->out, "Name");
                    write_stream(&c->out, ':');
                    json_write_string(&c->out, name);
                }
                if (desc != NULL) {
                    write_stream(&c->out, ',');
                    json_write_string(&c->out, "Description");
                    write_stream(&c->out, ':');
                    json_write_string(&c->out, desc);
                }
                write_stream(&c->out, ',');
                json_write_string(&c->out, "Code");
                write_stream(&c->out, ':');
                json_write_ulong(&c->out, signal_code(i));
                write_stream(&c->out, '}');
                n++;
            }
        }
        write_stream(&c->out, ']');
        write_stream(&c->out, 0);
    }

    write_stream(&c->out, MARKER_EOM);
}
Example #12
0
static void
handle_sigTSTP(int signo)
{
    sigset_t all_signals;
    int error, saved_errno = errno;

    DEBUG_RANDOM_SLEEP;
    sigfillset(&all_signals);

    DPRINTF2(DEBUG_SIGNALS, "got %s, sending it to pgid %d", signal_name(signo), command_pid);
    zero_select_timeout();
    /* Hand the SIGTSTP down to command and its process group */
    if (command_pid && (error = kill(-command_pid, SIGTSTP))) {
        myerror(FATAL|USE_ERRNO, "Failed to deliver SIGTSTP");
    }

    if (within_line_edit)
        save_rl_state();


    mysignal(SIGTSTP, SIG_DFL);   /* reset disposition to default (i.e. suspend) */
    sigprocmask(SIG_UNBLOCK, &all_signals, NULL); /* respond to sleep- and wake-up signals  */
    kill(getpid(), SIGTSTP); /* suspend */
    /* keyboard gathers dust, kingdoms crumble,.... */

    /* .... */

    /* Beautiful princess types "fg", (or her father tries to kill us...) and we wake up HERE: */
    sigprocmask(SIG_BLOCK, &all_signals, NULL);
    mysignal(SIGTSTP, &handle_sigTSTP);
    DPRINTF0(DEBUG_SIGNALS, "woken up");

    /* On most systems, command's process group will have been woken up by the handler of
       the signal that woke us up. This doesn't seem to happen for SIGCONT on QNX, so here goes: */

#ifdef __QNX__
    if (command_pid && (error = kill(-command_pid, SIGCONT))) {
        myerror(FATAL|USE_ERRNO, "Failed to deliver SIGCONT");
    }
#endif

    if (within_line_edit) {
        restore_rl_state();
    } else {
        set_echo(FALSE);
        cr();
        if (skip_rlwrap())
            return;
        move_cursor_to_start_of_prompt(ERASE);
        cook_prompt_if_necessary();
        my_putstr(saved_rl_state.cooked_prompt);
    }
    adapt_tty_winsize(STDIN_FILENO, master_pty_fd);       /* just in case */
    errno = saved_errno;
    sigprocmask(SIG_UNBLOCK, &all_signals, NULL);
}
Example #13
0
void suicide_by(int signal, int status) {
    /* Some signals suggest a program error. When rlwrap kills itself with one of those,
       the shell may tell the user that rlwrap itself has failed. Make clear that
       it didn't. @@@ We could also try argv[0] = command_name just before dying ? */

    if (signals_program_error(signal)) {
        myerror(WARNING|NOERRNO, "%s crashed, killed by %s%s.\n%s itself has not crashed, but for transparency,\n"
                "it will now kill itself %swith the same signal\n",
                command_name, signal_name(signal), (coredump(status) ? " (core dumped)" : ""),
                program_name, (coredump(status) ? "" : "(without dumping core) ") );
    }
    uninstall_signal_handlers();
    unblock_all_signals();
    set_ulimit(RLIMIT_CORE,0); /* prevent our own useless core dump from clobbering the interesting one created by command */
    DPRINTF1(DEBUG_SIGNALS, "suicide by signal %s", signal_name(signal));
    kill(getpid(), signal);
    /* still alive? */
    sleep(1);
    exit(0);
}
Example #14
0
// This function handles deadly signals.
// It tries to preserve any swap files and exit properly.
// (partly from Elvis).
// NOTE: Avoid unsafe functions, such as allocating memory, they can result in
// a deadlock.
static void deadly_signal(int signum)
{
  // Set the v:dying variable.
  set_vim_var_nr(VV_DYING, 1);

  snprintf((char *)IObuff, sizeof(IObuff), "Vim: Caught deadly signal '%s'\n",
      signal_name(signum));

  // Preserve files and exit.
  preserve_exit();
}
Example #15
0
// This function handles deadly signals.
// It tries to preserve any swap files and exit properly.
// (partly from Elvis).
// NOTE: Avoid unsafe functions, such as allocating memory, they can result in
// a deadlock.
static void deadly_signal(int signum)
{
  // Set the v:dying variable.
  set_vim_var_nr(VV_DYING, 1);

  sprintf((char *)IObuff, "Vim: Caught deadly signal '%s'\n",
      signal_name(signum));

  // Preserve files and exit.  This sets the really_exiting flag to prevent
  // calling free().
  preserve_exit();
}
Example #16
0
/*
 * If the given signal is still in its default state, set it to the given
 * handler.
 */
static int
CatchIfDefault(int sig, RETSIGTYPE (*handler) (int))
{
    int result;
#if HAVE_SIGACTION || HAVE_SIGVEC
    sigaction_t old_act;
    sigaction_t new_act;

    memset(&new_act, 0, sizeof(new_act));
    sigemptyset(&new_act.sa_mask);
#ifdef SA_RESTART
#ifdef SIGWINCH
    if (sig != SIGWINCH)
#endif
	new_act.sa_flags |= SA_RESTART;
#endif /* SA_RESTART */
    new_act.sa_handler = handler;

    if (sigaction(sig, NULL, &old_act) == 0
	&& (old_act.sa_handler == SIG_DFL
	    || old_act.sa_handler == handler
#if USE_SIGWINCH
	    || (sig == SIGWINCH && old_act.sa_handler == SIG_IGN)
#endif
	)) {
	(void) sigaction(sig, &new_act, NULL);
	result = TRUE;
    } else {
	result = FALSE;
    }
#else /* !HAVE_SIGACTION */
    RETSIGTYPE (*ohandler) (int);

    ohandler = signal(sig, SIG_IGN);
    if (ohandler == SIG_DFL
	|| ohandler == handler
#if USE_SIGWINCH
	|| (sig == SIGWINCH && ohandler == SIG_IGN)
#endif
	) {
	signal(sig, handler);
	result = TRUE;
    } else {
	signal(sig, ohandler);
	result = FALSE;
    }
#endif
    T(("CatchIfDefault - will %scatch %s",
       result ? "" : "not ", signal_name(sig)));
    return result;
}
Example #17
0
static void
handle_program_error_signal(int sig)
{   /* Even after sudden and unexpected death, leave the terminal in a tidy state */
    int res;

    printf("\n%s: Oops, crashed (caught %s) - this should not have happened!\n"
           "If you need a core dump, re-configure with --enable-debug and rebuild\n"
           "Resetting terminal and cleaning up...\n", program_name, signal_name(sig));
    if (colour_the_prompt || filter_pid)
        res = write(STDOUT_FILENO,"\033[0m",4); /* reset terminal colours */
    if (terminal_settings_saved)
        tcsetattr(STDIN_FILENO, TCSAFLUSH, &saved_terminal_settings);

    exit(EXIT_FAILURE);
}
Example #18
0
void
mysignal(int sig, sighandler_type handler) {

#ifdef HAVE_SIGACTION
    struct sigaction action;
    DPRINTF3(DEBUG_SIGNALS,"Setting handler for signal %d (%s) to <0x%lx>", sig, signal_name(sig), (long) handler);
    action.sa_handler = handler;
    sigfillset(&action.sa_mask); /* don't bother making our signal handlers re-entrant (they aren't) */
    action.sa_flags = (sig == SIGCHLD ? SA_NOCLDSTOP : 0); /* no SA_RESTART */
    if (sigaction(sig, &action, NULL) != 0)
# else /* rlwrap running in Ye Olde Computer Museum?? */
    if (signal(sig, handler) == SIG_ERR)
# endif
        if(handler != SIG_DFL) /* allow e.g. KILL to be set to its default */
            myerror(FATAL|USE_ERRNO, "Failed setting handler for signal %d (%s)", sig, signal_name(sig));
}
Example #19
0
v8::Handle<v8::Value> GetSignalDescriptionByClass(const v8::Arguments& args) {
  v8::HandleScope scope;
  if (args.Length() != 2) {
    ThrowException(v8::Exception::TypeError(v8::String::New("Wrong number of arguments")));
    return scope.Close(v8::Undefined());
  }
  if (!args[0]->IsString() || !args[1]->IsString()) {
    ThrowException(v8::Exception::TypeError(v8::String::New("Wrong arguments")));
    return scope.Close(v8::Undefined());
  }
  v8::String::AsciiValue class_name(args[0]->ToString());
  v8::String::AsciiValue signal_name(args[1]->ToString());

  v8::Handle<v8::String> res = 
    v8::String::New(switcher_container[0]->get_signal_description_by_class(std::string(*class_name), 
									   std::string(*signal_name)).c_str());
  return scope.Close(res);
}
Example #20
0
v8::Handle<v8::Value> UnsubscribeToSignal(const v8::Arguments& args) {
  v8::HandleScope scope;
  if (args.Length() != 2) {
    ThrowException(v8::Exception::TypeError(v8::String::New("Wrong number of arguments")));
    return scope.Close(v8::Undefined());
  }
  if (!args[0]->IsString() || !args[1]->IsString()) {
    ThrowException(v8::Exception::TypeError(v8::String::New("Wrong arguments")));
    return scope.Close(v8::Undefined());
  }
  v8::String::AsciiValue element_name(args[0]->ToString());
  v8::String::AsciiValue signal_name(args[1]->ToString());

  v8::Handle<v8::Boolean> res = 
    v8::Boolean::New(switcher_container[0]->unsubscribe_signal (std::string ("signal_sub"),
								std::string(*element_name), 
								std::string(*signal_name)));
  return scope.Close(res);
}
/* Check whether a fatal signal has occurred and, if so, call the fatal signal
 * hooks and exit.
 *
 * This function is called automatically by poll_block(), but specialized
 * programs that may not always call poll_block() on a regular basis should
 * also call it periodically.  (Therefore, any function with "block" in its
 * name should call fatal_signal_run() each time it is called, either directly
 * or through poll_block(), because such functions can only used by specialized
 * programs that can afford to block outside their main loop around
 * poll_block().)
 */
void
fatal_signal_run(void)
{
    sig_atomic_t sig_nr;

    fatal_signal_init();

    sig_nr = stored_sig_nr;
    if (sig_nr != SIG_ATOMIC_MAX) {
        VLOG_WARN("terminating with signal %d (%s)",
                  (int)sig_nr, signal_name(sig_nr));
        call_hooks(sig_nr);

        /* Re-raise the signal with the default handling so that the program
         * termination status reflects that we were killed by this signal */
        signal(sig_nr, SIG_DFL);
        raise(sig_nr);
    }
}
Example #22
0
/**
 * @brief	Handle signals that indicate the program was killed because of an invalid operation (including SIGSEGV).
 * @note	The signals handled by this function are: SIGSEGV, SIGFPE, SIGBUS, SIGSYS, and SIGABRT.
 * 			The handler will respond by logging a stack backtrace, and terminating the program with abort().
 * @param	signal	the number of the signal that was received.
 * @return	This function returns no value.
 */
void signal_segfault(int signal) {

	char signame[32];
	struct sigaction clear;

	// Log it.
	log_options(M_LOG_CRITICAL | M_LOG_STACK_TRACE, "Memory corruption has been detected. Attempting to print a back trace and exit. { signal = %s }",
			signal_name(signal, signame, 32));

	// Configure the structure to return a signal to its default handler via the sigaction call below.
	mm_wipe(&clear, sizeof(struct sigaction));
	sigemptyset(&clear.sa_mask);
	clear.sa_handler = SIG_DFL;
	clear.sa_flags = 0;

	// Return the SIGABRT handler to its default value. This allows us to call abort and trigger a core dump without creating a recursive loop.
	sigaction(SIGABRT, &clear, NULL);

	// The abort function should trigger the creation of a core dump file if core dumps have been enabled.
	abort();
}
Example #23
0
static void
pass_on_signal(int signo)
{
    int ret, saved_errno = errno, pass_it_on = TRUE;
    DEBUG_RANDOM_SLEEP;
    zero_select_timeout();
#ifdef DEBUG
    log_named_signal(signo);
#endif

    if(pass_on_sigINT_as_sigTERM && signo == SIGINT)
        signo=SIGTERM;

    switch (signo) {
    case SIGWINCH: /* non-POSIX, but present on most systems */
        /* Make slave pty's winsize equal to that of STDIN. Pass the signal on *only if*
           winsize has changed. This is particularly important because we have the slave pty
           still open - when we pass on the signal the child will probably do a TIOCSWINSZ ioctl()
           on the slave pty  - causing us (the parent) to get a SIGWINCH again, thus getting stuck in a loop */
        pass_it_on = adapt_tty_winsize(STDIN_FILENO, master_pty_fd);
        break;
    case SIGTERM:
        sigterm_received = TRUE;
        break;
    default:
        break;
    }
    if (!command_pid)
        pass_it_on = FALSE;         /* no child (yet) to pass it on to */

    if (pass_it_on) {             /* we resend the signal to the process *group* of the child */
        ret = kill( -command_pid, signo);
        DPRINTF3(DEBUG_SIGNALS, "kill(%d,%s) = %d", -command_pid, signal_name(signo), ret);
        we_just_got_a_signal_or_EOF = TRUE; /* signal to main loop that next command output should leave the prompt alone */
    }
    errno = saved_errno;

}
Example #24
0
NOEXPORT int signal_pipe_dispatch(void) {
    static int sig;
    static size_t ptr=0;
    ssize_t num;
    char *sig_name;

    s_log(LOG_DEBUG, "Dispatching signals from the signal pipe");
    for(;;) {
        num=readsocket(signal_pipe[0], (char *)&sig+ptr, sizeof sig-ptr);
        if(num==-1 && get_last_socket_error()==S_EWOULDBLOCK) {
            s_log(LOG_DEBUG, "Signal pipe is empty");
            return 0;
        }
        if(num==-1 || num==0) {
            if(num)
                sockerror("signal pipe read");
            else
                s_log(LOG_ERR, "Signal pipe closed");
            s_poll_remove(fds, signal_pipe[0]);
            closesocket(signal_pipe[0]);
            closesocket(signal_pipe[1]);
            if(signal_pipe_init()) {
                s_log(LOG_ERR,
                    "Signal pipe reinitialization failed; terminating");
                return 1;
            }
            s_poll_add(fds, signal_pipe[0], 1, 0);
            s_log(LOG_ERR, "Signal pipe reinitialized");
            return 0;
        }
        ptr+=(size_t)num;
        if(ptr<sizeof sig) {
            s_log(LOG_DEBUG, "Incomplete signal pipe read (ptr=%ld)",
                (long)ptr);
            return 0;
        }
        ptr=0;
        switch(sig) {
#ifndef USE_WIN32
        case SIGCHLD:
            s_log(LOG_DEBUG, "Processing SIGCHLD");
#ifdef USE_FORK
            client_status(); /* report status of client process */
#else /* USE_UCONTEXT || USE_PTHREAD */
            child_status();  /* report status of libwrap or 'exec' process */
#endif /* defined USE_FORK */
            break;
#endif /* !defind USE_WIN32 */
        case SIGNAL_RELOAD_CONFIG:
            s_log(LOG_DEBUG, "Processing SIGNAL_RELOAD_CONFIG");
            if(options_parse(CONF_RELOAD)) {
                s_log(LOG_ERR, "Failed to reload the configuration file");
            } else {
                unbind_ports();
                log_close();
                options_apply();
                log_open();
                ui_config_reloaded();
                if(bind_ports()) {
                    /* FIXME: handle the error */
                }
            }
            break;
        case SIGNAL_REOPEN_LOG:
            s_log(LOG_DEBUG, "Processing SIGNAL_REOPEN_LOG");
            log_close();
            log_open();
            s_log(LOG_NOTICE, "Log file reopened");
            break;
        case SIGNAL_TERMINATE:
            s_log(LOG_DEBUG, "Processing SIGNAL_TERMINATE");
            s_log(LOG_NOTICE, "Terminated");
            return 1;
        default:
            sig_name=signal_name(sig);
            s_log(LOG_ERR, "Received %s; terminating", sig_name);
            str_free(sig_name);
            return 1;
        }
    }
}
Example #25
0
/*
 * Entry pointer for signal handlers
 */
static void CppcheckSignalHandler(int signo, siginfo_t * info, void * /*context*/)
{
    const char * const signame = signal_name(signo);
    const char * const sigtext = strsignal(signo);
    bool bPrintCallstack=true;
    FILE* f=CppCheckExecutor::getExceptionOutput()=="stderr" ? stderr : stdout;
    fputs("Internal error: cppcheck received signal ", f);
    fputs(signame, f);
    fputs(", ", f);
    fputs(sigtext, f);
    switch (signo) {
    case SIGBUS:
        switch (info->si_code) {
        case BUS_ADRALN: // invalid address alignment
            fprintf(f, " - BUS_ADRALN");
            break;
        case BUS_ADRERR: // nonexistent physical address
            fprintf(f, " - BUS_ADRERR");
            break;
        case BUS_OBJERR: // object-specific hardware error
            fprintf(f, " - BUS_OBJERR");
            break;
#ifdef BUS_MCEERR_AR
        case BUS_MCEERR_AR: // Hardware memory error consumed on a machine check;
            fprintf(f, " - BUS_MCEERR_AR");
            break;
#endif
#ifdef BUS_MCEERR_AO
        case BUS_MCEERR_AO: // Hardware memory error detected in process but not consumed
            fprintf(f, " - BUS_MCEERR_AO");
            break;
#endif
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGFPE:
        switch (info->si_code) {
        case FPE_INTDIV: //     integer divide by zero
            fprintf(f, " - FPE_INTDIV");
            break;
        case FPE_INTOVF: //     integer overflow
            fprintf(f, " - FPE_INTOVF");
            break;
        case FPE_FLTDIV: //     floating-point divide by zero
            fprintf(f, " - FPE_FLTDIV");
            break;
        case FPE_FLTOVF: //     floating-point overflow
            fprintf(f, " - FPE_FLTOVF");
            break;
        case FPE_FLTUND: //     floating-point underflow
            fprintf(f, " - FPE_FLTUND");
            break;
        case FPE_FLTRES: //     floating-point inexact result
            fprintf(f, " - FPE_FLTRES");
            break;
        case FPE_FLTINV: //     floating-point invalid operation
            fprintf(f, " - FPE_FLTINV");
            break;
        case FPE_FLTSUB: //     subscript out of range
            fprintf(f, " - FPE_FLTSUB");
            break;
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGILL:
        switch (info->si_code) {
        case ILL_ILLOPC: //     illegal opcode
            fprintf(f, " - ILL_ILLOPC");
            break;
        case ILL_ILLOPN: //    illegal operand
            fprintf(f, " - ILL_ILLOPN");
            break;
        case ILL_ILLADR: //    illegal addressing mode
            fprintf(f, " - ILL_ILLADR");
            break;
        case ILL_ILLTRP: //    illegal trap
            fprintf(f, " - ILL_ILLTRP");
            break;
        case ILL_PRVOPC: //    privileged opcode
            fprintf(f, " - ILL_PRVOPC");
            break;
        case ILL_PRVREG: //    privileged register
            fprintf(f, " - ILL_PRVREG");
            break;
        case ILL_COPROC: //    coprocessor error
            fprintf(f, " - ILL_COPROC");
            break;
        case ILL_BADSTK: //    internal stack error
            fprintf(f, " - ILL_BADSTK");
            break;
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGINT:
        bPrintCallstack=false;
        fprintf(f, ".\n");
        break;
    case SIGSEGV:
        switch (info->si_code) {
        case SEGV_MAPERR: //    address not mapped to object
            fprintf(f, " - SEGV_MAPERR");
            break;
        case SEGV_ACCERR: //    invalid permissions for mapped object
            fprintf(f, " - SEGV_ACCERR");
            break;
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    default:
        fputs(".\n", f);
        break;
    }
    if (bPrintCallstack) {
        print_stacktrace(f, true);
        fputs("\nPlease report this to the cppcheck developers!\n", f);
    }
    abort();
}
Example #26
0
 * @note	This function handles the following signals: SIGINT, SIGQUIT, and SIGTERM.
 * 			The shutdown procedure is as follows:
 * 			1. Set status to -1 and sleep for .1 second to allow for normal daemon termination.
 * 			2. Signal all worker threads to wake up blocked threads, and sleep one more second.
 * 			3. Loop through all possible file descriptors and if the descriptor matches a socket that is bound to a magma server, close it.
 *
 * @param	signal	the number of the signal delivered to the process.
 * @return	This function returns no value.
 */
void signal_shutdown(int signal) {

	pthread_t status_thread;
	const struct timespec split = { .tv_sec = 0, .tv_nsec = 100000000 }, single = { .tv_sec = 1, .tv_nsec = 0 };

	// We assume the server is being shutdown for a good reason.
	log_critical("Signal received. The Magma daemon is attempting a graceful exit. { signal = %s }", signal_name(signal, MEMORYBUF(32), 32));

	// Clear the thread structure or we'll get a segfault when we attempt the thread join operation.
	mm_wipe(&status_thread, sizeof(pthread_t));

	// Set the status flag so all the worker threads exit nicely.
	thread_launch(&status_thread, &status_signal, NULL);

	// We give threads 0.1 seconds to ensure the status update is queued and awaiting the lock.
	nanosleep(&split, NULL);

	// Signals the worker threads, so they unblock one more time and see the updated status, thus exiting normally.
	queue_signal();

	// Then sleep for one second before forcibly shutting down the client connections.
	nanosleep(&single, NULL);
Example #27
0
/*
 * Entry pointer for signal handlers
 * It uses functions which are not safe to be called from a signal handler,
 * but when ending up here something went terribly wrong anyway.
 * And all which is left is just printing some information and terminate.
 */
static void CppcheckSignalHandler(int signo, siginfo_t * info, void * context)
{
    int type = -1;
    pid_t killid = getpid();
    const ucontext_t* uc = reinterpret_cast<const ucontext_t*>(context);
#ifdef __linux__
    killid = (pid_t) syscall(SYS_gettid);
    if (uc) {
        type = (int)uc->uc_mcontext.gregs[REG_ERR] & 2;
    }
#endif
    const char * const signame = signal_name(signo);
    const char * const sigtext = strsignal(signo);
    bool bPrintCallstack=true;
    FILE* f=CppCheckExecutor::getExceptionOutput()=="stderr" ? stderr : stdout;
    fputs("Internal error: cppcheck received signal ", f);
    fputs(signame, f);
    fputs(", ", f);
    fputs(sigtext, f);
    switch (signo) {
    case SIGBUS:
        switch (info->si_code) {
        case BUS_ADRALN: // invalid address alignment
            fputs(" - BUS_ADRALN", f);
            break;
        case BUS_ADRERR: // nonexistent physical address
            fputs(" - BUS_ADRERR", f);
            break;
        case BUS_OBJERR: // object-specific hardware error
            fputs(" - BUS_OBJERR", f);
            break;
#ifdef BUS_MCEERR_AR
        case BUS_MCEERR_AR: // Hardware memory error consumed on a machine check;
            fputs(" - BUS_MCEERR_AR", f);
            break;
#endif
#ifdef BUS_MCEERR_AO
        case BUS_MCEERR_AO: // Hardware memory error detected in process but not consumed
            fputs(" - BUS_MCEERR_AO", f);
            break;
#endif
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGFPE:
        switch (info->si_code) {
        case FPE_INTDIV: //     integer divide by zero
            fputs(" - FPE_INTDIV", f);
            break;
        case FPE_INTOVF: //     integer overflow
            fputs(" - FPE_INTOVF", f);
            break;
        case FPE_FLTDIV: //     floating-point divide by zero
            fputs(" - FPE_FLTDIV", f);
            break;
        case FPE_FLTOVF: //     floating-point overflow
            fputs(" - FPE_FLTOVF", f);
            break;
        case FPE_FLTUND: //     floating-point underflow
            fputs(" - FPE_FLTUND", f);
            break;
        case FPE_FLTRES: //     floating-point inexact result
            fputs(" - FPE_FLTRES", f);
            break;
        case FPE_FLTINV: //     floating-point invalid operation
            fputs(" - FPE_FLTINV", f);
            break;
        case FPE_FLTSUB: //     subscript out of range
            fputs(" - FPE_FLTSUB", f);
            break;
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGILL:
        switch (info->si_code) {
        case ILL_ILLOPC: //     illegal opcode
            fputs(" - ILL_ILLOPC", f);
            break;
        case ILL_ILLOPN: //    illegal operand
            fputs(" - ILL_ILLOPN", f);
            break;
        case ILL_ILLADR: //    illegal addressing mode
            fputs(" - ILL_ILLADR", f);
            break;
        case ILL_ILLTRP: //    illegal trap
            fputs(" - ILL_ILLTRP", f);
            break;
        case ILL_PRVOPC: //    privileged opcode
            fputs(" - ILL_PRVOPC", f);
            break;
        case ILL_PRVREG: //    privileged register
            fputs(" - ILL_PRVREG", f);
            break;
        case ILL_COPROC: //    coprocessor error
            fputs(" - ILL_COPROC", f);
            break;
        case ILL_BADSTK: //    internal stack error
            fputs(" - ILL_BADSTK", f);
            break;
        default:
            break;
        }
        fprintf(f, " (at 0x%p).\n",
                info->si_addr);
        break;
    case SIGINT:
        bPrintCallstack=false;
        fputs(".\n", f);
        break;
    case SIGSEGV:
        switch (info->si_code) {
        case SEGV_MAPERR: //    address not mapped to object
            fputs(" - SEGV_MAPERR", f);
            break;
        case SEGV_ACCERR: //    invalid permissions for mapped object
            fputs(" - SEGV_ACCERR", f);
            break;
        default:
            break;
        }
        fprintf(f, " (%sat 0x%p).\n",
                (type==-1)? "" :
                (type==0) ? "reading " : "writing ",
                info->si_addr);
        break;
    default:
        fputs(".\n", f);
        break;
    }
    if (bPrintCallstack) {
        print_stacktrace(f, true);
        fputs("\nPlease report this to the cppcheck developers!\n", f);
    }

    // now let the system proceed, shutdown and hopefully dump core for post-mortem analysis
    signal(signo, SIG_DFL);
    kill(killid, signo);
}
Example #28
0
void *POSIX_Init(
  void *argument
)
{
  int                 sc;
  pthread_t           id;
  struct sigaction    act;
  bool                trueArg = true;
  bool                falseArg = false;
  struct timespec     delay_request;

  puts( "\n\n*** POSIX TEST SIGNAL " TEST_NAME " ***" );
  puts( "Init - Variation is: " TEST_STRING );

  Signal_occurred = false;

  act.sa_handler = NULL;
  act.sa_sigaction = Signal_handler;
  act.sa_flags   = SA_SIGINFO;
  sigaction( SIGNAL_ONE, &act, NULL );
  sigaction( SIGNAL_TWO, &act, NULL );

  /* create threads */
  sc = pthread_create( &id, NULL, Test_Thread, &falseArg );
  rtems_test_assert(  !sc );

  sc = pthread_create( &id, NULL, Test_Thread, &trueArg );
  rtems_test_assert(  !sc );

  puts( "Init - sleep - let threads settle - OK" );
  delay_request.tv_sec = 0;
  delay_request.tv_nsec = 5 * 100000000;
  sc = nanosleep( &delay_request, NULL );
  rtems_test_assert(  !sc );

  puts( "Init - sleep - SignalBlocked thread settle - OK" );
  sc = nanosleep( &delay_request, NULL );
  rtems_test_assert(  !sc );

  printf( "Init - sending %s - deliver to one thread\n",
          signal_name(SIGNAL_TWO));
  sc =  SEND_SIGNAL( SIGNAL_TWO );
  rtems_test_assert(  !sc );

  printf( "Init - sending %s - deliver to other thread\n",
          signal_name(SIGNAL_TWO));
  sc =  SEND_SIGNAL( SIGNAL_TWO );
  rtems_test_assert(  !sc );

  #if defined(TO_PROCESS)
    printf( "Init - sending %s - expect EAGAIN\n", signal_name(SIGNAL_TWO) );
    sc =  SEND_SIGNAL( SIGNAL_TWO );
    rtems_test_assert(  sc == -1 );
    rtems_test_assert(  errno == EAGAIN );
  #endif

  puts( "Init - sleep - let thread report if it unblocked - OK" );
  usleep(500000);

  /* we are just sigwait'ing the signal, not delivering it */
  rtems_test_assert(  Signal_occurred == true );

  puts( "*** END OF POSIX TEST SIGNAL " TEST_NAME " ***" );
  rtems_test_exit(0);

  return NULL; /* just so the compiler thinks we returned something */
}
Example #29
0
static void
log_named_signal(int signo)
{
    if (debug)
        DPRINTF1(DEBUG_SIGNALS, "got %s", signal_name(signo));
}
Example #30
0
 * The string is probably a (possibly multi-word) description of the signal
 * (e.g. "Hangup") instead of just the stringified version of the macro
 * (e.g. "SIGHUP"). */
const char *
signal_name(int signum, char *namebuf, size_t bufsize)
{
#if HAVE_DECL_SYS_SIGLIST
    if (signum >= 0 && signum < N_SIGNALS) {
        const char *name = sys_siglist[signum];
        if (name) {
            return name;
        }
    }
#endif

    snprintf(namebuf, bufsize, "signal %d", signum);
    return namebuf;
}

void
xsigaction(int signum, const struct sigaction *new, struct sigaction *old)
{
    if (sigaction(signum, new, old)) {
        char namebuf[SIGNAL_NAME_BUFSIZE];

        VLOG_FATAL("sigaction(%s) failed (%s)",
                   signal_name(signum, namebuf, sizeof namebuf),
                   ovs_strerror(errno));
    }
}