在PHP中打开异步套接字 [英] Open asynchronous sockets in PHP

查看:70
本文介绍了在PHP中打开异步套接字的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在用PHP编写支持较小范围(例如端口21-25)的端口扫描程序.通过AJAX将要扫描的端口和IP发送到服务器,然后PHP尝试在每个端口上打开一个套接字.如果成功,则打开端口;如果超时,则关闭端口.

I am writing a port scanner in PHP that supports small ranges (e.g., ports 21-25). The ports and IP to be scanned are sent to the server via AJAX, and then PHP attempts to open a socket on each of the ports. If it succeeds, the port is open, if it times out, the port is closed.

当前,尽管同时为端口21-25发送了所有AJAX请求,但是每个套接字仅在最后一个套接字关闭后才打开.因此,检查端口21,关闭插座,然后检查端口22,依此类推.我想要的是同时检查所有端口,所以我要一次打开多个套接字.

Currently, despite sending all of the AJAX requests at the same time for ports 21-25, each socket is only opened after the last one closes. So, port 21 is checked, the socket is closed, and then port 22 is checked, and so on. What I want is for all ports to be checked concurrently, so I'd be opening several sockets at once.

我尝试过:

$fp = @fsockopen($ip,$port,$errno,$errstr,2);
socket_set_nonblock($fp);

但是这不起作用,因为在套接字已经打开并等待响应之后,我将设置为非阻塞状态.我想在PHP中做些什么吗?

But this doesn't work, as I'm setting non-block AFTER the socket has already been opened and is waiting for a response. Is what I'm trying to do possible in PHP?

推荐答案

使用不同的功能: socket_create() socket_connect() 而不是fsockopen().这有效:

Use different functions: socket_create() and socket_connect() instead of fsockopen(). This works:

$socks = array();
for ($port = 21; $port <= 25; $port++) {
    $sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
    socket_set_nonblock($sock);
    @socket_connect($sock, 'localhost', $port);
    $socks[$port] = $sock;
}

$startTime = microtime(true);
while ($socks && microtime(true) - $startTime < 3) {
    $null = null;
    $write = $socks;
    socket_select($null, $write, $null, 1);
    foreach ($write as $port => $sock) {
        $desc = "$port/tcp";
        $errno = socket_get_option($sock, SOL_SOCKET, SO_ERROR);

        if ($errno == 0) {
            echo "$desc open\n";
        } elseif ($errno == SOCKET_ECONNREFUSED) {
            echo "$desc closed\n";
        } elseif ($errno == SOCKET_ETIMEDOUT) {
            echo "$desc filtered\n";
        } else {
            $errmsg = socket_strerror($errno);
            echo "$desc error $errmsg\n";
        }

        unset($socks[$port]);
        socket_close($sock);
    }
}

foreach ($socks as $port => $sock) {
    $desc = "$port/tcp";
    echo "$desc filtered\n";
    socket_close($sock);
}

这篇关于在PHP中打开异步套接字的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆