2009-05-25 Ramon Novoa <rnovoa@artica.es>

* windows/pandora_wmi.cc, windows/pandora_wmi.h: Added functions for the
          new modules. Removed old logevent functions.

        * pandora_windows_service.h, pandora_windows_service.cc: Added support
          for data file buffering and startup delay.

        * modules/pandora_module_logevent.cc, modules/pandora_module_logevent.h:
          Rewritten to retrieve event log data using the PDH interface instead
          of WMI (was too slow).

        * modules/pandora_module_tcpcheck.cc, modules/pandora_module_tcpcheck.h,
          modules/pandora_module_regexp.cc, modules/pandora_module_regexp.h,
          modules/pandora_module_perfcounter.cc,
          modules/pandora_module_perfcounter.h,
          modules/pandora_module_freedisk_percent.cc,
          modules/pandora_module_freedisk_percent.h,
          modules/pandora_module_freememory_percent.cc,
          modules/pandora_module_freememory_percent.h: Added to repository.
          New modules, see http://openideas.info/wiki/.

        * modules/pandora_module.h, modules/pandora_module.cc,
          modules/pandora_module_factory.cc, modules/pandora_module_list.cc:
          Added support for the new modules.

        * bin/pandora_agent.conf: Included configuration examples for the new
          modules.

        * PandoraAgent.dev: Updated to compile the new modules.




git-svn-id: https://svn.code.sf.net/p/pandora/code/trunk@1707 c3f86ba8-e40f-0410-aaad-9ba5e7f4b01f
This commit is contained in:
ramonn 2009-05-25 17:50:27 +00:00
parent b143bf8d28
commit bc5437b952
23 changed files with 1576 additions and 196 deletions

View File

@ -1,3 +1,34 @@
2009-05-25 Ramon Novoa <rnovoa@artica.es>
* windows/pandora_wmi.cc, windows/pandora_wmi.h: Added functions for the
new modules. Removed old logevent functions.
* pandora_windows_service.h, pandora_windows_service.cc: Added support
for data file buffering and startup delay.
* modules/pandora_module_logevent.cc, modules/pandora_module_logevent.h:
Rewritten to retrieve event log data using the PDH interface instead
of WMI (was too slow).
* modules/pandora_module_tcpcheck.cc, modules/pandora_module_tcpcheck.h,
modules/pandora_module_regexp.cc, modules/pandora_module_regexp.h,
modules/pandora_module_perfcounter.cc,
modules/pandora_module_perfcounter.h,
modules/pandora_module_freedisk_percent.cc,
modules/pandora_module_freedisk_percent.h,
modules/pandora_module_freememory_percent.cc,
modules/pandora_module_freememory_percent.h: Added to repository.
New modules, see http://openideas.info/wiki/.
* modules/pandora_module.h, modules/pandora_module.cc,
modules/pandora_module_factory.cc, modules/pandora_module_list.cc:
Added support for the new modules.
* bin/pandora_agent.conf: Included configuration examples for the new
modules.
* PandoraAgent.dev: Updated to compile the new modules.
2009-04-13 Esteban Sanchez <estebans@artica.es>
* modules/pandora_module_odbc.cc: Fixed log message when no username

View File

@ -1,7 +1,7 @@
[Project]
FileName=PandoraAgent.dev
Name=PandoraAgent
UnitCount=81
UnitCount=91
Type=1
Ver=1
ObjFiles=
@ -10,9 +10,9 @@ Libs=
PrivateResource=
ResourceIncludes=
MakeIncludes=
Compiler=
CppCompiler=
Linker=-lole32_@@_-loleaut32_@@_-luuid_@@_-lpsapi_@@_-lwsock32_@@_-lz_@@_-liphlpapi_@@_-lnetapi32_@@_-lws2_32_@@_-lcrypto_@@_-lodbc++_@@_-lgdi32_@@_-lcurldll_@@_
Compiler=_@@_
CppCompiler=_@@_
Linker=-lole32_@@_-loleaut32_@@_-luuid_@@_-lpsapi_@@_-lwsock32_@@_-lz_@@_-liphlpapi_@@_-lnetapi32_@@_-lws2_32_@@_-lcrypto_@@_-lodbc++_@@_-lgdi32_@@_-lcurldll_@@_C:\Dev-Cpp\lib\libboost_regex-mgw-mt-s-1_33_1.lib_@@_
IsCpp=1
Icon=
ExeOutput=
@ -857,3 +857,103 @@ Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit82]
FileName=modules\pandora_module_freedisk_percent.h
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit83]
FileName=modules\pandora_module_freedisk_percent.cc
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit84]
FileName=modules\pandora_module_freememory_percent.h
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit85]
FileName=modules\pandora_module_freememory_percent.cc
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit86]
FileName=modules\pandora_module_perfcounter.h
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit87]
FileName=modules\pandora_module_perfcounter.cc
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit88]
FileName=modules\pandora_module_tcpcheck.h
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit89]
FileName=modules\pandora_module_tcpcheck.cc
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit90]
FileName=modules\pandora_module_regexp.h
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=
[Unit91]
FileName=modules\pandora_module_regexp.cc
CompileCpp=1
Folder=Modules
Compile=1
Link=1
Priority=1000
OverrideBuildCmd=0
BuildCmd=

View File

@ -1,6 +1,6 @@
# Base config file for Pandora FMS Windows Agent
# (c) 2006-2008 Artica Soluciones Tecnologicas
# Version 2.0
# Version 3.0
# This program is Free Software, you can redistribute it and/or modify it
# under the terms of the GNU General Public Licence as published by the Free Software
@ -19,6 +19,8 @@
server_ip $ServerIP$
server_path $ServerPath$
temporal "$AgentTemp$"
#temporal_min_size 1024
#startup_delay 5
# Agent uses your hostname automatically, if you need to change agent name
# use directive agent_name
@ -268,3 +270,27 @@ module_end
#process_firefox_start firefox
#process_firefox_stop killall firefox
#service_messenger 1
# Example of a remote TCP check
#module_begin
#module_name tcpcheck
#module_type generic_data
#module_tcpcheck www.artica.es
#module_port 80
#module_timeout 5
#module_end
# Example of regexp matching
#module_begin
#module_name regexp
#module_type generic_data_string
#module_regexp C:\WINDOWS\my.log
#module_pattern ^(a*).*\1$
#module_end
# Example of performance counter data retrieval
#module_begin
#module_name perfcounter
#module_type generic_data_string
#module_perfcounter \Memory\Pages/sec
#module_end

View File

@ -119,8 +119,12 @@ Pandora_Module::parseModuleKindFromString (string kind) {
return MODULE_SERVICE;
} else if (kind == module_freedisk_str) {
return MODULE_FREEDISK;
} else if (kind == module_freedisk_percent_str) {
return MODULE_FREEDISK_PERCENT;
} else if (kind == module_freememory_str) {
return MODULE_FREEMEMORY;
} else if (kind == module_freememory_percent_str) {
return MODULE_FREEMEMORY_PERCENT;
} else if (kind == module_cpuusage_str) {
return MODULE_CPUUSAGE;
} else if (kind == module_odbc_str) {
@ -129,6 +133,12 @@ Pandora_Module::parseModuleKindFromString (string kind) {
return MODULE_LOGEVENT;
} else if (kind == module_wmiquery_str) {
return MODULE_WMIQUERY;
} else if (kind == module_perfcounter_str) {
return MODULE_PERFCOUNTER;
} else if (kind == module_tcpcheck_str) {
return MODULE_TCPCHECK;
} else if (kind == module_regexp_str) {
return MODULE_REGEXP;
} else {
return MODULE_0;
}

View File

@ -72,23 +72,34 @@ namespace Pandora_Modules {
MODULE_SERVICE, /**< The module checks for a running
* service */
MODULE_FREEDISK, /**< The module checks the free */
MODULE_FREEDISK_PERCENT, /**< The module checks the free */
MODULE_CPUUSAGE, /**< The module checks the CPU usage */
MODULE_FREEMEMORY, /**< The module checks the amount of
MODULE_FREEMEMORY, /**< The module checks the percentage of
* freememory in the system */
MODULE_FREEMEMORY_PERCENT, /**< The module checks the amount of
* freememory in the system */
MODULE_ODBC, /**< The module performs a SQL query via ODBC */
MODULE_LOGEVENT, /**< The module checks for log events */
MODULE_WMIQUERY /**< The module runs WQL queries */
MODULE_WMIQUERY, /**< The module runs WQL queries */
MODULE_PERFCOUNTER, /**< The module reads performance counters */
MODULE_TCPCHECK, /**< The module checks whether a tcp port is open */
MODULE_REGEXP /**< The module searches a file for matches of a regular expression */
} Module_Kind;
const string module_exec_str = "module_exec";
const string module_proc_str = "module_proc";
const string module_service_str = "module_service";
const string module_freedisk_str = "module_freedisk";
const string module_freedisk_percent_str = "module_freedisk_percent";
const string module_freememory_str = "module_freememory";
const string module_freememory_percent_str = "module_freememory_percent";
const string module_cpuusage_str = "module_cpuusage";
const string module_odbc_str = "module_odbc";
const string module_logevent_str = "module_logevent";
const string module_wmiquery_str = "module_wmiquery";
const string module_perfcounter_str = "module_perfcounter";
const string module_tcpcheck_str = "module_tcpcheck";
const string module_regexp_str = "module_regexp";
/**
* Pandora module super-class exception.

View File

@ -24,11 +24,16 @@
#include "pandora_module_proc.h"
#include "pandora_module_service.h"
#include "pandora_module_freedisk.h"
#include "pandora_module_freedisk_percent.h"
#include "pandora_module_freememory.h"
#include "pandora_module_freememory_percent.h"
#include "pandora_module_cpuusage.h"
#include "pandora_module_odbc.h"
#include "pandora_module_logevent.h"
#include "pandora_module_wmiquery.h"
#include "pandora_module_perfcounter.h"
#include "pandora_module_tcpcheck.h"
#include "pandora_module_regexp.h"
#include "../pandora_strutils.h"
#include <list>
@ -43,7 +48,9 @@ using namespace Pandora_Strutils;
#define TOKEN_PROC ("module_proc ")
#define TOKEN_SERVICE ("module_service ")
#define TOKEN_FREEDISK ("module_freedisk ")
#define TOKEN_FREEDISK_PERCENT ("module_freepercentdisk ")
#define TOKEN_FREEMEMORY ("module_freememory")
#define TOKEN_FREEMEMORY_PERCENT ("module_freepercentmemory")
#define TOKEN_CPUUSAGE ("module_cpuusage ")
#define TOKEN_ODBC ("module_odbc ")
#define TOKEN_MAX ("module_max ")
@ -55,6 +62,7 @@ using namespace Pandora_Strutils;
#define TOKEN_EVENTTYPE ("module_eventtype ")
#define TOKEN_EVENTCODE ("module_eventcode ")
#define TOKEN_PATTERN ("module_pattern ")
#define TOKEN_APPLICATION ("module_application ")
#define TOKEN_ASYNC ("module_async")
#define TOKEN_WATCHDOG ("module_watchdog ")
#define TOKEN_START_COMMAND ("module_start_command ")
@ -63,6 +71,11 @@ using namespace Pandora_Strutils;
#define TOKEN_RETRIES ("module_retries ")
#define TOKEN_STARTDELAY ("module_startdelay ")
#define TOKEN_RETRYDELAY ("module_retrydelay ")
#define TOKEN_PERFCOUNTER ("module_perfcounter ")
#define TOKEN_TCPCHECK ("module_tcpcheck ")
#define TOKEN_PORT ("module_port ")
#define TOKEN_TIMEOUT ("module_timeout ")
#define TOKEN_REGEXP ("module_regexp ")
string
parseLine (string line, string token) {
@ -96,12 +109,15 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
string module_min, module_max, module_description;
string module_interval, module_proc, module_service;
string module_freedisk, module_cpuusage, module_odbc;
string module_freedisk_percent, module_freememory_percent;
string module_odbc_query, module_dsn, module_freememory;
string module_logevent, module_source, module_eventtype, module_eventcode;
string module_pattern, module_async;
string module_pattern, module_application, module_async;
string module_watchdog, module_start_command;
string module_wmiquery, module_wmicolumn;
string module_retries, module_startdelay, module_retrydelay;
string module_perfcounter, module_tcpcheck;
string module_port, module_timeout, module_regexp;
Pandora_Module *module;
bool numeric;
Module_Type type;
@ -122,6 +138,7 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
module_eventtype = "";
module_eventcode = "";
module_pattern = "";
module_application = "";
module_async = "";
module_watchdog = "";
module_start_command = "";
@ -130,6 +147,11 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
module_retries = "";
module_startdelay = "";
module_retrydelay = "";
module_perfcounter = "";
module_tcpcheck = "";
module_port = "";
module_timeout = "";
module_regexp = "";
stringtok (tokens, definition, "\n");
@ -161,9 +183,15 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
if (module_freedisk == "") {
module_freedisk = parseLine (line, TOKEN_FREEDISK);
}
if (module_freedisk_percent == "") {
module_freedisk_percent = parseLine (line, TOKEN_FREEDISK_PERCENT);
}
if (module_freememory == "") {
module_freememory = parseLine (line, TOKEN_FREEMEMORY);
}
if (module_freememory_percent == "") {
module_freememory_percent = parseLine (line, TOKEN_FREEMEMORY_PERCENT);
}
if (module_cpuusage == "") {
module_cpuusage = parseLine (line, TOKEN_CPUUSAGE);
}
@ -197,6 +225,9 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
if (module_pattern == "") {
module_pattern = parseLine (line, TOKEN_PATTERN);
}
if (module_application == "") {
module_application = parseLine (line, TOKEN_APPLICATION);
}
if (module_async == "") {
module_async = parseLine (line, TOKEN_ASYNC);
}
@ -221,6 +252,21 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
if (module_retrydelay == "") {
module_retrydelay = parseLine (line, TOKEN_RETRYDELAY);
}
if (module_perfcounter == "") {
module_perfcounter = parseLine (line, TOKEN_PERFCOUNTER);
}
if (module_tcpcheck == "") {
module_tcpcheck = parseLine (line, TOKEN_TCPCHECK);
}
if (module_port == "") {
module_port = parseLine (line, TOKEN_PORT);
}
if (module_timeout == "") {
module_timeout = parseLine (line, TOKEN_TIMEOUT);
}
if (module_regexp == "") {
module_regexp = parseLine (line, TOKEN_REGEXP);
}
iter++;
}
@ -267,17 +313,20 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
} else if (module_freedisk != "") {
module = new Pandora_Module_Freedisk (module_name,
module_freedisk);
} else if (module_freedisk_percent != "") {
module = new Pandora_Module_Freedisk_Percent (module_name,
module_freedisk_percent);
} else if (module_freememory != "") {
module = new Pandora_Module_Freememory (module_name);
} else if (module_freememory_percent != "") {
module = new Pandora_Module_Freememory_Percent (module_name);
} else if (module_cpuusage != "") {
int cpu_id;
try {
cpu_id = strtoint (module_cpuusage);
} catch (Invalid_Conversion e) {
pandoraLog ("Invalid CPU id '%s' on module_cpuusage %s",
module_name.c_str ());
return NULL;
cpu_id = -1;
}
module = new Pandora_Module_Cpuusage (module_name,
@ -292,10 +341,17 @@ Pandora_Module_Factory::getModuleFromDefinition (string definition) {
module_source,
module_eventtype,
module_eventcode,
module_pattern);
module_pattern,
module_application);
} else if (module_wmiquery != "") {
module = new Pandora_Module_WMIQuery (module_name,
module_wmiquery, module_wmicolumn);
} else if (module_perfcounter != "") {
module = new Pandora_Module_Perfcounter (module_name, module_perfcounter);
} else if (module_tcpcheck != "") {
module = new Pandora_Module_Tcpcheck (module_name, module_tcpcheck, module_port, module_timeout);
} else if (module_regexp != "") {
module = new Pandora_Module_Regexp (module_name, module_regexp, module_pattern);
} else {
return NULL;
}

View File

@ -0,0 +1,66 @@
/* Pandora freedisk module. These modules check the free space in a
logical drive.
Copyright (C) 2006 Artica ST.
Written by Esteban Sanchez.
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, or (at your option)
any later version.
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 "pandora_module_freedisk_percent.h"
#include "../windows/pandora_wmi.h"
#include "../pandora_strutils.h"
#include <algorithm>
#include <cctype>
using namespace Pandora;
using namespace Pandora_Modules;
using namespace Pandora_Strutils;
/**
* Creates a Pandora_Module_Freedisk object.
*
* @param name Module name.
* @param disk_id Logical drive id to be monitorized. Usually it's "C:"
*/
Pandora_Module_Freedisk_Percent::Pandora_Module_Freedisk_Percent (string name, string disk_id)
: Pandora_Module (name) {
this->disk_id = disk_id;
transform (disk_id.begin (), disk_id.end (),
this->disk_id.begin (), (int (*) (int)) toupper);
this->setKind (module_freedisk_percent_str);
}
void
Pandora_Module_Freedisk_Percent::run () {
long res;
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
try {
res = Pandora_Wmi::getDiskFreeSpacePercent (this->disk_id);
this->setOutput (longtostr (res));
} catch (Pandora_Wmi::Pandora_Wmi_Exception e) {
this->has_output = false;
}
}

View File

@ -0,0 +1,42 @@
/* Pandora freedisk module. These modules check the free space in a
logical drive.
Copyright (C) 2006 Artica ST.
Written by Esteban Sanchez.
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, or (at your option)
any later version.
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.
*/
#ifndef __PANDORA_MODULE_FREEDISK_PERCENT_H__
#define __PANDORA_MODULE_FREEDISK_PERCENT_H__
#include "pandora_module.h"
namespace Pandora_Modules {
/**
* Module to retrieve the free space available in a logical volume
* disk.
*/
class Pandora_Module_Freedisk_Percent : public Pandora_Module {
private:
string disk_id;
public:
Pandora_Module_Freedisk_Percent (string name, string disk_id);
void run ();
};
}
#endif

View File

@ -0,0 +1,61 @@
/* Pandora freememory module. These modules check if a freememory is running in the
system.
Copyright (C) 2006 Artica ST.
Written by Esteban Sanchez.
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, or (at your option)
any later version.
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 "pandora_module_freememory_percent.h"
#include "../windows/pandora_wmi.h"
#include "../pandora_strutils.h"
using namespace Pandora;
using namespace Pandora_Modules;
using namespace Pandora_Strutils;
/**
* Creates a Pandora_Module_Freememory object.
*
* @param name Module name.
*/
Pandora_Module_Freememory_Percent::Pandora_Module_Freememory_Percent (string name)
: Pandora_Module (name) {
this->setKind (module_freememory_percent_str);
}
void
Pandora_Module_Freememory_Percent::run () {
long res;
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
try {
res = Pandora_Wmi::getFreememoryPercent ();
this->setOutput (longtostr (res));
} catch (Pandora_Wmi::Pandora_Wmi_Exception e) {
this->has_output = false;
}
}

View File

@ -0,0 +1,38 @@
/* Pandora free memory module. These modules get amount of free memory.
Copyright (C) 2006 Artica ST.
Written by Esteban Sanchez.
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, or (at your option)
any later version.
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.
*/
#ifndef __PANDORA_MODULE_FREEMEMORY_PERCENT_H__
#define __PANDORA_MODULE_FREEMEMORY_PERCENT_H__
#include "pandora_module.h"
namespace Pandora_Modules {
/**
* Module to retrieve the free memory amount of the system.
*/
class Pandora_Module_Freememory_Percent : public Pandora_Module {
public:
Pandora_Module_Freememory_Percent (string name);
void run ();
};
}
#endif

View File

@ -24,11 +24,16 @@
#include "pandora_module_proc.h"
#include "pandora_module_service.h"
#include "pandora_module_freedisk.h"
#include "pandora_module_freedisk_percent.h"
#include "pandora_module_freememory.h"
#include "pandora_module_freememory_percent.h"
#include "pandora_module_cpuusage.h"
#include "pandora_module_odbc.h"
#include "pandora_module_logevent.h"
#include "pandora_module_wmiquery.h"
#include "pandora_module_perfcounter.h"
#include "pandora_module_tcpcheck.h"
#include "pandora_module_regexp.h"
#include <fstream>
using namespace std;
@ -132,12 +137,17 @@ Pandora_Modules::Pandora_Module_List::parseModuleDefinition (string definition)
Pandora_Module_Proc *module_proc;
Pandora_Module_Service *module_service;
Pandora_Module_Freedisk *module_freedisk;
Pandora_Module_Freedisk_Percent *module_freedisk_percent;
Pandora_Module_Cpuusage *module_cpuusage;
Pandora_Module_Freememory *module_freememory;
Pandora_Module_Freememory_Percent *module_freememory_percent;
Pandora_Module_Odbc *module_odbc;
Pandora_Module_Logevent *module_logevent;
Pandora_Module_WMIQuery *module_wmiquery;
Pandora_Module_Perfcounter *module_perfcounter;
Pandora_Module_Tcpcheck *module_tcpcheck;
Pandora_Module_Regexp *module_regexp;
module = Pandora_Module_Factory::getModuleFromDefinition (definition);
if (module != NULL) {
@ -163,11 +173,21 @@ Pandora_Modules::Pandora_Module_List::parseModuleDefinition (string definition)
module_freedisk = (Pandora_Module_Freedisk *) module;
modules->push_back (module_freedisk);
break;
case MODULE_FREEDISK_PERCENT:
module_freedisk_percent = (Pandora_Module_Freedisk_Percent *) module;
modules->push_back (module_freedisk_percent);
break;
case MODULE_FREEMEMORY:
module_freememory = (Pandora_Module_Freememory *) module;
modules->push_back (module_freememory);
break;
case MODULE_FREEMEMORY_PERCENT:
module_freememory_percent = (Pandora_Module_Freememory_Percent *) module;
modules->push_back (module_freememory_percent);
break;
case MODULE_CPUUSAGE:
module_cpuusage = (Pandora_Module_Cpuusage *) module;
@ -186,6 +206,18 @@ Pandora_Modules::Pandora_Module_List::parseModuleDefinition (string definition)
module_wmiquery = (Pandora_Module_WMIQuery *) module;
modules->push_back (module_wmiquery);
break;
case MODULE_PERFCOUNTER:
module_perfcounter = (Pandora_Module_Perfcounter *) module;
modules->push_back (module_perfcounter);
break;
case MODULE_TCPCHECK:
module_tcpcheck = (Pandora_Module_Tcpcheck *) module;
modules->push_back (module_tcpcheck);
break;
case MODULE_REGEXP:
module_regexp = (Pandora_Module_Regexp *) module;
modules->push_back (module_regexp);
break;
default:
break;
}

View File

@ -19,6 +19,8 @@
Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#include <time.h>
#include "pandora_module_logevent.h"
#include "../windows/pandora_wmi.h"
#include "../pandora_windows_service.h"
@ -32,44 +34,58 @@ using namespace Pandora_Modules;
* @param name Module name.
* @param service_name Service internal name to check.
*/
Pandora_Module_Logevent::Pandora_Module_Logevent (string name, string source, string type, string code, string pattern)
Pandora_Module_Logevent::Pandora_Module_Logevent (string name, string source, string type, string id, string pattern, string application)
: Pandora_Module (name) {
int i;
string upper_type = type;
// Convert the type string to uppercase
for (i = 0; i < type.length(); i++) {
upper_type[i] = toupper(type[i]);
}
// Set the type filter
if (upper_type.compare("ERROR") == 0) {
this->type = EVENTLOG_ERROR_TYPE;
} else if (upper_type.compare("WARNING") == 0) {
this->type = EVENTLOG_WARNING_TYPE;
} else if (upper_type.compare("INFORMATION") == 0) {
this->type = EVENTLOG_INFORMATION_TYPE;
} else if (upper_type.compare("AUDIT SUCCESS") == 0) {
this->type = EVENTLOG_AUDIT_SUCCESS;
} else if (upper_type.compare("AUDIT FAILURE") == 0) {
this->type = EVENTLOG_AUDIT_FAILURE;
} else {
this->type = -1;
}
this->id = atoi (id.c_str ());
this->source = source;
this->type = type;
this->code = code;
this->pattern = pattern;
this->application = application;
this->log_event = NULL;
this->setKind (module_logevent_str);
}
void
Pandora_Module_Logevent::run () {
int interval, module_interval;
string value;
list<string> event_list;
list<string>::iterator event;
Pandora_Agent_Conf::Pandora_Agent_Conf *conf;
SYSTEMTIME system_time;
conf = Pandora_Agent_Conf::getInstance ();
// Get execution interval
value = conf->getValue ("interval");
interval = atoi(value.c_str ());
module_interval = this->getInterval ();
if (module_interval > 0) {
interval *= module_interval;
}
// Run
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
Pandora_Wmi::getEventList (this->source, this->type, this->code, this->pattern, interval, event_list);
// Open log event
this->openLogEvent();
// Read events
this->getLogEvents (event_list);
// No data
if (event_list.size () < 1) {
@ -78,16 +94,278 @@ Pandora_Module_Logevent::run () {
}
for (event = event_list.begin (); event != event_list.end(); ++event) {
// No WMI timestamp?
if (event->size () < 26) {
this->setOutput (*event);
// No timestamp? Should not happen
if (event->size () < TIMESTAMP_LEN) {
continue;
}
// Get the timestamp
Pandora_Wmi::convertWMIDate (event->substr (0, 26), &system_time);
timestampToSystemtime (event->substr (0, TIMESTAMP_LEN), &system_time);
// Store the data
this->setOutput (event->substr (26), &system_time);
this->setOutput (event->substr (TIMESTAMP_LEN), &system_time);
}
}
/**
* Opens a handle to the module event log.
*
* @return A handle to the event log.
*/
HANDLE
Pandora_Module_Logevent::openLogEvent () {
// Check whether the event log is already open
if (this->log_event != NULL) {
return NULL;
}
// Open the event log
this->log_event = OpenEventLog (NULL, this->source.c_str ());
if (this->log_event == NULL) {
pandoraLog ("Could not open event log file '%s'", this->source.c_str ());
return NULL;
}
// Discard existing events
this->discardLogEvents ();
return this->log_event;
}
/**
* Closes the current event log.
*/
void
Pandora_Module_Logevent::closeLogEvent () {
if (this->log_event == NULL) {
return;
}
// Close the event log
CloseEventLog (this->log_event);
this->log_event = NULL;
}
/**
* Discards existing log events.
*/
void
Pandora_Module_Logevent::discardLogEvents () {
int rc;
BYTE bBuffer[BUFFER_SIZE];
DWORD read, needed;
DWORD oldest_event, newest_event, num_events;
EVENTLOGRECORD *pevlr;
if (this->log_event == NULL) {
return;
}
// Get the offset of the newest event
GetOldestEventLogRecord (this->log_event, &oldest_event);
GetNumberOfEventLogRecords (this->log_event, &num_events);
newest_event = oldest_event + num_events;
// Initialize the event record buffer
pevlr = (EVENTLOGRECORD *)&bBuffer;
// Read the newest event, subsequent calls to ReadEventLog will read from here
rc = ReadEventLog(this->log_event, EVENTLOG_FORWARDS_READ | EVENTLOG_SEEK_READ,
newest_event, pevlr, BUFFER_SIZE, &read, &needed);
// Something went wrong
if (rc != 0) {
pandoraLog ("ReadEventLog error %d", GetLastError ());
}
}
/**
* Reads available events from the event log.
*/
int
Pandora_Module_Logevent::getLogEvents (list<string> &event_list) {
char description[BUFFER_SIZE], timestamp[TIMESTAMP_LEN + 1];
struct tm *time_info = NULL;
time_t epoch;
string event;
BYTE buffer[BUFFER_SIZE];
DWORD read, needed;
EVENTLOGRECORD *pevlr = NULL;
LPCTSTR source_name;
if (this->log_event == NULL) {
return -1;
}
// Initialize the event record buffer
pevlr = (EVENTLOGRECORD *) &buffer;
// Read events
while (ReadEventLog(this->log_event, EVENTLOG_FORWARDS_READ | EVENTLOG_SEQUENTIAL_READ,
0, pevlr, BUFFER_SIZE, &read, &needed)) {
while (read > 0) {
// Retrieve the event description
getEventDescription (pevlr, description);
// Filter the event
if (filterEvent (pevlr, description) == 0) {
// Generate a timestamp for the event
epoch = pevlr->TimeGenerated;
time_info = localtime (&epoch);
strftime (timestamp, TIMESTAMP_LEN + 1, "%Y-%m-%d %H:%M:%S", time_info);
// Add the event to the list
event = timestamp;
event.append (description);
event_list.push_back (event);
}
// Move to the next event
read -= pevlr->Length;
pevlr = (EVENTLOGRECORD *) ((LPBYTE) pevlr + pevlr->Length);
}
pevlr = (EVENTLOGRECORD *) &buffer;
}
return 0;
}
/**
* Converts a timestamp in the format "%Y-%m-%d %H:%M:%S"
* to SYSTEMTIME format.
*
* @param wmi_date Timestamp.
* @param system_time Output SYSTEMTIME variable.
*/
void
Pandora_Module_Logevent::timestampToSystemtime (string timestamp, SYSTEMTIME *system_time) {
system_time->wYear = atoi (timestamp.substr (0, 4).c_str());
system_time->wMonth = atoi (timestamp.substr (5, 2).c_str());
system_time->wDay = atoi (timestamp.substr (8, 2).c_str());
system_time->wHour = atoi (timestamp.substr (11, 2).c_str());
system_time->wMinute = atoi (timestamp.substr (14, 2).c_str());
system_time->wSecond = atoi (timestamp.substr (17, 2).c_str());
}
/**
* Retrieves the description of the given event.
*
* @param event Event log record.
* @param message Buffer to store the description (at least _MAX_PATH + 1).
* @return 0 if the description could be retrieved, -1 otherwise.
*/
void
Pandora_Module_Logevent::getEventDescription (PEVENTLOGRECORD pevlr, char *message) {
int i, j, len, offset;
LPBYTE data = 0;
HMODULE module = 0;
TCHAR exe_file[_MAX_PATH + 1], exe_file_path[_MAX_PATH + 1];
HKEY hk = (HKEY)0;
TCHAR key_name[_MAX_PATH + 1];
DWORD max_path, type;
LPCSTR source_name;
TCHAR **strings = NULL;
message[0] = 0;
// Read the source name
source_name = (LPCTSTR) ((LPBYTE) pevlr + sizeof(EVENTLOGRECORD));
// Read the key that points to the message file
wsprintf (key_name, "SYSTEM\\CurrentControlSet\\Services\\EventLog\\%s\\%s", this->source.c_str (), source_name);
if (RegOpenKeyEx (HKEY_LOCAL_MACHINE, key_name, 0L, KEY_READ, &hk) != NOERROR) {
return;
}
max_path = _MAX_PATH + 1;
if (RegQueryValueEx (hk, "EventMessageFile", 0, &type, (LPBYTE)exe_file, &max_path) != NOERROR) {
RegCloseKey(hk);
return;
}
if (ExpandEnvironmentStrings (exe_file, exe_file_path, _MAX_PATH + 1) == 0) {
strncpy(exe_file_path, exe_file, _MAX_PATH + 1);
}
// Load the DLL
module = LoadLibraryEx (exe_file_path, 0, DONT_RESOLVE_DLL_REFERENCES);
if(module == NULL) {
RegCloseKey(hk);
return;
}
// Get the event strings
strings = (TCHAR**)malloc (pevlr->NumStrings * sizeof(TCHAR *));
if (strings == NULL) {
RegCloseKey(hk);
return;
}
offset = pevlr->StringOffset;
for (i = 0; i < pevlr->NumStrings; i++) {
len = strlen ((TCHAR *)pevlr + offset);
strings[i] = (TCHAR *) malloc ((len + 1) * sizeof(TCHAR));
if (strings[i] == NULL) {
for (j = 0; j < i; j++) {
if (strings[j] != NULL) {
free ((void *)strings[j]);
}
}
}
strcpy(strings[i], (TCHAR *)pevlr + offset);
offset += len + 1;
}
// Get the description
if (FormatMessage (FORMAT_MESSAGE_FROM_HMODULE | FORMAT_MESSAGE_ARGUMENT_ARRAY, module, pevlr->EventID, 0, (LPTSTR)message, BUFFER_SIZE, strings) == 0) {
message[0] = 0;
}
// Clean up
for (i = 0; i < pevlr->NumStrings; i++) {
if (strings[i] != NULL) {
free ((void *)strings[i]);
}
}
free ((void *)strings);
FreeLibrary(module);
RegCloseKey(hk);
}
/**
* Filters the given event according to the module parameters.
*
* @param event Event log record.
* @param event Event description.22
* @return Returns 0 if the event matches the filters, -1 otherwise.
*/
int
Pandora_Module_Logevent::filterEvent (PEVENTLOGRECORD pevlr, string description) {
LPCSTR source_name;
// Event ID filter
if (this->id > 0 && this->id != pevlr->EventID) {
return -1;
}
// Type filter
if (this->type != -1 && this->type != pevlr->EventType) {
return -1;
}
// Application filter
source_name = (LPCTSTR) ((LPBYTE) pevlr + sizeof(EVENTLOGRECORD));
if (! this->application.empty () && this->application.compare (source_name) != 0) {
return -1;
}
// Pattern filter
if (! this->pattern.empty () && description.find(this->pattern) == string::npos) {
return -1;
}
return 0;
}

View File

@ -24,6 +24,12 @@
#include "pandora_module.h"
// Log event read buffer size
#define BUFFER_SIZE 1024
// Length of a timestamp string YYYY-MM-DD HH:MM:SS
#define TIMESTAMP_LEN 19
namespace Pandora_Modules {
/**
@ -33,12 +39,24 @@ namespace Pandora_Modules {
class Pandora_Module_Logevent : public Pandora_Module {
private:
int id;
int type;
string source;
string type;
string code;
string application;
string pattern;
HANDLE log_event;
HANDLE messages_dll;
HANDLE openLogEvent ();
void closeLogEvent ();
void discardLogEvents ();
int getLogEvents (list<string> &event_list);
void timestampToSystemtime (string timestamp, SYSTEMTIME *system_time);
void getEventDescription (PEVENTLOGRECORD pevlr, char *message);
int filterEvent (PEVENTLOGRECORD pevlr, string description);
public:
Pandora_Module_Logevent (string name, string source, string type, string code, string pattern);
Pandora_Module_Logevent (string name, string source, string type, string id, string pattern, string application);
void run ();
};
}

View File

@ -0,0 +1,158 @@
/* Pandora perfcounter module. This module retrieves information from
performance counters.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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 <iostream>
#include <sstream>
#include <string>
#include "pandora_module_perfcounter.h"
using namespace Pandora;
using namespace Pandora_Modules;
// Pointers to pdh.dll functions
static HINSTANCE PDH = NULL;
static PdhOpenQueryT PdhOpenQuery = NULL;
static PdhAddCounterT PdhAddCounter = NULL;
static PdhCollectQueryDataT PdhCollectQueryData = NULL;
static PdhGetRawCounterValueT PdhGetRawCounterValue = NULL;
static PdhCloseQueryT PdhCloseQuery = NULL;
/**
* Creates a Pandora_Module_Perfcounter object.
*
* @param name Module name.
* @param service_name Service internal name to check.
*/
Pandora_Module_Perfcounter::Pandora_Module_Perfcounter (string name, string source)
: Pandora_Module (name) {
this->source = source;
this->setKind (module_perfcounter_str);
// Load pdh.dll and some functions
if (PDH == NULL) {
PDH = LoadLibrary("pdh.dll");
if (PDH == NULL) {
pandoraLog ("Error loading library pdh.dll");
return;
}
PdhOpenQuery = (PdhOpenQueryT) GetProcAddress (PDH, "PdhOpenQueryA");
if (PdhOpenQuery == NULL) {
pandoraLog ("Error loading function PdhOpenQueryA");
FreeLibrary (PDH);
PDH = NULL;
return;
}
PdhAddCounter = (PdhAddCounterT) GetProcAddress (PDH, "PdhAddCounterA");
if (PdhAddCounter == NULL) {
pandoraLog ("Error loading function PdhAddCounterA");
FreeLibrary (PDH);
PDH = NULL;
return;
}
PdhCollectQueryData = (PdhCollectQueryDataT) GetProcAddress (PDH, "PdhCollectQueryData");
if (PdhCollectQueryData == NULL) {
pandoraLog ("Error loading function PdhCollectQueryData");
FreeLibrary (PDH);
PDH = NULL;
return;
}
PdhGetRawCounterValue = (PdhGetRawCounterValueT) GetProcAddress (PDH, "PdhGetRawCounterValue");
if (PdhGetRawCounterValue == NULL) {
pandoraLog ("Error loading function PdhGetRawCounterValue");
FreeLibrary (PDH);
PDH = NULL;
return;
}
PdhCloseQuery = (PdhCloseQueryT) GetProcAddress (PDH, "PdhCloseQuery");
if (PdhCloseQuery == NULL) {
pandoraLog ("Error loading function PdhCloseQuery");
FreeLibrary (PDH);
PDH = NULL;
return;
}
}
}
/**
* Pandora_Module_Perfcounter destructor.
*/
Pandora_Module_Perfcounter::~Pandora_Module_Perfcounter () {
FreeLibrary (PDH);
}
void
Pandora_Module_Perfcounter::run () {
WCHAR source [MAX_PATH];
HQUERY query;
PDH_STATUS status;
HCOUNTER counter;
PDH_RAW_COUNTER value;
ostringstream string_value;
// Run
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
if(PDH == NULL) {
pandoraLog ("pdh.dll not found.");
return;
}
// Open a query object
status = PdhOpenQuery (NULL, 0, &query);
if (status != ERROR_SUCCESS) {
pandoraLog ("PdhOpenQuery failed with error %d", status);
return;
}
// Add the counter that will provide the data
status = PdhAddCounter (query, this->source.c_str (), 0, &counter);
if (status != ERROR_SUCCESS) {
pandoraLog ("PdhAddCounter failed with error %d", status);
return;
}
// Collect the data
status = PdhCollectQueryData (query);
if (status != ERROR_SUCCESS) {
// No data
return;
}
// Retrieve the counter value
status = PdhGetRawCounterValue(counter, NULL, &value);
// Close the query object
PdhCloseQuery (query);
string_value << value.FirstValue;
this->setOutput (string_value.str ());
}

View File

@ -0,0 +1,65 @@
/* Pandora perfcounter module. This module retrieves information from
performance counters.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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.
*/
#ifndef __PANDORA_MODULE_PERFCOUNTER_H__
#define __PANDORA_MODULE_PERFCOUNTER_H__
#include "pandora_module.h"
#define BUFFER_SIZE 1024
// Some definitions to use pdh.dll
typedef LONG PDH_STATUS;
typedef HANDLE HCOUNTER;
typedef HANDLE HQUERY;
typedef struct _PDH_RAW_COUNTER {
DWORD CStatus;
FILETIME TimeStamp;
LONGLONG FirstValue;
LONGLONG SecondValue;
DWORD MultiCount;
} PDH_RAW_COUNTER, *PPDH_RAW_COUNTER;
#define PDH_FUNCTION PDH_STATUS __stdcall
typedef PDH_FUNCTION (*PdhOpenQueryT) (IN LPCSTR szDataSource, IN DWORD_PTR dwUserData, IN HQUERY *phQuery);
typedef PDH_FUNCTION (*PdhAddCounterT) (IN HQUERY hQuery, IN LPCSTR szFullCounterPath, IN DWORD_PTR dwUserData, IN HCOUNTER *phCounter);
typedef PDH_FUNCTION (*PdhCollectQueryDataT) (IN HQUERY hQuery);
typedef PDH_FUNCTION (*PdhGetRawCounterValueT) (IN HCOUNTER, IN LPDWORD lpdwType, IN PPDH_RAW_COUNTER pValue);
typedef PDH_FUNCTION (*PdhCloseQueryT) (IN HQUERY hQuery);
namespace Pandora_Modules {
/**
* This module retrieves information from performance counters.
*/
class Pandora_Module_Perfcounter : public Pandora_Module {
private:
string source;
public:
Pandora_Module_Perfcounter (string name, string source);
virtual ~Pandora_Module_Perfcounter ();
void run ();
};
}
#endif

View File

@ -0,0 +1,136 @@
/* Pandora regexp module. This module searches a file for matches of
a regular expression.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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 <iostream>
#include <sstream>
#include <string>
#include "pandora_module_regexp.h"
#include "../pandora_windows_service.h"
using namespace Pandora;
using namespace Pandora_Modules;
/**
* Creates a Pandora_Module_Regexp object.
*
* @param name Module name.
* @param source File to search.
* @param pattern Regular expression to match.
*/
Pandora_Module_Regexp::Pandora_Module_Regexp (string name, string source, string pattern)
: Pandora_Module (name) {
this->source = source;
// Compile the regular expression
if (regcomp (&this->regexp, pattern.c_str (), 0) != 0) {
pandoraLog ("Invalid regular expression %s", pattern.c_str ());
}
// Open the file and skip to the end
this->file.open (source.c_str ());
if (this->file.is_open ()) {
this->file.seekg (0, ios_base::end);
} else {
pandoraLog ("Error opening file %s", source.c_str ());
}
this->setKind (module_regexp_str);
}
/**
* Pandora_Module_Regexp destructor.
*/
Pandora_Module_Regexp::~Pandora_Module_Regexp () {
this->file.close();
}
void
Pandora_Module_Regexp::run () {
int count;
string line;
ostringstream output;
Module_Type type;
type = this->getTypeInt ();
// Run
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
// Check if the file could be opened
if (! file.is_open () || ! file.good ()) {
this->restart ();
return;
}
// Read new lines
count = 0;
while (! file.eof ()) {
getline (file, line);
// Discard empty lines
if (line.empty ()) {
continue;
}
// Try to match the line with the regexp
if (regexec (&this->regexp, line.c_str (), 0, NULL, 0) == 0) {
if (type == TYPE_GENERIC_DATA_STRING || type == TYPE_ASYNC_STRING) {
this->setOutput (line);
}
count++;
}
}
// Set output according to the module type
if (type == TYPE_GENERIC_DATA_STRING || type == TYPE_ASYNC_STRING) {
// Already set
}
else if (type == TYPE_GENERIC_PROC || type == TYPE_ASYNC_PROC) {
this->setOutput (count > 0 ? "1" : "0");
} else {
output << count;
this->setOutput (output.str ());
}
// Clear the EOF flag
file.clear ();
}
/**
* Closes, re-opens and seeks to the end of the current file.
*/
void
Pandora_Module_Regexp::restart () {
this->file.close ();
this->file.open (this->source.c_str ());
if (this->file.is_open ()) {
this->file.seekg (0, ios_base::end);
return;
}
pandoraLog ("Error opening file %s", this->source.c_str ());
}

View File

@ -0,0 +1,52 @@
/* Pandora regexp module. This module searches a file for matches of
a regular expression.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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.
*/
#ifndef __PANDORA_MODULE_REGEXP_H__
#define __PANDORA_MODULE_REGEXP_H__
#include <iostream>
#include <fstream>
#include <string>
#include "pandora_module.h"
#include "boost/regex.h"
namespace Pandora_Modules {
/**
* This module searches a file for matches of a regular expression.
*/
class Pandora_Module_Regexp : public Pandora_Module {
private:
string source;
ifstream file;
regex_t regexp;
void restart ();
public:
Pandora_Module_Regexp (string name, string source, string pattern);
virtual ~Pandora_Module_Regexp ();
void run ();
};
}
#endif

View File

@ -0,0 +1,131 @@
/* Pandora tcpcheck module. This module checks whether a tcp port is open.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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 <winsock.h>
#include "pandora_module_tcpcheck.h"
using namespace Pandora;
using namespace Pandora_Modules;
/**
* Creates a Pandora_Module_Tcpcheck object.
*
* @param name Module name.
* @param address Target address.
* @param port Target port.
* @param timeout Connection timeout.
*/
Pandora_Module_Tcpcheck::Pandora_Module_Tcpcheck (string name, string address, string port, string timeout)
: Pandora_Module (name) {
int rc;
WSADATA wsa_data;
// Initialize Winsock
WSAStartup (MAKEWORD(2,2), &wsa_data);
this->address = address;
this->port = atoi (port.c_str ());
this->timeout = atoi (timeout.c_str ());
// Set a default timeout
if (this->timeout < 1) {
this->timeout = DEFAULT_TIMEOUT;
}
this->setKind (module_tcpcheck_str);
}
/**
* Pandora_Module_Tcpcheck destructor.
*/
Pandora_Module_Tcpcheck::~Pandora_Module_Tcpcheck () {
WSACleanup ();
}
void
Pandora_Module_Tcpcheck::run () {
int rc, sock, port;
unsigned long mode = 1;
struct sockaddr_in server;
struct hostent *host = NULL;
fd_set socket_set;
timeval timer;
// Run
try {
Pandora_Module::run ();
} catch (Interval_Not_Fulfilled e) {
return;
}
if (this->address.empty ()) {
return;
}
// Create the TCP socket
sock = socket (PF_INET, SOCK_STREAM, IPPROTO_TCP);
if (sock == SOCKET_ERROR) {
pandoraLog ("Error %d creating socket", WSAGetLastError ());
return;
}
memset(&server, 0, sizeof(server));
server.sin_family = AF_INET;
server.sin_port = htons(this->port);
server.sin_addr.s_addr = inet_addr(this->address.c_str ());
if (server.sin_addr.s_addr == -1) {
// Try to resolve the address
host = gethostbyname(this->address.c_str ());
if (host == NULL) {
pandoraLog ("Could not resolve address for %s", this->address.c_str ());
return;
}
memcpy(&server.sin_addr, host->h_addr_list[0], host->h_length);
}
// Use non-blocking sockets to implement a timeout
ioctlsocket (sock, FIONBIO, &mode);
// Connection request
rc = connect(sock, (struct sockaddr *) &server, sizeof(server));
if (rc == SOCKET_ERROR) {
rc = WSAGetLastError ();
if (rc != WSAEWOULDBLOCK) {
pandoraLog ("connect error %d", rc);
return;
}
}
// Determine the completion of the connection request by checking to see if
// the socket is writeable
socket_set.fd_array[0] = sock;
socket_set.fd_count = 1;
timer.tv_sec = this->timeout;
rc = select(0, NULL, &socket_set, NULL, &timer);
if (rc == 0) {
this->setOutput ("0");
return;
}
this->setOutput ("1");
}

View File

@ -0,0 +1,47 @@
/* Pandora tcpcheck module. This module checks whether a tcp port is open.
Copyright (C) 2008 Artica ST.
Written by Ramon Novoa.
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, or (at your option)
any later version.
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.
*/
#ifndef __PANDORA_MODULE_TCPCHECK_H__
#define __PANDORA_MODULE_TCPCHECK_H__
#include "pandora_module.h"
#define DEFAULT_TIMEOUT 3
namespace Pandora_Modules {
/**
* This module checks whether a tcp port is open.
*/
class Pandora_Module_Tcpcheck : public Pandora_Module {
private:
string address;
int port;
int timeout;
public:
Pandora_Module_Tcpcheck (string name, string address, string port, string timeout);
virtual ~Pandora_Module_Tcpcheck ();
void run ();
};
}
#endif

View File

@ -683,6 +683,12 @@ Pandora_Windows_Service::sendXml (Pandora_Module_List *modules) {
string encoding;
bool saved;
static HANDLE mutex = 0;
ULARGE_INTEGER free_bytes;
double min_free_bytes = 0;
Pandora_Agent_Conf *conf = NULL;
conf = this->getConf ();
min_free_bytes = 1024 * atoi (conf->getValue ("temporal_min_size").c_str ());
if (mutex == 0) {
mutex = CreateMutex (NULL, FALSE, NULL);
@ -749,24 +755,76 @@ Pandora_Windows_Service::sendXml (Pandora_Module_List *modules) {
/* Only send if debug is not activated */
if (getPandoraDebug () == false) {
this->copyDataFile (tmp_filename);
Pandora_File::removeFile (tmp_filepath);
rc = this->copyDataFile (tmp_filename);
/* Delete the file if successfully copied or not enough space available */
if (rc == 0 || (GetDiskFreeSpaceEx (tmp_filepath.c_str (), &free_bytes, NULL, NULL) != 0
&& free_bytes.QuadPart < min_free_bytes)) {
Pandora_File::removeFile (tmp_filepath);
}
/* Send any buffered data files */
this->sendBufferedXml (conf->getValue ("temporal"));
}
ReleaseMutex (mutex);
}
void
Pandora_Windows_Service::sendBufferedXml (string path) {
string base_path = path, file_path;
WIN32_FIND_DATA file_data;
HANDLE find;
if (base_path[base_path.length () - 1] != '\\') {
base_path += "\\";
}
file_path = base_path + "*.data";
/* Search for buffered data files */
find = FindFirstFile(file_path.c_str (), &file_data);
if (find == INVALID_HANDLE_VALUE) {
return;
}
/* Send data files as long as there are no errors */
if (this->copyDataFile (file_data.cFileName) != 0) {
FindClose(find);
return;
}
Pandora_File::removeFile (base_path + file_data.cFileName);
while (FindNextFile(find, &file_data) != 0) {
if (this->copyDataFile (file_data.cFileName) != 0) {
FindClose(find);
return;
}
Pandora_File::removeFile (base_path + file_data.cFileName);
}
FindClose(find);
}
void
Pandora_Windows_Service::pandora_run () {
Pandora_Agent_Conf *conf = NULL;
string server_addr;
int startup_delay = 0;
pandoraDebug ("Run begin");
conf = this->getConf ();
/* Sleep if a startup delay was specified */
startup_delay = atoi (conf->getValue ("startup_delay").c_str ());
if (startup_delay > 0) {
pandoraLog ("Delaying startup %d seconds", startup_delay);
Sleep (startup_delay);
}
/* Check for configuration changes */
this->checkConfig ();
conf = this->getConf ();
server_addr = conf->getValue ("server_ip");
execution_number++;

View File

@ -84,6 +84,7 @@ namespace Pandora {
void start ();
int sendXml (Pandora_Module_List *modules);
void sendBufferedXml (string path);
Pandora_Agent_Conf *getConf ();
};
}

View File

@ -179,6 +179,56 @@ Pandora_Wmi::getDiskFreeSpace (string disk_id) {
throw Pandora_Wmi_Exception ();
}
/**
* Get the free space in a logical disk drive.
*
* @param disk_id Disk drive letter (C: for example).
*
* @return Free space percentage.
*
* @exception Pandora_Wmi_Exception Throwd if an error occured when reading
* from WMI database.
*/
unsigned long
Pandora_Wmi::getDiskFreeSpacePercent (string disk_id) {
CDhInitialize init;
CDispPtr wmi_svc, quickfixes;
unsigned long free_space = 0, size = 0;
unsigned long total_free_space = 0, total_size = 0;
string query, free_str, size_str;
query = "SELECT Size, FreeSpace FROM Win32_LogicalDisk WHERE DeviceID = \"" + disk_id + "\"";
try {
dhCheck (dhGetObject (getWmiStr (L"."), NULL, &wmi_svc));
dhCheck (dhGetValue (L"%o", &quickfixes, wmi_svc,
L".ExecQuery(%T)",
query.c_str ()));
FOR_EACH (quickfix, quickfixes, NULL) {
dhGetValue (L"%s", &free_str, quickfix,
L".FreeSpace");
dhGetValue (L"%s", &size_str, quickfix,
L".Size");
free_space = Pandora_Strutils::strtoulong (free_str);
size = Pandora_Strutils::strtoulong (size_str);
total_free_space += free_space;
total_size += size;
} NEXT_THROW (quickfix);
if (total_size == 0) {
return 0;
}
return total_free_space * 100 / total_size;
} catch (string errstr) {
pandoraLog ("getDiskFreeSpace error. %s", errstr.c_str ());
}
throw Pandora_Wmi_Exception ();
}
/**
* Get the CPU usage percentage in the last minutes.
*
@ -194,24 +244,40 @@ Pandora_Wmi::getCpuUsagePercentage (int cpu_id) {
CDhInitialize init;
CDispPtr wmi_svc, quickfixes;
string query;
long load_percentage;
long load_percentage, total_load;
int total_cpus;
std::ostringstream stm;
stm << cpu_id;
query = "SELECT * FROM Win32_Processor WHERE DeviceID = \"CPU" + stm.str () + "\"";
// Select all CPUs
if (cpu_id < 0) {
query = "SELECT * FROM Win32_Processor";
// Select a single CPUs
} else {
stm << cpu_id;
query = "SELECT * FROM Win32_Processor WHERE DeviceID = \"CPU" + stm.str () + "\"";
}
try {
dhCheck (dhGetObject (getWmiStr (L"."), NULL, &wmi_svc));
dhCheck (dhGetValue (L"%o", &quickfixes, wmi_svc,
L".ExecQuery(%T)",
query.c_str ()));
total_cpus = 0;
total_load = 0;
FOR_EACH (quickfix, quickfixes, NULL) {
dhGetValue (L"%d", &load_percentage, quickfix,
L".LoadPercentage");
return load_percentage;
total_cpus++;
total_load += load_percentage;
} NEXT_THROW (quickfix);
if (total_cpus == 0) {
return 0;
}
return total_load / total_cpus;
} catch (string errstr) {
pandoraLog ("getCpuUsagePercentage error. %s", errstr.c_str ());
}
@ -251,6 +317,45 @@ Pandora_Wmi::getFreememory () {
throw Pandora_Wmi_Exception ();
}
/**
* Get the percentage of free memory in the system
*
* @return The percentage of free memory.
* @exception Pandora_Wmi_Exception Throwd if an error occured when reading
* from WMI database.
*/
long
Pandora_Wmi::getFreememoryPercent () {
CDhInitialize init;
CDispPtr wmi_svc, quickfixes;
long free_memory, total_memory;
try {
dhCheck (dhGetObject (getWmiStr (L"."), NULL, &wmi_svc));
dhCheck (dhGetValue (L"%o", &quickfixes, wmi_svc,
L".ExecQuery(%S)",
L"SELECT FreePhysicalMemory, TotalVisibleMemorySize FROM Win32_OperatingSystem "));
FOR_EACH (quickfix, quickfixes, NULL) {
dhGetValue (L"%d", &free_memory, quickfix,
L".FreePhysicalMemory");
dhGetValue (L"%d", &total_memory, quickfix,
L".TotalVisibleMemorySize");
if (total_memory == 0) {
return 0;
}
return free_memory * 100 / total_memory;
} NEXT_THROW (quickfix);
} catch (string errstr) {
pandoraLog ("getFreememory error. %s", errstr.c_str ());
}
throw Pandora_Wmi_Exception ();
}
/**
* Get the name of the operating system.
*
@ -383,139 +488,6 @@ Pandora_Wmi::getSystemName () {
return ret;
}
/**
* Get a list of events that match a given pattern.
*
* @return The list of events.
*/
void
Pandora_Wmi::getEventList (string source, string type, string code,
string pattern, int interval,
list<string> &event_list) {
CDhInitialize init;
CDispPtr wmi_svc, quickfixes;
char *value = NULL;
WCHAR *unicode_value;
string event, limit, message, query, timestamp;
char *encode;
limit = getTimestampLimit (interval);
if (limit.empty()) {
pandoraDebug ("Pandora_Wmi::getEventList: getTimestampLimit error");
return;
}
// Build the WQL query
query = "SELECT * FROM Win32_NTLogEvent WHERE TimeWritten >= '" + limit + "'";
if (! source.empty()) {
query += " AND Logfile = '" + source + "'";
}
if (! type.empty()) {
query += " AND Type = '" + type + "'";
}
if (! code.empty()) {
query += " AND EventCode = '" + code + "'";
}
try {
dhCheck (dhGetObject (getWmiStr (L"."), NULL, &wmi_svc));
dhCheck (dhGetValue (L"%o", &quickfixes, wmi_svc,
L".ExecQuery(%s)",
query.c_str()));
FOR_EACH (quickfix, quickfixes, NULL) {
// Timestamp
dhGetValue (L"%s", &value, quickfix,
L".TimeWritten");
timestamp = value;
dhFreeString (value);
// Message
dhGetValue (L"%S", &unicode_value, quickfix,
L".Message");
value = Pandora_Strutils::strUnicodeToAnsi (unicode_value);
message = Pandora_Strutils::trim (value);
dhFreeString (value);
// LIKE is not always available, we have to filter ourselves
if (pattern.empty () || (message.find (pattern) != string::npos)) {
event = timestamp + " " + message;
event_list.push_back(event);
}
} NEXT_THROW (quickfix);
} catch (string errstr) {
pandoraDebug ("Pandora_Wmi::getEventList: error: %s", errstr.c_str ());
}
}
/**
* Returns the limit date (WMI format) for event searches.
*
* @return The timestamp in WMI format.
*/
string
Pandora_Wmi::getTimestampLimit (int interval) {
char limit_str[26], diff_sign;
time_t limit_time, limit_time_utc, limit_diff;
struct tm *limit_tm = NULL, *limit_tm_utc = NULL;
// Get current time
limit_time = time(0);
if (limit_time == (time_t)-1) {
return "";
}
// Get UTC time
limit_tm_utc = gmtime (&limit_time);
limit_time_utc = mktime (limit_tm_utc);
// Calculate the difference in minutes
limit_diff = limit_time - limit_time_utc;
if (limit_diff >= 0) {
diff_sign = '+';
}
else {
diff_sign = '-';
}
limit_diff = abs(limit_diff);
limit_diff /= 60;
// Substract the agent interval
limit_time -= interval;
limit_tm = localtime (&limit_time);
if (limit_tm == NULL) {
return "";
}
// WMI date format: yyyymmddHHMMSS.xxxxxx+UUU
snprintf (limit_str, 26, "%.4d%.2d%.2d%.2d%.2d%.2d.000000%c%.3d",
limit_tm->tm_year + 1900, limit_tm->tm_mon + 1,
limit_tm->tm_mday, limit_tm->tm_hour,
limit_tm->tm_min, limit_tm->tm_sec, diff_sign, limit_diff);
limit_str[25] = '\0';
return string (limit_str);
}
/**
* Converts a date in WMI format to SYSTEMTIME format.
*
* @param wmi_date Date in WMI format
* @param system_time Output system time variable
*/
void
Pandora_Wmi::convertWMIDate (string wmi_date, SYSTEMTIME *system_time)
{
system_time->wYear = atoi (wmi_date.substr (0, 4).c_str());
system_time->wMonth = atoi (wmi_date.substr (4, 2).c_str());
system_time->wDay = atoi (wmi_date.substr (6, 2).c_str());
system_time->wHour = atoi (wmi_date.substr (8, 2).c_str());
system_time->wMinute = atoi (wmi_date.substr (10, 2).c_str());
system_time->wSecond = atoi (wmi_date.substr (12, 2).c_str());
}
/**
* Runs a program in a new process.
*

View File

@ -41,23 +41,14 @@ namespace Pandora_Wmi {
int isProcessRunning (string process_name);
int isServiceRunning (string service_name);
unsigned long getDiskFreeSpace (string disk_id);
unsigned long getDiskFreeSpacePercent (string disk_id);
int getCpuUsagePercentage (int cpu_id);
long getFreememory ();
long getFreememoryPercent ();
string getOSName ();
string getOSVersion ();
string getOSBuild ();
string getSystemName ();
void getEventList (string source,
string type,
string code,
string pattern,
int interval,
list<string> &event_list);
string getTimestampLimit (int interval);
void convertWMIDate (string wmi_date,
SYSTEMTIME *system_time);
string getSystemName ();
bool runProgram (string command, DWORD flags = 0);
bool startService (string service_name);
bool stopService (string service_name);