簡體   English   中英

如何在PHP中將受信任的證書頒發機構列表設置為socket客戶端?

[英]How to set trusted certificate authorities list to socket client in PHP?

在IHE Con​​nectathon的上下文中,我想創建一個響應ATNA配置文件的原始套接字服務器,它需要具有兩端證書的TLS套接字。

如果在此消息中總結我的問題: https//groups.google.com/d/msg/eu_connectathon/O-VGI_3cltw/ARsElA65ZkkJ

編輯 :對不起,Google網上論壇不公開,以下是留言:

嗨弗洛里安,

錯誤消息“服務器要求提供證書,但發布者列表不包含有效的證書頒發機構”究竟是什么? 是指並且在過去幾年中TLS工具客戶端的實施發生了變化,還是我使用了錯誤的證書?

該消息表示服務器已將CertificateRequest消息發送到clienmt,而certificate_authorities字段中沒有值。

我去年遇到了這個問題,並與TLS工具的開發人員討論過這個問題。 他聲稱,如果服務器不包含此字段,客戶端將無法確定要返回哪種類型的證書,假設您將連接頂部多個關聯域,每個域都有自己的CA.

您似乎可以通過調用SSL_CTX_set_client_CA_list來指示OpenSSL返回此值,例如在DcmTLSTransportLayer :: addTrustedCertificateFile中。 我還沒有使用TLS工具測試過這個,但我希望在connectathon啟動之前完成它。

但是我在PHP中的實現與它們的實現並不相同。 看起來PHP缺少“SSL CTX設置客戶端CA列表”的可能性,告訴客戶端它應該使用哪個證書頒發機構。

$context = stream_context_create();

if ($certificate) {
  // Server certificate + private key
  stream_context_set_option($context, 'ssl', 'local_cert', "/path/to/server.pem"); 
  stream_context_set_option($context, 'ssl', 'passphrase', $passphrase); 

  // Client public certificates
  stream_context_set_option($context, 'ssl', 'cafile', "/path/to/ca.pem");

  stream_context_set_option($context, 'ssl', 'allow_self_signed', false);
  stream_context_set_option($context, 'ssl', 'verify_peer', true);
  stream_context_set_option($context, 'ssl', 'peer_name', "TlsTools2");
  stream_context_set_option($context, 'ssl', 'capture_peer_cert', true);
  stream_context_set_option($context, 'ssl', 'capture_peer_cert_chain', true);
}

$this->__socket = @stream_socket_server("tcp://$address:$port", $errno, $errstr, STREAM_SERVER_BIND | STREAM_SERVER_LISTEN, $context);

IHE Gazelle TLS客戶端告訴我“服務器要求提供證書,但發布者列表不包含有效的證書頒發機構。”

客戶端和服務器之間的消息傳遞,但測試不正常,因為“不夠安全”,告訴消息。

你看到了一個問題嗎?PHP有沒有我沒看到的更多選項?

謝謝你的幫助。

編輯 :正如@rdlowrey建議我,我剛剛創建了一個錯誤報告: https ://bugs.php.net/bug.php?id = 69215

正如我在最初的評論中所提到的:

PHP的流服務器實現從未實際使用SSL_CTX_set_client_CA_list()來加密流。

這已在相關錯誤報告中引用的上游更正:

https://bugs.php.net/bug.php?id=69215

一旦發布了PHP 5.6.8二進制文件(或者您可以在該版本之前針對當前源手動構建PHP),將反映此更改。

履行

使用更新的二進制文件,OP的示例代碼將按預期工作而無需修改。 在服務器中使用的加密上下文的簡單示例:

<?php
$serverCtx = stream_context_create(['ssl' => [
    'local_cert' => '/path/to/my-server-cert.pem',
    'passphrase' => 'elephpant',
    'cafile' => '/path/to/my-ca-certs.pem',
    'verify_peer' => true
]]);

在上面的示例中,當作為TLS握手的一部分發送客戶端CA列表時,PHP會自動使用my-ca-certs.pemmy-ca-certs.pem文件中的證書名稱。

筆記

通過"verify_peer" => true啟用加密服務器流中的對等驗證時,PHP將不會自動啟用對等名稱驗證。 除非您只希望允許單個證書持有者(具有特定的已知名稱)訪問您的服務器,否則這正是您想要的。 此默認行為支持更常見的用例,即允許其證書由可信CA簽名的任何客戶端建立與服務器的連接。 但是,如果您希望在加密服務器中強制執行名稱驗證,請修改上面的上下文示例,如下所示:

<?php
$serverCtx = stream_context_create(['ssl' => [
    'local_cert' => '/path/to/my-server-cert.pem',
    'passphrase' => 'elephpant',
    'cafile' => '/path/to/my-ca-certs.pem',
    'verify_peer' => true,
    'verify_peer_name' => true, // verify the name on the cert
    'peer_name' => 'zanzibar' // ensure the cert's name matches this
]]);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM