2013-04-30 13 views
5

Oto prosty skrypt PHP, który otwiera gniazdo SSL gotowy do wysyłania żądań http:PHP i CA Weryfikacja SSL - OS Niezależne

 
$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.'); 

To działa - Właśnie testowałem go - ale nie ma walidacji przeciwko zaufanemu sklepowi CA.

Możemy zmodyfikować ten skrypt do używania 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.'); 

Dopóki 'cafile' istnieje i ma poprawne CA to ten przykład działa również ...

... ale jak możemy to zrobić bez twardego kodowania nazwy pliku/ścieżki do pliku CA? Próbujemy stworzyć coś, co weryfikuje certyfikaty SSL OS niezależnie, bez konieczności oddzielnej konfiguracji dla każdego serwera, na którym działa ten skrypt.

Wiem, że Linux ma katalog dla urzędów certyfikacji, który możemy umieścić jako "capath". A co z Windows? Gdzie przechowują swoje zaufane ośrodki CA? Szukałem i te niestety wydawały się być w rejestrze, więc czy nie ma możliwości, abyśmy mogli uzyskać do nich dostęp z PHP? A co z innymi systemami operacyjnymi?

Odpowiedz

12

na straconej pozycji ...

Nie ma sposobu, aby przeprowadzić bezpieczny szyfrowany transfer w PHP bez konieczności ręcznego ustawiania opcji przed PHP 5.6 "cafile" i "CN_match" kontekstowych. I niestety, nawet jeśli ustawisz te wartości poprawnie do, twoje transfery nadal będą bardzo podatne na niepowodzenie, ponieważ wersje wcześniejsze niż 5.6 nie sprawdzają coraz popularniejszego rozszerzenia SAN (subjectAltName) obecnego w certyfikatach równorzędnych podczas sprawdzania nazw hostów. W rezultacie "bezpieczne" szyfrowanie poprzez wbudowane owijacze strumieniowe PHP jest w dużej mierze mylące. Najbezpieczniejszym zakładem (dosłownie) ze starszymi wersjami PHP jest rozszerzenie curl.

Odnośnie okien CERT ...

Windows wykorzystuje swój własny sklep cert i koduje swoje certyfikaty w innym formacie z OpenSSL. Dla porównania, aplikacje openssl używają otwartego formatu .PEM. Wersje PHP w wersji wcześniejszej niż 5.6 nie mogą w żaden sposób łączyć się ze sklepem certyfikatów Windows. Z tego powodu niemożliwe jest posiadanie niezawodnego i bezpiecznego szyfrowania w systemie z różnymi systemami operacyjnymi za pomocą wbudowanej funkcji tworzenia strumienia strumieniowego.

PHP 5.6 jest dużym krokiem naprzód

  • New openssl.cafile i openssl.capath dyrektyw php.ini pozwala globalnie przypisać cert lokalizacje bez ustawić je w każdym kontekście strumienia

  • Wszystkie zaszyfrowane strumienie weryfikują domyślnie certyfikaty i nazwy hostów, a nazwa hosta jest automatycznie przetwarzana z identyfikatora URI, jeśli nie podano opcji kontekstowej "CN_match".

  • operacje kryptograficzne Stream teraz sprawdzić Peer cert wpisami SAN przy sprawdzaniu nazw hostów

  • Jeśli plik nie CA/ścieżka jest określona w ramach strumienia lub php.Dyrektywy ini PHP automatycznie wraca do sklepów cert systemu operacyjnego (w systemie Windows, też!)

Tytułem przykładu, to wszystko trzeba by zrobić, aby bezpiecznie podłączyć do github.com w PHP- 5.6:

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

Tak. To naprawdę jest to. Bez kłopotów z ustawieniami kontekstowymi i parametrami weryfikacji. PHP działa teraz jak twoja przeglądarka w tym zakresie.

Więcej odczyt na temat

Te PHP 5.6 zmiany są tylko wierzchołkiem góry lodowej w odniesieniu do poprawy SSL/TLS. Ciężko pracowaliśmy, aby uczynić 5.6 najbezpieczniejszą wersję PHP do tej pory w odniesieniu do szyfrowanej komunikacji.

Jeśli chcesz dowiedzieć się więcej na temat tych nowych cech jest bogactwo informacji dostępnych za pośrednictwem oficjalnych kanałów

Uwaga na SAN dopasowywania w 5.4/5.5

Mamy pracy do backport przynajmniej dopasowanie SAN do 5,4 i 5,5 oddziałów, jak to niezwykle trudne do korzystania z owijarki szyfrowania w żaden sensowny sposób (jako klient) bez tej funkcji. Mimo że praca polegająca na przenoszeniu jest w dużej mierze zależna od mojego wolnego czasu jako wolontariusza, wzięcie udziału w tej odpowiedzi może z pewnością pomóc w osiągnięciu tego celu szybciej :)

+0

rdlowrey ma absolutną rację. Możesz jednak pobrać liść z Guzzle i spakować swój własny plik CA w swoim kodzie: https://github.com/guzzle/guzzle/blob/master/src/Guzzle/Http/Resources/cacert.pem – Tom

+1

Powinienem dodaj, że przy stosowaniu podejścia zwiniętego nakłada się na ciebie obowiązek upewnienia się, że twoje certyfikaty CA są aktualne. Zwykle zmieniają się one kilka razy w roku, a jeśli nie są aktualizowane, istnieje możliwość zweryfikowania równorzędnych użytkowników za pomocą zaatakowanego urzędu certyfikacji. Zdolność 5.6 do używania certyfikatów zarządzanych przez system operacyjny jest dużym krokiem naprzód, ponieważ nie musisz nic o tym wiedzieć. Jednak to również jest tak dobre, jak twoja skłonność do instalowania najnowszych aktualizacji systemu operacyjnego, więc twoje certyfikaty nie są nieaktualne. Niestety, jest to funkcja, która w najbliższym czasie nie pojawi się w libcurl. – rdlowrey

+0

Najlepszym rozwiązaniem z dużym marginesem, jeśli potrzebujesz maksymalnego bezpieczeństwa (dla paranoików i świadomych NSA) jest użycie znanego skrótu linii papilarnych do weryfikacji certyfikatu peera. Jest to funkcjonalność, która będzie dostępna dla zaszyfrowanych strumieni również w PHP 5.6. To powiedziawszy, jest * dużo * pracy do zrobienia w odniesieniu do dokumentacji dla tych rzeczy, więc możemy uzyskać informację w ciągu najbliższych kilku miesięcy przed wydaniem. Tak: jesteśmy tego świadomi i tak, będziemy ciężko pracować, aby podręcznik był przydatnym zasobem, jeśli chcesz chronić swoje transfery :) – rdlowrey