bug(software): Bug fix with software detection

Ubuntu.png - Add new Ubuntu checklist icon
Database_Baseline.zip - Update software detection tables
checklist.inc - Fix software icon detection for IE and SLES, and added detection for Ubuntu
software.inc - Fix bug adding extra spaces to software strings
parse_stig.php - Formatting and add save for when icon is updated
parse_stig_viewer.php - Add scan note when CKL file is missing or has empty <HOST_NAME> tag

Fix #87
This commit is contained in:
Ryan Prather 2019-01-17 12:20:18 -05:00
parent 87991666fd
commit 55f086e8af
No known key found for this signature in database
GPG Key ID: 66FDE2B4E8AB87A7
6 changed files with 498 additions and 467 deletions

Binary file not shown.

View File

@ -5,7 +5,7 @@
* Purpose: Represents a checklist that links a PDI and software package * Purpose: Represents a checklist that links a PDI and software package
* Created: Sep 12, 2013 * Created: Sep 12, 2013
* *
* Portions Copyright 2017: Cyber Perspectives, All rights reserved * Portions Copyright 2017-2019: CyberPerspectives, LLC, All rights reserved
* Released under the Apache v2.0 License * Released under the Apache v2.0 License
* *
* Portions Copyright (c) 2012-2015, Salient Federal Solutions * Portions Copyright (c) 2012-2015, Salient Federal Solutions
@ -406,7 +406,7 @@ class checklist
case (preg_match("/Dot Net|DotNet/i", $this->name) ? true : false): case (preg_match("/Dot Net|DotNet/i", $this->name) ? true : false):
$this->icon = 'Microsoft .NET.png'; $this->icon = 'Microsoft .NET.png';
break; break;
case (preg_match("/Internet Explorer/i", $this->name) ? true : false): case (preg_match("/Internet Explorer|Microsoft IE/i", $this->name) ? true : false):
$this->icon = 'Internet Explorer.png'; $this->icon = 'Internet Explorer.png';
break; break;
case (preg_match("/Windows Phone/i", $this->name) ? true : false): case (preg_match("/Windows Phone/i", $this->name) ? true : false):
@ -452,7 +452,7 @@ class checklist
case (preg_match("/Red ?Hat/i", $this->name) ? true : false): case (preg_match("/Red ?Hat/i", $this->name) ? true : false):
$this->icon = 'RedHat Linux.jpg'; $this->icon = 'RedHat Linux.jpg';
break; break;
case (preg_match("/SUSE Linux/i", $this->name) ? true : false): case (preg_match("/SUSE Linux|SLES/i", $this->name) ? true : false):
$this->icon = 'SUSE Linux.png'; $this->icon = 'SUSE Linux.png';
break; break;
case (preg_match("/Solaris/i", $this->name) ? true : false): case (preg_match("/Solaris/i", $this->name) ? true : false):
@ -461,6 +461,9 @@ class checklist
case (preg_match("/Storage Area/i", $this->name) ? true : false): case (preg_match("/Storage Area/i", $this->name) ? true : false):
$this->icon = 'Storage Area Network.gif'; $this->icon = 'Storage Area Network.gif';
break; break;
case (preg_match("/Ubuntu/i", $this->name) ? true : false):
$this->icon = 'Ubuntu.png';
break;
case (preg_match("/z\/OS/i", $this->name) ? true : false): case (preg_match("/z\/OS/i", $this->name) ? true : false):
$this->icon = 'ZOS.jpg'; $this->icon = 'ZOS.jpg';
break; break;

View File

@ -595,7 +595,7 @@ class software {
if ($regex2['name_match']) { if ($regex2['name_match']) {
foreach (explode(",", $regex2['name_match']) as $idx) { foreach (explode(",", $regex2['name_match']) as $idx) {
if (isset($match[$idx])) { if (isset($match[$idx]) && $match[$idx]) {
$sw['name'] .= " " . $match[$idx]; $sw['name'] .= " " . $match[$idx];
} }
} }
@ -603,7 +603,7 @@ class software {
if ($regex2['ver_match']) { if ($regex2['ver_match']) {
foreach (explode(",", $regex2['ver_match']) as $idx) { foreach (explode(",", $regex2['ver_match']) as $idx) {
if (isset($match[$idx])) { if (isset($match[$idx]) && $match[$idx]) {
$sw['ver'] .= $match[$idx] . " "; $sw['ver'] .= $match[$idx] . " ";
} }
} }

View File

@ -6,7 +6,7 @@
* Purpose: To parse a STIG file * Purpose: To parse a STIG file
* Created: Jul 9, 2014 * Created: Jul 9, 2014
* *
* Portions Copyright 2016-2017: Cyber Perspectives, LLC, All rights reserved * Portions Copyright 2016-2019: CyberPerspectives, LLC, All rights reserved
* Released under the Apache v2.0 License * Released under the Apache v2.0 License
* *
* Portions Copyright (c) 2012-2015, Salient Federal Solutions * Portions Copyright (c) 2012-2015, Salient Federal Solutions
@ -31,9 +31,14 @@
* - Dec 27, 2017 - Added up date for load date * - Dec 27, 2017 - Added up date for load date
* - May 10, 2018 - Starting to migrate logging and fixed install status bar issues (#403) * - May 10, 2018 - Starting to migrate logging and fixed install status bar issues (#403)
*/ */
$cmd = getopt("f:", ['debug::', 'ia_reset::', 'draft::', 'help::']); $cmd = getopt("f:", [
'debug::',
'ia_reset::',
'draft::',
'help::'
]);
if (!isset($cmd['f']) || isset($cmd['help'])) { if (! isset($cmd['f']) || isset($cmd['help'])) {
die(usage()); die(usage());
} }
@ -50,20 +55,19 @@ use Monolog\Formatter\LineFormatter;
$stream = new StreamHandler("php://output", Logger::INFO); $stream = new StreamHandler("php://output", Logger::INFO);
$stream->setFormatter(new LineFormatter("%datetime% %level_name% %message%", "H:i:s.u")); $stream->setFormatter(new LineFormatter("%datetime% %level_name% %message%", "H:i:s.u"));
/* /*
$log = new Logger("parse_stig"); * $log = new Logger("parse_stig");
$log->pushHandler(new StreamHandler(LOG_PATH . "/" . basename($cmd['f']) . ".log", LOG_LEVEL)); * $log->pushHandler(new StreamHandler(LOG_PATH . "/" . basename($cmd['f']) . ".log", LOG_LEVEL));
$log->pushHandler($stream); * $log->pushHandler($stream);
*/ */
chdir(DOC_ROOT . "/exec"); chdir(DOC_ROOT . "/exec");
// Capture start time for performance metrics // Capture start time for performance metrics
$start = new DateTime(); $start = new DateTime();
// Check to make sure file argument exists and is an XCCDF file // Check to make sure file argument exists and is an XCCDF file
if (!file_exists($cmd['f'])) { if (! file_exists($cmd['f'])) {
Sagacity_Error::err_handler("XML file not found {$cmd['f']}", E_ERROR); Sagacity_Error::err_handler("XML file not found {$cmd['f']}", E_ERROR);
} } elseif (strpos(strtolower($cmd['f']), "xccdf") === false) {
elseif (strpos(strtolower($cmd['f']), "xccdf") === false) {
Sagacity_Error::err_handler("Only compatible with XCCDF file formats", E_ERROR); Sagacity_Error::err_handler("Only compatible with XCCDF file formats", E_ERROR);
} }
@ -73,7 +77,11 @@ check_path(DOC_ROOT . "/reference/stigs");
// open db connection // open db connection
$db = new db(); $db = new db();
$content = str_replace(["’", "–", "“", "â€"], ["'", "-", '"', '"'], file_get_contents($cmd['f'])); $content = str_replace([
"’", "–", "“", "â€"
], [
"'", "-", '"', '"'
], file_get_contents($cmd['f']));
file_put_contents($cmd['f'], $content); file_put_contents($cmd['f'], $content);
// open xml file // open xml file
@ -93,12 +101,17 @@ $db->help->select_count("sagacity.catalog_scripts", [
]); ]);
$exists = $db->help->execute(); $exists = $db->help->execute();
if (!$exists) { if (! $exists) {
$db->add_Catalog_Script($base_name); $db->add_Catalog_Script($base_name);
} }
$db->update_Catalog_Script($base_name, ['name' => 'pid', 'value' => getmypid()]); $db->update_Catalog_Script($base_name, [
$db->help->update("sagacity.settings", ['meta_value' => new DateTime()], [ 'name' => 'pid',
'value' => getmypid()
]);
$db->help->update("sagacity.settings", [
'meta_value' => new DateTime()
], [
[ [
'field' => 'meta_key', 'field' => 'meta_key',
'op' => '=', 'op' => '=',
@ -115,19 +128,30 @@ foreach ($tmp as $s) {
print "Currently " . count($stigs) . " in the DB" . PHP_EOL; print "Currently " . count($stigs) . " in the DB" . PHP_EOL;
// Load XML into DOMDocument // Load XML into DOMDocument
$xml = new DOMDocument(); $xml = new DOMDocument();
if (!$xml->load($cmd['f'])) { if (! $xml->load($cmd['f'])) {
$log->script_log("Error opening file", E_ERROR); $log->script_log("Error opening file", E_ERROR);
} }
// Get regexes used to assess the STIG for known applicable software products // Get regexes used to assess the STIG for known applicable software products
$regex_arr = $db->get_Regex_Array("checklist"); $regex_arr = $db->get_Regex_Array("checklist");
if (is_array($regex_arr) && !count($regex_arr)) { if (is_array($regex_arr) && ! count($regex_arr)) {
die("There are no regular expressions to detect checklist software"); die("There are no regular expressions to detect checklist software");
} }
$csv_file = substr($cmd['f'], 0, -3) . "csv"; $csv_file = substr($cmd['f'], 0, - 3) . "csv";
$csv = fopen($csv_file, "w"); $csv = fopen($csv_file, "w");
fputcsv($csv, ["STIG_ID", "VMS_ID", "CAT", "IA_Controls", "Short_Title", "Status", "Notes", "Check_Contents", "SV_Rule_ID", "Oval_ID"]); fputcsv($csv, [
"STIG_ID",
"VMS_ID",
"CAT",
"IA_Controls",
"Short_Title",
"Status",
"Notes",
"Check_Contents",
"SV_Rule_ID",
"Oval_ID"
]);
// get checklist data // get checklist data
$checklist = []; $checklist = [];
@ -135,9 +159,12 @@ $checklist['id'] = str_replace("-", '.', getValue($xml, '@id'));
$checklist['status'] = getValue($xml, "/x:Benchmark/x:status"); $checklist['status'] = getValue($xml, "/x:Benchmark/x:status");
// Skip draft STIGs if debug flag is not set. @Ryan: Shouldn't this be checking the draft flag instead of debug? // Skip draft STIGs if debug flag is not set. @Ryan: Shouldn't this be checking the draft flag instead of debug?
if (!isset($cmd['draft'])) { if (! isset($cmd['draft'])) {
if (strtolower($checklist['status']) == 'draft') { if (strtolower($checklist['status']) == 'draft') {
$db->update_Catalog_Script($base_name, ["name" => "status", "value" => "SKIPPED"]); $db->update_Catalog_Script($base_name, [
"name" => "status",
"value" => "SKIPPED"
]);
fclose($csv); fclose($csv);
unset($xml); unset($xml);
unlink($cmd['f']); unlink($cmd['f']);
@ -159,7 +186,7 @@ if (isset($cmd['debug'])) {
} }
// If no matching software is found, default to "generic" // If no matching software is found, default to "generic"
if (!count($checklist['software'])) { if (! count($checklist['software'])) {
$log->script_log("Could not identify software, setting as Generic/Generic", E_NOTICE); $log->script_log("Could not identify software, setting as Generic/Generic", E_NOTICE);
$checklist['software'][] = [ $checklist['software'][] = [
'man' => 'Generic', 'man' => 'Generic',
@ -179,37 +206,31 @@ if (isset($cmd['debug'])) {
foreach ($sw_arr as $key => $sw) { foreach ($sw_arr as $key => $sw) {
do { do {
$cpe = "cpe:/" . ($sw->is_OS() ? "o" : "a") . ":{$sw->get_Man()}:{$sw->get_Name()}" . $cpe = "cpe:/" . ($sw->is_OS() ? "o" : "a") . ":{$sw->get_Man()}:{$sw->get_Name()}" . ($sw->get_Version() != '-' ? ":{$sw->get_Version()}" : "");
($sw->get_Version() != '-' ? ":{$sw->get_Version()}" : ""); $cpe = str_replace([" ", "(", ")"], ["_", "%28","%29"], strtolower($cpe));
$cpe = str_replace(
[" ", "(", ")"], ["_", "%28", "%29"], strtolower($cpe)
);
$db_sw = $db->get_Software($cpe); $db_sw = $db->get_Software($cpe);
if (!count($db_sw) && !count($checklist['software'])) { if (! count($db_sw) && ! count($checklist['software'])) {
$sw->reduce_CPE(); $sw->reduce_CPE();
} } elseif (is_array($db_sw) && count($db_sw) == 1 && $db_sw[0]->get_Version() == '-' && ! preg_match("/generic/", $sw->get_CPE())) {
elseif (is_array($db_sw) && count($db_sw) == 1 && $db_sw[0]->get_Version() == '-' && !preg_match("/generic/", $sw->get_CPE())) {
$checklist['software'] = array_merge($checklist['software'], $db_sw); $checklist['software'] = array_merge($checklist['software'], $db_sw);
$sw->reduce_CPE(); $sw->reduce_CPE();
$db_sw = []; $db_sw = [];
} } else {
else {
break; break;
} }
if (isset($cmd['debug'])) { if (isset($cmd['debug'])) {
$log->script_log("$cpe found " . count($db_sw), E_DEBUG); $log->script_log("$cpe found " . count($db_sw), E_DEBUG);
} }
} } while (! count($db_sw));
while (!count($db_sw));
$checklist['software'] = array_merge($checklist['software'], $db_sw); $checklist['software'] = array_merge($checklist['software'], $db_sw);
} }
foreach ($checklist['software'] as $key => $sw) { foreach ($checklist['software'] as $key => $sw) {
if (!is_a($sw, 'software')) { if (! is_a($sw, 'software')) {
unset($checklist['software'][$key]); unset($checklist['software'][$key]);
} }
} }
@ -218,16 +239,14 @@ $match = [];
if (preg_match('/Release: (\d+\.\d+|\d+)/', $checklist['plain_text'], $match)) { if (preg_match('/Release: (\d+\.\d+|\d+)/', $checklist['plain_text'], $match)) {
$checklist['rel'] = $match[1]; $checklist['rel'] = $match[1];
} } else {
else {
$checklist['rel'] = ''; $checklist['rel'] = '';
} }
// Get the date of the benchmark in the 'plain-text' element or set to 'status-date' if match fails // Get the date of the benchmark in the 'plain-text' element or set to 'status-date' if match fails
if (preg_match('/Benchmark Date: (.*)$/', $checklist['plain_text'], $match)) { if (preg_match('/Benchmark Date: (.*)$/', $checklist['plain_text'], $match)) {
$checklist['benchmark_date'] = new DateTime($match[1]); $checklist['benchmark_date'] = new DateTime($match[1]);
} } else {
else {
$checklist['benchmark_date'] = $checklist['status_date']; $checklist['benchmark_date'] = $checklist['status_date'];
} }
@ -244,26 +263,22 @@ $checklist['type'] = 'benchmark';
if (preg_match('/IAVM/i', $base_name)) { if (preg_match('/IAVM/i', $base_name)) {
$checklist['type'] = 'iavm'; $checklist['type'] = 'iavm';
} } elseif (preg_match('/policy|srg/i', $base_name)) {
elseif (preg_match('/policy|srg/i', $base_name)) {
$checklist['type'] = 'policy'; $checklist['type'] = 'policy';
} } elseif (preg_match('/manual/i', $base_name)) {
elseif (preg_match('/manual/i', $base_name)) {
$checklist['type'] = 'manual'; $checklist['type'] = 'manual';
} }
// Capture version release in filename as sometimes it doesn't match the plain_text element // Capture version release in filename as sometimes it doesn't match the plain_text element
if (preg_match('/V(\d+)R/', $base_name, $match)) { if (preg_match('/V(\d+)R/', $base_name, $match)) {
$checklist['file_ver'] = $match[1]; $checklist['file_ver'] = $match[1];
} } else {
else {
$checklist['file_ver'] = 0; $checklist['file_ver'] = 0;
} }
if (preg_match('/V\d+R(\d+|\d+\.\d+)/', $base_name, $match)) { if (preg_match('/V\d+R(\d+|\d+\.\d+)/', $base_name, $match)) {
$checklist['file_rel'] = $match[1]; $checklist['file_rel'] = $match[1];
} } else {
else {
$checklist['file_rel'] = 0; $checklist['file_rel'] = 0;
} }
@ -310,36 +325,31 @@ if ($chk) {
if (count($chk) && is_a($chk[0], 'checklist')) { if (count($chk) && is_a($chk[0], 'checklist')) {
$chk = $chk[0]; $chk = $chk[0];
} }
/** @var checklist $chk */
$chk->find_Icon();
// Update software products associated with this checklist // Update software products associated with this checklist
$sw_arr = [];
foreach ($checklist['software'] as $sw) { foreach ($checklist['software'] as $sw) {
$sw_arr[] = [$chk->get_ID(), $sw->get_ID()]; $chk->add_SW($sw);
} }
if (is_array($sw_arr) && count($sw_arr)) { $db->save_Checklist($chk);
$db->help->extended_insert("sagacity.checklist_software_lookup", ['chk_id', 'sw_id'], $sw_arr, true);
if (!$db->help->execute()) {
$db->debug(E_WARNING);
}
}
if (isset($cmd['debug'])) { if (isset($cmd['debug'])) {
$log->script_log(print_r($chk, true), E_DEBUG); $log->script_log(print_r($chk, true), E_DEBUG);
} }
} } else {
else {
// If checklist is not found, add checklist to DB // If checklist is not found, add checklist to DB
$chk = new checklist( $chk = new checklist(null, $checklist['id'], $checklist['title'], $checklist['desc'], $checklist['status_date'], $base_name, $checklist['ver'], $checklist['rel'], ($checklist['type'] == 'iavm' ? 'IAVM' : ucfirst($checklist['type'])), null);
null, $checklist['id'], $checklist['title'], $checklist['desc'], $checklist['status_date'], $base_name, $checklist['ver'], $checklist['rel'], ($checklist['type'] == 'iavm' ? 'IAVM' : ucfirst($checklist['type'])), null
);
$chk->add_SW($checklist['software']); $chk->add_SW($checklist['software']);
if (!($chk->id = $db->save_Checklist($chk))) { if (! ($chk->id = $db->save_Checklist($chk))) {
$log->script_log("Failed to save new checklist ({$chk->get_Name()})", E_ERROR); $log->script_log("Failed to save new checklist ({$chk->get_Name()})", E_ERROR);
} }
} }
if (!$chk->id) { if (! $chk->id) {
$log->script_log("Could not find or create checklist", E_ERROR); $log->script_log("Could not find or create checklist", E_ERROR);
} }
@ -351,7 +361,10 @@ $groups = getValue($xml, '/x:Benchmark/x:Group', null, true);
$log->script_log("$groups->length STIGs to run", E_DEBUG); $log->script_log("$groups->length STIGs to run", E_DEBUG);
$db->update_Catalog_Script($base_name, ['name' => 'stig_count', 'value' => $groups->length]); $db->update_Catalog_Script($base_name, [
'name' => 'stig_count',
'value' => $groups->length
]);
print "File: $base_name" . PHP_EOL; print "File: $base_name" . PHP_EOL;
print "Total: $groups->length" . PHP_EOL; print "Total: $groups->length" . PHP_EOL;
@ -363,7 +376,7 @@ foreach ($groups as $group) {
$references = []; $references = [];
$ias = []; $ias = [];
$ia_controls = ''; $ia_controls = '';
$perc_comp++; $perc_comp ++;
$vms_id = $group->getAttribute('id'); $vms_id = $group->getAttribute('id');
// the ".//" indicates that we are starting at the current node ($group) and looking in all child nodes for the "title" and "description" nodes // the ".//" indicates that we are starting at the current node ($group) and looking in all child nodes for the "title" and "description" nodes
@ -379,11 +392,9 @@ foreach ($groups as $group) {
$cat = 0; $cat = 0;
if ($group_rule->getAttribute('severity') == 'high') { if ($group_rule->getAttribute('severity') == 'high') {
$cat = 1; $cat = 1;
} } elseif ($group_rule->getAttribute('severity') == 'medium') {
elseif ($group_rule->getAttribute('severity') == 'medium') {
$cat = 2; $cat = 2;
} } elseif ($group_rule->getAttribute('severity') == 'low') {
elseif ($group_rule->getAttribute('severity') == 'low') {
$cat = 3; $cat = 3;
} }
@ -397,8 +408,7 @@ foreach ($groups as $group) {
$fix_text = getValue($xml, './/x:fixtext', $group_rule); $fix_text = getValue($xml, './/x:fixtext', $group_rule);
if ($rule_check_ref->length) { if ($rule_check_ref->length) {
$oval_id = $rule_check_ref->item(0)->getAttribute('name'); $oval_id = $rule_check_ref->item(0)->getAttribute('name');
} } else {
else {
$oval_id = ''; $oval_id = '';
} }
$match = []; $match = [];
@ -409,16 +419,16 @@ foreach ($groups as $group) {
// Remove unnecessary whitespace from and concatenate check content // Remove unnecessary whitespace from and concatenate check content
if ($check_content_nodes->length > 0) { if ($check_content_nodes->length > 0) {
for ($x = 0; $x < $check_content_nodes->length; $x++) { for ($x = 0; $x < $check_content_nodes->length; $x ++) {
$rule_check_content .= ($x + 1) . ") " . textCleanup($check_content_nodes->item($x)->textContent) . PHP_EOL; $rule_check_content .= ($x + 1) . ") " . textCleanup($check_content_nodes->item($x)->textContent) . PHP_EOL;
} }
$rule_check_content = trim($rule_check_content, PHP_EOL); $rule_check_content = trim($rule_check_content, PHP_EOL);
} }
//$log->script_log("STIG ID: $rule_stig_id", E_DEBUG); // $log->script_log("STIG ID: $rule_stig_id", E_DEBUG);
// Assign default category if not provided and add comment indicating such to rule description // Assign default category if not provided and add comment indicating such to rule description
if (!$cat) { if (! $cat) {
$cat = 2; $cat = 2;
$discussion .= " :CAT SET BY SCRIPT"; $discussion .= " :CAT SET BY SCRIPT";
} }
@ -428,11 +438,10 @@ foreach ($groups as $group) {
$discussion .= "\n{$match[1]}"; $discussion .= "\n{$match[1]}";
} }
if (!$rule_stig_id) { if (! $rule_stig_id) {
if ($vms_id == 'V0001073' || $vms_id == 'V-1073') { if ($vms_id == 'V0001073' || $vms_id == 'V-1073') {
$rule_stig_id = '2.005'; $rule_stig_id = '2.005';
} } elseif ($vms_id == 'V0001103' || $vms_id == 'V-1103') {
elseif ($vms_id == 'V0001103' || $vms_id == 'V-1103') {
$rule_stig_id = '4.010'; $rule_stig_id = '4.010';
} }
} }
@ -441,7 +450,7 @@ foreach ($groups as $group) {
$is_iavm = false; $is_iavm = false;
if (preg_match('/([\d]+\-[ABT]\-[\d]+)/', $rule_title, $match)) { if (preg_match('/([\d]+\-[ABT]\-[\d]+)/', $rule_title, $match)) {
$references[] = $match[1]; $references[] = $match[1];
if (!$rule_stig_id) { if (! $rule_stig_id) {
$rule_stig_id = $match[1]; $rule_stig_id = $match[1];
$is_iavm = true; $is_iavm = true;
} }
@ -449,13 +458,13 @@ foreach ($groups as $group) {
// Check if rule is an MS bulletin // Check if rule is an MS bulletin
if (preg_match('/(MS[\d]\-[\d]+)/', $rule_title, $match)) { if (preg_match('/(MS[\d]\-[\d]+)/', $rule_title, $match)) {
$references[] = $match[1]; $references[] = $match[1];
if (!$rule_stig_id) { if (! $rule_stig_id) {
$rule_stig_id = $match[1]; $rule_stig_id = $match[1];
} }
} }
// If no STIG ID found, set to "No Reference" // If no STIG ID found, set to "No Reference"
if (!$rule_stig_id) { if (! $rule_stig_id) {
error_log("Could not find stig id for group id $vms_id"); error_log("Could not find stig id for group id $vms_id");
$rule_stig_id = 'No Reference'; $rule_stig_id = 'No Reference';
} }
@ -468,16 +477,16 @@ foreach ($groups as $group) {
foreach ($searchstring as $string) { foreach ($searchstring as $string) {
if (preg_match_all("/($string)/", $rule_desc, $match)) { if (preg_match_all("/($string)/", $rule_desc, $match)) {
for ($x = 0; $x < count($match[0]); $x++) { for ($x = 0; $x < count($match[0]); $x ++) {
if (!in_array($match[0][$x], $references)) { if (! in_array($match[0][$x], $references)) {
$references[] = $match[0][$x]; $references[] = $match[0][$x];
} }
} }
} }
if (preg_match_all("/($string)/", $rule_check_content, $match)) { if (preg_match_all("/($string)/", $rule_check_content, $match)) {
for ($x = 0; $x < count($match[0]); $x++) { for ($x = 0; $x < count($match[0]); $x ++) {
if (!in_array($match[0][$x], $references)) { if (! in_array($match[0][$x], $references)) {
$references[] = $match[0][$x]; $references[] = $match[0][$x];
} }
} }
@ -490,7 +499,7 @@ foreach ($groups as $group) {
if (isset($stigs["$rule_stig_id"])) { if (isset($stigs["$rule_stig_id"])) {
print "."; print ".";
$updated_count++; $updated_count ++;
$db_stig = $stigs["$rule_stig_id"]; $db_stig = $stigs["$rule_stig_id"];
$db_pdi = $db->get_PDI($db_stig->get_PDI_ID(), $chk->get_ID()); $db_pdi = $db->get_PDI($db_stig->get_PDI_ID(), $chk->get_ID());
$db_pdi->set_Group_Title($group_title); $db_pdi->set_Group_Title($group_title);
@ -505,11 +514,10 @@ foreach ($groups as $group) {
} }
$db->save_PDI($db_pdi, $chk); $db->save_PDI($db_pdi, $chk);
} } else {
else {
print "*"; print "*";
// add pdi // add pdi
$new_count++; $new_count ++;
$db_pdi = new pdi(null, $cat, $checklist['benchmark_date']->format('Y-m-d')); $db_pdi = new pdi(null, $cat, $checklist['benchmark_date']->format('Y-m-d'));
$db_pdi->set_Group_Title($group_title); $db_pdi->set_Group_Title($group_title);
$db_pdi->set_Short_Title($rule_title); $db_pdi->set_Short_Title($rule_title);
@ -525,7 +533,7 @@ foreach ($groups as $group) {
$new = true; $new = true;
} }
if (!empty($vms_id)) { if (! empty($vms_id)) {
$vms_id = preg_replace("/^V0+/", "V-", $vms_id); $vms_id = preg_replace("/^V0+/", "V-", $vms_id);
$gd = $db->get_GoldDisk($vms_id); $gd = $db->get_GoldDisk($vms_id);
if (empty($gd)) { if (empty($gd)) {
@ -535,16 +543,20 @@ foreach ($groups as $group) {
} }
/* /*
if (!$db->save_Check_Contents($db_pdi, $chk, $rule_check_content, $fix_text)) { * if (!$db->save_Check_Contents($db_pdi, $chk, $rule_check_content, $fix_text)) {
$log->script_log("Couldn't save check contents for STIG ID: {$db_stig->get_ID()} in checklist {$chk->get_Checklist_ID()} ({$chk->get_File_Name()})\n", E_ERROR); * $log->script_log("Couldn't save check contents for STIG ID: {$db_stig->get_ID()} in checklist {$chk->get_Checklist_ID()} ({$chk->get_File_Name()})\n", E_ERROR);
} * }
*/ */
$new_controls = []; $new_controls = [];
$control_fields = ['pdi_id', 'type', 'type_id']; $control_fields = [
'pdi_id',
'type',
'type_id'
];
if (preg_match("/<IAControls>(.*)<\/IAControls>/i", $rule_desc, $match)) { if (preg_match("/<IAControls>(.*)<\/IAControls>/i", $rule_desc, $match)) {
$ia_controls = (isset($match[1]) && !empty($match[1]) ? $match[1] : null); $ia_controls = (isset($match[1]) && ! empty($match[1]) ? $match[1] : null);
if (preg_match("/DCSQ|ECMT/i", $ia_controls)) { if (preg_match("/DCSQ|ECMT/i", $ia_controls)) {
$new_controls[] = [ $new_controls[] = [
@ -553,8 +565,7 @@ foreach ($groups as $group) {
'1' '1'
]; ];
$ias[] = "VIVM-1"; $ias[] = "VIVM-1";
} } elseif ($ia_controls) {
elseif ($ia_controls) {
$split_ias = preg_split('/\, ?/', $ia_controls); $split_ias = preg_split('/\, ?/', $ia_controls);
foreach ($split_ias as $ia) { foreach ($split_ias as $ia) {
@ -570,9 +581,8 @@ foreach ($groups as $group) {
} }
} }
} }
} } elseif ($rule_ident->length) {
elseif ($rule_ident->length) { for ($x = 0; $x < $rule_ident->length; $x ++) {
for ($x = 0; $x < $rule_ident->length; $x++) {
if (substr($rule_ident->item($x)->textContent, 0, 3) == 'CCI') { if (substr($rule_ident->item($x)->textContent, 0, 3) == 'CCI') {
$split_ia = explode("-", $rule_ident->item($x)->textContent); $split_ia = explode("-", $rule_ident->item($x)->textContent);
@ -586,8 +596,7 @@ foreach ($groups as $group) {
} }
} }
} }
} } else {
else {
if ($is_iavm) { if ($is_iavm) {
$ias[] = "CCI-002613"; $ias[] = "CCI-002613";
$new_controls[] = [ $new_controls[] = [
@ -595,8 +604,7 @@ foreach ($groups as $group) {
"CCI", "CCI",
"002613" "002613"
]; ];
} } else {
else {
$ias[] = "CCI-000366"; $ias[] = "CCI-000366";
$new_controls[] = [ $new_controls[] = [
$pdi_id, $pdi_id,
@ -606,8 +614,8 @@ foreach ($groups as $group) {
} }
} }
//$db_ia = $db->get_IA_Controls_By_PDI($db_pdi->get_ID()); // $db_ia = $db->get_IA_Controls_By_PDI($db_pdi->get_ID());
if (isset($cmd['ia_reset']) && !$new) { if (isset($cmd['ia_reset']) && ! $new) {
// delete ia controls // delete ia controls
$db->help->delete("sagacity.ia_controls", [ $db->help->delete("sagacity.ia_controls", [
[ [
@ -621,17 +629,19 @@ foreach ($groups as $group) {
if (count($new_controls)) { if (count($new_controls)) {
$db->help->extended_replace("sagacity.ia_controls", $control_fields, $new_controls); $db->help->extended_replace("sagacity.ia_controls", $control_fields, $new_controls);
if (!$db->help->execute()) { if (! $db->help->execute()) {
$db->help->debug(E_ERROR); $db->help->debug(E_ERROR);
} }
} }
$sv = new sv_rule($pdi_id, $sv_rule); $sv = new sv_rule($pdi_id, $sv_rule);
$db->save_SV_Rule(array(0 => $sv)); $db->save_SV_Rule(array(
0 => $sv
));
if ($rule_ident->length) { if ($rule_ident->length) {
foreach ($rule_ident as $ident_node) { foreach ($rule_ident as $ident_node) {
if (!in_array($ident_node->textContent, $references) && $ident_node->textContent != 'CCI') { if (! in_array($ident_node->textContent, $references) && $ident_node->textContent != 'CCI') {
$references[] = $ident_node->textContent; $references[] = $ident_node->textContent;
} }
} }
@ -643,19 +653,14 @@ foreach ($groups as $group) {
if (substr($ref, 0, 3) == 'CVE' || substr($ref, 0, 3) == 'CAN') { if (substr($ref, 0, 3) == 'CVE' || substr($ref, 0, 3) == 'CAN') {
$tmp[] = new cve($pdi_id, $ref); $tmp[] = new cve($pdi_id, $ref);
$db->save_CVE($tmp); $db->save_CVE($tmp);
} } elseif (substr($ref, 0, 3) == 'CCE') {
elseif (substr($ref, 0, 3) == 'CCE') {
$tmp[] = new cce($pdi_id, $ref); $tmp[] = new cce($pdi_id, $ref);
$db->save_CCE($tmp); $db->save_CCE($tmp);
} } elseif (substr($ref, 0, 2) == 'KB') {} elseif (substr($ref, 0, 2) == 'MS') {
elseif (substr($ref, 0, 2) == 'KB') {
}
elseif (substr($ref, 0, 2) == 'MS') {
$tmp[] = new advisory($pdi_id, $ref, '', 'MS', ''); $tmp[] = new advisory($pdi_id, $ref, '', 'MS', '');
$db->save_Advisory($tmp); $db->save_Advisory($tmp);
} }
//print_r($tmp[0]); // print_r($tmp[0]);
unset($tmp); unset($tmp);
} }
} }
@ -665,10 +670,24 @@ foreach ($groups as $group) {
} }
// Output the CSV contents // Output the CSV contents
fputcsv($csv, [$rule_stig_id, $vms_id, implode("", array_fill(0, $cat, "I")), implode(" ", $ias), $rule_title, "Not Reviewed", "", $rule_check_content, $sv_rule, $oval_id]); fputcsv($csv, [
$rule_stig_id,
$vms_id,
implode("", array_fill(0, $cat, "I")),
implode(" ", $ias),
$rule_title,
"Not Reviewed",
"",
$rule_check_content,
$sv_rule,
$oval_id
]);
unset($references); unset($references);
$db->update_Catalog_Script($base_name, ['name' => 'perc_comp', 'value' => ($perc_comp / $groups->length) * 100]); $db->update_Catalog_Script($base_name, [
'name' => 'perc_comp',
'value' => ($perc_comp / $groups->length) * 100
]);
} }
$db->help->select_count("sagacity.stigs"); $db->help->select_count("sagacity.stigs");
@ -678,26 +697,34 @@ $db->set_Setting('stig-count', $stig_count);
$end = new DateTime(); $end = new DateTime();
$diff = $end->diff($start); $diff = $end->diff($start);
print PHP_EOL . "Start Time: {$start->format("H:i:s")}" . PHP_EOL; print <<<EOO
print "End Time: {$end->format("H:i:s")}" . PHP_EOL;
print "Execution time: {$diff->format("%H:%I:%S")}" . PHP_EOL . PHP_EOL; Start Time: {$start->format("H:i:s")}
print "New STIGs: $new_count" . PHP_EOL; End Time: {$end->format("H:i:s")}
print "Updated STIGs: $updated_count" . PHP_EOL; Execution time: {$diff->format("%H:%I:%S")}
print "Total STIGs: " . ($new_count + $updated_count) . PHP_EOL . PHP_EOL . PHP_EOL;
New STIGs: $new_count
Updated STIGs: $updated_count
Total STIGs: ($new_count + $updated_count)
$log->script_log("$groups->length complete"); $log->script_log("$groups->length complete");
fclose($csv); fclose($csv);
if (!isset($cmd['debug'])) { if (! isset($cmd['debug'])) {
rename($cmd['f'], DOC_ROOT . "/reference/stigs/$base_name"); rename($cmd['f'], DOC_ROOT . "/reference/stigs/$base_name");
} }
rename($csv_file, DOC_ROOT . "/reference/stigs/" . basename($csv_file)); rename($csv_file, DOC_ROOT . "/reference/stigs/" . basename($csv_file));
$db->update_Catalog_Script($base_name, ['name' => 'perc_comp', 'value' => 100, 'complete' => 1]); $db->update_Catalog_Script($base_name, [
'name' => 'perc_comp',
'value' => 100,
'complete' => 1
]);
/** /**
* Usage output * Usage output
*/ */
function usage() { function usage()
{
print <<<EOO print <<<EOO
Purpose: To parse a STIG XCCDF checklist file and populate/update the database Purpose: To parse a STIG XCCDF checklist file and populate/update the database

View File

@ -5,7 +5,7 @@
* Purpose: Read STIG Viewer checklist files * Purpose: Read STIG Viewer checklist files
* Created: Apr 10, 2014 * Created: Apr 10, 2014
* *
* Portions Copyright 2016-2017: Cyber Perspectives, LLC, All rights reserved * Portions Copyright 2016-2019: CyberPerspectives, LLC, All rights reserved
* Released under the Apache v2.0 License * Released under the Apache v2.0 License
* *
* Portions Copyright (c) 2012-2015, Salient Federal Solutions * Portions Copyright (c) 2012-2015, Salient Federal Solutions
@ -74,6 +74,7 @@ $host_mac = getValue($xml, '//HOST_MAC');
if (!$host_name) { if (!$host_name) {
$db->update_Running_Scan($base_name, ['name' => 'status', 'value' => 'TERMINATED']); $db->update_Running_Scan($base_name, ['name' => 'status', 'value' => 'TERMINATED']);
$db->update_Running_Scan($base_name, ['name' => 'notes', 'value' => 'File parsing was terminated because <HOST_NAME> was empty or absent']);
unset($xml); unset($xml);
rename($cmd['f'], TMP . "/terminated/{$base_name}"); rename($cmd['f'], TMP . "/terminated/{$base_name}");

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB