int main(int argc, char **argv) { int c, test_config = 0; int uid=0,gid=0; int do_chroot = 0; char *dir = DEFAULTDIR; char *user = USER; char *group = GROUPGLOBAL; char *cfg = DEFAULTCPATH; char *filter_by = NULL; char *filter_value = NULL; char *related_of = NULL; char *related_values = NULL; report_filter r_filter; /* Setting the name */ OS_SetName(ARGV0); r_filter.group = NULL; r_filter.rule = NULL; r_filter.level = NULL; r_filter.location = NULL; r_filter.srcip = NULL; r_filter.user = NULL; r_filter.files = NULL; r_filter.show_alerts = 0; r_filter.related_group = 0; r_filter.related_rule = 0; r_filter.related_level = 0; r_filter.related_location = 0; r_filter.related_srcip = 0; r_filter.related_user = 0; r_filter.related_file = 0; r_filter.report_name = NULL; while((c = getopt(argc, argv, "Vdhstu:g:D:c:f:v:n:r:NC")) != -1) { switch(c){ case 'V': print_version(); break; case 'h': report_help(); break; case 'd': nowDebug(); break; case 'n': if(!optarg) ErrorExit("%s: -n needs an argument",ARGV0); r_filter.report_name = optarg; break; case 'r': if(!optarg || !argv[optind]) ErrorExit("%s: -r needs two argument",ARGV0); related_of = optarg; related_values = argv[optind]; if(os_report_configfilter(related_of, related_values, &r_filter, REPORT_RELATED) < 0) { ErrorExit(CONFIG_ERROR, ARGV0, "user argument"); } optind++; break; case 'f': if(!optarg) ErrorExit("%s: -f needs two argument",ARGV0); filter_by = optarg; filter_value = argv[optind]; if(os_report_configfilter(filter_by, filter_value, &r_filter, REPORT_FILTER) < 0) { ErrorExit(CONFIG_ERROR, ARGV0, "user argument"); } optind++; break; case 'u': if(!optarg) ErrorExit("%s: -u needs an argument",ARGV0); user=optarg; break; case 'g': if(!optarg) ErrorExit("%s: -g needs an argument",ARGV0); group=optarg; break; case 'D': if(!optarg) ErrorExit("%s: -D needs an argument",ARGV0); dir=optarg; break; case 'c': if(!optarg) ErrorExit("%s: -c needs an argument",ARGV0); cfg = optarg; break; case 't': test_config = 1; break; case 's': r_filter.show_alerts = 1; break; case 'N': do_chroot = 0; break; case 'C': do_chroot = 1; break; default: report_help(); break; } } /* Starting daemon */ debug1(STARTED_MSG,ARGV0); /* Check if the user/group given are valid */ uid = Privsep_GetUser(user); gid = Privsep_GetGroup(group); if((uid < 0)||(gid < 0)) ErrorExit(USER_ERROR,ARGV0,user,group); /* Exit here if test config is set */ if(test_config) exit(0); /* Privilege separation */ if(Privsep_SetGroup(gid) < 0) ErrorExit(SETGID_ERROR,ARGV0,group); /* chrooting */ if (do_chroot) { if(Privsep_Chroot(dir) < 0) ErrorExit(CHROOT_ERROR,ARGV0,dir); nowChroot(); } else { chdir(dir); } /* Changing user */ if(Privsep_SetUser(uid) < 0) ErrorExit(SETUID_ERROR,ARGV0,user); debug1(PRIVSEP_MSG,ARGV0,dir,user); /* Signal manipulation */ StartSIG(ARGV0); /* Creating PID files */ if(CreatePID(ARGV0, getpid()) < 0) ErrorExit(PID_ERROR,ARGV0); /* Start up message */ verbose(STARTUP_MSG, ARGV0, (int)getpid()); /* the real stuff now */ os_ReportdStart(&r_filter); exit(0); }
void generate_reports(int cday, int cmon, int cyear, const struct tm *p) { int s = 0; if (!mond.smtpserver) { return; } if (mond.reports) { int twait = 0; int childcount = 0; while (mond.reports[s]) { pid_t pid; if (mond.reports[s]->emailto == NULL) { s++; continue; } /* We create a new process to run the report and send the email. * To avoid crashing monitord if something goes wrong. */ pid = fork(); if (pid < 0) { merror("%s: ERROR: Fork failed. cause: %d - %s", ARGV0, errno, strerror(errno)); s++; continue; } else if (pid == 0) { char fname[256]; char aname[256]; fname[255] = '\0'; aname[255] = '\0'; snprintf(fname, 255, "/logs/.report-%d.log", (int)getpid()); merror("%s: INFO: Starting daily reporting for '%s'", ARGV0, mond.reports[s]->title); mond.reports[s]->r_filter.fp = fopen(fname, "w+"); if (!mond.reports[s]->r_filter.fp) { merror("%s: ERROR: Unable to open temporary reports file.", ARGV0); s++; continue; } /* Open the log file */ snprintf(aname, 255, "%s/%d/%s/ossec-%s-%02d.log", ALERTS, cyear, monthss[cmon], "alerts", cday); os_strdup(aname, mond.reports[s]->r_filter.filename); /* Start report */ os_ReportdStart(&mond.reports[s]->r_filter); fflush(mond.reports[s]->r_filter.fp); if (ftell(mond.reports[s]->r_filter.fp) < 10) { merror("%s: INFO: Report '%s' empty.", ARGV0, mond.reports[s]->title); } else if (OS_SendCustomEmail(mond.reports[s]->emailto, mond.reports[s]->title, mond.smtpserver, mond.emailfrom, NULL, mond.emailidsname, mond.reports[s]->r_filter.fp, p) != 0) { merror("%s: WARN: Unable to send report email.", ARGV0); } fclose(mond.reports[s]->r_filter.fp); unlink(fname); free(mond.reports[s]->r_filter.filename); mond.reports[s]->r_filter.filename = NULL; exit(0); } else { /* Sleep between each report. Time is not important in here. */ sleep(20); childcount++; } s++; } while (childcount) { int wp; wp = waitpid((pid_t) - 1, NULL, WNOHANG); if (wp < 0) { merror(WAITPID_ERROR, ARGV0, errno, strerror(errno)); } else if (wp == 0) { /* If there is still any report left, sleep 5 and try again */ sleep(5); twait++; if (twait > 2) { merror("%s: WARN: Report taking too long to complete. Waiting for it to finish...", ARGV0); sleep(10); if (twait > 10) { merror("%s: WARN: Report took too long. Moving on...", ARGV0); break; } } } else { childcount--; } } } return; }