⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 spp_perfmonitor.c

📁 著名的入侵检测系统snort的最新版本的源码
💻 C
字号:
/* $Id$ ****  spp_perfmonitor.c****  Copyright (C) 2002 Sourcefire, Inc.**  Marc Norton <mnorton@sourcefire.com>**  Dan Roelker <droelker@sourcefire.com>****  NOTES**  6.4.02 - Initial Source Code.  Norton/Roelker****  This program is free software; you can redistribute it and/or modify**  it under the terms of the GNU General Public License Version 2 as**  published by the Free Software Foundation.  You may not use, modify or**  distribute this program under any other version of the GNU General**  Public License.****  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.***/#include <stdlib.h>#include <ctype.h>#include "plugbase.h"#include "mstring.h"#include "util.h"#include "debug.h"#include "parser.h"#include "snort.h"#include "perf.h"#include "profiler.h"/**  Protype these forward references, and don't clutter up the name space*/static void PerfMonitorInit(char *args);static void ParsePerfMonitorArgs(char *args);static void ProcessPerfMonitor(Packet *p, void *);void PerfMonitorCleanExit(int, void *);void PerfMonitorRestart(int, void *);#ifdef PERF_PROFILINGPreprocStats perfmonStats;#endif/* * Function: SetupPerfMonitor() * * Purpose: Registers the preprocessor keyword and initialization  *          function into the preprocessor list.  This is the function that *          gets called from InitPreprocessors() in plugbase.c. * * Arguments: None. * * Returns: void function * */void SetupPerfMonitor(){    /* link the preprocessor keyword to the init function in        the preproc list */    RegisterPreprocessor("PerfMonitor", PerfMonitorInit);    DEBUG_WRAP(DebugMessage(DEBUG_PLUGIN,"Preprocessor: PerfMonitor is setup...\n"););}/* * Function: PerfMonitorInit(char *) * * Purpose: Calls the argument parsing function, performs final setup on data *          structs, links the preproc function into the function list. * * Arguments: args => ptr to argument string * * Returns: void function * */static void PerfMonitorInit(char *args){    DEBUG_WRAP(DebugMessage(DEBUG_PLUGIN,"Preprocessor: PerfMonitor Initialized\n"););    /* parse the argument list from the rules file */    ParsePerfMonitorArgs(args);    /* Set the preprocessor function into the function list */    AddFuncToPreprocList(ProcessPerfMonitor, PRIORITY_SCANNER, PP_PERFMONITOR);#ifdef PERF_PROFILING    RegisterPreprocessorProfile("perfmon", &perfmonStats, 0, &totalPerfStats);#endif}/*   Perf file -  specified on the command line */static char perf_file[1025]={""};void SetPerfmonitorFile( char * s ){   if( strlen(s) < sizeof(perf_file)-1 )   {      SnortStrncpy(perf_file, s, sizeof(perf_file));   }}/* * Function: ParsePerfMonitorArgs(char *) * * Purpose: Process the preprocessor arguements from the rules file and  *          initialize the preprocessor's data struct.  This function doesn't *          have to exist if it makes sense to parse the args in the init  *          function. * * Arguments: args => argument list * * *  perfmonitor: [ time 10 flow ] * * Returns: void function * */static void ParsePerfMonitorArgs( char *args){    char **Tokens=NULL;    int   iTokenNum=0;    int   i, iTime=60, iFlow=0, iFlowMaxPort=1023, iEvents=0, iMaxPerfStats=0;    int   iFile=0, iSnortFile=0, iConsole=0, iPkts=10000, iReset=1;    int   iStatsExit=0;    char  file[1025];    char  snortfile[1025];    int   iRet;    char  *pcEnd;    if( args )    {       Tokens = mSplit(args, " \t", 50, &iTokenNum, '\\');    }        for( i = 0; i < iTokenNum; i++ )    {        /* Check for a 'time number' parameter */        if( strcmp( Tokens[i],"time")==0 )        {            /* make sure we have at least one more argument */            if( i == (iTokenNum-1) )            {                FatalError("%s(%d) => Missing Time.  The value must be a "                           "positive integer number.\n", file_name, file_line);            }            iTime = strtol(Tokens[++i], &pcEnd, 10);            if(iTime <= 0 || *pcEnd)                FatalError("%s(%d) => Invalid Time.  The value must be a "                           "positive integer number.\n", file_name, file_line);        }        else if( strcmp( Tokens[i],"flow-ports")==0 )        {              i++;              if( (i< iTokenNum) && Tokens[i] )                  iFlowMaxPort= atoi(Tokens[i]);                            if( iFlowMaxPort > SF_MAX_PORT )                  iFlowMaxPort = SF_MAX_PORT;              iFlow=1;        }        else if( strcmp( Tokens[i],"flow")==0 )        {            /*            **  This parameter turns on the flow statistics.            **  Flow statistics give you the traffic profile            **  that snort is processing.  This helps in            **  troubleshooting and performance tuning.            */            iFlow = 1;        }               else if( strcmp( Tokens[i],"accumulate")==0)        {            iReset=0;        }        else if( strcmp( Tokens[i],"reset")==0 )        {            iReset=1;        }        else if( strcmp( Tokens[i],"events")==0 )        {            /*            **  The events paramenter gives the total number            **  of qualified and non-qualified events during            **  the processing sample time.  This allows             **  performance problems to be seen in a general            **  manner.            */            iEvents = 1;        }        else if(!strcmp(Tokens[i], "max"))        {            iMaxPerfStats = 1;        }        else if(!strcmp(Tokens[i], "console"))        {            iConsole = 1;        }        else if(!strcmp(Tokens[i], "file"))        {            if( i == (iTokenNum-1) )            {                FatalError("%s(%d) => Missing 'file' argument.  This value "                           "is the file that save stats.\n",                            file_name, file_line);            }            iFile = 1;                        strncpy( file, Tokens[++i], sizeof(file)-1 );            file[sizeof(file)-1] = 0x00;        }        else if(!strcmp(Tokens[i], "snortfile"))        {            if( i == (iTokenNum-1) )            {                FatalError("%s(%d) => Missing 'snortfile' argument.  This "                           "value is the file that save stats.\n",                            file_name, file_line);            }            iSnortFile = 1;            if(pv.log_dir[strlen(pv.log_dir)-1] == '/')            {                iRet = snprintf(snortfile, sizeof(snortfile),                                "%s%s", pv.log_dir, Tokens[++i]);            }            else            {                iRet = snprintf(snortfile, sizeof(snortfile),                                "%s/%s", pv.log_dir, Tokens[++i]);            }            if(iRet < 0)            {                FatalError("%s(%d) => 'snortfile' argument path is too long.\n",                           file_name, file_line);            }        }        else if(!strcmp(Tokens[i], "pktcnt"))        {            if( i == (iTokenNum-1) )            {                FatalError("%s(%d) => Missing 'pktcnt' argument.  This value "                           "should be a positive integer or zero.\n",                            file_name, file_line);            }            iPkts = atoi(Tokens[++i]);            if( iPkts < 0 )                iPkts = 1000;        }        else if (!strcmp(Tokens[i], "atexitonly"))        {            iStatsExit = 1;        }        else        {            FatalError("%s(%d)=> Invalid parameter '%s' to preprocessor"                       " PerfMonitor.\n", file_name, file_line, Tokens[i]);        }    }    mSplitFree(&Tokens, iTokenNum);    /*    *  Initialize the performance system and set flags    */    sfInitPerformanceStatistics(&sfPerf);         sfSetPerformanceSampleTime( &sfPerf, iTime );    sfSetPerformanceStatistics( &sfPerf, SFPERF_BASE );        sfSetPerformanceAccounting( &sfPerf, iReset );        if( iFlow  )    {        sfSetPerformanceStatistics( &sfPerf, SFPERF_FLOW );        sfPerf.sfFlow.maxPortToTrack = iFlowMaxPort;    }        if( iEvents) sfSetPerformanceStatistics( &sfPerf, SFPERF_EVENT );    if( iMaxPerfStats ) sfSetPerformanceStatistics(&sfPerf, SFPERF_BASE_MAX);         if( iConsole ) sfSetPerformanceStatistics( &sfPerf, SFPERF_CONSOLE );    if( iFile && iSnortFile )    {        FatalError("%s(%d)=> Cannot log to both 'file' and 'snortfile'.\n",                   file_name, file_line);    }        if( iFile || iSnortFile || strlen(perf_file) )     {        /* use command line override if applicable */        if( strlen(perf_file) )        {            iFile=1;            if( sfSetPerformanceStatisticsEx( &sfPerf, SFPERF_FILE, perf_file ) )            {                FatalError("Cannot open performance log file '%s'\n",perf_file);            }        }        else        {            if(iFile)            {                if( sfSetPerformanceStatisticsEx( &sfPerf, SFPERF_FILE, file ) )                {                    FatalError("Cannot open performance log file '%s'\n",file);                }            }            else if(iSnortFile)            {                if( sfSetPerformanceStatisticsEx(&sfPerf, SFPERF_FILE, snortfile) )                {                    FatalError("Cannot open performance log file '%s'\n",snortfile);                }            }        }    }        if( iPkts) sfSetPerformanceStatisticsEx( &sfPerf, SFPERF_PKTCNT, &iPkts );    if( iStatsExit) sfSetPerformanceStatisticsEx( &sfPerf, SFPERF_SUMMARY, &iStatsExit );    LogMessage("PerfMonitor config:\n");    LogMessage("    Time:           %d seconds\n", iTime);    LogMessage("    Flow Stats:     %s\n", iFlow ? "ACTIVE" : "INACTIVE");    LogMessage("    Event Stats:    %s\n", iEvents ? "ACTIVE" : "INACTIVE");    LogMessage("    Max Perf Stats: %s\n",             iMaxPerfStats ? "ACTIVE" : "INACTIVE");    LogMessage("    Console Mode:   %s\n", iConsole ? "ACTIVE" : "INACTIVE");    LogMessage("    File Mode:      %s\n",             iFile ? file : "INACTIVE");    LogMessage("    SnortFile Mode: %s\n",             iSnortFile ? snortfile : "INACTIVE");    LogMessage("    Packet Count:   %d\n", iPkts);    LogMessage("    Dump Summary:   %s\n", sfPerf.iPerfFlags & SFPERF_SUMMARY ?        "Yes" : "No");    AddFuncToPreprocCleanExitList(PerfMonitorCleanExit, NULL, PRIORITY_LAST, PP_PERFMONITOR);    AddFuncToPreprocRestartList(PerfMonitorRestart, NULL, PRIORITY_LAST, PP_PERFMONITOR);    if (sfPerf.iPerfFlags & SFPERF_SUMMARY)    {        CheckSampleInterval(time(NULL), &sfPerf);    }       return;}/* * Function: ProcessPerfMonitor(Packet *) * * Purpose: Perform the preprocessor's intended function.  This can be *          simple (statistics collection) or complex (IP defragmentation) *          as you like.  Try not to destroy the performance of the whole *          system by trying to do too much.... * * Arguments: p => pointer to the current packet data struct  * * Returns: void function * */static void ProcessPerfMonitor(Packet *p, void *context){    static int first = 1;    PROFILE_VARS;    if( first )    {        extern pcap_t * pd;        if ((pd != NULL)#ifdef WIN32            && (!pv.readmode_flag)#endif           )        {            if (UpdatePcapPktStats() != -1)            {                sfPerf.sfBase.pkt_stats.pkts_recv = GetPcapPktStatsRecv();                sfPerf.sfBase.pkt_stats.pkts_drop = GetPcapPktStatsDrop();            }        }        first = 0;    }    if(p == NULL)     {        return;    }    PREPROC_PROFILE_START(perfmonStats);    /*    *  Performance Statistics      */    if (pv.rotate_perf_file)    {        sfRotatePerformanceStatisticsFile(&sfPerf);        pv.rotate_perf_file = 0;    }    if(sfPerf.sample_interval > 0)    {        if(p->pkth)        {            sfPerformanceStats(&sfPerf, p->pkt, p->pkth->caplen,                                p->packet_flags & PKT_REBUILT_STREAM);        }    }        if( p->tcph )    {        if((p->tcph->th_flags & TH_SYN) && !(p->tcph->th_flags & TH_ACK))        {            /* changed to measure syns */            sfPerf.sfBase.iSyns++;        }        else if((p->tcph->th_flags & TH_SYN) && (p->tcph->th_flags & TH_ACK ))        {            /* this is a better approximation of connections */            sfPerf.sfBase.iSynAcks++;        }    }    /*    *  TCP Flow Perf    */    if(p->pkth && (sfPerf.iPerfFlags & SFPERF_FLOW))   {        /*        **  TCP Flow Stats        */        if( p->tcph )        {            UpdateTCPFlowStatsEx(p->sp, p->dp, p->pkth->caplen);        }        /*        *  UDP Flow Stats        */        else if( p->udph )            UpdateUDPFlowStatsEx(p->sp, p->dp, p->pkth->caplen);        /*        *  Get stats for ICMP packets        */        else if( p->icmph )            UpdateICMPFlowStatsEx(p->icmph->type, p->pkth->caplen);    }    PREPROC_PROFILE_END(perfmonStats);    return;}/** * CleanExit func required by preprocessors */void PerfMonitorCleanExit(int signal, void *foo){    if (sfPerf.iPerfFlags & SFPERF_SUMMARY)    {        sfProcessPerfStats(&sfPerf);    }    /* Close the performance stats file */    sfSetPerformanceStatisticsEx(&sfPerf, SFPERF_FILECLOSE, NULL);    return;}/** * Restart func required by preprocessors */void PerfMonitorRestart(int signal, void *foo){    /* Close the performance stats file */    sfSetPerformanceStatisticsEx(&sfPerf, SFPERF_FILECLOSE, NULL);    return;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -