Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / net / third_party / nss / ssl / authcert.c
blobbd0f6ed49a2befc803e379aaff10992ad8c0cb0c
1 /*
2 * NSS utility functions
4 * This Source Code Form is subject to the terms of the Mozilla Public
5 * License, v. 2.0. If a copy of the MPL was not distributed with this
6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8 #include <stdio.h>
9 #include <string.h>
10 #include "prerror.h"
11 #include "secitem.h"
12 #include "prnetdb.h"
13 #include "cert.h"
14 #include "nspr.h"
15 #include "secder.h"
16 #include "key.h"
17 #include "nss.h"
18 #include "ssl.h"
19 #include "pk11func.h" /* for PK11_ function calls */
22 * This callback used by SSL to pull client sertificate upon
23 * server request
25 SECStatus
26 NSS_GetClientAuthData(void * arg,
27 PRFileDesc * socket,
28 struct CERTDistNamesStr * caNames,
29 struct CERTCertificateStr ** pRetCert,
30 struct SECKEYPrivateKeyStr **pRetKey)
32 CERTCertificate * cert = NULL;
33 SECKEYPrivateKey * privkey = NULL;
34 char * chosenNickName = (char *)arg; /* CONST */
35 void * proto_win = NULL;
36 SECStatus rv = SECFailure;
38 proto_win = SSL_RevealPinArg(socket);
40 if (chosenNickName) {
41 cert = CERT_FindUserCertByUsage(CERT_GetDefaultCertDB(),
42 chosenNickName, certUsageSSLClient,
43 PR_FALSE, proto_win);
44 if ( cert ) {
45 privkey = PK11_FindKeyByAnyCert(cert, proto_win);
46 if ( privkey ) {
47 rv = SECSuccess;
48 } else {
49 CERT_DestroyCertificate(cert);
52 } else { /* no name given, automatically find the right cert. */
53 CERTCertNicknames * names;
54 int i;
56 names = CERT_GetCertNicknames(CERT_GetDefaultCertDB(),
57 SEC_CERT_NICKNAMES_USER, proto_win);
58 if (names != NULL) {
59 for (i = 0; i < names->numnicknames; i++) {
60 cert = CERT_FindUserCertByUsage(CERT_GetDefaultCertDB(),
61 names->nicknames[i], certUsageSSLClient,
62 PR_FALSE, proto_win);
63 if ( !cert )
64 continue;
65 /* Only check unexpired certs */
66 if (CERT_CheckCertValidTimes(cert, PR_Now(), PR_TRUE) !=
67 secCertTimeValid ) {
68 CERT_DestroyCertificate(cert);
69 continue;
71 rv = NSS_CmpCertChainWCANames(cert, caNames);
72 if ( rv == SECSuccess ) {
73 privkey = PK11_FindKeyByAnyCert(cert, proto_win);
74 if ( privkey )
75 break;
77 rv = SECFailure;
78 CERT_DestroyCertificate(cert);
80 CERT_FreeNicknames(names);
83 if (rv == SECSuccess) {
84 *pRetCert = cert;
85 *pRetKey = privkey;
87 return rv;