gpt4 book ai didi

PHP 和 SSL CA 验证 - 独立于操作系统

转载 作者:IT王子 更新时间:2023-10-29 01:06:09 27 4
gpt4 key购买 nike

这是一个简单的 PHP 脚本,它打开一个准备好发送 HTTP 请求的 SSL 套接字:

$contextOptions = array();$socketUrl = 'ssl://google.com:443';$streamContext = stream_context_create($contextOptions);$socket = stream_socket_client($socketUrl, $errno, $errstr, 30, STREAM_CLIENT_CONNECT, $streamContext);if (!$socket || $errno !== 0) {    var_dump($socket, $errstr);    exit;}var_dump($socket);exit('Socket created.');

这有效 - 我刚刚对其进行了测试 - 但没有针对受信任的 CA 存储进行验证。

我们可以修改该脚本以使用 PHP 的 SSL Context options :

$contextOptions = array(    'ssl' => array(        'cafile' => 'C:\xampp\cacerts.pem',        'CN_match' => '*.google.com',  // CN_match will only be checked if 'verify_peer' is set to TRUE.  See https://bugs.php.net/bug.php?id=47030.        'verify_peer' => TRUE,    ));$socketUrl = 'ssl://google.com:443';$streamContext = stream_context_create($contextOptions);$socket = stream_socket_client($socketUrl, $errno, $errstr, 30, STREAM_CLIENT_CONNECT, $streamContext);if (!$socket || $errno !== 0) {    var_dump($socket, $errstr);    exit;}var_dump($socket);exit('Socket created.');

只要“cafile”存在并且具有正确的 CA,那么这个示例也可以工作...

...但是我们如何在不对 CA 文件名/文件路径进行硬编码的情况下做到这一点?我们正在尝试创建一些东西来独立于操作系统验证 SSL 证书,而不需要为运行此脚本的每个服务器单独配置。

我知道 Linux 有一个 CA 目录,我们可以将其作为“capath”。 Windows呢?它在哪里存储其受信任的 CA?我搜索了一下,不幸的是这些似乎在注册表中,所以我们无法从 PHP 访问它们吗?其他操作系统呢?

最佳答案

一场失败的战斗......

在 PHP 5.6 之前,如果不手动设置 "cafile""CN_match" 上下文选项,则无法在 PHP 中进行安全的加密传输。不幸的是,即使您确实正确地设置了这些值,您的传输仍然很可能会失败,因为 5.6 之前的版本在验证主机名时不会引用对等证书中日益流行的 SAN (subjectAltName) 扩展.因此,通过 PHP 的内置流包装器进行的“安全”加密在很大程度上是用词不当。使用旧版本的 PHP 最安全的选择(字面上)是 curl 扩展。

关于 Windows 证书 ...

Windows 使用自己的证书库并以不同于 OpenSSL 的格式对其证书进行编码。相比之下,openssl 应用程序使用开放的 .PEM 格式。 5.6 之前的 PHP 版本无法以任何方式与 Windows 证书存储进行交互。出于这个原因,不可能使用内置的流包装器功能以跨操作系统的方式进行可靠和安全的加密。

PHP 5.6 是向前迈出的重要一步

  • 新的 openssl.cafileopenssl.capath php.ini 指令允许您全局分配证书位置,而无需在每个流上下文中设置它们

  • 默认情况下,所有加密流都会验证对等证书和主机名,如果未提供 "CN_match" 上下文选项,则会自动从 URI 解析主机名。

    <
  • 流加密操作现在在验证主机名时检查对等证书 SAN 条目

  • 如果在流上下文中未指定 CA 文件/路径 php.ini 指令,PHP 会自动回退到操作系统的证书存储(在 Windows 中也是如此!)

举例来说,这就是您在 PHP-5.6 中安全连接到 github.com 所需要做的一切:

<?php
$socket = stream_socket_client("tls://github.com:443");

是的。真的是这样。不用担心上下文设置和验证参数。在这方面,PHP 现在可以像您的浏览器一样运行。

有关该主题的更多阅读

这些 PHP 5.6 的变化只是 SSL/TLS 改进的冰山一角。我们努力使 5.6 成为迄今为止在加密通信方面最安全的 PHP 版本。

如果您想了解有关这些新功能的更多信息,可以通过官方 channel 获得大量信息

5.4/5.5中SAN匹配注意事项

我们正在努力将至少与 5.4 和 5.5 分支匹配的 SAN 向后移植,因为如果没有此功能,就很难以任何有意义的方式(作为客户端)使用加密包装器。尽管这项向后移植工作在很大程度上取决于我作为志愿者的可用空闲时间,但支持这个答案肯定会帮助它更快地发生:)

关于PHP 和 SSL CA 验证 - 独立于操作系统,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16298282/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com