Beispiel #1
0
/* send failed result */
void send_failed_result(gm_job_t * exec_job, int sig) {
    struct timeval end_time;
    char buffer[GM_BUFFERSIZE];
    char * signame;
    buffer[0] = '\x0';

    gm_log( GM_LOG_TRACE, "send_failed_result()\n");

    gettimeofday(&end_time, NULL);
    exec_job->finish_time = end_time;
    exec_job->return_code = STATE_CRITICAL;

    signame = nr2signal(sig);
    snprintf( buffer, sizeof( buffer )-1, "(Return code of %d is out of bounds. Worker exited by signal %s on worker: %s)", sig, signame, mod_gm_opt->identifier);
    free(exec_job->output);
    exec_job->output = strdup( buffer );
    free(signame);

    send_result_back(exec_job);

    return;
}
Beispiel #2
0
int main(void) {
    plan(60);

    /* lowercase */
    char test[100];
    ok(lc(NULL) == NULL, "lc(NULL)");
    strcpy(test, "Yes"); like(lc(test), "yes", "lc(yes)");
    strcpy(test, "YES"); like(lc(test), "yes", "lc(YES)");
    strcpy(test, "yeS"); like(lc(test), "yes", "lc(yeS)");


    /* trim */
    strcpy(test, "    text  "); like(ltrim(test), "text  ",   "ltrim()");
    strcpy(test, "    text  "); like(rtrim(test), "    text", "rtrim()");
    strcpy(test, "    text  "); like(trim(test),  "text",     "trim()");
    char *test2;
    test2 = strdup("   text   ");  like(trim(test2),  "text", "trim()");
    free(test2);

    /* parse_yes_or_no */
    ok(parse_yes_or_no(NULL,    GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 1");
    ok(parse_yes_or_no(NULL,    GM_DISABLED) == GM_DISABLED, "parse_yes_or_no 2");
    strcpy(test, "");      ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 3");
    strcpy(test, "");      ok(parse_yes_or_no(test, GM_DISABLED) == GM_DISABLED, "parse_yes_or_no 4");
    strcpy(test, "yes");   ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 5");
    strcpy(test, "true");  ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 6");
    strcpy(test, "Yes");   ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 7");
    strcpy(test, "1");     ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 8");
    strcpy(test, "On");    ok(parse_yes_or_no(test, GM_ENABLED)  == GM_ENABLED, "parse_yes_or_no 9");
    strcpy(test, "Off");   ok(parse_yes_or_no(test, GM_ENABLED)  == GM_DISABLED, "parse_yes_or_no 10");
    strcpy(test, "false"); ok(parse_yes_or_no(test, GM_ENABLED)  == GM_DISABLED, "parse_yes_or_no 11");
    strcpy(test, "no");    ok(parse_yes_or_no(test, GM_ENABLED)  == GM_DISABLED, "parse_yes_or_no 12");
    strcpy(test, "0");     ok(parse_yes_or_no(test, GM_ENABLED)  == GM_DISABLED, "parse_yes_or_no 13");


    /* trim */
    ok(trim(NULL) == NULL, "trim(NULL)");
    strcpy(test, " test "); like(trim(test), "^test$", "trim(' test ')");
    strcpy(test, "\ntest\n"); like(trim(test), "^test$", "trim('\\ntest\\n')");

    /* reading keys */
    mod_gm_opt_t *mod_gm_opt;
    mod_gm_opt = malloc(sizeof(mod_gm_opt_t));
    int rc = set_default_options(mod_gm_opt);

    ok(rc == 0, "setting default options");
    mod_gm_opt->keyfile = strdup("t/data/test1.key");
    read_keyfile(mod_gm_opt);
    //printf_hex(mod_gm_opt->crypt_key, 32);
    test[0]='\x0';
    int i = 0;
    char hex[4];
    for(i=0; i<32; i++) {
        hex[0] = '\x0';
        snprintf(hex, 4, "%02x", mod_gm_opt->crypt_key[i]);
        strncat(test, hex, 4);
    }
    like(test, "3131313131313131313131313131313131313131313131313131313131310000", "read keyfile t/data/test1.key");

    free(mod_gm_opt->keyfile);
    mod_gm_opt->keyfile = strdup("t/data/test2.key");
    read_keyfile(mod_gm_opt);

    like(mod_gm_opt->crypt_key, "abcdef", "reading keyfile t/data/test2.key");

    free(mod_gm_opt->keyfile);
    mod_gm_opt->keyfile = strdup("t/data/test3.key");
    read_keyfile(mod_gm_opt);
    //printf_hex(mod_gm_opt->crypt_key, 32);
    like(mod_gm_opt->crypt_key, "11111111111111111111111111111111", "reading keyfile t/data/test3.key");
    ok(strlen(mod_gm_opt->crypt_key) == 32, "key size for t/data/test3.key");


    /* encrypt */
    char * key       = "test1234";
    char * encrypted = malloc(GM_BUFFERSIZE);
    char * text      = "test message";
    char * base      = "a7HqhQEE8TQBde9uknpPYQ==";
    mod_gm_crypt_init(key);
    int len;
    len = mod_gm_encrypt(&encrypted, text, GM_ENCODE_AND_ENCRYPT);
    ok(len == 24, "length of encrypted only");
    like(encrypted, base, "encrypted string");

    /* decrypt */
    char * decrypted = malloc(GM_BUFFERSIZE);
    mod_gm_decrypt(&decrypted, encrypted, GM_ENCODE_AND_ENCRYPT);
    like(decrypted, text, "decrypted text");
    free(decrypted);
    free(encrypted);

    /* base 64 */
    char * base64 = malloc(GM_BUFFERSIZE);
    len = mod_gm_encrypt(&base64, text, GM_ENCODE_ONLY);
    ok(len == 16, "length of encode only");
    like(base64, "dGVzdCBtZXNzYWdl", "base64 only string");

    /* debase 64 */
    char * debase64 = malloc(GM_BUFFERSIZE);
    mod_gm_decrypt(&debase64, base64, GM_ENCODE_ONLY);
    like(debase64, text, "debase64 text");
    free(debase64);
    free(base64);


    /* file_exists */
    ok(file_exists("01_utils") == 1, "file_exists('01_utils')");
    ok(file_exists("non-exist") == 0, "file_exists('non-exist')");

    /* nr2signal */
    char * signame1 = nr2signal(9);
    like(signame1, "SIGKILL", "get SIGKILL for 9");
    free(signame1);

    char * signame2 = nr2signal(15);
    like(signame2, "SIGTERM", "get SIGTERM for 15");
    free(signame2);


    /* string2timeval */
    struct timeval t;
    string2timeval("100.50", &t);
    ok(t.tv_sec  == 100, "string2timeval 1");
    ok(t.tv_usec == 50, "string2timeval 2");

    string2timeval("100", &t);
    ok(t.tv_sec  == 100, "string2timeval 3");
    ok(t.tv_usec == 0, "string2timeval 4");

    string2timeval("", &t);
    ok(t.tv_sec  == 0, "string2timeval 5");
    ok(t.tv_usec == 0, "string2timeval 6");

    string2timeval(NULL, &t);
    ok(t.tv_sec  == 0, "string2timeval 7");
    ok(t.tv_usec == 0, "string2timeval 8");

    /* command line parsing */
    mod_gm_free_opt(mod_gm_opt);
    mod_gm_opt = renew_opts();
    strcpy(test, "server=host:4730");
    parse_args_line(mod_gm_opt, test, 0);
    like(mod_gm_opt->server_list[0], "host:4730", "server=host:4730");
    ok(mod_gm_opt->server_num == 1, "server_number = %d", mod_gm_opt->server_num);

    mod_gm_free_opt(mod_gm_opt);
    mod_gm_opt = renew_opts();
    strcpy(test, "server=:4730");
    parse_args_line(mod_gm_opt, test, 0);
    like(mod_gm_opt->server_list[0], "localhost:4730", "server=:4730");
    ok(mod_gm_opt->server_num == 1, "server_number = %d", mod_gm_opt->server_num);

    mod_gm_free_opt(mod_gm_opt);
    mod_gm_opt = renew_opts();
    strcpy(test, "server=localhost:4730");
    parse_args_line(mod_gm_opt, test, 0);
    strcpy(test, "server=localhost:4730");
    parse_args_line(mod_gm_opt, test, 0);
    like(mod_gm_opt->server_list[0], "localhost:4730", "duplicate server");
    ok(mod_gm_opt->server_num == 1, "server_number = %d", mod_gm_opt->server_num);

    mod_gm_free_opt(mod_gm_opt);
    mod_gm_opt = renew_opts();
    strcpy(test, "server=localhost:4730,localhost:4730,:4730,host:4730,");
    parse_args_line(mod_gm_opt, test, 0);
    like(mod_gm_opt->server_list[0], "localhost:4730", "duplicate server");
    like(mod_gm_opt->server_list[1], "host:4730", "duplicate server");
    ok(mod_gm_opt->server_num == 2, "server_number = %d", mod_gm_opt->server_num);

    /* escape newlines */
    char * escaped = gm_escape_newlines(" test\n", GM_DISABLED);
    is(escaped, " test\\n", "untrimmed escape string");
    free(escaped);
    escaped = gm_escape_newlines(" test\n", GM_ENABLED);
    is(escaped, "test", "trimmed escape string");
    free(escaped);

    /* md5 sum */
    char * sum = NULL;
    strcpy(test, "");
    sum = md5sum(test);
    like(sum, "d41d8cd98f00b204e9800998ecf8427e", "md5sum()");
    free(sum);

    strcpy(test, "The quick brown fox jumps over the lazy dog.");
    sum = md5sum(test);
    like(sum, "e4d909c290d0fb1ca068ffaddf22cbd0", "md5sum()");
    free(sum);

    mod_gm_free_opt(mod_gm_opt);

    return exit_status();
}
Beispiel #3
0
/* execute this command with given timeout */
int execute_safe_command(gm_job_t * exec_job, int fork_exec, char * identifier) {
    int pipe_stdout[2] , pipe_stderr[2];
    int return_code;
    int pclose_result;
    char *plugin_output, *plugin_error;
    char *bufdup;
    char buffer[GM_BUFFERSIZE], buf_error[GM_BUFFERSIZE];
    struct timeval start_time,end_time;
    pid_t pid    = 0;
    buffer[0]    = '\x0';
    buf_error[0] = '\x0';

    gm_log( GM_LOG_TRACE, "execute_safe_command()\n" );

    // mark all filehandles to close on exec
    int x;
    for(x = 0; x<=64; x++)
        fcntl(x, F_SETFD, FD_CLOEXEC);

    signal(SIGTERM, SIG_DFL);
    signal(SIGINT, SIG_DFL);

    if(exec_job->start_time.tv_sec == 0) {
        gettimeofday(&start_time,NULL);
        exec_job->start_time = start_time;
    }

    /* fork a child process */
    if(fork_exec == GM_ENABLED) {
        if(pipe(pipe_stdout) != 0)
            perror("pipe stdout");
        if(pipe(pipe_stderr) != 0)
            perror("pipe stderr");

        pid=fork();

        /*fork error */
        if( pid == -1 ) {
            exec_job->output      = strdup("(Error On Fork)");
            exec_job->return_code = 3;
            return(GM_ERROR);
        }
    }

    /* we are in the child process */
    if( fork_exec == GM_DISABLED || pid == 0 ) {

        /* become the process group leader */
        setpgid(0,0);
        pid = getpid();

        if( fork_exec == GM_ENABLED ) {
            close(pipe_stdout[0]);
            close(pipe_stderr[0]);
        }
        signal(SIGALRM, check_alarm_handler);
        alarm(exec_job->timeout);

        /* run the plugin check command */
        pclose_result = run_check(exec_job->command_line, &plugin_output, &plugin_error);
        return_code   = pclose_result;

        if(fork_exec == GM_ENABLED) {
            if(write(pipe_stdout[1], plugin_output, strlen(plugin_output)+1) <= 0)
                perror("write stdout");
            if(write(pipe_stderr[1], plugin_error, strlen(plugin_error)+1) <= 0)
                perror("write");

            if(pclose_result == -1) {
                char error[GM_BUFFERSIZE];
                snprintf(error, sizeof(error), "error on %s: %s", identifier, strerror(errno));
                if(write(pipe_stdout[1], error, strlen(error)+1) <= 0)
                    perror("write");
            }

            return_code = real_exit_code(pclose_result);
            free(plugin_output);
            free(plugin_error);
            _exit(return_code);
        }
        else {
            snprintf( buffer,    sizeof( buffer )-1,    "%s", plugin_output );
            snprintf( buf_error, sizeof( buf_error )-1, "%s", plugin_error  );
            free(plugin_output);
            free(plugin_error);
        }
    }

    /* we are the parent */
    if( fork_exec == GM_DISABLED || pid > 0 ){

        if( fork_exec == GM_ENABLED) {
            gm_log( GM_LOG_TRACE, "started check with pid: %d\n", pid);

            close(pipe_stdout[1]);
            close(pipe_stderr[1]);

            waitpid(pid, &return_code, 0);
            gm_log( GM_LOG_TRACE, "finished check from pid: %d with status: %d\n", pid, return_code);
            /* get all lines of plugin output */
            if(read(pipe_stdout[0], buffer, sizeof(buffer)-1) < 0)
                perror("read");
            if(read(pipe_stderr[0], buf_error, sizeof(buf_error)-1) < 0)
                perror("read");
        }
        return_code = real_exit_code(return_code);

        /* file not executable? */
        if(return_code == 126) {
            return_code = STATE_CRITICAL;
            snprintf( buffer, sizeof( buffer )-1, "CRITICAL: Return code of 126 is out of bounds. Make sure the plugin you're trying to run is executable. (worker: %s)", identifier);
        }
        /* file not found errors? */
        else if(return_code == 127) {
            return_code = STATE_CRITICAL;
            snprintf( buffer, sizeof( buffer )-1, "CRITICAL: Return code of 127 is out of bounds. Make sure the plugin you're trying to run actually exists. (worker: %s)", identifier);
        }
        /* signaled */
        else if(return_code >= 128 && return_code < 144) {
            char * signame = nr2signal((int)(return_code-128));
            bufdup = strdup(buffer);
            snprintf( buffer, sizeof( buffer )-1, "CRITICAL: Return code of %d is out of bounds. Plugin exited by signal %s. (worker: %s)\\n%s", (int)(return_code), signame, identifier, bufdup);
            return_code = STATE_CRITICAL;
            free(bufdup);
            free(signame);
        }
        /* other error codes > 3 */
        else if(return_code > 3) {
            gm_log( GM_LOG_DEBUG, "check exited with exit code > 3. Exit: %d\n", (int)(return_code));
            gm_log( GM_LOG_DEBUG, "stdout: %s\n", buffer);
            bufdup = strdup(buffer);
            snprintf( buffer, sizeof( buffer )-1, "CRITICAL: Return code of %d is out of bounds. (worker: %s)\\n%s", (int)(return_code), identifier, bufdup);
            free(bufdup);
            if(return_code != 25 && mod_gm_opt->workaround_rc_25 == GM_DISABLED) {
                return_code = STATE_CRITICAL;
            }
        }

        exec_job->output      = strdup(buffer);
        exec_job->error       = strdup(buf_error);
        exec_job->return_code = return_code;
        if( fork_exec == GM_ENABLED) {
            close(pipe_stdout[0]);
            close(pipe_stderr[0]);
        }
    }
    alarm(0);
    current_child_pid = 0;
    pid               = 0;

    /* record check result info */
    gettimeofday(&end_time, NULL);
    exec_job->finish_time = end_time;

    /* did we have a timeout? */
    if(exec_job->timeout < ((int)end_time.tv_sec - (int)exec_job->start_time.tv_sec)) {
        exec_job->return_code   = 2;
        exec_job->early_timeout = 1;
        if ( !strcmp( exec_job->type, "service" ) )
            snprintf( buffer, sizeof( buffer ) -1, "(Service Check Timed Out On Worker: %s)", identifier);
        if ( !strcmp( exec_job->type, "host" ) )
            snprintf( buffer, sizeof( buffer ) -1, "(Host Check Timed Out On Worker: %s)", identifier);
        free(exec_job->output);
        exec_job->output = strdup( buffer );
    }

    return(GM_OK);
}