Bug 1395897, certutil shouldn't prompt for password if -f is given, r=rrelyea
authorKai Engert <kaie@kuix.de>
Fri, 08 Sep 2017 12:38:49 +0200
changeset 13575 69f83c64dec4f66c7652c9bf0def19b901738c98
parent 13574 6cec805417f542db9ccc86034c27e3658e8d744e
child 13576 ac61b8c99fa285342ec19478c2eb9ee5f508076f
push id2363
push userkaie@kuix.de
push dateFri, 08 Sep 2017 10:38:36 +0000
reviewersrrelyea
bugs1395897
Bug 1395897, certutil shouldn't prompt for password if -f is given, r=rrelyea
cmd/certutil/certutil.c
cmd/lib/secutil.c
lib/certdb/cert.h
lib/certdb/stanpcertdb.c
lib/nss/nss.def
--- a/cmd/certutil/certutil.c
+++ b/cmd/certutil/certutil.c
@@ -360,17 +360,17 @@ CertReq(SECKEYPrivateKey *privk, SECKEYP
 static SECStatus
 ChangeTrustAttributes(CERTCertDBHandle *handle, PK11SlotInfo *slot,
                       char *name, char *trusts, void *pwdata)
 {
     SECStatus rv;
     CERTCertificate *cert;
     CERTCertTrust *trust;
 
-    cert = CERT_FindCertByNicknameOrEmailAddr(handle, name);
+    cert = CERT_FindCertByNicknameOrEmailAddrCX(handle, name, pwdata);
     if (!cert) {
         SECU_PrintError(progName, "could not find certificate named \"%s\"",
                         name);
         return SECFailure;
     }
 
     trust = (CERTCertTrust *)PORT_ZAlloc(sizeof(CERTCertTrust));
     if (!trust) {
--- a/cmd/lib/secutil.c
+++ b/cmd/lib/secutil.c
@@ -479,58 +479,16 @@ SECU_ConfigDirectory(const char *base)
         if (buf[strlen(buf) - 1] == '/')
             buf[strlen(buf) - 1] = 0;
     }
 
     initted = PR_TRUE;
     return buf;
 }
 
-/*Turn off SSL for now */
-/* This gets called by SSL when server wants our cert & key */
-int
-SECU_GetClientAuthData(void *arg, PRFileDesc *fd,
-                       struct CERTDistNamesStr *caNames,
-                       struct CERTCertificateStr **pRetCert,
-                       struct SECKEYPrivateKeyStr **pRetKey)
-{
-    SECKEYPrivateKey *key;
-    CERTCertificate *cert;
-    int errsave;
-
-    if (arg == NULL) {
-        fprintf(stderr, "no key/cert name specified for client auth\n");
-        return -1;
-    }
-    cert = PK11_FindCertFromNickname(arg, NULL);
-    errsave = PORT_GetError();
-    if (!cert) {
-        if (errsave == SEC_ERROR_BAD_PASSWORD)
-            fprintf(stderr, "Bad password\n");
-        else if (errsave > 0)
-            fprintf(stderr, "Unable to read cert (error %d)\n", errsave);
-        else if (errsave == SEC_ERROR_BAD_DATABASE)
-            fprintf(stderr, "Unable to get cert from database (%d)\n", errsave);
-        else
-            fprintf(stderr, "SECKEY_FindKeyByName: internal error %d\n", errsave);
-        return -1;
-    }
-
-    key = PK11_FindKeyByAnyCert(arg, NULL);
-    if (!key) {
-        fprintf(stderr, "Unable to get key (%d)\n", PORT_GetError());
-        return -1;
-    }
-
-    *pRetCert = cert;
-    *pRetKey = key;
-
-    return 0;
-}
-
 SECStatus
 SECU_ReadDERFromFile(SECItem *der, PRFileDesc *inFile, PRBool ascii,
                      PRBool warnOnPrivateKeyInAsciiFile)
 {
     SECStatus rv;
     if (ascii) {
         /* First convert ascii to binary */
         SECItem filedata;
@@ -3624,54 +3582,16 @@ SECU_DerSignDataCRL(PLArenaPool *arena, 
         goto loser;
     }
 
 loser:
     PORT_Free(it.data);
     return rv;
 }
 
-#if 0
-
-/* we need access to the private function cert_FindExtension for this code to work */
-
-CERTAuthKeyID *
-SECU_FindCRLAuthKeyIDExten (PLArenaPool *arena, CERTSignedCrl *scrl)
-{
-    SECItem encodedExtenValue;
-    SECStatus rv;
-    CERTAuthKeyID *ret;
-    CERTCrl* crl;
-
-    if (!scrl) {
-        PORT_SetError(SEC_ERROR_INVALID_ARGS);
-        return NULL;
-    }
-
-    crl = &scrl->crl;
-
-    encodedExtenValue.data = NULL;
-    encodedExtenValue.len = 0;
-
-    rv = cert_FindExtension(crl->extensions, SEC_OID_X509_AUTH_KEY_ID,
-                            &encodedExtenValue);
-    if ( rv != SECSuccess ) {
-        return (NULL);
-    }
-
-    ret = CERT_DecodeAuthKeyID (arena, &encodedExtenValue);
-
-    PORT_Free(encodedExtenValue.data);
-    encodedExtenValue.data = NULL;
-
-    return(ret);
-}
-
-#endif
-
 /*
  * Find the issuer of a Crl.  Use the authorityKeyID if it exists.
  */
 CERTCertificate *
 SECU_FindCrlIssuer(CERTCertDBHandle *dbhandle, SECItem *subject,
                    CERTAuthKeyID *authorityKeyID, PRTime validTime)
 {
     CERTCertificate *issuerCert = NULL;
@@ -3735,17 +3655,17 @@ SECU_EncodeAndAddExtensionValue(PLArenaP
 }
 
 CERTCertificate *
 SECU_FindCertByNicknameOrFilename(CERTCertDBHandle *handle,
                                   char *name, PRBool ascii,
                                   void *pwarg)
 {
     CERTCertificate *the_cert;
-    the_cert = CERT_FindCertByNicknameOrEmailAddr(handle, name);
+    the_cert = CERT_FindCertByNicknameOrEmailAddrCX(handle, name, pwarg);
     if (the_cert) {
         return the_cert;
     }
     the_cert = PK11_FindCertFromNickname(name, pwarg);
     if (!the_cert) {
         /* Don't have a cert with name "name" in the DB. Try to
          * open a file with such name and get the cert from there.*/
         SECStatus rv;
--- a/lib/certdb/cert.h
+++ b/lib/certdb/cert.h
@@ -499,16 +499,18 @@ extern CERTCertificate *CERT_FindCertByK
 
 /*
 ** Generate a certificate key from the issuer and serialnumber, then look it
 ** up in the database.  Return the cert if found.
 **	"issuerAndSN" is the issuer and serial number to look for
 */
 extern CERTCertificate *CERT_FindCertByIssuerAndSN(
     CERTCertDBHandle *handle, CERTIssuerAndSN *issuerAndSN);
+extern CERTCertificate *CERT_FindCertByIssuerAndSNCX(
+    CERTCertDBHandle *handle, CERTIssuerAndSN *issuerAndSN, void *wincx);
 
 /*
 ** Find a certificate in the database by a subject key ID
 **	"subjKeyID" is the subject Key ID to look for
 */
 extern CERTCertificate *CERT_FindCertBySubjectKeyID(CERTCertDBHandle *handle,
                                                     SECItem *subjKeyID);
 
@@ -542,24 +544,30 @@ CERTCertificate *CERT_FindCertByEmailAdd
                                           char *emailAddr);
 
 /*
 ** Find a certificate in the database by a email address or nickname
 **	"name" is the email address or nickname to look up
 */
 CERTCertificate *CERT_FindCertByNicknameOrEmailAddr(CERTCertDBHandle *handle,
                                                     const char *name);
+CERTCertificate *CERT_FindCertByNicknameOrEmailAddrCX(CERTCertDBHandle *handle,
+                                                      const char *name,
+                                                      void *wincx);
 
 /*
 ** Find a certificate in the database by a email address or nickname
 ** and require it to have the given usage.
 **      "name" is the email address or nickname to look up
 */
 CERTCertificate *CERT_FindCertByNicknameOrEmailAddrForUsage(
     CERTCertDBHandle *handle, const char *name, SECCertUsage lookingForUsage);
+CERTCertificate *CERT_FindCertByNicknameOrEmailAddrForUsageCX(
+    CERTCertDBHandle *handle, const char *name, SECCertUsage lookingForUsage,
+    void *wincx);
 
 /*
 ** Find a certificate in the database by a digest of a subject public key
 **	"spkDigest" is the digest to look up
 */
 extern CERTCertificate *CERT_FindCertBySPKDigest(CERTCertDBHandle *handle,
                                                  SECItem *spkDigest);
 
--- a/lib/certdb/stanpcertdb.c
+++ b/lib/certdb/stanpcertdb.c
@@ -452,30 +452,48 @@ loser:
 /* This symbol is exported for backward compatibility. */
 CERTCertificate *
 __CERT_NewTempCertificate(CERTCertDBHandle *handle, SECItem *derCert,
                           char *nickname, PRBool isperm, PRBool copyDER)
 {
     return CERT_NewTempCertificate(handle, derCert, nickname, isperm, copyDER);
 }
 
+static CERTCertificate *
+common_FindCertByIssuerAndSN(CERTCertDBHandle *handle,
+                             CERTIssuerAndSN *issuerAndSN,
+                             void *wincx)
+{
+    PK11SlotInfo *slot;
+    CERTCertificate *cert;
+
+    cert = PK11_FindCertByIssuerAndSN(&slot, issuerAndSN, wincx);
+    if (cert && slot) {
+        PK11_FreeSlot(slot);
+    }
+
+    return cert;
+}
+
+
 /* maybe all the wincx's should be some const for internal token login? */
 CERTCertificate *
 CERT_FindCertByIssuerAndSN(CERTCertDBHandle *handle,
                            CERTIssuerAndSN *issuerAndSN)
 {
-    PK11SlotInfo *slot;
-    CERTCertificate *cert;
+    return common_FindCertByIssuerAndSN(handle, issuerAndSN, NULL);
+}
 
-    cert = PK11_FindCertByIssuerAndSN(&slot, issuerAndSN, NULL);
-    if (cert && slot) {
-        PK11_FreeSlot(slot);
-    }
-
-    return cert;
+/* maybe all the wincx's should be some const for internal token login? */
+CERTCertificate *
+CERT_FindCertByIssuerAndSNCX(CERTCertDBHandle *handle,
+                             CERTIssuerAndSN *issuerAndSN,
+                             void *wincx)
+{
+    return common_FindCertByIssuerAndSN(handle, issuerAndSN, wincx);
 }
 
 static NSSCertificate *
 get_best_temp_or_perm(NSSCertificate *ct, NSSCertificate *cp)
 {
     NSSUsage usage;
     NSSCertificate *arr[3];
     if (!ct) {
@@ -582,17 +600,18 @@ CERT_FindCertByDERCert(CERTCertDBHandle 
             return NULL;
     }
     return STAN_GetCERTCertificateOrRelease(c);
 }
 
 static CERTCertificate *
 common_FindCertByNicknameOrEmailAddrForUsage(CERTCertDBHandle *handle,
                                              const char *name, PRBool anyUsage,
-                                             SECCertUsage lookingForUsage)
+                                             SECCertUsage lookingForUsage,
+                                             void *wincx)
 {
     NSSCryptoContext *cc;
     NSSCertificate *c, *ct;
     CERTCertificate *cert = NULL;
     NSSUsage usage;
     CERTCertList *certlist;
 
     if (NULL == name) {
@@ -615,29 +634,29 @@ common_FindCertByNicknameOrEmailAddrForU
         if (lowercaseName) {
             ct = NSSCryptoContext_FindBestCertificateByEmail(
                 cc, lowercaseName, NULL, &usage, NULL);
             PORT_Free(lowercaseName);
         }
     }
 
     if (anyUsage) {
-        cert = PK11_FindCertFromNickname(name, NULL);
+        cert = PK11_FindCertFromNickname(name, wincx);
     } else {
         if (ct) {
             /* Does ct really have the required usage? */
             nssDecodedCert *dc;
             dc = nssCertificate_GetDecoding(ct);
             if (!dc->matchUsage(dc, &usage)) {
                 CERT_DestroyCertificate(STAN_GetCERTCertificateOrRelease(ct));
                 ct = NULL;
             }
         }
 
-        certlist = PK11_FindCertsFromNickname(name, NULL);
+        certlist = PK11_FindCertsFromNickname(name, wincx);
         if (certlist) {
             SECStatus rv =
                 CERT_FilterCertListByUsage(certlist, lookingForUsage, PR_FALSE);
             if (SECSuccess == rv && !CERT_LIST_EMPTY(certlist)) {
                 cert = CERT_DupCertificate(CERT_LIST_HEAD(certlist)->cert);
             }
             CERT_DestroyCertList(certlist);
         }
@@ -654,26 +673,44 @@ common_FindCertByNicknameOrEmailAddrForU
     }
     return c ? STAN_GetCERTCertificateOrRelease(c) : NULL;
 }
 
 CERTCertificate *
 CERT_FindCertByNicknameOrEmailAddr(CERTCertDBHandle *handle, const char *name)
 {
     return common_FindCertByNicknameOrEmailAddrForUsage(handle, name, PR_TRUE,
-                                                        0);
+                                                        0, NULL);
+}
+
+CERTCertificate *
+CERT_FindCertByNicknameOrEmailAddrCX(CERTCertDBHandle *handle, const char *name,
+                                     void *wincx)
+{
+    return common_FindCertByNicknameOrEmailAddrForUsage(handle, name, PR_TRUE,
+                                                        0, wincx);
 }
 
 CERTCertificate *
 CERT_FindCertByNicknameOrEmailAddrForUsage(CERTCertDBHandle *handle,
                                            const char *name,
                                            SECCertUsage lookingForUsage)
 {
     return common_FindCertByNicknameOrEmailAddrForUsage(handle, name, PR_FALSE,
-                                                        lookingForUsage);
+                                                        lookingForUsage, NULL);
+}
+
+CERTCertificate *
+CERT_FindCertByNicknameOrEmailAddrForUsageCX(CERTCertDBHandle *handle,
+                                             const char *name,
+                                             SECCertUsage lookingForUsage,
+                                             void *wincx)
+{
+    return common_FindCertByNicknameOrEmailAddrForUsage(handle, name, PR_FALSE,
+                                                        lookingForUsage, wincx);
 }
 
 static void
 add_to_subject_list(CERTCertList *certList, CERTCertificate *cert,
                     PRBool validOnly, PRTime sorttime)
 {
     SECStatus secrv;
     if (!validOnly ||
--- a/lib/nss/nss.def
+++ b/lib/nss/nss.def
@@ -1110,8 +1110,16 @@ CERT_GetCertIsPerm;
 CERT_GetCertIsTemp;
 PK11_FindCertFromURI;
 PK11_FindCertsFromURI;
 PK11_GetModuleURI;
 PK11_GetTokenURI;
 ;+    local:
 ;+       *;
 ;+};
+;+NSS_3.33 { 	# NSS 3.33 release
+;+    global:
+CERT_FindCertByIssuerAndSNCX;
+CERT_FindCertByNicknameOrEmailAddrCX;
+CERT_FindCertByNicknameOrEmailAddrForUsageCX;
+;+    local:
+;+       *;
+;+};