diff options
Diffstat (limited to 'nss/lib/certhigh/certhigh.c')
-rw-r--r-- | nss/lib/certhigh/certhigh.c | 1256 |
1 files changed, 636 insertions, 620 deletions
diff --git a/nss/lib/certhigh/certhigh.c b/nss/lib/certhigh/certhigh.c index b06b7af..5525989 100644 --- a/nss/lib/certhigh/certhigh.c +++ b/nss/lib/certhigh/certhigh.c @@ -17,36 +17,36 @@ #include "pkitm.h" #include "pki3hack.h" - PRBool -CERT_MatchNickname(char *name1, char *name2) { - char *nickname1= NULL; +CERT_MatchNickname(char *name1, char *name2) +{ + char *nickname1 = NULL; char *nickname2 = NULL; char *token1; char *token2; /* first deal with the straight comparison */ if (PORT_Strcmp(name1, name2) == 0) { - return PR_TRUE; + return PR_TRUE; } /* we need to handle the case where one name has an explicit token and the other * doesn't */ - token1 = PORT_Strchr(name1,':'); - token2 = PORT_Strchr(name2,':'); + token1 = PORT_Strchr(name1, ':'); + token2 = PORT_Strchr(name2, ':'); if ((token1 && token2) || (!token1 && !token2)) { - /* either both token names are specified or neither are, not match */ - return PR_FALSE; + /* either both token names are specified or neither are, not match */ + return PR_FALSE; } if (token1) { - nickname1=token1; - nickname2=name2; + nickname1 = token1; + nickname2 = name2; } else { - nickname1=token2; - nickname2=name1; + nickname1 = token2; + nickname2 = name1; } nickname1++; - if (PORT_Strcmp(nickname1,nickname2) != 0) { - return PR_FALSE; + if (PORT_Strcmp(nickname1, nickname2) != 0) { + return PR_FALSE; } /* Bug 1192443 - compare the other token with the internal slot here */ return PR_TRUE; @@ -54,20 +54,20 @@ CERT_MatchNickname(char *name1, char *name2) { /* * Find all user certificates that match the given criteria. - * - * "handle" - database to search - * "usage" - certificate usage to match - * "oneCertPerName" - if set then only return the "best" cert per - * name - * "validOnly" - only return certs that are curently valid - * "proto_win" - window handle passed to pkcs11 + * + * "handle" - database to search + * "usage" - certificate usage to match + * "oneCertPerName" - if set then only return the "best" cert per + * name + * "validOnly" - only return certs that are curently valid + * "proto_win" - window handle passed to pkcs11 */ CERTCertList * CERT_FindUserCertsByUsage(CERTCertDBHandle *handle, - SECCertUsage usage, - PRBool oneCertPerName, - PRBool validOnly, - void *proto_win) + SECCertUsage usage, + PRBool oneCertPerName, + PRBool validOnly, + void *proto_win) { CERTCertNicknames *nicknames = NULL; char **nnptr; @@ -79,267 +79,268 @@ CERT_FindUserCertsByUsage(CERTCertDBHandle *handle, CERTCertListNode *node = NULL; CERTCertListNode *freenode = NULL; int n; - + time = PR_Now(); - + nicknames = CERT_GetCertNicknames(handle, SEC_CERT_NICKNAMES_USER, - proto_win); - - if ( ( nicknames == NULL ) || ( nicknames->numnicknames == 0 ) ) { - goto loser; + proto_win); + + if ((nicknames == NULL) || (nicknames->numnicknames == 0)) { + goto loser; } nnptr = nicknames->nicknames; nn = nicknames->numnicknames; - while ( nn > 0 ) { - cert = NULL; - /* use the pk11 call so that we pick up any certs on tokens, - * which may require login - */ - if ( proto_win != NULL ) { - cert = PK11_FindCertFromNickname(*nnptr,proto_win); - } - - /* Sigh, It turns out if the cert is already in the temp db, because - * it's in the perm db, then the nickname lookup doesn't work. - * since we already have the cert here, though, than we can just call - * CERT_CreateSubjectCertList directly. For those cases where we didn't - * find the cert in pkcs #11 (because we didn't have a password arg, - * or because the nickname is for a peer, server, or CA cert, then we - * go look the cert up. - */ - if (cert == NULL) { - cert = CERT_FindCertByNickname(handle,*nnptr); - } - - if ( cert != NULL ) { - /* collect certs for this nickname, sorting them into the list */ - certList = CERT_CreateSubjectCertList(certList, handle, - &cert->derSubject, time, validOnly); - - CERT_FilterCertListForUserCerts(certList); - - /* drop the extra reference */ - CERT_DestroyCertificate(cert); - } - - nnptr++; - nn--; + while (nn > 0) { + cert = NULL; + /* use the pk11 call so that we pick up any certs on tokens, + * which may require login + */ + if (proto_win != NULL) { + cert = PK11_FindCertFromNickname(*nnptr, proto_win); + } + + /* Sigh, It turns out if the cert is already in the temp db, because + * it's in the perm db, then the nickname lookup doesn't work. + * since we already have the cert here, though, than we can just call + * CERT_CreateSubjectCertList directly. For those cases where we didn't + * find the cert in pkcs #11 (because we didn't have a password arg, + * or because the nickname is for a peer, server, or CA cert, then we + * go look the cert up. + */ + if (cert == NULL) { + cert = CERT_FindCertByNickname(handle, *nnptr); + } + + if (cert != NULL) { + /* collect certs for this nickname, sorting them into the list */ + certList = CERT_CreateSubjectCertList(certList, handle, + &cert->derSubject, time, validOnly); + + CERT_FilterCertListForUserCerts(certList); + + /* drop the extra reference */ + CERT_DestroyCertificate(cert); + } + + nnptr++; + nn--; } /* remove certs with incorrect usage */ rv = CERT_FilterCertListByUsage(certList, usage, PR_FALSE); - if ( rv != SECSuccess ) { - goto loser; + if (rv != SECSuccess) { + goto loser; } /* remove any extra certs for each name */ - if ( oneCertPerName ) { - PRBool *flags; - - nn = nicknames->numnicknames; - nnptr = nicknames->nicknames; - - flags = (PRBool *)PORT_ZAlloc(sizeof(PRBool) * nn); - if ( flags == NULL ) { - goto loser; - } - - node = CERT_LIST_HEAD(certList); - - /* treverse all certs in the list */ - while ( !CERT_LIST_END(node, certList) ) { - - /* find matching nickname index */ - for ( n = 0; n < nn; n++ ) { - if ( CERT_MatchNickname(nnptr[n], node->cert->nickname) ) { - /* We found a match. If this is the first one, then - * set the flag and move on to the next cert. If this - * is not the first one then delete it from the list. - */ - if ( flags[n] ) { - /* We have already seen a cert with this nickname, - * so delete this one. - */ - freenode = node; - node = CERT_LIST_NEXT(node); - CERT_RemoveCertListNode(freenode); - } else { - /* keep the first cert for each nickname, but set the - * flag so we know to delete any others with the same - * nickname. - */ - flags[n] = PR_TRUE; - node = CERT_LIST_NEXT(node); - } - break; - } - } - if ( n == nn ) { - /* if we get here it means that we didn't find a matching - * nickname, which should not happen. - */ - PORT_Assert(0); - node = CERT_LIST_NEXT(node); - } - } - PORT_Free(flags); + if (oneCertPerName) { + PRBool *flags; + + nn = nicknames->numnicknames; + nnptr = nicknames->nicknames; + + if (!certList) { + goto loser; + } + + flags = (PRBool *)PORT_ZAlloc(sizeof(PRBool) * nn); + if (flags == NULL) { + goto loser; + } + + node = CERT_LIST_HEAD(certList); + + /* treverse all certs in the list */ + while (!CERT_LIST_END(node, certList)) { + + /* find matching nickname index */ + for (n = 0; n < nn; n++) { + if (CERT_MatchNickname(nnptr[n], node->cert->nickname)) { + /* We found a match. If this is the first one, then + * set the flag and move on to the next cert. If this + * is not the first one then delete it from the list. + */ + if (flags[n]) { + /* We have already seen a cert with this nickname, + * so delete this one. + */ + freenode = node; + node = CERT_LIST_NEXT(node); + CERT_RemoveCertListNode(freenode); + } else { + /* keep the first cert for each nickname, but set the + * flag so we know to delete any others with the same + * nickname. + */ + flags[n] = PR_TRUE; + node = CERT_LIST_NEXT(node); + } + break; + } + } + if (n == nn) { + /* if we get here it means that we didn't find a matching + * nickname, which should not happen. + */ + PORT_Assert(0); + node = CERT_LIST_NEXT(node); + } + } + PORT_Free(flags); } goto done; - + loser: - if ( certList != NULL ) { - CERT_DestroyCertList(certList); - certList = NULL; + if (certList != NULL) { + CERT_DestroyCertList(certList); + certList = NULL; } done: - if ( nicknames != NULL ) { - CERT_FreeNicknames(nicknames); + if (nicknames != NULL) { + CERT_FreeNicknames(nicknames); } - return(certList); + return (certList); } /* * Find a user certificate that matchs the given criteria. - * - * "handle" - database to search - * "nickname" - nickname to match - * "usage" - certificate usage to match - * "validOnly" - only return certs that are curently valid - * "proto_win" - window handle passed to pkcs11 + * + * "handle" - database to search + * "nickname" - nickname to match + * "usage" - certificate usage to match + * "validOnly" - only return certs that are curently valid + * "proto_win" - window handle passed to pkcs11 */ CERTCertificate * CERT_FindUserCertByUsage(CERTCertDBHandle *handle, - const char *nickname, - SECCertUsage usage, - PRBool validOnly, - void *proto_win) + const char *nickname, + SECCertUsage usage, + PRBool validOnly, + void *proto_win) { CERTCertificate *cert = NULL; CERTCertList *certList = NULL; SECStatus rv; PRTime time; - + time = PR_Now(); - + /* use the pk11 call so that we pick up any certs on tokens, * which may require login */ /* XXX - why is this restricted? */ - if ( proto_win != NULL ) { - cert = PK11_FindCertFromNickname(nickname,proto_win); + if (proto_win != NULL) { + cert = PK11_FindCertFromNickname(nickname, proto_win); } - /* sigh, There are still problems find smart cards from the temp * db. This will get smart cards working again. The real fix * is to make sure we can search the temp db by their token nickname. */ if (cert == NULL) { - cert = CERT_FindCertByNickname(handle,nickname); + cert = CERT_FindCertByNickname(handle, nickname); } - if ( cert != NULL ) { - unsigned int requiredKeyUsage; - unsigned int requiredCertType; - - rv = CERT_KeyUsageAndTypeForCertUsage(usage, PR_FALSE, - &requiredKeyUsage, &requiredCertType); - if ( rv != SECSuccess ) { - /* drop the extra reference */ - CERT_DestroyCertificate(cert); - cert = NULL; - goto loser; - } - /* If we already found the right cert, just return it */ - if ( (!validOnly || CERT_CheckCertValidTimes(cert, time, PR_FALSE) - == secCertTimeValid) && - (CERT_CheckKeyUsage(cert, requiredKeyUsage) == SECSuccess) && - (cert->nsCertType & requiredCertType) && - CERT_IsUserCert(cert) ) { - return(cert); - } - - /* collect certs for this nickname, sorting them into the list */ - certList = CERT_CreateSubjectCertList(certList, handle, - &cert->derSubject, time, validOnly); - - CERT_FilterCertListForUserCerts(certList); - - /* drop the extra reference */ - CERT_DestroyCertificate(cert); - cert = NULL; + if (cert != NULL) { + unsigned int requiredKeyUsage; + unsigned int requiredCertType; + + rv = CERT_KeyUsageAndTypeForCertUsage(usage, PR_FALSE, + &requiredKeyUsage, &requiredCertType); + if (rv != SECSuccess) { + /* drop the extra reference */ + CERT_DestroyCertificate(cert); + cert = NULL; + goto loser; + } + /* If we already found the right cert, just return it */ + if ((!validOnly || CERT_CheckCertValidTimes(cert, time, PR_FALSE) == secCertTimeValid) && + (CERT_CheckKeyUsage(cert, requiredKeyUsage) == SECSuccess) && + (cert->nsCertType & requiredCertType) && + CERT_IsUserCert(cert)) { + return (cert); + } + + /* collect certs for this nickname, sorting them into the list */ + certList = CERT_CreateSubjectCertList(certList, handle, + &cert->derSubject, time, validOnly); + + CERT_FilterCertListForUserCerts(certList); + + /* drop the extra reference */ + CERT_DestroyCertificate(cert); + cert = NULL; } - - if ( certList == NULL ) { - goto loser; + + if (certList == NULL) { + goto loser; } - + /* remove certs with incorrect usage */ rv = CERT_FilterCertListByUsage(certList, usage, PR_FALSE); - if ( rv != SECSuccess ) { - goto loser; + if (rv != SECSuccess) { + goto loser; } - if ( ! CERT_LIST_END(CERT_LIST_HEAD(certList), certList) ) { - cert = CERT_DupCertificate(CERT_LIST_HEAD(certList)->cert); + if (!CERT_LIST_END(CERT_LIST_HEAD(certList), certList)) { + cert = CERT_DupCertificate(CERT_LIST_HEAD(certList)->cert); } - + loser: - if ( certList != NULL ) { - CERT_DestroyCertList(certList); + if (certList != NULL) { + CERT_DestroyCertList(certList); } - return(cert); + return (cert); } CERTCertList * CERT_MatchUserCert(CERTCertDBHandle *handle, - SECCertUsage usage, - int nCANames, char **caNames, - void *proto_win) + SECCertUsage usage, + int nCANames, char **caNames, + void *proto_win) { CERTCertList *certList = NULL; SECStatus rv; certList = CERT_FindUserCertsByUsage(handle, usage, PR_TRUE, PR_TRUE, - proto_win); - if ( certList == NULL ) { - goto loser; + proto_win); + if (certList == NULL) { + goto loser; } - + rv = CERT_FilterCertListByCANames(certList, nCANames, caNames, usage); - if ( rv != SECSuccess ) { - goto loser; + if (rv != SECSuccess) { + goto loser; } - + goto done; - + loser: - if ( certList != NULL ) { - CERT_DestroyCertList(certList); - certList = NULL; + if (certList != NULL) { + CERT_DestroyCertList(certList); + certList = NULL; } done: - return(certList); + return (certList); } - typedef struct stringNode { struct stringNode *next; char *string; } stringNode; - + static PRStatus -CollectNicknames( NSSCertificate *c, void *data) +CollectNicknames(NSSCertificate *c, void *data) { CERTCertNicknames *names; PRBool saveit = PR_FALSE; @@ -351,103 +352,104 @@ CollectNicknames( NSSCertificate *c, void *data) #endif char *stanNickname; char *nickname = NULL; - + names = (CERTCertNicknames *)data; - stanNickname = nssCertificate_GetNickname(c,NULL); - - if ( stanNickname ) { + stanNickname = nssCertificate_GetNickname(c, NULL); + + if (stanNickname) { nss_ZFreeIf(stanNickname); stanNickname = NULL; - if (names->what == SEC_CERT_NICKNAMES_USER) { - saveit = NSSCertificate_IsPrivateKeyAvailable(c, NULL, NULL); - } + if (names->what == SEC_CERT_NICKNAMES_USER) { + saveit = NSSCertificate_IsPrivateKeyAvailable(c, NULL, NULL); + } #ifdef notdef - else { - td = NSSCertificate_GetTrustDomain(c); - if (!td) { - return PR_SUCCESS; - } - trust = nssTrustDomain_FindTrustForCertificate(td,c); - - switch(names->what) { - case SEC_CERT_NICKNAMES_ALL: - if ((trust->sslFlags & (CERTDB_VALID_CA|CERTDB_VALID_PEER) ) || - (trust->emailFlags & (CERTDB_VALID_CA|CERTDB_VALID_PEER) ) || - (trust->objectSigningFlags & - (CERTDB_VALID_CA|CERTDB_VALID_PEER))) { - saveit = PR_TRUE; - } - - break; - case SEC_CERT_NICKNAMES_SERVER: - if ( trust->sslFlags & CERTDB_VALID_PEER ) { - saveit = PR_TRUE; - } - - break; - case SEC_CERT_NICKNAMES_CA: - if (((trust->sslFlags & CERTDB_VALID_CA ) == CERTDB_VALID_CA)|| - ((trust->emailFlags & CERTDB_VALID_CA ) == CERTDB_VALID_CA) || - ((trust->objectSigningFlags & CERTDB_VALID_CA ) - == CERTDB_VALID_CA)) { - saveit = PR_TRUE; - } - break; - } - } + else { + td = NSSCertificate_GetTrustDomain(c); + if (!td) { + return PR_SUCCESS; + } + trust = nssTrustDomain_FindTrustForCertificate(td, c); + + switch (names->what) { + case SEC_CERT_NICKNAMES_ALL: + if ((trust->sslFlags & (CERTDB_VALID_CA | CERTDB_VALID_PEER)) || + (trust->emailFlags & (CERTDB_VALID_CA | CERTDB_VALID_PEER)) || + (trust->objectSigningFlags & + (CERTDB_VALID_CA | CERTDB_VALID_PEER))) { + saveit = PR_TRUE; + } + + break; + case SEC_CERT_NICKNAMES_SERVER: + if (trust->sslFlags & CERTDB_VALID_PEER) { + saveit = PR_TRUE; + } + + break; + case SEC_CERT_NICKNAMES_CA: + if (((trust->sslFlags & CERTDB_VALID_CA) == CERTDB_VALID_CA) || + ((trust->emailFlags & CERTDB_VALID_CA) == CERTDB_VALID_CA) || + ((trust->objectSigningFlags & CERTDB_VALID_CA) == + CERTDB_VALID_CA)) { + saveit = PR_TRUE; + } + break; + } + } #endif } /* traverse the list of collected nicknames and make sure we don't make * a duplicate */ - if ( saveit ) { - nickname = STAN_GetCERTCertificateName(NULL, c); - /* nickname can only be NULL here if we are having memory - * alloc problems */ - if (nickname == NULL) { - return PR_FAILURE; - } - node = (stringNode *)names->head; - while ( node != NULL ) { - if ( PORT_Strcmp(nickname, node->string) == 0 ) { - /* if the string matches, then don't save this one */ - saveit = PR_FALSE; - break; - } - node = node->next; - } + if (saveit) { + nickname = STAN_GetCERTCertificateName(NULL, c); + /* nickname can only be NULL here if we are having memory + * alloc problems */ + if (nickname == NULL) { + return PR_FAILURE; + } + node = (stringNode *)names->head; + while (node != NULL) { + if (PORT_Strcmp(nickname, node->string) == 0) { + /* if the string matches, then don't save this one */ + saveit = PR_FALSE; + break; + } + node = node->next; + } } - if ( saveit ) { - - /* allocate the node */ - node = (stringNode*)PORT_ArenaAlloc(names->arena, sizeof(stringNode)); - if ( node == NULL ) { - PORT_Free(nickname); - return PR_FAILURE; - } - - /* copy the string */ - len = PORT_Strlen(nickname) + 1; - node->string = (char*)PORT_ArenaAlloc(names->arena, len); - if ( node->string == NULL ) { - PORT_Free(nickname); - return PR_FAILURE; - } - PORT_Memcpy(node->string, nickname, len); - - /* link it into the list */ - node->next = (stringNode *)names->head; - names->head = (void *)node; - - /* bump the count */ - names->numnicknames++; + if (saveit) { + + /* allocate the node */ + node = (stringNode *)PORT_ArenaAlloc(names->arena, sizeof(stringNode)); + if (node == NULL) { + PORT_Free(nickname); + return PR_FAILURE; + } + + /* copy the string */ + len = PORT_Strlen(nickname) + 1; + node->string = (char *)PORT_ArenaAlloc(names->arena, len); + if (node->string == NULL) { + PORT_Free(nickname); + return PR_FAILURE; + } + PORT_Memcpy(node->string, nickname, len); + + /* link it into the list */ + node->next = (stringNode *)names->head; + names->head = (void *)node; + + /* bump the count */ + names->numnicknames++; } - - if (nickname) PORT_Free(nickname); - return(PR_SUCCESS); + + if (nickname) + PORT_Free(nickname); + return (PR_SUCCESS); } CERTCertNicknames * @@ -457,16 +459,16 @@ CERT_GetCertNicknames(CERTCertDBHandle *handle, int what, void *wincx) CERTCertNicknames *names; int i; stringNode *node; - + arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if ( arena == NULL ) { - PORT_SetError(SEC_ERROR_NO_MEMORY); - return(NULL); + if (arena == NULL) { + PORT_SetError(SEC_ERROR_NO_MEMORY); + return (NULL); } - + names = (CERTCertNicknames *)PORT_ArenaAlloc(arena, sizeof(CERTCertNicknames)); - if ( names == NULL ) { - goto loser; + if (names == NULL) { + goto loser; } names->arena = arena; @@ -477,43 +479,44 @@ CERT_GetCertNicknames(CERTCertDBHandle *handle, int what, void *wincx) names->totallen = 0; /* make sure we are logged in */ - (void) pk11_TraverseAllSlots(NULL, NULL, PR_TRUE, wincx); - + (void)pk11_TraverseAllSlots(NULL, NULL, PR_TRUE, wincx); + NSSTrustDomain_TraverseCertificates(handle, - CollectNicknames, (void *)names); - if ( names->numnicknames ) { - names->nicknames = (char**)PORT_ArenaAlloc(arena, - names->numnicknames * sizeof(char *)); - - if ( names->nicknames == NULL ) { - goto loser; - } - - node = (stringNode *)names->head; - - for ( i = 0; i < names->numnicknames; i++ ) { - PORT_Assert(node != NULL); - - names->nicknames[i] = node->string; - names->totallen += PORT_Strlen(node->string); - node = node->next; - } - - PORT_Assert(node == NULL); + CollectNicknames, (void *)names); + if (names->numnicknames) { + names->nicknames = (char **)PORT_ArenaAlloc(arena, + names->numnicknames * + sizeof(char *)); + + if (names->nicknames == NULL) { + goto loser; + } + + node = (stringNode *)names->head; + + for (i = 0; i < names->numnicknames; i++) { + PORT_Assert(node != NULL); + + names->nicknames[i] = node->string; + names->totallen += PORT_Strlen(node->string); + node = node->next; + } + + PORT_Assert(node == NULL); } - return(names); - + return (names); + loser: PORT_FreeArena(arena, PR_FALSE); - return(NULL); + return (NULL); } void CERT_FreeNicknames(CERTCertNicknames *nicknames) { PORT_FreeArena(nicknames->arena, PR_FALSE); - + return; } @@ -528,53 +531,53 @@ void CERT_FreeDistNames(CERTDistNames *names) { PORT_FreeArena(names->arena, PR_FALSE); - + return; } static SECStatus -CollectDistNames( CERTCertificate *cert, SECItem *k, void *data) +CollectDistNames(CERTCertificate *cert, SECItem *k, void *data) { CERTDistNames *names; PRBool saveit = PR_FALSE; CERTCertTrust trust; dnameNode *node; int len; - + names = (CERTDistNames *)data; - - if ( CERT_GetCertTrust(cert, &trust) == SECSuccess ) { - /* only collect names of CAs trusted for issuing SSL clients */ - if ( trust.sslFlags & CERTDB_TRUSTED_CLIENT_CA ) { - saveit = PR_TRUE; - } + + if (CERT_GetCertTrust(cert, &trust) == SECSuccess) { + /* only collect names of CAs trusted for issuing SSL clients */ + if (trust.sslFlags & CERTDB_TRUSTED_CLIENT_CA) { + saveit = PR_TRUE; + } } - if ( saveit ) { - /* allocate the node */ - node = (dnameNode*)PORT_ArenaAlloc(names->arena, sizeof(dnameNode)); - if ( node == NULL ) { - return(SECFailure); - } - - /* copy the name */ - node->name.len = len = cert->derSubject.len; - node->name.type = siBuffer; - node->name.data = (unsigned char*)PORT_ArenaAlloc(names->arena, len); - if ( node->name.data == NULL ) { - return(SECFailure); - } - PORT_Memcpy(node->name.data, cert->derSubject.data, len); - - /* link it into the list */ - node->next = (dnameNode *)names->head; - names->head = (void *)node; - - /* bump the count */ - names->nnames++; + if (saveit) { + /* allocate the node */ + node = (dnameNode *)PORT_ArenaAlloc(names->arena, sizeof(dnameNode)); + if (node == NULL) { + return (SECFailure); + } + + /* copy the name */ + node->name.len = len = cert->derSubject.len; + node->name.type = siBuffer; + node->name.data = (unsigned char *)PORT_ArenaAlloc(names->arena, len); + if (node->name.data == NULL) { + return (SECFailure); + } + PORT_Memcpy(node->name.data, cert->derSubject.data, len); + + /* link it into the list */ + node->next = (dnameNode *)names->head; + names->head = (void *)node; + + /* bump the count */ + names->nnames++; } - - return(SECSuccess); + + return (SECSuccess); } /* @@ -587,18 +590,18 @@ CERT_DupDistNames(CERTDistNames *orig) CERTDistNames *names; int i; SECStatus rv; - + /* allocate an arena to use */ arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); if (arena == NULL) { - PORT_SetError(SEC_ERROR_NO_MEMORY); - return(NULL); + PORT_SetError(SEC_ERROR_NO_MEMORY); + return (NULL); } - + /* allocate the header structure */ names = (CERTDistNames *)PORT_ArenaAlloc(arena, sizeof(CERTDistNames)); if (names == NULL) { - goto loser; + goto loser; } /* initialize the header struct */ @@ -606,26 +609,26 @@ CERT_DupDistNames(CERTDistNames *orig) names->head = NULL; names->nnames = orig->nnames; names->names = NULL; - + /* construct the array from the list */ if (orig->nnames) { - names->names = (SECItem*)PORT_ArenaNewArray(arena, SECItem, - orig->nnames); - if (names->names == NULL) { - goto loser; - } - for (i = 0; i < orig->nnames; i++) { + names->names = (SECItem *)PORT_ArenaNewArray(arena, SECItem, + orig->nnames); + if (names->names == NULL) { + goto loser; + } + for (i = 0; i < orig->nnames; i++) { rv = SECITEM_CopyItem(arena, &names->names[i], &orig->names[i]); if (rv != SECSuccess) { goto loser; } } } - return(names); - + return (names); + loser: PORT_FreeArena(arena, PR_FALSE); - return(NULL); + return (NULL); } CERTDistNames * @@ -636,18 +639,18 @@ CERT_GetSSLCACerts(CERTCertDBHandle *handle) int i; SECStatus rv; dnameNode *node; - + /* allocate an arena to use */ arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if ( arena == NULL ) { - PORT_SetError(SEC_ERROR_NO_MEMORY); - return(NULL); + if (arena == NULL) { + PORT_SetError(SEC_ERROR_NO_MEMORY); + return (NULL); } - + /* allocate the header structure */ names = (CERTDistNames *)PORT_ArenaAlloc(arena, sizeof(CERTDistNames)); - if ( names == NULL ) { - goto loser; + if (names == NULL) { + goto loser; } /* initialize the header struct */ @@ -655,48 +658,48 @@ CERT_GetSSLCACerts(CERTCertDBHandle *handle) names->head = NULL; names->nnames = 0; names->names = NULL; - + /* collect the names from the database */ rv = PK11_TraverseSlotCerts(CollectDistNames, (void *)names, NULL); - if ( rv ) { - goto loser; + if (rv) { + goto loser; } /* construct the array from the list */ - if ( names->nnames ) { - names->names = (SECItem*)PORT_ArenaAlloc(arena, names->nnames * sizeof(SECItem)); - - if ( names->names == NULL ) { - goto loser; - } - - node = (dnameNode *)names->head; - - for ( i = 0; i < names->nnames; i++ ) { - PORT_Assert(node != NULL); - - names->names[i] = node->name; - node = node->next; - } - - PORT_Assert(node == NULL); + if (names->nnames) { + names->names = (SECItem *)PORT_ArenaAlloc(arena, names->nnames * sizeof(SECItem)); + + if (names->names == NULL) { + goto loser; + } + + node = (dnameNode *)names->head; + + for (i = 0; i < names->nnames; i++) { + PORT_Assert(node != NULL); + + names->names[i] = node->name; + node = node->next; + } + + PORT_Assert(node == NULL); } - return(names); - + return (names); + loser: PORT_FreeArena(arena, PR_FALSE); - return(NULL); + return (NULL); } CERTDistNames * CERT_DistNamesFromCertList(CERTCertList *certList) { - CERTDistNames * dnames = NULL; - PLArenaPool * arena; + CERTDistNames *dnames = NULL; + PLArenaPool *arena; CERTCertListNode *node = NULL; - SECItem * names = NULL; - int listLen = 0, i = 0; + SECItem *names = NULL; + int listLen = 0, i = 0; if (certList == NULL) { PORT_SetError(SEC_ERROR_INVALID_ARGS); @@ -704,23 +707,26 @@ CERT_DistNamesFromCertList(CERTCertList *certList) } node = CERT_LIST_HEAD(certList); - while ( ! CERT_LIST_END(node, certList) ) { + while (!CERT_LIST_END(node, certList)) { listLen += 1; node = CERT_LIST_NEXT(node); } - + arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if (arena == NULL) goto loser; + if (arena == NULL) + goto loser; dnames = PORT_ArenaZNew(arena, CERTDistNames); - if (dnames == NULL) goto loser; + if (dnames == NULL) + goto loser; dnames->arena = arena; dnames->nnames = listLen; dnames->names = names = PORT_ArenaZNewArray(arena, SECItem, listLen); - if (names == NULL) goto loser; + if (names == NULL) + goto loser; node = CERT_LIST_HEAD(certList); - while ( ! CERT_LIST_END(node, certList) ) { + while (!CERT_LIST_END(node, certList)) { CERTCertificate *cert = node->cert; SECStatus rv = SECITEM_CopyItem(arena, &names[i++], &cert->derSubject); if (rv == SECFailure) { @@ -738,38 +744,43 @@ loser: CERTDistNames * CERT_DistNamesFromNicknames(CERTCertDBHandle *handle, char **nicknames, - int nnames) + int nnames) { CERTDistNames *dnames = NULL; PLArenaPool *arena; int i, rv; SECItem *names = NULL; CERTCertificate *cert = NULL; - + arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if (arena == NULL) goto loser; + if (arena == NULL) + goto loser; dnames = PORT_ArenaZNew(arena, CERTDistNames); - if (dnames == NULL) goto loser; + if (dnames == NULL) + goto loser; dnames->arena = arena; dnames->nnames = nnames; dnames->names = names = PORT_ArenaZNewArray(arena, SECItem, nnames); - if (names == NULL) goto loser; - + if (names == NULL) + goto loser; + for (i = 0; i < nnames; i++) { - cert = CERT_FindCertByNicknameOrEmailAddr(handle, nicknames[i]); - if (cert == NULL) goto loser; - rv = SECITEM_CopyItem(arena, &names[i], &cert->derSubject); - if (rv == SECFailure) goto loser; - CERT_DestroyCertificate(cert); + cert = CERT_FindCertByNicknameOrEmailAddr(handle, nicknames[i]); + if (cert == NULL) + goto loser; + rv = SECITEM_CopyItem(arena, &names[i], &cert->derSubject); + if (rv == SECFailure) + goto loser; + CERT_DestroyCertificate(cert); } return dnames; - + loser: if (cert != NULL) - CERT_DestroyCertificate(cert); + CERT_DestroyCertificate(cert); if (arena != NULL) - PORT_FreeArena(arena, PR_FALSE); + PORT_FreeArena(arena, PR_FALSE); return NULL; } @@ -784,36 +795,36 @@ CERT_FindCertByNameString(CERTCertDBHandle *handle, char *nameStr) SECItem *nameItem; CERTCertificate *cert = NULL; PLArenaPool *arena = NULL; - + arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - - if ( arena == NULL ) { - goto loser; + + if (arena == NULL) { + goto loser; } - + name = CERT_AsciiToName(nameStr); - - if ( name ) { - nameItem = SEC_ASN1EncodeItem (arena, NULL, (void *)name, - CERT_NameTemplate); - if ( nameItem != NULL ) { + + if (name) { + nameItem = SEC_ASN1EncodeItem(arena, NULL, (void *)name, + CERT_NameTemplate); + if (nameItem != NULL) { cert = CERT_FindCertByName(handle, nameItem); - } - CERT_DestroyName(name); + } + CERT_DestroyName(name); } loser: - if ( arena ) { - PORT_FreeArena(arena, PR_FALSE); + if (arena) { + PORT_FreeArena(arena, PR_FALSE); } - - return(cert); + + return (cert); } /* From certv3.c */ CERTCrlDistributionPoints * -CERT_FindCRLDistributionPoints (CERTCertificate *cert) +CERT_FindCRLDistributionPoints(CERTCertificate *cert) { SECItem encodedExtenValue; SECStatus rv; @@ -823,9 +834,9 @@ CERT_FindCRLDistributionPoints (CERTCertificate *cert) encodedExtenValue.len = 0; rv = cert_FindExtension(cert->extensions, SEC_OID_X509_CRL_DIST_POINTS, - &encodedExtenValue); - if ( rv != SECSuccess ) { - return (NULL); + &encodedExtenValue); + if (rv != SECSuccess) { + return (NULL); } dps = CERT_DecodeCRLDistributionPoints(cert->arena, &encodedExtenValue); @@ -836,13 +847,13 @@ CERT_FindCRLDistributionPoints (CERTCertificate *cert) } /* From crl.c */ -CERTSignedCrl * CERT_ImportCRL - (CERTCertDBHandle *handle, SECItem *derCRL, char *url, int type, void *wincx) +CERTSignedCrl * +CERT_ImportCRL(CERTCertDBHandle *handle, SECItem *derCRL, char *url, int type, void *wincx) { - CERTSignedCrl* retCrl = NULL; - PK11SlotInfo* slot = PK11_GetInternalKeySlot(); + CERTSignedCrl *retCrl = NULL; + PK11SlotInfo *slot = PK11_GetInternalKeySlot(); retCrl = PK11_ImportCRL(slot, derCRL, url, type, wincx, - CRL_IMPORT_DEFAULT_OPTIONS, NULL, CRL_DECODE_DEFAULT_OPTIONS); + CRL_IMPORT_DEFAULT_OPTIONS, NULL, CRL_DECODE_DEFAULT_OPTIONS); PK11_FreeSlot(slot); return retCrl; @@ -861,110 +872,109 @@ cert_ImportCAChain(SECItem *certs, int numcerts, SECCertUsage certUsage, PRBool PRBool isca; char *nickname; unsigned int certtype; - + handle = CERT_GetDefaultCertDB(); - + while (numcerts--) { - derCert = certs; - certs++; - - /* decode my certificate */ - /* This use is ok -- only looks at decoded parts, calls NewTemp later */ - newcert = CERT_DecodeDERCertificate(derCert, PR_FALSE, NULL); - if ( newcert == NULL ) { - goto loser; - } - - if (!trusted) { - /* make sure that cert is valid */ - rv = CERT_CertTimesValid(newcert); - if ( rv == SECFailure ) { - goto endloop; - } - } - - /* does it have the CA extension */ - - /* - * Make sure that if this is an intermediate CA in the chain that - * it was given permission by its signer to be a CA. - */ - isca = CERT_IsCACert(newcert, &certtype); - - if ( !isca ) { - if (!trusted) { - goto endloop; - } - trust.sslFlags = CERTDB_VALID_CA; - trust.emailFlags = CERTDB_VALID_CA; - trust.objectSigningFlags = CERTDB_VALID_CA; - } else { - /* SSL ca's must have the ssl bit set */ - if ( ( certUsage == certUsageSSLCA ) && - (( certtype & NS_CERT_TYPE_SSL_CA ) != NS_CERT_TYPE_SSL_CA )) { - goto endloop; - } - - /* it passed all of the tests, so lets add it to the database */ - /* mark it as a CA */ - PORT_Memset((void *)&trust, 0, sizeof(trust)); - switch ( certUsage ) { - case certUsageSSLCA: - trust.sslFlags = CERTDB_VALID_CA; - break; - case certUsageUserCertImport: - if ((certtype & NS_CERT_TYPE_SSL_CA) == NS_CERT_TYPE_SSL_CA) { - trust.sslFlags = CERTDB_VALID_CA; - } - if ((certtype & NS_CERT_TYPE_EMAIL_CA) - == NS_CERT_TYPE_EMAIL_CA ) { - trust.emailFlags = CERTDB_VALID_CA; - } - if ( ( certtype & NS_CERT_TYPE_OBJECT_SIGNING_CA ) == - NS_CERT_TYPE_OBJECT_SIGNING_CA ) { - trust.objectSigningFlags = CERTDB_VALID_CA; - } - break; - default: - PORT_Assert(0); - break; - } - } - - cert = CERT_NewTempCertificate(handle, derCert, NULL, - PR_FALSE, PR_FALSE); - if ( cert == NULL ) { - goto loser; - } - - /* if the cert is temp, make it perm; otherwise we're done */ - if (cert->istemp) { - /* get a default nickname for it */ - nickname = CERT_MakeCANickname(cert); - - rv = CERT_AddTempCertToPerm(cert, nickname, &trust); - - /* free the nickname */ - if ( nickname ) { - PORT_Free(nickname); - } - } else { - rv = SECSuccess; - } - - CERT_DestroyCertificate(cert); - cert = NULL; - - if ( rv != SECSuccess ) { - goto loser; - } - -endloop: - if ( newcert ) { - CERT_DestroyCertificate(newcert); - newcert = NULL; - } - + derCert = certs; + certs++; + + /* decode my certificate */ + /* This use is ok -- only looks at decoded parts, calls NewTemp later */ + newcert = CERT_DecodeDERCertificate(derCert, PR_FALSE, NULL); + if (newcert == NULL) { + goto loser; + } + + if (!trusted) { + /* make sure that cert is valid */ + rv = CERT_CertTimesValid(newcert); + if (rv == SECFailure) { + goto endloop; + } + } + + /* does it have the CA extension */ + + /* + * Make sure that if this is an intermediate CA in the chain that + * it was given permission by its signer to be a CA. + */ + isca = CERT_IsCACert(newcert, &certtype); + + if (!isca) { + if (!trusted) { + goto endloop; + } + trust.sslFlags = CERTDB_VALID_CA; + trust.emailFlags = CERTDB_VALID_CA; + trust.objectSigningFlags = CERTDB_VALID_CA; + } else { + /* SSL ca's must have the ssl bit set */ + if ((certUsage == certUsageSSLCA) && + ((certtype & NS_CERT_TYPE_SSL_CA) != NS_CERT_TYPE_SSL_CA)) { + goto endloop; + } + + /* it passed all of the tests, so lets add it to the database */ + /* mark it as a CA */ + PORT_Memset((void *)&trust, 0, sizeof(trust)); + switch (certUsage) { + case certUsageSSLCA: + trust.sslFlags = CERTDB_VALID_CA; + break; + case certUsageUserCertImport: + if ((certtype & NS_CERT_TYPE_SSL_CA) == NS_CERT_TYPE_SSL_CA) { + trust.sslFlags = CERTDB_VALID_CA; + } + if ((certtype & NS_CERT_TYPE_EMAIL_CA) == + NS_CERT_TYPE_EMAIL_CA) { + trust.emailFlags = CERTDB_VALID_CA; + } + if ((certtype & NS_CERT_TYPE_OBJECT_SIGNING_CA) == + NS_CERT_TYPE_OBJECT_SIGNING_CA) { + trust.objectSigningFlags = CERTDB_VALID_CA; + } + break; + default: + PORT_Assert(0); + break; + } + } + + cert = CERT_NewTempCertificate(handle, derCert, NULL, + PR_FALSE, PR_FALSE); + if (cert == NULL) { + goto loser; + } + + /* if the cert is temp, make it perm; otherwise we're done */ + if (cert->istemp) { + /* get a default nickname for it */ + nickname = CERT_MakeCANickname(cert); + + rv = CERT_AddTempCertToPerm(cert, nickname, &trust); + + /* free the nickname */ + if (nickname) { + PORT_Free(nickname); + } + } else { + rv = SECSuccess; + } + + CERT_DestroyCertificate(cert); + cert = NULL; + + if (rv != SECSuccess) { + goto loser; + } + + endloop: + if (newcert) { + CERT_DestroyCertificate(newcert); + newcert = NULL; + } } rv = SECSuccess; @@ -972,18 +982,18 @@ endloop: loser: rv = SECFailure; done: - - if ( newcert ) { - CERT_DestroyCertificate(newcert); - newcert = NULL; + + if (newcert) { + CERT_DestroyCertificate(newcert); + newcert = NULL; } - - if ( cert ) { - CERT_DestroyCertificate(cert); - cert = NULL; + + if (cert) { + CERT_DestroyCertificate(cert); + cert = NULL; } - - return(rv); + + return (rv); } SECStatus @@ -993,7 +1003,8 @@ CERT_ImportCAChain(SECItem *certs, int numcerts, SECCertUsage certUsage) } SECStatus -CERT_ImportCAChainTrusted(SECItem *certs, int numcerts, SECCertUsage certUsage) { +CERT_ImportCAChainTrusted(SECItem *certs, int numcerts, SECCertUsage certUsage) +{ return cert_ImportCAChain(certs, numcerts, certUsage, PR_TRUE); } @@ -1014,7 +1025,7 @@ typedef struct certNode { CERTCertificateList * CERT_CertChainFromCert(CERTCertificate *cert, SECCertUsage usage, - PRBool includeRoot) + PRBool includeRoot) { CERTCertificateList *chain = NULL; NSSCertificate **stanChain; @@ -1022,7 +1033,7 @@ CERT_CertChainFromCert(CERTCertificate *cert, SECCertUsage usage, PLArenaPool *arena; NSSUsage nssUsage; int i, len; - NSSTrustDomain *td = STAN_GetDefaultTrustDomain(); + NSSTrustDomain *td = STAN_GetDefaultTrustDomain(); NSSCryptoContext *cc = STAN_GetDefaultCryptoContext(); stanCert = STAN_GetNSSCertificate(cert); @@ -1034,55 +1045,57 @@ CERT_CertChainFromCert(CERTCertificate *cert, SECCertUsage usage, nssUsage.nss3usage = usage; nssUsage.nss3lookingForCA = PR_FALSE; stanChain = NSSCertificate_BuildChain(stanCert, NULL, &nssUsage, NULL, NULL, - CERT_MAX_CERT_CHAIN, NULL, NULL, td, cc); + CERT_MAX_CERT_CHAIN, NULL, NULL, td, cc); if (!stanChain) { - PORT_SetError(SEC_ERROR_UNKNOWN_ISSUER); - return NULL; + PORT_SetError(SEC_ERROR_UNKNOWN_ISSUER); + return NULL; } len = 0; stanCert = stanChain[0]; while (stanCert) { - stanCert = stanChain[++len]; + stanCert = stanChain[++len]; } arena = PORT_NewArena(4096); if (arena == NULL) { - goto loser; + goto loser; } - chain = (CERTCertificateList *)PORT_ArenaAlloc(arena, - sizeof(CERTCertificateList)); - if (!chain) goto loser; - chain->certs = (SECItem*)PORT_ArenaAlloc(arena, len * sizeof(SECItem)); - if (!chain->certs) goto loser; + chain = (CERTCertificateList *)PORT_ArenaAlloc(arena, + sizeof(CERTCertificateList)); + if (!chain) + goto loser; + chain->certs = (SECItem *)PORT_ArenaAlloc(arena, len * sizeof(SECItem)); + if (!chain->certs) + goto loser; i = 0; stanCert = stanChain[i]; while (stanCert) { - SECItem derCert; - CERTCertificate *cCert = STAN_GetCERTCertificate(stanCert); - if (!cCert) { - goto loser; - } - derCert.len = (unsigned int)stanCert->encoding.size; - derCert.data = (unsigned char *)stanCert->encoding.data; - derCert.type = siBuffer; - SECITEM_CopyItem(arena, &chain->certs[i], &derCert); - stanCert = stanChain[++i]; - if (!stanCert && !cCert->isRoot) { - /* reached the end of the chain, but the final cert is - * not a root. Don't discard it. - */ - includeRoot = PR_TRUE; - } - CERT_DestroyCertificate(cCert); + SECItem derCert; + CERTCertificate *cCert = STAN_GetCERTCertificate(stanCert); + if (!cCert) { + goto loser; + } + derCert.len = (unsigned int)stanCert->encoding.size; + derCert.data = (unsigned char *)stanCert->encoding.data; + derCert.type = siBuffer; + SECITEM_CopyItem(arena, &chain->certs[i], &derCert); + stanCert = stanChain[++i]; + if (!stanCert && !cCert->isRoot) { + /* reached the end of the chain, but the final cert is + * not a root. Don't discard it. + */ + includeRoot = PR_TRUE; + } + CERT_DestroyCertificate(cCert); } - if ( !includeRoot && len > 1) { - chain->len = len - 1; + if (!includeRoot && len > 1) { + chain->len = len - 1; } else { - chain->len = len; + chain->len = len; } - + chain->arena = arena; nss_ZFreeIf(stanChain); return chain; @@ -1090,15 +1103,15 @@ loser: i = 0; stanCert = stanChain[i]; while (stanCert) { - CERTCertificate *cCert = STAN_GetCERTCertificate(stanCert); - if (cCert) { - CERT_DestroyCertificate(cCert); - } - stanCert = stanChain[++i]; + CERTCertificate *cCert = STAN_GetCERTCertificate(stanCert); + if (cCert) { + CERT_DestroyCertificate(cCert); + } + stanCert = stanChain[++i]; } nss_ZFreeIf(stanChain); if (arena) { - PORT_FreeArena(arena, PR_FALSE); + PORT_FreeArena(arena, PR_FALSE); } return NULL; } @@ -1115,15 +1128,19 @@ CERT_CertListFromCert(CERTCertificate *cert) /* arena for SecCertificateList */ arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if (arena == NULL) goto no_memory; + if (arena == NULL) + goto no_memory; /* build the CERTCertificateList */ chain = (CERTCertificateList *)PORT_ArenaAlloc(arena, sizeof(CERTCertificateList)); - if (chain == NULL) goto no_memory; - chain->certs = (SECItem*)PORT_ArenaAlloc(arena, 1 * sizeof(SECItem)); - if (chain->certs == NULL) goto no_memory; + if (chain == NULL) + goto no_memory; + chain->certs = (SECItem *)PORT_ArenaAlloc(arena, 1 * sizeof(SECItem)); + if (chain->certs == NULL) + goto no_memory; rv = SECITEM_CopyItem(arena, chain->certs, &(cert->derCert)); - if (rv < 0) goto loser; + if (rv < 0) + goto loser; chain->len = 1; chain->arena = arena; @@ -1133,41 +1150,41 @@ no_memory: PORT_SetError(SEC_ERROR_NO_MEMORY); loser: if (arena != NULL) { - PORT_FreeArena(arena, PR_FALSE); + PORT_FreeArena(arena, PR_FALSE); } return NULL; } CERTCertificateList * -CERT_DupCertList(const CERTCertificateList * oldList) +CERT_DupCertList(const CERTCertificateList *oldList) { CERTCertificateList *newList = NULL; - PLArenaPool *arena = NULL; - SECItem *newItem; - SECItem *oldItem; - int len = oldList->len; - int rv; + PLArenaPool *arena = NULL; + SECItem *newItem; + SECItem *oldItem; + int len = oldList->len; + int rv; /* arena for SecCertificateList */ arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); - if (arena == NULL) - goto no_memory; + if (arena == NULL) + goto no_memory; /* now build the CERTCertificateList */ newList = PORT_ArenaNew(arena, CERTCertificateList); - if (newList == NULL) - goto no_memory; + if (newList == NULL) + goto no_memory; newList->arena = arena; - newItem = (SECItem*)PORT_ArenaAlloc(arena, len * sizeof(SECItem)); - if (newItem == NULL) - goto no_memory; + newItem = (SECItem *)PORT_ArenaAlloc(arena, len * sizeof(SECItem)); + if (newItem == NULL) + goto no_memory; newList->certs = newItem; - newList->len = len; + newList->len = len; for (oldItem = oldList->certs; len > 0; --len, ++newItem, ++oldItem) { - rv = SECITEM_CopyItem(arena, newItem, oldItem); - if (rv < 0) - goto loser; + rv = SECITEM_CopyItem(arena, newItem, oldItem); + if (rv < 0) + goto loser; } return newList; @@ -1175,7 +1192,7 @@ no_memory: PORT_SetError(SEC_ERROR_NO_MEMORY); loser: if (arena != NULL) { - PORT_FreeArena(arena, PR_FALSE); + PORT_FreeArena(arena, PR_FALSE); } return NULL; } @@ -1185,4 +1202,3 @@ CERT_DestroyCertificateList(CERTCertificateList *list) { PORT_FreeArena(list->arena, PR_FALSE); } - |