1

我让 cygwin 和 sshd 工作正常。而且使用腻子完全没有问题。即使对于多个命令,它也会按预期响应。但是当使用 phpseclib 时,只会收到第一个命令的响应。随后的命令给出了空白回复。这是我要执行的脚本 -

<?php
include('Net/SSH2.php');
define('NET_SSH2_LOGGING', NET_SSH2_LOG_COMPLEX);
$host = "XXXX";
$username = "XXXX"; 
$password = "XXXX"; 
$ssh = new Net_SSH2($host);
if (!$ssh->login($username, $password)) {
    exit('Login Failed');
}
echo $ssh->exec('nproc');
echo $ssh->exec('nproc');
echo $ssh->getLog();
?>

然而,创建一个新的 ssh 对象确实会给出响应。但是,我无法将同一个对象用于第二个 exec 请求。当目标是 centos 机器时,这工作正常。

这是 phpseclib- http://pastebin.com/ff3sfux7的日志输出

4

2 回答 2

1

这很奇怪。FWIW 它似乎不是 phpseclib 问题,而是服务器问题。如果您查看日志,您将看到两个<- NET_SSH2_MSG_CHANNEL_EOF数据包。nproc 响应就在第一个 ( <- NET_SSH2_MSG_CHANNEL_DATA) 之前,但第二个没有类似的响应。

您发出的每个 nproc 请求都会导致服务器最终发送退出状态 SSH_MSG_CHANNEL_REQUEST。这是您的日志文件中的第一个:

<- NET_SSH2_MSG_CHANNEL_REQUEST (since last: 0.0839, network: 0.0838s)
00000000  00:00:00:00:00:00:00:0b:65:78:69:74:2d:73:74:61  ........exit-sta
00000010  74:75:73:00:00:00:00:00                          tus.....

这是您的日志文件中的第二个

<- NET_SSH2_MSG_CHANNEL_REQUEST (since last: 0.0461, network: 0.046s)
00000000  00:00:00:00:00:00:00:0b:65:78:69:74:2d:73:74:61  ........exit-sta
00000010  74:75:73:00:00:00:00:ff                          tus.....

它们几乎相同,除了最后一个字节是第一个字节(好字节)中的 00 和第二个字节(坏字节)中的 ff 。这是退出状态的 SSH_MSG_CHANNEL_REQUEST 数据包的剖析:

  byte      SSH_MSG_CHANNEL_REQUEST
  uint32    recipient channel
  string    "exit-status"
  boolean   FALSE
  uint32    exit_status

所以基本上最后四个字节代表 255 的 uint32 exit_status。

引用维基百科关于退出状态的文章,“退出状态介于 0 和 255 之间”。还,

出于 shell 的目的,以零退出状态退出的命令已成功。非零退出状态表示失败。

因此,在运行第二个命令时,您的 Linux 机器上出现了某种错误。

stderr ( ) 上也没有输出SSH_MSG_CHANNEL_EXTENDED_DATA任何内容,因此很难说发生了什么。

根据http://tldp.org/LDP/abs/html/exitcodes.html 255 退出状态表示“退出状态超出范围”。IE。nproc 试图做exit -1exit 256。无论哪种方式,它听起来都可能是一个 nproc 错误或其他东西。也许尝试确保系统上的所有内容都是最新的?

于 2015-02-01T01:48:32.573 回答
1

我找到了解决方案 - 问题的原因是,在基于 Windows 的系统中,setuid 在执行新命令之前被调用。对于第一个命令,它最初是设置的,所以没有问题。然而,随后的调用会导致尝试重新分配它并且失败,openssh 将无法做到这一点。这已经在 ssh-host-config 脚本中进行了解释-

*** Info: You appear to be running Windows XP 64bit, Windows 2003 Server,
*** Info: or later.  On these systems, it's not possible to use the LocalSystem
*** Info: account for services that can change the user id without an
*** Info: explicit password (such as passwordless logins [e.g. public key
*** Info: authentication] via sshd).

*** Info: If you want to enable that functionality, it's required to create
*** Info: a new account with special privileges (unless a similar account
*** Info: already exists). This account is then used to run these special
*** Info: servers.

为了解决它,您需要创建脚本尝试创建的特权用户帐户,并确保在脚本末尾显示 -

*** Info: The sshd service has been installed under the 'cyg_server'
*** Info: account.  To start the service now, call `net start sshd' or
*** Info: `cygrunsrv -S sshd'.  Otherwise, it will start automatically
*** Info: after the next reboot.

任何表明该帐户未找到且默认为“SYSTEM”帐户的消息都将导致该问题。在这种情况下,请确保 passwd 文件是最新的并包含新用户。

当您启动 Windows 服务管理器并检查 CYGWIN sshd 服务的属性时,在登录选项卡下它需要说它正在使用新创建的特权帐户而不是本地帐户。

还要验证在组策略编辑器 -> 安全设置 -> 本地策略 -> 用户权限分配下,新用户帐户需要具有创建令牌对象并充当操作系统一部分的权限。

于 2015-02-01T14:26:15.173 回答