Błąd certyfikatu SSL: błąd weryfikacji: num = 20: nie można uzyskać certyfikatu lokalnego wystawcy

11

Próbowałem uzyskać połączenie SSL z serwerem LDAPS (Active Directory), ale nadal mam problemy. Próbowałem użyć tego:

openssl s_client -connect the.server.edu:3269 

Z następującym wynikiem:

verify error:num=20:unable to get local issuer certificate 

Pomyślałem, OK, no cóż, serwer to stary serwer produkcyjny kilka lat. Może CA nie jest obecny. Następnie wyciągnąłem certyfikat z pliku wyjściowego do pliku pem i próbowałem:

openssl s_client -CAfile mycert.pem -connect the.server.edu:3269

I to też nie działało.

czego mi brakuje? Czy to nie powinno ZAWSZE działać?


źródło
Dla jasności wydaje się, że LDAPS, gdy jest obsługiwany z systemu Windows, nie przedstawia certyfikatu CA podczas nawiązywania połączenia. Dlatego należy uzyskać certyfikat CA X.509, wyeksportować jako base64 i przypisać zgodnie z opisem w odpowiedziach poniżej. W moim przypadku przy użyciu python-ldap przypisujesz go w zakresie GLOBALNYM (a nie do instancji ldap.initialize ()), ponieważ: ldap.set_option(ldap.OPT_X_TLS_CACERTFILE,'./ca_issuer_cert.pem') Po tym byłem w stanie używać STARTTLS (na porcie LDAP 389) zgodnie z oczekiwaniami.
mbrownnyc

Odpowiedzi:

4

Oto co widzę jako nazwę certyfikatu CA:

depth=1 /C=US/O=VeriSign, Inc./OU=VeriSign Trust Network/OU=Terms of use at //www.verisign.com/rpa (c)10/CN=VeriSign Class 3 International Server CA - G3
verify error:num=20:unable to get local issuer certificate
verify return:0

To była nazwa certyfikatu, który zaimportowałem po przeprowadzeniu -showcerts w mojej drugiej próbie powyżej. Wymieniłem certyfikaty w magazynie kluczy, wykonując następujące czynności:

$JAVA_HOME/bin/keytool -list -v -keystore $JAVA_HOME/jre/lib/security/cacerts

Widzę tam certyfikat CA.

Alias name: versign2006
Creation date: Jan 21, 2011
Entry type: trustedCertEntry

Owner: CN=VeriSign Class 3 International Server CA - G3, OU=Terms of use at www.verisign.com/rpa (c)10, OU=VeriSign Trust Network, O="VeriSign, Inc.", C=US
Issuer: CN=VeriSign Class 3 Public Primary Certification Authority - G5, OU="(c) 2006 VeriSign, Inc. - For authorized use only", OU=VeriSign Trust Network, O="VeriSign, Inc.", C=US
Serial number: 641be820ce020813f32d4d2d95d67e67
Valid from: Sun Feb 07 19:00:00 EST 2010 until: Fri Feb 07 18:59:59 EST 2020
Certificate fingerprints:
  MD5:  BA:B0:65:B4:3B:9C:E8:40:30:21:7D:C5:C6:CD:3F:EB
  SHA1: B1:8D:9D:19:56:69:BA:0F:78:29:51:75:66:C2:5F:42:2A:27:71:04

Aby upewnić się, że openssl korzysta z magazynu kluczy, którego używam z serwerem, używam argumentu -CAfile:

openssl s_client -connect the.server.edu:3269 -CAfile $JAVA_HOME/jre/lib/security/cacerts

Wiedząc, że magazyn kluczy Java dla CA ma hasło, próbowałem użyć opcji -pass pass: password w następujący sposób:

openssl s_client -connect the.server.edu:3269 -CAfile $JAVA_HOME/jre/lib/security/cacerts -pass pass:changeit

ale to też nie działało.

Zabawne jest to, że plik cacerts ma hasło i openssl nie narzeka, że ​​nie może odczytać pliku cacerts. To wydaje mi się podejrzane. Czy to czy coś jeszcze dzwoni dzwonkiem?

Brian
źródło
3

Ten błąd to sposób, w jaki openssl mówi: „Nie mogę podążać za łańcuchem certyfikatów do zaufanego katalogu głównego”. Właśnie wykonałem to samo polecenie na moich własnych serwerach AD i otrzymuję pełny łańcuch certyfikatów, ale najwyższy certyfikat zawiera dokładnie ten błąd. Jeśli masz klucz publikacji urzędu certyfikacji, który podpisał certyfikat, możesz go określić za pomocą opcji -CAfilelub-CApath

sysadmin1138
źródło
Ok, dzięki za odpowiedź. Więc próbowałem tego. Zdobyłem certyfikat urzędu certyfikacji, robiąc to samo z włączoną opcją -showcerts, i wziąłem drugi certyfikat. To powinien być certyfikat CA, prawda? Próbowałem tego zamiast certyfikatu serwera w pliku pem i dostałem ten sam komunikat o błędzie. Jakieś inne myśli?
W takim przypadku prawdopodobne jest, że nie powiedzie się walidacja z innego powodu, np. Wygasła.
sysadmin1138
1

Próbowałem uzyskać połączenie SSL z serwerem LDAPS (Active Directory), ale nadal mam problemy. Próbowałem użyć tego:

Jeśli korzystasz z OpenLDAP, możesz ustawić:

TLS_REQCERT=never

w openldap.confpliku, który instruuje OpenLDAP, aby nie próbował weryfikować certyfikatu. Jest podobna opcja, jeśli wykonujesz uwierzytelnianie LDAP za pomocą Apache.

Jeśli naprawdę chcesz przeprowadzić weryfikację certyfikatu, pomocne mogą być:

czego mi brakuje? Czy to nie powinno ZAWSZE działać?

Nie wydaje mi się Chociaż poniższe brzmienie może wydawać się ostateczne, to tak naprawdę mój najlepszy gość:

To, co próbowałeś, działałoby tylko w przypadku certyfikatu z podpisem własnym. Ponieważ certyfikat został faktycznie wydany przez urząd certyfikacji systemu Windows, próba użycia certyfikatu serwera jako argumentu, -CAfileże nic ci nie da.

Zdobyłem certyfikat urzędu certyfikacji, robiąc to samo z włączoną opcją -showcerts, i wziąłem drugi certyfikat. To powinien być certyfikat CA, prawda?

Niekoniecznie nie. Nie ma gwarancji, że zdalny serwer przedstawi certyfikat CA na swoim wyjściu. Najpierw spójrz na wystawcę certyfikatu serwera:

openssl x509 -in server.crt -noout -text | grep Issuer

... a następnie sprawdź, czy jeden z pozostałych certyfikatów jest zgodny z tym wystawcą.

Larsks
źródło