Personal tools
You are here: Home オペレーティングシステム論 演習 2007年度 第3回 signal.c
Document Actions

signal.c

by 管理者 last modified 2007-05-07 17:28

Click here to get the file

Size 2.7 kB - File type text/x-csrc

File contents

/*
 * $Id: alarm.c,v 1.2 2007/04/30 17:50:51 yamamoto Exp yamamoto $ 
 */

#include <signal.h>             /* For sigaction(). */
#include <stdarg.h>             /* For variable argument lists. */
#include <stdio.h>
#include <stdlib.h>             /* For EXIT_SUCCESS. */

#ifndef FALSE
#define FALSE           0
#define TRUE            1
#endif

static int          debug_mode = FALSE;

static void set_signal_handler(void);
static void debug(const char *format, ...);
static void handler(int x);

int main(int argc, char *argv[])
{
    int         status;
    pid_t       pid;

    if (2 <= argc && !strcmp(argv[1], "-d")) {
        debug_mode = TRUE;
    }
    set_signal_handler();               /* シグナルハンドラの登録. */
    debug("catch: getpid() %d.\n", getpid());
    while (1) {
        fprintf(stderr, "catch: Zzz.\n");
        /* sleep(1); */
        alarm(1); pause();
    }
    exit (EXIT_SUCCESS);
}

/*
 * シグナルハンドラを設定する.
 */

static void set_signal_handler(void)
{
    static struct sigaction    action;
    action.sa_handler = handler;            /* シグナルハンドラ. */
    /* ハンドラ内でSIGINTをブロックする. */
    sigemptyset(&action.sa_mask);           /* マスクのクリア. */  
    sigaddset(&action.sa_mask, SIGINT);
    action.sa_flags = SA_RESTART;           /* BSDとの互換性(おまじない). */
    sigaction(SIGINT, &action, NULL);       /* SIGINTにハンドラを設定.*/
    sigaction(SIGSEGV, &action, NULL);      /* SIGSEGVにも設定.*/ 
    sigaction(SIGALRM, &action, NULL);      /* SIGALRMにも設定. */
    sigaction(SIGUSR1, &action, NULL);      /* SIGUSR1にも設定. */
    sigaction(SIGCONT, &action, NULL);      /* SIGCONTにも設定. */
}

/*
 * シグナルハンドラ.
 */

static void handler(int x)
{
    char    *sig_name;
    fflush(stdout);
    fflush(stderr);
    /* !! Not so good. */
    if (x == SIGINT) {
        sig_name = "SIGINT";
    } else if (x == SIGSEGV) {
        sig_name = "SIGSEGV";
    } else if (x == SIGALRM) {
        sig_name = "SIGALRM";
    } else if (x == SIGUSR1) {
        sig_name = "SIGUSR1";
    } else if (x == SIGCONT) {
        sig_name = "SIGCONT";
    } else {
        sig_name = "UNKNOWN";    
    }    

    fprintf(stderr, "catch: Signal (%s, %d).\n", sig_name, x);

    if (x == SIGSEGV) {
        exit (EXIT_FAILURE);
    }
}

static void debug(const char *format, ...)
{
    va_list     args;
    
    if (!debug_mode) {
        return;
    }

    fflush(stdout);
    fflush(stderr);

    fputs("Debug: ", stderr);
    va_start(args, format);
    vfprintf(stderr, format, args);
    va_end(args);

    fflush(stderr);
}