当前位置:  开发笔记 > 编程语言 > 正文

从未收到SSH服务器标识 - 握手死锁[SSHJ]

如何解决《从未收到SSH服务器标识-握手死锁[SSHJ]》经验,为你挑选了0个好方法。

我们在尝试为我们的应用程序实现SftpConnections池时遇到了一些麻烦.

我们目前正在使用SSHJ(Schmizz)作为传输库,面临一个我们在开发环境中无法模拟的问题(但错误在生产中随机显示,有时在三天之后,有时仅在10分钟之后).

问题是,当尝试通过SFTP发送文件时,线程被锁定在initschmizz' TransportImpl类的方法中:

   @Override
    public void init(String remoteHost, int remotePort, InputStream in, OutputStream out)
            throws TransportException {
        connInfo = new ConnInfo(remoteHost, remotePort, in, out);

    try {

        if (config.isWaitForServerIdentBeforeSendingClientIdent()) {
            receiveServerIdent();
            sendClientIdent();
        } else {
            sendClientIdent();
            receiveServerIdent();
        }


        log.info("Server identity string: {}", serverID);

    } catch (IOException e) {
        throw new TransportException(e);
    }

    reader.start();
}

isWaitForServerIdentBeforeSendingClientIdent对我们来说是假的,所以首先客户端(我们)发送我们的标识,如日志中所示:

" 客户身份字符串:blabla "

然后转向receiveServerIdent:

    private void receiveServerIdent() throws IOException 
{
        final Buffer.PlainBuffer buf = new Buffer.PlainBuffer();
        while ((serverID = readIdentification(buf)).isEmpty()) {
            int b = connInfo.in.read();
            if (b == -1)
                throw new TransportException("Server closed connection during identification exchange");
            buf.putByte((byte) b);
        }
    }

线程永远不会得到控制权,因为服务器永远不会回复其身份.好像代码卡在这个While循环中.没有超时或SSH异常被抛出,我的客户端只是一直等待,线程陷入僵局.

这是readIdentification方法的impl:

private String readIdentification(Buffer.PlainBuffer buffer)
        throws IOException {
    String ident = new IdentificationStringParser(buffer, loggerFactory).parseIdentificationString();
    if (ident.isEmpty()) {
        return ident;
    }

    if (!ident.startsWith("SSH-2.0-") && !ident.startsWith("SSH-1.99-"))
        throw new TransportException(DisconnectReason.PROTOCOL_VERSION_NOT_SUPPORTED,
                                     "Server does not support SSHv2, identified as: " + ident);

    return ident;
}

看起来像ConnectionInfo的输入流永远不会获取要读取的数据,就像服务器关闭了连接一样(即使如前所述,也没有抛出任何异常).

我试图通过使协商饱和来模拟这个错误,在连接时关闭套接字,使用conntrack在进行握手时杀死已建立的连接,但是根本没有运气,所以任何帮助都会非常感激.

:)

推荐阅读
牛尾巴2010
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有