wazuh通过wazuh-modulesd进程启动各个模块的提供的线程函数来运行各个模块的功能
int main(int argc, char **argv)
{
int c;
int wm_debug = 0;
int test_config = 0;
/* Set the name */
OS_SetName(ARGV0);
// Define current working directory
char * home_path = w_homedir(argv[0]);
if (chdir(home_path) == -1) {
merror_exit(CHDIR_ERROR, home_path, errno, strerror(errno));
}
wmodule *cur_module;
wm_debug_level = getDefine_Int("wazuh_modules", "debug", 0, 2);
// Get command line options
while ((c = getopt(argc, argv, "dfht")) != -1) {
switch (c) {
case 'd':
nowDebug();
wm_debug = 1;
break;
case 'f':
flag_foreground = 1;
break;
case 'h':
wm_help();
break;
case 't':
test_config = 1;
flag_foreground = 1;
break;
default:
print_out(" ");
wm_help();
}
}
// Get default debug level
if (wm_debug == 0) {
wm_debug = wm_debug_level;
while (wm_debug != 0) {
nowDebug();
wm_debug--;
}
}
mdebug1(WAZUH_HOMEDIR, home_path);
os_free(home_path);
// Setup daemon
wm_setup();
if (test_config)
exit(EXIT_SUCCESS);
minfo(STARTUP_MSG, (int)getpid());
// Run modules
for (cur_module = wmodules; cur_module; cur_module = cur_module->next) {
if (CreateThreadJoinable(&cur_module->thread, cur_module->context->start, cur_module->data) < 0) {
merror_exit("CreateThreadJoinable() for '%s': %s", cur_module->tag, strerror(errno));
}
mdebug2("Created new thread for the '%s' module.", cur_module->tag);
}
// Start com request thread
w_create_thread(wmcom_main, NULL);
// Wait for threads
for (cur_module = wmodules; cur_module; cur_module = cur_module->next) {
pthread_join(cur_module->thread, NULL);
}
return EXIT_SUCCESS;
}
wazuh-modulesd 必须要在home目录下才能启动, w_homedir(argv[0]); argv[0]是当前命令所在的命令行绝对路径,比如在/var/ossec/目录下执行 wazuh-modulesd, 那么argv[0]就是/var/ossec,
// Define current working directory
char * home_path = w_homedir(argv[0]);
if (chdir(home_path) == -1) {
merror_exit(CHDIR_ERROR, home_path, errno, strerror(errno));
}
w_homedir()函数,分析/proc , argv[0], 环境变量WAZUH_HOME。home目录下必须包含"/bin"
/**
* @brief Get the Wazuh installation directory
*
* It is obtained from the /proc directory, argv[0], or the env variable WAZUH_HOME
*
* @param arg ARGV0 - Program name
* @return Pointer to the Wazuh installation path on success
*/
char *w_homedir(char *arg) {
minfo("heath arg : '%s'", arg);
char *buff = NULL;
struct stat buff_stat;
char * delim = "/bin";
os_calloc(PATH_MAX, sizeof(char), buff);
#ifdef __MACH__
pid_t pid = getpid();
if (proc_pidpath(pid, buff, PATH_MAX) > 0) {
buff = w_strtok_r_str_delim(delim, &buff);
}
#else
if (realpath("/proc/self/exe", buff) != NULL) {
dirname(buff);
buff = w_strtok_r_str_delim(delim, &buff);
}
else if (realpath("/proc/curproc/file", buff) != NULL) {
dirname(buff);
buff = w_strtok_r_str_delim(delim, &buff);
}
else if (realpath("/proc/self/path/a.out", buff) != NULL) {
dirname(buff);
buff = w_strtok_r_str_delim(delim, &buff);
}
#endif
else if (realpath(arg, buff) != NULL) {
dirname(buff);
buff = w_strtok_r_str_delim(delim, &buff);
} else {
// The path was not found so read WAZUH_HOME env var
char * home_env = NULL;
if (home_env = getenv(WAZUH_HOME_ENV), home_env) {
snprintf(buff, PATH_MAX, "%s", home_env);
}
}
if ((stat(buff, &buff_stat) < 0) || !S_ISDIR(buff_stat.st_mode)) {
os_free(buff);
merror_exit(HOME_ERROR);
}
return buff;
}
创建各模块线程, 这里主要关注sca模块的线程函数
// Run modules
for (cur_module = wmodules; cur_module; cur_module = cur_module->next) {
if (CreateThreadJoinable(&cur_module->thread, cur_module->context->start, cur_module->data) < 0) {
merror_exit("CreateThreadJoinable() for '%s': %s", cur_module->tag, strerror(errno));
}
mdebug2("Created new thread for the '%s' module.", cur_module->tag);
}