main.c
来自「一百个病毒的源代码 包括熊猫烧香等 极其具有研究价值」· C语言 代码 · 共 586 行
C
586 行
/*** Modular Logfile Analyzer** Copyright 2000 Jan Kneschke <jan@kneschke.de>**** Homepage: http://www.kneschke.de/projekte/modlogan** This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version, and provided that the above copyright and permission notice is included with all distributed copies of this or derived software. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA**** $Id: main.c,v 1.36 2001/01/11 22:19:40 jk Exp $*/#include <libintl.h>#include <locale.h>#include <stdlib.h>#include <stdio.h>#include <time.h>#include <unistd.h>#include <dirent.h>#include <errno.h>#include <string.h>#include <sys/stat.h>#include <sys/time.h>#include "config.h"#ifdef HAVE_GETOPT_H#include <getopt.h>#endif#ifdef HAVE_LIBZ#include <zlib.h>#else #include "zlibwrapper.h"#endif#include "mrecord.h"#include "mstate.h"#include "mlocale.h"#include "mconfig.h"#include "mplugins.h"#include "mdatatypes.h"int history_write(mconfig *conf, mlist *l, char *subpath) { char filename[255]; gzFile *f; sprintf(filename, "%s%s%s/modlogan.history%s", conf->outputdir ? conf->outputdir : ".", subpath ? "/" : "", subpath ? subpath : "", ".gz"); if (!(f = gzopen(filename, "wb"))) { return -1; } mlist_write(f, l); gzprintf(f, "# end of history\n"); gzclose(f); return 0;}int history_read(mconfig *conf, mlist *l, char *subpath) { char filename[255]; gzFile *f; data_History *data; sprintf(filename, "%s%s%s/modlogan.history%s", conf->outputdir ? conf->outputdir : ".", subpath ? "/" : "", subpath ? subpath : "", ".gz"); if (!(f = gzopen(filename, "r"))) { return -1; } data = History_init(); while ((data->read(data, f) == 0)) { if (!data->string) { break; } mlist_insert(l, data); data = History_init(); } data->destructor(data); gzclose(f); return 0;}void show_version() { printf("%s %s\n", PACKAGE, VERSION);}void show_header() { printf("%s %s", PACKAGE, VERSION);#ifdef NO_PLUGINS printf(" - static i(%s) p(%s) o(%s)\n", INPUT_PLUGIN, PROCESSOR_PLUGIN, OUTPUT_PLUGIN);#else printf(" - dynamic\n");#endif}void show_usage() { show_header();#ifdef HAVE_GETOPT_LONG printf("Options:\n"); printf(" -c <configfile> filename of the configfile\n"); printf(" -h --help this help screen\n"); printf(" -v --version display version\n");#else printf("Options:\n"); printf(" -c <configfile> filename of the configfile\n"); printf(" -h this help screen\n"); printf(" -v display version\n");#endif};int restore_internal_state (mconfig *conf, mlist *state_list) { DIR *dir; int splitter = 0; /* scan the outputdir for directories */ if ((dir = opendir(conf->outputdir)) == NULL) { fprintf(stderr, "can't open the outputdir: %s - %s\n", conf->outputdir, strerror(errno)); return -1; } else { struct dirent * dent; while ((dent = readdir(dir))) { struct stat st; char *dirname = NULL; /* skip '.', '..' and hidden directories */ if (*(dent->d_name) == '.') continue; dirname = malloc(strlen(conf->outputdir)+strlen(dent->d_name)+2); sprintf(dirname, "%s/%s", conf->outputdir, dent->d_name); if (stat(dirname, &st)) { fprintf(stderr, "%s.%d: can't stat the output directory (%s) : %s\n", __FILE__, __LINE__, dirname, strerror(errno)); } else if (S_ISDIR(st.st_mode)) { mstate *state = NULL; mlist *hist = mlist_init(); if (conf->debug_level > 1) fprintf(stderr, "%s.%d: reading statefile from %s\n", __FILE__, __LINE__, dent->d_name); if (history_read(conf, hist, dent->d_name)) { mlist_free(hist); hist = NULL; } if (conf->incremental) { state = mstate_init(); if (mstate_read(conf, state, 0, 0, dent->d_name)) { mstate_free(state); state = NULL; } } if (!hist || (conf->incremental && !state)) { if (hist) mlist_free(hist); else fprintf(stderr, "%s\n", _("Reading History file failed")); if (state) mstate_free(state); else if (conf->incremental) fprintf(stderr, "%s\n", _("Reading State file failed")); } else { data_State *data = createState(dent->d_name, state, hist); mlist_insert(state_list, data); if (conf->debug_level > 2) fprintf(stderr, "%s.%d: state restored for %s\n", __FILE__, __LINE__, dent->d_name); splitter = 1; } } free(dirname); } closedir(dir); } if (!splitter) { mstate *state = NULL; mlist *hist = mlist_init(); if (history_read(conf, hist, NULL)) { mlist_free(hist); hist = NULL; } if (conf->incremental) { state = mstate_init(); if (mstate_read(conf, state, 0, 0, NULL)) { mstate_free(state); state = NULL; } else { splitter = 1; } } if (!hist || !state) { if (hist) mlist_free(hist); else fprintf(stderr, "%s\n", _("Reading History file failed")); if (state) mstate_free(state); else fprintf(stderr, "%s\n", _("Reading State file failed")); } else { data_State *data = createState("", state, hist); mlist_insert(state_list, data); } } return 0;}typedef struct { struct timeval start; struct timeval stop; long int span;} mtimer;#define MTIMER_START(x)\ gettimeofday(&(x.start), NULL);#define MTIMER_STOP(x)\ gettimeofday(&(x.stop), NULL);#define MTIMER_CALC(x)\ x.span += ((x.stop.tv_sec * 1000 + x.stop.tv_usec / 1000) - (x.start.tv_sec * 1000 + x.start.tv_usec / 1000)); \ #define MTIMER_GET_MSEC(x) \ x.span #define MTIMER_RESET(x) \ x.span = 0;int main (int argc, char **argv) { mconfig *conf = NULL; mlogrec *rec = NULL; mlist *state_list = NULL; mlist *l; int ret, l_month = -1, l_year = -1, l_hour = -1, l_day = -1, i; char *conf_filename = NULL; long lines = 0, lines_corrupt = 0, lines_skipped = 0; int first_valid_line = 0; struct tm *tm; time_t l_stamp = -1; mtimer process_timer, post_process_timer, parse_timer, setup_timer; #ifdef HAVE_GETOPT_LONG int option_index = 0; static struct option long_options[] = { {"help", 0, NULL, 0}, {"version", 0, NULL, 0}, {NULL, 0, NULL, 0} };#endif MTIMER_RESET(process_timer); MTIMER_RESET(post_process_timer); MTIMER_RESET(parse_timer); MTIMER_RESET(setup_timer); #ifdef HAVE_GETOPT_LONG while ((i = getopt_long(argc,argv,"c:hv", long_options, &option_index)) != -1) { /* map the long options to the short ones */ if (i == 0) { switch(option_index) { case 0: i = 'h'; break; case 1: i = 'v'; break; default: show_usage(); exit( EXIT_FAILURE); } }#else while ((i = getopt(argc,argv,"c:hv")) != EOF) { #endif switch(i) { case 'c': conf_filename = optarg; break; case 'h': show_usage(); exit( EXIT_SUCCESS); case 'v': show_version(); exit( EXIT_SUCCESS); default: show_usage(); exit( EXIT_FAILURE); } } show_header(); MTIMER_START(setup_timer); if (!(conf = mconfig_init(conf_filename))) { fprintf(stderr, "%s\n", _("Reading Configfile failed")); return -1; } state_list = mlist_init(); rec = mrecord_init(); restore_internal_state(conf, state_list); if (conf->incremental) { l = state_list; while (l) { data_State *data = l->data; if (!data) break; if (data->state->timestamp > l_stamp) { l_stamp = data->state->timestamp; l_year = data->state->year-1900; l_month = data->state->month-1; } l = l->next; } } if (l_stamp != -1 && conf->debug_level > 0) printf("%s %s", _("Starting at"),ctime(&l_stamp)); if (conf->debug_level > 0) printf("%s\n", _("startup - finished")); MTIMER_STOP(setup_timer); MTIMER_CALC(setup_timer); MTIMER_START(parse_timer); while ((ret = get_next_record(conf, rec)) != M_RECORD_EOF) { MTIMER_STOP(parse_timer); MTIMER_CALC(parse_timer); MTIMER_START(process_timer); lines++; if (ret == M_RECORD_NO_ERROR) { if (l_month == -1) { tm = localtime(&(rec->timestamp)); l_month = tm->tm_mon; l_year = tm->tm_year; l_stamp = rec->timestamp; l_hour = tm->tm_hour; } if (l_stamp > rec->timestamp) { if (first_valid_line == 0 && conf->incremental == 1) { lines_skipped++; continue; } if (conf->debug_level > 2) fprintf(stderr, "Out of Sequence - ignoring timestamp: %ld > %ld\n", l_stamp, rec->timestamp); rec->timestamp = l_stamp; } tm = localtime(&(rec->timestamp)); if (l_day != tm->tm_mday) { if (conf->debug_level > 1) { printf("|-| %02i.%02i.%4i", tm->tm_mday, tm->tm_mon+1, tm->tm_year+1900); if (conf->debug_level > 1) { printf(" - %10.2f (%10ld, %4ld, %4ld)", (lines)/((MTIMER_GET_MSEC(parse_timer)+MTIMER_GET_MSEC(process_timer))/1000.0), lines, lines_corrupt, lines_skipped); } printf("\n"); } l_day = tm->tm_mday; } if (conf->gen_report_threshold > 0 && (lines - lines_corrupt + 1) % conf->gen_report_threshold == 0) { MTIMER_STOP(process_timer); MTIMER_CALC(process_timer); MTIMER_START(post_process_timer); if (conf->debug_level > 0) printf("o(t) %s %02i - %04i\n", _("writing month"), l_month+1, l_year+1900); l = state_list; while (l) { data_State *data = l->data; data_History *histdata = NULL; if (!data) break; histdata = createHistory(data->state); mlist_insert(data->history, histdata); mstate_write(conf, data->state, M_STATE_WRITE_BY_MONTH, *(data->string) ? data->string : NULL); history_write(conf, data->history, *(data->string) ? data->string : NULL); generate_monthly_output(conf, data->state, *(data->string) ? data->string : NULL); generate_history_output(conf, data->history, *(data->string) ? data->string : NULL); l = l->next; } MTIMER_STOP(post_process_timer); MTIMER_CALC(post_process_timer); MTIMER_START(process_timer); } if (tm->tm_mon != l_month || tm->tm_year != l_year) { MTIMER_STOP(process_timer); MTIMER_CALC(process_timer); MTIMER_START(post_process_timer); if (conf->debug_level > 0) printf("o %s %02i - %04i\n", _("writing month"), l_month+1, l_year+1900); l = state_list; while (l) { data_State *data = l->data; data_History *histdata = NULL; if (!data) break; histdata = createHistory(data->state); mlist_insert(data->history, histdata); if (conf->debug_level > 0) printf("o(t) -- state written: (...)/%s/\n", *(data->string) ? data->string : "."); mstate_write(conf, data->state, M_STATE_WRITE_BY_MONTH, *(data->string) ? data->string : NULL); generate_monthly_output(conf, data->state, *(data->string) ? data->string : NULL); mstate_free(data->state); data->state = mstate_init(); l = l->next; } tm = localtime(&(rec->timestamp)); l_month = tm->tm_mon; l_year = tm->tm_year; MTIMER_STOP(post_process_timer); MTIMER_CALC(post_process_timer); MTIMER_START(process_timer); } insert_record(conf, state_list, rec); first_valid_line = 1; l_stamp = rec->timestamp; } else { lines_corrupt++; if (conf->debug_level > 0) { fprintf (stderr, "%s.%d: parser reported an error in line %ld\n", __FILE__, __LINE__, lines); } } mrecord_free(rec); rec = mrecord_init(); MTIMER_STOP(process_timer); MTIMER_CALC(process_timer); MTIMER_START(parse_timer); } MTIMER_STOP(parse_timer); MTIMER_START(post_process_timer); if (l_month != -1) { if (conf->debug_level > 0) printf("%s %02i - %04i\n", _("writing month"), l_month+1, l_year+1900); if (conf->debug_level > 1) fprintf(stderr, "%s.%d: writing the last month\n", __FILE__, __LINE__ ); l = state_list; while (l) { data_State *data = l->data; data_History *histdata = NULL; if (!data) break; if (conf->debug_level > 1) fprintf(stderr, "%s.%d: subpath = %s\n", __FILE__, __LINE__, data->string); histdata = createHistory(data->state); mlist_insert(data->history, histdata); mstate_write(conf, data->state, M_STATE_WRITE_DEFAULT, *(data->string) ? data->string : NULL); history_write(conf, data->history, *(data->string) ? data->string : NULL); generate_monthly_output(conf, data->state, *(data->string) ? data->string : NULL); generate_history_output(conf, data->history, *(data->string) ? data->string : NULL); l = l->next; } } MTIMER_STOP(post_process_timer); MTIMER_CALC(post_process_timer); mlist_free(state_list); mrecord_free(rec); mplugins_free(conf); if (conf->debug_level > 0) { printf(" --> Setup : %10.2fs <--\n", MTIMER_GET_MSEC(setup_timer)/1000.0); printf(" --> Parse : %10.2fs <--\n", MTIMER_GET_MSEC(parse_timer)/1000.0); printf(" --> Process : %10.2fs <--\n", MTIMER_GET_MSEC(process_timer)/1000.0); printf(" --> Post-Process: %10.2fs <--\n", MTIMER_GET_MSEC(post_process_timer)/1000.0); printf("%s: %.2f %s (%ld %s, %ld %s, %ld %s)\n", _("Throughput"), (lines)/((MTIMER_GET_MSEC(parse_timer)+MTIMER_GET_MSEC(process_timer))/1000.0), _("rec/s"), lines, _("records"), lines_corrupt, _("corrupt records"), lines_skipped, _("skipped records")); } mconfig_free(conf); return 0;}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?