refactored reason string and remediation instructions framework

This commit is contained in:
Andreas Steffen
2012-11-23 12:30:33 +01:00
parent b5d27839ad
commit ee6aeca892
15 changed files with 781 additions and 389 deletions
+154 -225
View File
@@ -14,6 +14,9 @@
*/
#include "imv_os_state.h"
#include "imv/imv_lang_string.h"
#include "imv/imv_reason_string.h"
#include "imv/imv_remediation_string.h"
#include <utils/debug.h>
#include <collections/linked_list.h>
@@ -89,19 +92,24 @@ struct private_imv_os_state_t {
chunk_t version;
/**
* List of vulnerable or blacklisted packages
* List of blacklisted packages to be removed
*/
linked_list_t *bad_packages;
linked_list_t *remove_packages;
/**
* Local copy of the reason string
* List of vulnerable packages to be updated
*/
char *reasons;
linked_list_t *update_packages;
/**
* Local copy of the remediation instruction string
* TNC Reason String
*/
char *instructions;
imv_reason_string_t *reason_string;
/**
* IETF Remediation Instructions String
*/
imv_remediation_string_t *remediation_string;
/**
* Number of processed packages
@@ -141,89 +149,120 @@ struct private_imv_os_state_t {
};
/**
* Store a bad package entry
* Supported languages
*/
struct package_entry_t {
char *name;
os_package_state_t state;
static char* languages[] = { "en", "de", "pl" };
/**
* Table of "OS settings" reason strings
*/
static imv_lang_string_t reason_settings[] = {
{ "en", "Improper OS settings were detected" },
{ "de", "Unzulässige OS Einstellungen wurden festgestellt" },
{ NULL, NULL }
};
/**
* Free a bad package entry
* Table of "software packages" reason strings
*/
static void free_package_entry(package_entry_t *this)
{
free(this->name);
free(this);
static imv_lang_string_t reason_packages[] = {
{ "en", "Vulnerable or blacklisted software packages were found" },
{ "de", "Schwachstellenbehaftete oder gesperrte Softwarepakete wurden gefunden" },
{ NULL, NULL }
};
/**
* Table of "software packages update" instruction title strings
*/
static imv_lang_string_t instr_update_packages_title[] = {
{ "en", "Software Security Updates" },
{ "de", "Software Sicherheitsupdates" },
{ "pl", "Software Security Updates" }, /* TODO */
{ NULL, NULL }
};
/**
* Table of "software packages update" instruction description strings
*/
static imv_lang_string_t instr_update_packages_descr[] = {
{ "en", "Please update the following software packages" },
{ "de", "Bitte updaten Sie die folgenden Softwarepakete" },
{ "pl", "Proszę zaktualizować następujące pakiety" },
{ NULL, NULL }
};
/**
* Tables of "software package removal" instruction titlestrings
*/
static imv_lang_string_t instr_remove_packages_title[] = {
{ "en", "Blacklisted Software Packages" },
{ "de", "Gesperrte Softwarepakete" },
{ "pl", "Blacklisted Software Packages" }, /* TODO */
{ NULL, NULL }
};
/**
* Tables of "software package removal" instruction strings
*/
static imv_lang_string_t instr_remove_packages_descr[] = {
{ "en", "Please remove the following software packages" },
{ "de", "Bitte entfernen Sie die folgenden Softwarepakete" },
{ "pl", "Proszę usunąć następujące pakiety" },
{ NULL, NULL }
}
/**
* Define a language string entry
;/**
* Table of "forwarding enable" instruction title strings
*/
struct entry_t {
char *lang;
char *string;
static imv_lang_string_t instr_fwd_enabled_title[] = {
{ "en", "IP Packet Forwarding" },
{ "de", "Weiterleitung von IP Paketen" },
{ NULL, NULL }
};
/**
* Table of multi-lingual improper settings reason string entries
* Table of "forwarding enable" instruction description strings
*/
static entry_t settings_reasons[] = {
{ "en", "Improper OS settings were detected" },
{ "de", "Unzulässige OS Einstellungen wurden festgestellt" }
static imv_lang_string_t instr_fwd_enabled_descr[] = {
{ "en", "Please disable the forwarding of IP packets" },
{ "de", "Bitte deaktivieren Sie das Forwarding von IP Paketen" },
{ NULL, NULL }
};
/**
* Table of multi-lingual reason string entries
* Table of "default password enabled" instruction title strings
*/
static entry_t reasons[] = {
{ "en", "Vulnerable or blacklisted software packages were found" },
{ "de", "Schwachstellenbehaftete oder gesperrte Softwarepakete wurden gefunden" }
static imv_lang_string_t instr_default_pwd_enabled_title[] = {
{ "en", "Default Password" },
{ "de", "Default Passwort" },
{ NULL, NULL }
};
/**
* Table of multi-lingual forwarding enable string entries
* Table of "default password enabled" instruction description strings
*/
static entry_t instruction_fwd_enabled[] = {
{ "en", "Please disable IP forwarding" },
{ "de", "Bitte deaktivieren Sie das IP Forwarding" }
};
/**
* Table of multi-lingual default password enabled string entries
*/
static entry_t instruction_default_pwd_enabled[] = {
static imv_lang_string_t instr_default_pwd_enabled_descr[] = {
{ "en", "Please change the default password" },
{ "de", "Bitte ändern Sie das default Passwort" }
{ "de", "Bitte ändern Sie das Default Passwort" },
{ NULL, NULL }
};
/**
* Table of multi-lingual defaul install non market apps string entries
* Table of "install non market apps" instruction title strings
*/
static entry_t instruction_non_market_apps[] = {
static imv_lang_string_t instr_non_market_apps_title[] = {
{ "en", "Unknown Software Origin" },
{ "de", "Unbekannte Softwareherkunft" },
{ NULL, NULL }
};
/**
* Table of "install non market apps" instruction description strings
*/
static imv_lang_string_t instr_non_market_apps_descr[] = {
{ "en", "Do not allow the installation of apps from unknown sources" },
{ "de", "Erlauben Sie nicht die Installation von Apps von unbekannten Quellen" }
};
/**
* Define a remediation instruction string entry
*/
struct instruction_entry_t {
char *lang;
char *update_string;
char *removal_string;
};
/**
* Tables of multi-lingual remediation instruction string entries
*/
static instruction_entry_t instructions [] = {
{ "en", "Please update the following software packages:\n",
"Please remove the following software packages:\n" },
{ "de", "Bitte updaten Sie die folgenden Softwarepakete\n",
"Bitte entfernen Sie die folgenden Softwarepakete\n" },
{ "pl", "Proszę zaktualizować następujące pakiety:\n",
"Proszę usunąć następujące pakiety:\n" }
{ "de", "Erlauben Sie nicht die Installation von Apps von unbekannten Quellen" },
{ NULL, NULL }
};
METHOD(imv_state_t, get_connection_id, TNC_ConnectionID,
@@ -287,204 +326,89 @@ METHOD(imv_state_t, set_recommendation, void,
METHOD(imv_state_t, get_reason_string, bool,
private_imv_os_state_t *this, enumerator_t *language_enumerator,
char **reason_string, char **reason_language)
chunk_t *reason_string, char **reason_language)
{
bool match = FALSE;
char *lang, *pos;
int i, i_chosen = 0, len = 0, nr_of_reasons = 0;
if (!this->count_update && !this->count_blacklist & !this->os_settings)
{
return FALSE;
}
*reason_language = imv_lang_string_select_lang(language_enumerator,
languages, countof(languages));
while (language_enumerator->enumerate(language_enumerator, &lang))
{
for (i = 0; i < countof(reasons); i++)
{
if (streq(lang, reasons[i].lang))
{
match = TRUE;
i_chosen = i;
break;
}
}
if (match)
{
break;
}
}
*reason_language = reasons[i_chosen].lang;
/* Instantiate a TNC Reason String object */
DESTROY_IF(this->reason_string);
this->reason_string = imv_reason_string_create(*reason_language);
if (this->count_update || this->count_blacklist)
if (this->count_update || this->count_blacklist)
{
len += strlen(reasons[i_chosen].string);
nr_of_reasons++;
this->reason_string->add_reason(this->reason_string, reason_packages);
}
if (this->os_settings)
{
len += strlen(settings_reasons[i_chosen].string);
nr_of_reasons++;
this->reason_string->add_reason(this->reason_string, reason_settings);
}
/* Allocate memory for the reason string */
pos = this->reasons = malloc(len + nr_of_reasons);
if (this->count_update || this->count_blacklist)
{
strcpy(pos, reasons[i_chosen].string);
pos += strlen(reasons[i_chosen].string);
if (--nr_of_reasons)
{
*pos++ = '\n';
}
}
if (this->os_settings)
{
strcpy(pos, settings_reasons[i_chosen].string);
pos += strlen(settings_reasons[i_chosen].string);
}
*pos = '\0';
*reason_string = this->reasons;
*reason_string = this->reason_string->get_encoding(this->reason_string);
return TRUE;
}
METHOD(imv_state_t, get_remediation_instructions, bool,
private_imv_os_state_t *this, enumerator_t *language_enumerator,
char **string, char **lang_code, char **uri)
chunk_t *string, char **lang_code, char **uri)
{
bool match = FALSE;
char *lang, *pos;
enumerator_t *enumerator;
package_entry_t *entry;
int i, i_chosen = 0, len = 0, nr_of_instructions = 0;
if (!this->count_update && !this->count_blacklist & !this->os_settings)
{
return FALSE;
}
*lang_code = imv_lang_string_select_lang(language_enumerator,
languages, countof(languages));
while (language_enumerator->enumerate(language_enumerator, &lang))
{
for (i = 0; i < countof(instructions); i++)
{
if (streq(lang, instructions[i].lang))
{
match = TRUE;
i_chosen = i;
break;
}
}
if (match)
{
break;
}
}
*lang_code = instructions[i_chosen].lang;
/* Instantiate an IETF Remediation Instructions String object */
DESTROY_IF(this->remediation_string);
this->remediation_string = imv_remediation_string_create(
this->type == OS_TYPE_ANDROID, *lang_code);
/* Compute the size of the remediation string */
if (this->count_update)
{
len += strlen(instructions[i_chosen].update_string);
}
/* List of blacklisted packages to be removed, if any */
if (this->count_blacklist)
{
len += strlen(instructions[i_chosen].removal_string);
}
if (this->os_settings & OS_SETTINGS_FWD_ENABLED)
{
len += strlen(instruction_fwd_enabled[i_chosen].string);
nr_of_instructions++;
}
if (this->os_settings & OS_SETTINGS_DEFAULT_PWD_ENABLED)
{
len += strlen(instruction_default_pwd_enabled[i_chosen].string);
nr_of_instructions++;
}
if (this->os_settings & OS_SETTINGS_NON_MARKET_APPS)
{
len += strlen(instruction_non_market_apps[i_chosen].string);
nr_of_instructions++;
}
enumerator = this->bad_packages->create_enumerator(this->bad_packages);
while (enumerator->enumerate(enumerator, &entry))
{
len += strlen(entry->name) + 1;
}
enumerator->destroy(enumerator);
/* Allocate memory for the remediation instructions */
pos = this->instructions = malloc(len + nr_of_instructions + 1);
/* List of blacklisted packages, if any */
if (this->count_blacklist)
{
strcpy(pos, instructions[i_chosen].removal_string);
pos += strlen(instructions[i_chosen].removal_string);
enumerator = this->bad_packages->create_enumerator(this->bad_packages);
while (enumerator->enumerate(enumerator, &entry))
{
if (entry->state == OS_PACKAGE_STATE_BLACKLIST)
{
strcpy(pos, entry->name);
pos += strlen(entry->name);
*pos++ = '\n';
}
}
enumerator->destroy(enumerator);
this->remediation_string->add_instruction(this->remediation_string,
instr_remove_packages_title,
instr_remove_packages_descr, NULL,
this->remove_packages);
}
/* List of packages in need of an update, if any */
if (this->count_update)
{
strcpy(pos, instructions[i_chosen].update_string);
pos += strlen(instructions[i_chosen].update_string);
enumerator = this->bad_packages->create_enumerator(this->bad_packages);
while (enumerator->enumerate(enumerator, &entry))
{
if (entry->state != OS_PACKAGE_STATE_BLACKLIST)
{
strcpy(pos, entry->name);
pos += strlen(entry->name);
*pos++ = '\n';
}
}
enumerator->destroy(enumerator);
this->remediation_string->add_instruction(this->remediation_string,
instr_update_packages_title,
instr_update_packages_descr, NULL,
this->update_packages);
}
/* Add instructions concerning improper OS settings */
if (this->os_settings & OS_SETTINGS_FWD_ENABLED)
{
strcpy(pos, instruction_fwd_enabled[i_chosen].string);
pos += strlen(instruction_fwd_enabled[i_chosen].string);
if (--nr_of_instructions)
{
*pos++ = '\n';
}
this->remediation_string->add_instruction(this->remediation_string,
instr_fwd_enabled_title,
instr_fwd_enabled_descr, NULL, NULL);
}
if (this->os_settings & OS_SETTINGS_DEFAULT_PWD_ENABLED)
{
strcpy(pos, instruction_default_pwd_enabled[i_chosen].string);
pos += strlen(instruction_default_pwd_enabled[i_chosen].string);
if (--nr_of_instructions)
{
*pos++ = '\n';
}
this->remediation_string->add_instruction(this->remediation_string,
instr_default_pwd_enabled_title,
instr_default_pwd_enabled_descr, NULL, NULL);
}
if (this->os_settings & OS_SETTINGS_NON_MARKET_APPS)
{
strcpy(pos, instruction_non_market_apps[i_chosen].string);
pos += strlen(instruction_non_market_apps[i_chosen].string);
this->remediation_string->add_instruction(this->remediation_string,
instr_non_market_apps_title,
instr_non_market_apps_descr, NULL, NULL);
}
*pos = '\0';
*string = this->instructions;
*string = this->remediation_string->get_encoding(this->remediation_string);
*uri = lib->settings->get_str(lib->settings,
"libimcv.plugins.imv-os.remediation_uri", NULL);
"libimcv.plugins.imv-os.remediation_uri", NULL);
return TRUE;
}
@@ -492,10 +416,10 @@ METHOD(imv_state_t, get_remediation_instructions, bool,
METHOD(imv_state_t, destroy, void,
private_imv_os_state_t *this)
{
this->bad_packages->destroy_function(this->bad_packages,
(void*)free_package_entry);
free(this->reasons);
free(this->instructions);
DESTROY_IF(this->reason_string);
DESTROY_IF(this->remediation_string);
this->update_packages->destroy_function(this->update_packages, free);
this->remove_packages->destroy_function(this->remove_packages, free);
free(this->info);
free(this->name.ptr);
free(this->version.ptr);
@@ -608,12 +532,16 @@ METHOD(imv_os_state_t, add_bad_package, void,
private_imv_os_state_t *this, char *package,
os_package_state_t package_state)
{
package_entry_t *entry;
package = strdup(package);
entry = malloc_thing(package_entry_t);
entry->name = strdup(package);
entry->state = package_state;
this->bad_packages->insert_last(this->bad_packages, entry);
if (package_state == OS_PACKAGE_STATE_BLACKLIST)
{
this->remove_packages->insert_last(this->remove_packages, package);
}
else
{
this->update_packages->insert_last(this->update_packages, package);
}
}
/**
@@ -655,7 +583,8 @@ imv_state_t *imv_os_state_create(TNC_ConnectionID connection_id)
.rec = TNC_IMV_ACTION_RECOMMENDATION_NO_RECOMMENDATION,
.eval = TNC_IMV_EVALUATION_RESULT_DONT_KNOW,
.connection_id = connection_id,
.bad_packages = linked_list_create(),
.update_packages = linked_list_create(),
.remove_packages = linked_list_create(),
);
return &this->public.interface;
@@ -14,6 +14,9 @@
*/
#include "imv_scanner_state.h"
#include "imv/imv_lang_string.h"
#include "imv/imv_reason_string.h"
#include "imv/imv_remediation_string.h"
#include <utils/lexparser.h>
#include <utils/debug.h>
@@ -71,39 +74,53 @@ struct private_imv_scanner_state_t {
char *violating_ports;
/**
* Local copy of the remediation instruction string
* TNC Reason String
*/
char *instructions;
};
imv_reason_string_t *reason_string;
typedef struct entry_t entry_t;
/**
* IETF Remediation Instructions String
*/
imv_remediation_string_t *remediation_string;
/**
* Define an internal reason string entry
*/
struct entry_t {
char *lang;
char *string;
};
/**
* Table of multi-lingual reason string entries
* Supported languages
*/
static entry_t reasons[] = {
static char* languages[] = { "en", "de", "fr", "pl" };
/**
* Table of reason strings
*/
static imv_lang_string_t reasons[] = {
{ "en", "Open server ports were detected" },
{ "de", "Offene Serverports wurden festgestellt" },
{ "fr", "Il y a des ports du serveur ouverts" },
{ "pl", "Są otwarte porty serwera" }
{ "pl", "Są otwarte porty serwera" },
{ NULL, NULL }
};
/**
* Table of multi-lingual remediation instruction string entries
* Table of "ports" remediation instruction title strings
*/
static entry_t instructions [] = {
{ "en", "Please close the following server ports:" },
{ "de", "Bitte schliessen Sie die folgenden Serverports:" },
{ "fr", "Fermez les ports du serveur suivants s'il vous plait:" },
{ "pl", "Proszę zamknąć następujące porty serwera:" }
static imv_lang_string_t instr_ports_title[] = {
{ "en", "Open Server Ports" },
{ "de", "Offene Server Ports" },
{ "fr", "Ports ouverts du serveur" },
{ "pl", "Otwarte Porty Serwera" },
{ NULL, NULL }
};
/**
* Table of "ports" remediation instruction descriptions strings
*/
static imv_lang_string_t instr_ports_descr[] = {
{ "en", "Please close the following server ports" },
{ "de", "Bitte schliessen Sie die folgenden Serverports" },
{ "fr", "Fermez les ports du serveur suivants s'il vous plait" },
{ "pl", "Proszę zamknąć następujące porty serwera" },
{ NULL, NULL }
};
METHOD(imv_state_t, get_connection_id, TNC_ConnectionID,
@@ -167,80 +184,44 @@ METHOD(imv_state_t, set_recommendation, void,
METHOD(imv_state_t, get_reason_string, bool,
private_imv_scanner_state_t *this, enumerator_t *language_enumerator,
char **reason_string, char **reason_language)
chunk_t *reason_string, char **reason_language)
{
bool match = FALSE;
char *lang;
int i;
if (!this->violating_ports)
{
return FALSE;
}
*reason_language = imv_lang_string_select_lang(language_enumerator,
languages, countof(languages));
/* set the default language */
*reason_language = reasons[0].lang;
*reason_string = reasons[0].string;
while (language_enumerator->enumerate(language_enumerator, &lang))
{
for (i = 0; i < countof(reasons); i++)
{
if (streq(lang, reasons[i].lang))
{
match = TRUE;
*reason_language = reasons[i].lang;
*reason_string = reasons[i].string;
break;
}
}
if (match)
{
break;
}
}
/* Instantiate a TNC Reason String object */
DESTROY_IF(this->reason_string);
this->reason_string = imv_reason_string_create(*reason_language);
this->reason_string->add_reason(this->reason_string, reasons);
*reason_string = this->reason_string->get_encoding(this->reason_string);
return TRUE;
}
METHOD(imv_state_t, get_remediation_instructions, bool,
private_imv_scanner_state_t *this, enumerator_t *language_enumerator,
char **string, char **lang_code, char **uri)
chunk_t *string, char **lang_code, char **uri)
{
bool match = FALSE;
char *lang;
int i;
if (!this->violating_ports)
{
return FALSE;
}
*lang_code = imv_lang_string_select_lang(language_enumerator,
languages, countof(languages));
/* set the default language */
*lang_code = instructions[0].lang;
*string = instructions[0].string;
/* Instantiate an IETF Remediation Instructions String object */
DESTROY_IF(this->remediation_string);
this->remediation_string = imv_remediation_string_create(
TRUE, *lang_code); /* TODO get os_type */
while (language_enumerator->enumerate(language_enumerator, &lang))
{
for (i = 0; i < countof(instructions); i++)
{
if (streq(lang, instructions[i].lang))
{
match = TRUE;
*lang_code = instructions[i].lang;
*string = instructions[i].string;
break;
}
}
if (match)
{
break;
}
}
this->instructions = malloc(strlen(*string) +
strlen(this->violating_ports) + 1);
sprintf(this->instructions, "%s%s", *string, this->violating_ports);
*string = this->instructions;
this->remediation_string->add_instruction(this->remediation_string,
instr_ports_title, instr_ports_descr, NULL, NULL);
*string = this->remediation_string->get_encoding(this->remediation_string);
*uri = lib->settings->get_str(lib->settings,
"libimcv.plugins.imv-scanner.remediation_uri", NULL);
@@ -250,8 +231,9 @@ METHOD(imv_state_t, get_remediation_instructions, bool,
METHOD(imv_state_t, destroy, void,
private_imv_scanner_state_t *this)
{
DESTROY_IF(this->reason_string);
DESTROY_IF(this->remediation_string);
free(this->violating_ports);
free(this->instructions);
free(this);
}
+25 -38
View File
@@ -14,6 +14,8 @@
*/
#include "imv_test_state.h"
#include "imv/imv_lang_string.h"
#include "imv/imv_reason_string.h"
#include <utils/lexparser.h>
#include <collections/linked_list.h>
@@ -66,6 +68,11 @@ struct private_imv_test_state_t {
*/
TNC_IMV_Evaluation_Result eval;
/**
* TNC Reason String
*/
imv_reason_string_t *reason_string;
/**
* List of IMCs
*/
@@ -83,24 +90,20 @@ struct imc_entry_t {
int rounds;
};
typedef struct entry_t entry_t;
/**
* Supported languages
*/
static char* languages[] = { "en", "de", "fr", "pl" };
/**
* Define an internal reason string entry
* Table of reason strings
*/
struct entry_t {
char *lang;
char *string;
};
/**
* Table of multi-lingual reason string entries
*/
static entry_t reasons[] = {
static imv_lang_string_t reasons[] = {
{ "en", "IMC Test was not configured with \"command = allow\"" },
{ "de", "IMC Test wurde nicht mit \"command = allow\" konfiguriert" },
{ "fr", "IMC Test n'etait pas configuré avec \"command = allow\"" },
{ "pl", "IMC Test nie zostało skonfigurowany z \"command = allow\"" }
{ "pl", "IMC Test nie zostało skonfigurowany z \"command = allow\"" },
{ NULL, NULL }
};
METHOD(imv_state_t, get_connection_id, TNC_ConnectionID,
@@ -164,40 +167,23 @@ METHOD(imv_state_t, set_recommendation, void,
METHOD(imv_state_t, get_reason_string, bool,
private_imv_test_state_t *this, enumerator_t *language_enumerator,
char **reason_string, char **reason_language)
chunk_t *reason_string, char **reason_language)
{
bool match = FALSE;
char *lang;
int i;
*reason_language = imv_lang_string_select_lang(language_enumerator,
languages, countof(languages));
/* set the default language */
*reason_language = reasons[0].lang;
*reason_string = reasons[0].string;
while (language_enumerator->enumerate(language_enumerator, &lang))
{
for (i = 0 ; i < countof(reasons); i++)
{
if (streq(lang, reasons[i].lang))
{
match = TRUE;
*reason_language = reasons[i].lang;
*reason_string = reasons[i].string;
break;
}
}
if (match)
{
break;
}
}
/* Instantiate a TNC Reason String object */
DESTROY_IF(this->reason_string);
this->reason_string = imv_reason_string_create(*reason_language);
this->reason_string->add_reason(this->reason_string, reasons);
*reason_string = this->reason_string->get_encoding(this->reason_string);
return TRUE;
}
METHOD(imv_state_t, get_remediation_instructions, bool,
private_imv_test_state_t *this, enumerator_t *language_enumerator,
char **string, char **lang_code, char **uri)
chunk_t *string, char **lang_code, char **uri)
{
return FALSE;
}
@@ -205,6 +191,7 @@ METHOD(imv_state_t, get_remediation_instructions, bool,
METHOD(imv_state_t, destroy, void,
private_imv_test_state_t *this)
{
DESTROY_IF(this->reason_string);
this->imcs->destroy_function(this->imcs, free);
free(this);
}