使用 sftp 和 ssh2 的 fopen 分段错误
Segmentation fault on fopen using sftp and ssh2
我在 AWS 上有一个 php 系统 运行 和一个使用 [=15] 在外部服务器上传 xlsx 文件的 class =]shh2 和 sftp。
此代码工作正常,直到上次升级 aws 包 openssh-clients-6.6.1p1-31.62 和 openssh-server-6.6.1p1-31.62这次我在 fopen 期间有一个 segfault。
Fopen 在外部服务器上创建一个文件。
这里的代码:
$stream = @fopen("ssh2.sftp://$this->sftp$remote_file", 'w');
然后我使用 $stream 来编写内容,但是代码停止在 fopen 上,因为出现段错误。
我没有找到关于这个问题的任何信息,我认为问题是 opnessh 的新升级,因为 php 代码没有改变。
有什么想法吗?
在 Whosebug 上找到答案:
自从这次 PHP 更新后,您必须用 intval()
:
包围您的主机部分(ssh2_sftp()
的结果)
$handle = opendir("ssh2.sftp://".intval($sftp)."/path/to/directory");
在我的例子中有 fopen
而不是 opendir
,但解决方案是相同的。
我遇到了同样的错误,但我发现了这个 PHP bug(参见 post 来自:[2016-12-15 09:47 UTC] 作者:ovoelker 在 wavecon dot de)
- 添加php5-dev用于编译pecl模块
- 重新安装 ssh2 pecl 模块。
- 重新启动 apache 并正常工作
在我们的例子中,intval() 没有解决分段错误。但是,更改调用格式确实有效:
fopen("ssh2.sftp://{$username}:{$password}@{$host}:{$port}/{$absolutePath}/{$filename}", 'w');
如果您正在关闭与 ssh2_disconnect()
的连接,即使使用 intval($sftp)
解决方案,您也可能会遇到 "segmentation fault" 问题。正确的解决方案是在通过 unset($sftp)
或 $sftp = null
关闭 SSH2 连接之前关闭 SFTP 连接。这是我读取远程文件的完整示例:
if (!$ssh2_connection = ssh2_connect($host, $port)) {
die("Failed to connect\n");
}
if (!ssh2_auth_password($ssh2_connection, $username, $password)) {
die("Failed to login\n");
}
if (!$sftp_connection = ssh2_sftp($ssh2_connection)) {
die("Failed to open SFTP session\n");
}
if (!$fh = fopen("ssh2.sftp://".intval($sftp_connection).$path, 'r')) {
die("Failed to open file\n");
}
while (($s = fgets($fh)) !== false) {
echo $s;
}
fclose($fh);
unset($sftp_connection);
if (!ssh2_disconnect($ssh2_connection)) {
die("Failed to disconnect\n");
}
P.S。此外,您可能会看到类似 "segmentation fault" 的内容:
php: channel.c:2570: _libssh2_channel_free: Assertion `session' failed.
Aborted
我的方案解决了。
我在 AWS 上有一个 php 系统 运行 和一个使用 [=15] 在外部服务器上传 xlsx 文件的 class =]shh2 和 sftp。 此代码工作正常,直到上次升级 aws 包 openssh-clients-6.6.1p1-31.62 和 openssh-server-6.6.1p1-31.62这次我在 fopen 期间有一个 segfault。 Fopen 在外部服务器上创建一个文件。 这里的代码:
$stream = @fopen("ssh2.sftp://$this->sftp$remote_file", 'w');
然后我使用 $stream 来编写内容,但是代码停止在 fopen 上,因为出现段错误。 我没有找到关于这个问题的任何信息,我认为问题是 opnessh 的新升级,因为 php 代码没有改变。 有什么想法吗?
在 Whosebug 上找到答案:
自从这次 PHP 更新后,您必须用 intval()
:
ssh2_sftp()
的结果)
$handle = opendir("ssh2.sftp://".intval($sftp)."/path/to/directory");
在我的例子中有 fopen
而不是 opendir
,但解决方案是相同的。
我遇到了同样的错误,但我发现了这个 PHP bug(参见 post 来自:[2016-12-15 09:47 UTC] 作者:ovoelker 在 wavecon dot de)
- 添加php5-dev用于编译pecl模块
- 重新安装 ssh2 pecl 模块。
- 重新启动 apache 并正常工作
在我们的例子中,intval() 没有解决分段错误。但是,更改调用格式确实有效:
fopen("ssh2.sftp://{$username}:{$password}@{$host}:{$port}/{$absolutePath}/{$filename}", 'w');
如果您正在关闭与 ssh2_disconnect()
的连接,即使使用 intval($sftp)
解决方案,您也可能会遇到 "segmentation fault" 问题。正确的解决方案是在通过 unset($sftp)
或 $sftp = null
关闭 SSH2 连接之前关闭 SFTP 连接。这是我读取远程文件的完整示例:
if (!$ssh2_connection = ssh2_connect($host, $port)) {
die("Failed to connect\n");
}
if (!ssh2_auth_password($ssh2_connection, $username, $password)) {
die("Failed to login\n");
}
if (!$sftp_connection = ssh2_sftp($ssh2_connection)) {
die("Failed to open SFTP session\n");
}
if (!$fh = fopen("ssh2.sftp://".intval($sftp_connection).$path, 'r')) {
die("Failed to open file\n");
}
while (($s = fgets($fh)) !== false) {
echo $s;
}
fclose($fh);
unset($sftp_connection);
if (!ssh2_disconnect($ssh2_connection)) {
die("Failed to disconnect\n");
}
P.S。此外,您可能会看到类似 "segmentation fault" 的内容:
php: channel.c:2570: _libssh2_channel_free: Assertion `session' failed.
Aborted
我的方案解决了。