Сканирование портов PHP

Это может быть повторяющееся сообщение, НО я не видел ни одного ответа, который правильно решает эту проблему.

Я пытаюсь найти скрипт php, который может правильно определить состояние порта TCP или UDP.

Я пробовал несколько из тех, которые я нашел в Интернете, и все они дают неправильные результаты. Например: в моей локальной сети порты 5000 UDP и 5060 TCP/UDP открыты и правильно маршрутизируются.

Если я запускаю тест через http://www.ipfingerprints.com/portscan.php или GRC Shields Up, то возвращаются правильные результаты, но все скрипты PHP, которые я пробовал, терпят неудачу и показывают порты как закрытые.

Я запускаю скрипт php через свою учетную запись и пытаюсь проверить и протестировать свою собственную сеть.

Это один из скриптов, которые я пробовал:

    <html>
<head>
<?php echo "<title>Port Scanning " . $_GET['host'] . "</title>"; ?>
</head>
<body>
<?php
ini_set('display_errors', 0);

if(isset($_GET['host']) == true) 
    $host = $_GET['host'];
else
{
    echo "You didn't set the host parameter";
    die();
}

if(isset($_GET['sport']) == true) 
    $sport = $_GET['sport'];
else
{
    echo "You didn't set the sport parameter";
    die();
}

if(isset($_GET['eport']) == true) 
    $eport = $_GET['eport'];
else
{
    echo "You didn't set the eport parameter";
    die();
}

if($sport > $eport)
{
    $sport = $eport;
}

$scanned = 0;
$openports = 0;
$maxports = 1;
$totalports = ($eport - $sport) + 1;
$mins = floor(($totalports / 10) / 60);
$secs = ($totalports / 10) - $mins * 60;

echo "<font color=\"blue\">Scanning " . $totalports . " ports on " . $host . ", this should take around " . $mins . " minute(s) and " . $secs . " second(s), probably more depending on local website load, hardware, and other factors.<br/><br/></font>";
flush();

do
{
    if($scanned >= $maxports && $maxports != 0)
    {
        echo "<font color=\"darkgreen\" size=\"4\">Scan limit of " . $maxports . " ports reached, scanning stopped.</font><br/><br/><font color=\"darkred\" size=\"4\">Scanner written by Samo502</font>";
        flush();
        die();
    }
    if(fsockopen($host, $sport, $errorno, $errorstr, 0.1))
    {
        echo "<font color=\"darkgreen\">Port " . $sport . " is open on " . $host . "</font><br/>";
        $openports++;
        flush();
    }
    else
    {
        echo "<font color=\"red\">Port " . $sport . " is not open on " . $host . "</font><br/>";
        flush();
    }
    $scanned++;
    $sport++;
} while($sport <= $eport);

echo "<br/><font color=\"blue\">Done, " . $openports . " out of " . $totalports . " ports are open.</font><br/><br/><br/><font color=\"darkred\" size=\"4\">Scanner written by Samo502</font>";
die();
?>
</body>
</html>

Кто-нибудь знает способ сделать это правильно?

Спасибо

** ОБНОВЛЕНИЕ ** Я нашел это, который, кажется, работает немного лучше, но он все еще не обнаруживает, что порт 21 в настоящее время открыт в моей сети..

http://resources.infosecinstitute.com/php-build-your-own-mini-port-scanner-2/

Любая помощь с благодарностью получена. Спасибо

3 ответа

Решение

Лучшее решение - написать оболочку на PHP для nmap - серьезно, вы не можете перекодировать лучший порт, чем nmap.

Если вы действительно хотите это сделать, вы не должны просто открывать порт TCP и проверять, подключается ли он, вы должны начинать с более низкого уровня сокетов, необработанных сокетов.

$mysocket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);

Это позволяет вам исследовать SYN, ACK флаги рукопожатия и стелс или просто более быстрое сканирование.

Вы можете создавать (неблокирующие) сокеты параллельно и проверять их буфер / соединение, используя socket_select();, который является самым быстрым и самым надежным способом обработки нескольких сокетов в PHP. Вероятно, я бы использовал вилки или потоки или отправлял части кода для запуска полного сканирования портов за то же время, что и сканирование одного порта.

Другие функции, которые вы хотели бы использовать socket_set_timeout() а также socket_set_blocking(),

shell_exec не работает с командой nmap

https://unix.stackexchange.com/questions/28732/fastest-way-to-port-scan-nmap

http://phpnmap.sourceforge.net/

Вероятно, лучшее решение - оболочка nmap для пакета PEAR: http://pear.php.net/package/Net_Nmap/

Вместо

if(fsockopen($host, $sport, $errorno, $errorstr, 0.1))

Пытаться

$connection = @fsockopen($host, $sport);
if (is_resource($connection)){
  // OK
}

Я попробовал то же самое на моей учетной записи общего хостинга, и это не сработало. Я смог установить пакеты PEAR, необходимые для сканирования портов, и он работал на интернет-сайтах, таких как "yahoo.com", но не на любом из портов, которые я хотел. В итоге я настроил отдельную виртуальную машину с установленными пакетами APACHE и PEAR, и теперь код работает просто отлично. Здесь вы можете попробовать это сами:

www.admin-toolkit.com/port_scan.html

Вот код для этого. Сначала присвойте значение $scanhost, $port а также $timeout (в секундах), затем:

$status = Net_Portscan::checkPort($scanhost, $port, $timeout);

$servicename = Net_Portscan::getService($port);

if ($status == NET_PORTSCAN_SERVICE_FOUND) {
    if($servicename == null)
        echo $port.": OPEN ".PHP_EOL;
   else
        echo $port." (".$servicename .") : OPEN ".PHP_EOL;
   }
else{
   if($servicename == null)
      echo $port.": CLOSED".PHP_EOL;
   else
      echo $port." (".$servicename ."): CLOSED".PHP_EOL;
}
Другие вопросы по тегам