<?php /*** * $>php CSharpConfChecker.php /path/to/src/ * will output csv with status of packages (out of dat, known vulnerable) */ $total = 0; function findConfFiles($folderPath) { $confFiles = array(); $iterator = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($folderPath)); foreach($iterator as $file) { //echo "$file \r"; if ($file->isFile() && $file->getExtension() == 'config') { $confFiles[] = $file->getPathname(); } } return $confFiles; } function parseConfFiles($confFiles) { global $total; $result = array(); foreach($confFiles as $file) { $lines = file($file, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES); foreach($lines as $line) { if(strpos($line, 'id=') !== false && strpos($line, 'version=') !== false) { $id = ''; $version = ''; preg_match('/id=(\S+)/', $line, $idMatch); if(!empty($idMatch)) { $id = $idMatch[1]; } preg_match('/version=(\S+)/', $line, $versionMatch); if(!empty($versionMatch)) { $version = $versionMatch[1]; } if(!empty($id) && !empty($version)) { if(empty($result[$id][$version])){ $total++; } $result[$id][$version][] = $file; } } } } // sort by id and then by version number uksort($result, function($a, $b) use ($result) { $aVersions = array_keys($result[$a]); $bVersions = array_keys($result[$b]); $aVersion = $aVersions[count($aVersions) - 1]; $bVersion = $bVersions[count($bVersions) - 1]; $aVersion = preg_replace('/[^0-9.]/', '', $aVersion); $bVersion = preg_replace('/[^0-9.]/', '', $bVersion); if($a == $b) { return version_compare($aVersion, $bVersion); } else { return strcmp($a, $b); } }); return $result; } function downloadUrls($parsedConf) { global $total; $count = 0; foreach ($parsedConf as $id => $versions) { foreach ($versions as $version => $files) { $url = "https://www.nuget.org/packages/" . str_replace('"', '', trim($id)) . "/" . str_replace('"', '', trim($version)); $count++; echo "downloading: $count of $total \r"; $response = getdataz($url); if (strpos($response, 'This package has at least one') !== false) { $parsedConf[$id][$version]['status'] = 'vulnerable'; } elseif (strpos($response, 'There is a newer version of this package') !== false) { $parsedConf[$id][$version]['status'] = 'outdated'; } } } echo "downloaded all\n"; return $parsedConf; } function getdataz($target){ $ch = curl_init($target); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); $result = curl_exec($ch); curl_close($ch); return $result; } $folderPath = isset($argv[1]) ? $argv[1] : ''; if (!empty($folderPath)) { echo "searching $folderPath\n"; $confFiles = findConfFiles($folderPath); echo "parsing\n"; $parsedConfFiles = parseConfFiles($confFiles); echo "found: $total\n"; $parsedConfFiles = downloadUrls($parsedConfFiles); $csvString = "id, version, status, file\n"; foreach ($parsedConfFiles as $id => $versions) { foreach ($versions as $version => $files) { $status = isset($files['status']) ? $files['status'] : ''; $file = isset($files[0]) ? $files[0] : ''; // Add a row to the CSV $csvString .= "$id, $version, $status, $file\n"; } } echo $csvString; } ?>