在ssh守护程序的非阻塞套接字中,select()总是在执行nmap脚本后返回1

时间:2014-03-11 13:04:06

标签: c sockets select ssh nonblocking

在ssh守护程序中,select()总是正确返回但在执行下面的nmap脚本后

nmap -sV -O -A --script ssh2-enum-algos

select()总是返回1,即使没有与ssh服务器建立连接。

还有其他几个这样的线程,但是我找不到代码的问题。

我的代码看起来像这样,

while (1) 
{
    memcpy(tmp_read_set, read_set, sizeof(fd_set));
    retValSS = select(FD_SETSIZE, tmp_read_set, NULL, NULL, NULL);
    switch (retValSS)
    {
        case -1:
            LOG1(CRIT, "select() failed, errno=%d", ipcom_errno);
            goto cleanup;
        case 0: // Timeout....
            break;
        default:
            for(i=0; i<MAX_LISTEN_PORTS; i++)
            {
                if(lst_sock[i] == INVALID_SOCKET)
                    break;

                if(FD_ISSET(lst_sock[i], tmp_read_set))
                {
                    clt_sock = accept(lst_sock[i], NULL, NULL);
                    if (INVALID_SOCKET == clt_sock) /*INVALID_SOCKET is -1*/
                    {
                        LOG1(ERR, "accept() failed, errno=%d", errno);
                        continue;
                    }
                    if(srv_ctx->no_clients >= srv_ctx->max_clients)
                    {
                        LOG0(INFO, "max no of connected clients reached, disconnecting client");
                        close(clt_sock);
                        continue;
                    }
                    else
                    {
                       //some work is being done
                    }
                }
            }
        }
    }

我正在连续跟踪错误日志,

accept()失败,错误= 0

奇怪的是,errno为0表示没有错误。如果没有错误,我认为那么accept()不应该失败。 有人可以解释在什么情况下accept()可能会失败。

如果有人可以提供帮助,我将非常感激。

1 个答案:

答案 0 :(得分:0)

您期望select()返回什么?考虑select()通常用于等待多个文件描述符 - 如果你连接两个,你怎么知道哪一个成功/失败纯粹基于select的返回值?显然你不会。

这就是为什么select()只是告诉你哪些文件描述符以某种方式发生了变化,你应该独立地确定它是什么。在connect()的情况下,您应该调用getsockopt()来检索连接尝试的结果。请参阅this answer,其中说明了如何进行非阻塞连接()。