From d5ffd2cb82363df08dc7b79eb98e1523ac78d880 Mon Sep 17 00:00:00 2001 From: fermin831 Date: Mon, 25 Sep 2017 19:42:58 +0200 Subject: [PATCH] Improve performance module_logevent Windows --- .../win32/modules/pandora_module_logevent.cc | 86 +++++++++++++++++-- .../win32/modules/pandora_module_logevent.h | 3 +- 2 files changed, 80 insertions(+), 9 deletions(-) diff --git a/pandora_agents/win32/modules/pandora_module_logevent.cc b/pandora_agents/win32/modules/pandora_module_logevent.cc index 5a2926b202..2230504ebd 100755 --- a/pandora_agents/win32/modules/pandora_module_logevent.cc +++ b/pandora_agents/win32/modules/pandora_module_logevent.cc @@ -169,7 +169,7 @@ Pandora_Module_Logevent::run () { this->openLogEvent(); // Read events - this->getLogEvents (event_list, 0); + this->getLogEvents (event_list); // No data if (event_list.size () < 1) { @@ -215,7 +215,7 @@ Pandora_Module_Logevent::openLogEvent () { if (this->first_run == 1) { this->first_run = 0; if (Pandora::getPandoraDebug() == false) { - this->getLogEvents (event_list, 1); + this->seekAtTop (event_list); } } @@ -237,11 +237,86 @@ Pandora_Module_Logevent::closeLogEvent () { this->log_event = NULL; } +/** + * Puts the event handler on top of event list + * avoiding the use of EVENTLOG_SEEK_READ because it is buggy + */ +int +Pandora_Module_Logevent::seekAtTop (list &event_list) { + BYTE *buffer = NULL, *new_buffer = NULL; + DWORD to_read, read, needed; + EVENTLOGRECORD *pevlr = NULL; + bool rc = false; + DWORD last_error; + DWORD direction = EVENTLOG_BACKWARDS_READ; + + if (this->log_event == NULL) { + return -1; + } + + // Initialize the event record buffer + to_read = BUFFER_SIZE; + buffer = (BYTE *) malloc (sizeof (BYTE) * BUFFER_SIZE); + if (buffer == NULL) { + return -1; + } + pevlr = (EVENTLOGRECORD *) buffer; + + // Read events + while (1) { + + rc = ReadEventLog (this->log_event, direction | EVENTLOG_SEQUENTIAL_READ, 0, pevlr, to_read, &read, &needed); + direction = EVENTLOG_FORWARDS_READ; + if (!rc) { + + // Get error details + last_error = GetLastError(); + + // Not enough space in the buffer + if(last_error == ERROR_INSUFFICIENT_BUFFER) { + + // Initialize the new event record buffer + to_read = needed; + new_buffer = (BYTE *) realloc (buffer, sizeof (BYTE) * needed); + if (new_buffer == NULL) { + free ((void *) buffer); + return -1; + } + + buffer = new_buffer; + pevlr = (EVENTLOGRECORD *) buffer; + + // Try to read the event again + continue; + // File corrupted or cleared + } else if (last_error == ERROR_EVENTLOG_FILE_CORRUPT || last_error == ERROR_EVENTLOG_FILE_CHANGED) { + closeLogEvent (); + free ((void *) buffer); + return -1; + } + // Unknown error + else { + free ((void *) buffer); + return -1; + } + } + + // No more events + if (read == 0) { + free ((void *) buffer); + return 0; + } + } + + free ((void *) buffer); + return 0; +} + /** * Reads available events from the event log. */ int -Pandora_Module_Logevent::getLogEvents (list &event_list, unsigned char discard) { +Pandora_Module_Logevent::getLogEvents (list &event_list) { char message[BUFFER_SIZE], timestamp[TIMESTAMP_LEN + 1]; struct tm *time_info = NULL; time_t epoch; @@ -313,11 +388,6 @@ Pandora_Module_Logevent::getLogEvents (list &event_list, unsigned char d free ((void *) buffer); return 0; } - - // Discard existing events - if (discard == 1) { - continue; - } // Process read events while (read > 0) { diff --git a/pandora_agents/win32/modules/pandora_module_logevent.h b/pandora_agents/win32/modules/pandora_module_logevent.h index 8f33671775..3615a0ee5a 100755 --- a/pandora_agents/win32/modules/pandora_module_logevent.h +++ b/pandora_agents/win32/modules/pandora_module_logevent.h @@ -69,7 +69,8 @@ namespace Pandora_Modules { HANDLE openLogEvent (); void closeLogEvent (); - int getLogEvents (list &event_list, unsigned char discard); + int getLogEvents (list &event_list); + int seekAtTop (list &event_list); void timestampToSystemtime (string timestamp, SYSTEMTIME *system_time); void getEventDescription (PEVENTLOGRECORD pevlr, char *message, DWORD flags); string getEventDescriptionXPATH (PEVENTLOGRECORD pevlr);