runlevel.c | runlevel.c | |||
---|---|---|---|---|
skipping to change at line 61 | skipping to change at line 61 | |||
#define _BSD_SOURCE | #define _BSD_SOURCE | |||
#include <stdio.h> | #include <stdio.h> | |||
#include <stdbool.h> | #include <stdbool.h> | |||
#include <string.h> | #include <string.h> | |||
#include <errno.h> | #include <errno.h> | |||
#include <assert.h> | #include <assert.h> | |||
#include <unistd.h> | #include <unistd.h> | |||
#include <sys/types.h> | #include <sys/types.h> | |||
#include <sys/stat.h> | #include <sys/stat.h> | |||
#include <dirent.h> | #include <dirent.h> | |||
#include <limits.h> | ||||
#include <seap.h> | #include <seap.h> | |||
#include <probe-api.h> | #include <probe-api.h> | |||
#include <probe/entcmp.h> | #include <probe/entcmp.h> | |||
#include <alloc.h> | #include <alloc.h> | |||
#include "common/debug_priv.h" | #include "common/debug_priv.h" | |||
#ifndef _A | #ifndef _A | |||
#define _A(x) assert(x) | #define _A(x) assert(x) | |||
#endif | #endif | |||
skipping to change at line 87 | skipping to change at line 88 | |||
struct runlevel_rep { | struct runlevel_rep { | |||
char *service_name; | char *service_name; | |||
char *runlevel; | char *runlevel; | |||
bool start; | bool start; | |||
bool kill; | bool kill; | |||
struct runlevel_rep *next; | struct runlevel_rep *next; | |||
}; | }; | |||
static int get_runlevel (struct runlevel_req *req, struct runlevel_rep **re p); | static int get_runlevel (struct runlevel_req *req, struct runlevel_rep **re p); | |||
#if defined(__linux__) || defined(__GLIBC__) | #if defined(__linux__) || defined(__GLIBC__) || (defined(__SVR4) && defined | |||
static int get_runlevel_redhat (struct runlevel_req *req, struct runlevel_r | (__sun)) | |||
ep **rep) | static int get_runlevel_sysv (struct runlevel_req *req, struct runlevel_rep | |||
**rep) | ||||
{ | { | |||
const char runlevel_list[] = {'0', '1', '2', '3', '4', '5', '6'}; | const char runlevel_list[] = {'0', '1', '2', '3', '4', '5', '6'}; | |||
#if defined(__linux__) || defined(__GLIBC__) | ||||
const char *init_path = "/etc/rc.d/init.d"; | const char *init_path = "/etc/rc.d/init.d"; | |||
#elif defined(__SVR4) && defined(__sun) | ||||
const char *init_path = "/etc/init.d"; | ||||
#endif | ||||
const char *rc_path = "/etc/rc%c.d"; | const char *rc_path = "/etc/rc%c.d"; | |||
char pathbuf[PATH_MAX]; | char pathbuf[PATH_MAX]; | |||
DIR *init_dir, *rc_dir; | DIR *init_dir, *rc_dir; | |||
struct dirent *init_dp, *rc_dp; | struct dirent *init_dp, *rc_dp; | |||
struct stat init_st, rc_st; | struct stat init_st, rc_st; | |||
struct runlevel_rep *rep_lst = NULL; | struct runlevel_rep *rep_lst = NULL; | |||
_A(req != NULL); | _A(req != NULL); | |||
_A(rep != NULL); | _A(rep != NULL); | |||
init_dir = opendir(init_path); | init_dir = opendir(init_path); | |||
if (init_dir == NULL) { | if (init_dir == NULL) { | |||
_D("Can't open directory \"%s\": errno=%d, %s.\n", | _D("Can't open directory \"%s\": errno=%d, %s.\n", | |||
init_path, errno, strerror (errno)); | init_path, errno, strerror (errno)); | |||
return (-1); | return (-1); | |||
} | } | |||
if (fchdir(dirfd(init_dir)) != 0) { | if (chdir(init_path) != 0) { | |||
_D("Can't fchdir to \"%s\": errno=%d, %s.\n", | _D("Can't fchdir to \"%s\": errno=%d, %s.\n", | |||
init_path, errno, strerror (errno)); | init_path, errno, strerror (errno)); | |||
closedir(init_dir); | closedir(init_dir); | |||
return (-1); | return (-1); | |||
} | } | |||
while ((init_dp = readdir(init_dir)) != NULL) { | while ((init_dp = readdir(init_dir)) != NULL) { | |||
char *service_name; | char *service_name; | |||
unsigned int i; | unsigned int i; | |||
SEXP_t *r0; | SEXP_t *r0; | |||
skipping to change at line 153 | skipping to change at line 158 | |||
SEXP_free(r0); | SEXP_free(r0); | |||
runlevel[0] = runlevel_list[i]; | runlevel[0] = runlevel_list[i]; | |||
snprintf(pathbuf, sizeof (pathbuf), rc_path, runleve l_list[i]); | snprintf(pathbuf, sizeof (pathbuf), rc_path, runleve l_list[i]); | |||
rc_dir = opendir(pathbuf); | rc_dir = opendir(pathbuf); | |||
if (rc_dir == NULL) { | if (rc_dir == NULL) { | |||
_D("Can't open directory \"%s\": errno=%d, % s.\n", | _D("Can't open directory \"%s\": errno=%d, % s.\n", | |||
rc_path, errno, strerror (errno)); | rc_path, errno, strerror (errno)); | |||
continue; | continue; | |||
} | } | |||
if (fchdir(dirfd(rc_dir)) != 0) { | if (chdir(pathbuf) != 0) { | |||
_D("Can't fchdir to \"%s\": errno=%d, %s.\n" , | _D("Can't fchdir to \"%s\": errno=%d, %s.\n" , | |||
rc_path, errno, strerror (errno)); | rc_path, errno, strerror (errno)); | |||
closedir(rc_dir); | closedir(rc_dir); | |||
continue; | continue; | |||
} | } | |||
start = kill = false; | start = kill = false; | |||
while ((rc_dp = readdir(rc_dir)) != NULL) { | while ((rc_dp = readdir(rc_dir)) != NULL) { | |||
if (stat(rc_dp->d_name, &rc_st) != 0) { | if (stat(rc_dp->d_name, &rc_st) != 0) { | |||
skipping to change at line 285 | skipping to change at line 290 | |||
} | } | |||
static int is_suse (void) | static int is_suse (void) | |||
{ | { | |||
struct stat st; | struct stat st; | |||
return (stat ("/etc/SuSE-release", &st) == 0 || | return (stat ("/etc/SuSE-release", &st) == 0 || | |||
stat ("/etc/sles-release", &st) == 0 || | stat ("/etc/sles-release", &st) == 0 || | |||
stat ("/etc/novell-release", &st) == 0); | stat ("/etc/novell-release", &st) == 0); | |||
} | } | |||
static int is_solaris (void) | ||||
{ | ||||
struct stat st; | ||||
return (stat ("/etc/release", &st) == 0); | ||||
} | ||||
static int is_common (void) | static int is_common (void) | |||
{ | { | |||
return (1); | return (1); | |||
} | } | |||
typedef struct { | typedef struct { | |||
int (*distrop)(void); | int (*distrop)(void); | |||
int (*get_runlevel)(struct runlevel_req *, struct runlevel_rep **); | int (*get_runlevel)(struct runlevel_req *, struct runlevel_rep **); | |||
} distro_tbl_t; | } distro_tbl_t; | |||
const distro_tbl_t distro_tbl[] = { | const distro_tbl_t distro_tbl[] = { | |||
{ &is_debian, &get_runlevel_debian }, | { &is_debian, &get_runlevel_debian }, | |||
{ &is_redhat, &get_runlevel_redhat }, | { &is_redhat, &get_runlevel_sysv }, | |||
{ &is_slack, &get_runlevel_slack }, | { &is_slack, &get_runlevel_slack }, | |||
{ &is_gentoo, &get_runlevel_gentoo }, | { &is_gentoo, &get_runlevel_gentoo }, | |||
{ &is_arch, &get_runlevel_arch }, | { &is_arch, &get_runlevel_arch }, | |||
{ &is_mandriva, &get_runlevel_mandriva }, | { &is_mandriva, &get_runlevel_mandriva }, | |||
{ &is_suse, &get_runlevel_suse }, | { &is_suse, &get_runlevel_suse }, | |||
{ &is_solaris, &get_runlevel_sysv }, | ||||
{ &is_common, &get_runlevel_common } | { &is_common, &get_runlevel_common } | |||
}; | }; | |||
#define DISTRO_TBL_SIZE ((sizeof distro_tbl)/sizeof (distro_tbl_t)) | #define DISTRO_TBL_SIZE ((sizeof distro_tbl)/sizeof (distro_tbl_t)) | |||
static int get_runlevel_generic (struct runlevel_req *req, struct runlevel_ rep **rep) | static int get_runlevel_generic (struct runlevel_req *req, struct runlevel_ rep **rep) | |||
{ | { | |||
uint16_t i; | uint16_t i; | |||
_A(req != NULL); | _A(req != NULL); | |||
skipping to change at line 346 | skipping to change at line 358 | |||
static int get_runlevel (struct runlevel_req *req, struct runlevel_rep **re p) | static int get_runlevel (struct runlevel_req *req, struct runlevel_rep **re p) | |||
{ | { | |||
_A(req != NULL); | _A(req != NULL); | |||
_A(rep != NULL); | _A(rep != NULL); | |||
return (-1); | return (-1); | |||
} | } | |||
#else | #else | |||
# error "Sorry, your OS isn't supported." | # error "Sorry, your OS isn't supported." | |||
#endif | #endif | |||
int probe_main (SEXP_t *object, SEXP_t *probe_out, void *arg, SEXP_t *filte rs) | int probe_main (probe_ctx *ctx, void *arg) | |||
{ | { | |||
SEXP_t *object; | ||||
struct runlevel_req request_st; | struct runlevel_req request_st; | |||
struct runlevel_rep *reply_st = NULL; | struct runlevel_rep *reply_st = NULL; | |||
(void)filters; | object = probe_ctx_getobject(ctx); | |||
if (object == NULL || probe_out == NULL) { | ||||
return (PROBE_EINVAL); | ||||
} | ||||
request_st.service_name_ent = probe_obj_getent(object, "service_name ", 1); | request_st.service_name_ent = probe_obj_getent(object, "service_name ", 1); | |||
if (request_st.service_name_ent == NULL) { | if (request_st.service_name_ent == NULL) { | |||
_D("%s: element not found\n", "service_name"); | _D("%s: element not found\n", "service_name"); | |||
return PROBE_ENOELM; | return PROBE_ENOELM; | |||
} | } | |||
request_st.runlevel_ent = probe_obj_getent(object, "runlevel", 1); | request_st.runlevel_ent = probe_obj_getent(object, "runlevel", 1); | |||
if (request_st.runlevel_ent == NULL) { | if (request_st.runlevel_ent == NULL) { | |||
SEXP_free(request_st.service_name_ent); | SEXP_free(request_st.service_name_ent); | |||
_D("%s: element not found\n", "runlevel"); | _D("%s: element not found\n", "runlevel"); | |||
return PROBE_ENOELM; | return PROBE_ENOELM; | |||
} | } | |||
if (get_runlevel(&request_st, &reply_st) == -1) { | if (get_runlevel(&request_st, &reply_st) == -1) { | |||
SEXP_t *msg; | SEXP_t *msg; | |||
msg = probe_msg_creat(OVAL_MESSAGE_LEVEL_ERROR, "get_runleve l failed."); | msg = probe_msg_creat(OVAL_MESSAGE_LEVEL_ERROR, "get_runleve l failed."); | |||
probe_cobj_add_msg(probe_out, msg); | probe_cobj_add_msg(probe_ctx_getresult(ctx), msg); | |||
SEXP_free(msg); | SEXP_free(msg); | |||
probe_cobj_set_flag(probe_out, SYSCHAR_FLAG_ERROR); | probe_cobj_set_flag(probe_ctx_getresult(ctx), SYSCHAR_FLAG_E RROR); | |||
} else { | } else { | |||
struct runlevel_rep *next_rep; | struct runlevel_rep *next_rep; | |||
SEXP_t *item; | SEXP_t *item; | |||
while (reply_st != NULL) { | while (reply_st != NULL) { | |||
dI("get_runlevel: [0]=\"%s\", [1]=\"%s\", [2]=\"%d\" , [3]=\"%d\"\n", | dI("get_runlevel: [0]=\"%s\", [1]=\"%s\", [2]=\"%d\" , [3]=\"%d\"\n", | |||
reply_st->service_name, reply_st->runlevel, reply _st->start, reply_st->kill); | reply_st->service_name, reply_st->runlevel, reply _st->start, reply_st->kill); | |||
item = probe_item_create(OVAL_UNIX_RUNLEVEL, NULL, | item = probe_item_create(OVAL_UNIX_RUNLEVEL, NULL, | |||
"service_name", OVAL_DATAT YPE_STRING, reply_st->service_name, | "service_name", OVAL_DATAT YPE_STRING, reply_st->service_name, | |||
"runlevel", OVAL_DATAT YPE_STRING, reply_st->runlevel, | "runlevel", OVAL_DATAT YPE_STRING, reply_st->runlevel, | |||
"start", OVAL_DATAT YPE_BOOLEAN, reply_st->start, | "start", OVAL_DATAT YPE_BOOLEAN, reply_st->start, | |||
"kill", OVAL_DATAT YPE_BOOLEAN, reply_st->kill, | "kill", OVAL_DATAT YPE_BOOLEAN, reply_st->kill, | |||
NULL); | NULL); | |||
probe_cobj_add_item(probe_out, item); | probe_item_collect(ctx, item); | |||
SEXP_free(item); | ||||
next_rep = reply_st->next; | next_rep = reply_st->next; | |||
oscap_free(reply_st->service_name); | oscap_free(reply_st->service_name); | |||
oscap_free(reply_st->runlevel); | oscap_free(reply_st->runlevel); | |||
oscap_free(reply_st); | oscap_free(reply_st); | |||
reply_st = next_rep; | reply_st = next_rep; | |||
} | } | |||
} | } | |||
SEXP_free(request_st.runlevel_ent); | SEXP_free(request_st.runlevel_ent); | |||
End of changes. 15 change blocks. | ||||
16 lines changed or deleted | 25 lines changed or added | |||
This html diff was produced by rfcdiff 1.41. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ |