1 diff -pu a/nss/lib/ssl/sslauth.c b/nss/lib/ssl/sslauth.c 2 --- a/nss/lib/ssl/sslauth.c 2013-07-31 12:07:10.974699609 -0700 3 +++ b/nss/lib/ssl/sslauth.c 2013-07-31 12:32:07.996451064 -0700 4 @@ -28,6 +28,41 @@ SSL_PeerCertificate(PRFileDesc *fd) 5 } 6 7 /* NEED LOCKS IN HERE. */ 8 +SECStatus 9 +SSL_PeerCertificateChain(PRFileDesc *fd, CERTCertificate **certs, 10 + unsigned int *numCerts, unsigned int maxNumCerts) 11 +{ 12 + sslSocket *ss; 13 + ssl3CertNode* cur; 14 + 15 + ss = ssl_FindSocket(fd); 16 + if (!ss) { 17 + SSL_DBG(("%d: SSL[%d]: bad socket in PeerCertificateChain", 18 + SSL_GETPID(), fd)); 19 + return SECFailure; 20 + } 21 + if (!ss->opt.useSecurity) 22 + return SECFailure; 23 + 24 + if (ss->sec.peerCert == NULL) { 25 + *numCerts = 0; 26 + return SECSuccess; 27 + } 28 + 29 + *numCerts = 1; /* for the leaf certificate */ 30 + if (maxNumCerts > 0) 31 + certs[0] = CERT_DupCertificate(ss->sec.peerCert); 32 + 33 + for (cur = ss->ssl3.peerCertChain; cur; cur = cur->next) { 34 + if (*numCerts < maxNumCerts) 35 + certs[*numCerts] = CERT_DupCertificate(cur->cert); 36 + (*numCerts)++; 37 + } 38 + 39 + return SECSuccess; 40 +} 41 + 42 +/* NEED LOCKS IN HERE. */ 43 CERTCertificate * 44 SSL_LocalCertificate(PRFileDesc *fd) 45 { 46 diff -pu a/nss/lib/ssl/ssl.h b/nss/lib/ssl/ssl.h 47 --- a/nss/lib/ssl/ssl.h 2013-07-31 12:07:10.964699464 -0700 48 +++ b/nss/lib/ssl/ssl.h 2013-07-31 12:32:07.996451065 -0700 49 @@ -426,6 +426,18 @@ SSL_SetStapledOCSPResponses(PRFileDesc * 50 SSLKEAType kea); 51 52 /* 53 +** Return references to the certificates presented by the SSL peer. 54 +** |maxNumCerts| must contain the size of the |certs| array. On successful 55 +** return, |*numCerts| contains the number of certificates available and 56 +** |certs| will contain references to as many certificates as would fit. 57 +** Therefore if |*numCerts| contains a value less than or equal to 58 +** |maxNumCerts|, then all certificates were returned. 59 +*/ 60 +SSL_IMPORT SECStatus SSL_PeerCertificateChain( 61 + PRFileDesc *fd, CERTCertificate **certs, 62 + unsigned int *numCerts, unsigned int maxNumCerts); 63 + 64 +/* 65 ** Authenticate certificate hook. Called when a certificate comes in 66 ** (because of SSL_REQUIRE_CERTIFICATE in SSL_Enable) to authenticate the 67 ** certificate. 68