Correct NSS's key usage tests for certs with non-RSA public keys.

Bug 221638. r=relyea.
This commit is contained in:
nelsonb%netscape.com 2004-01-22 22:04:54 +00:00
Родитель e14c5e9a65
Коммит 7709686c56
1 изменённых файлов: 29 добавлений и 18 удалений

Просмотреть файл

@ -34,7 +34,7 @@
/* /*
* Certificate handling code * Certificate handling code
* *
* $Id: certdb.c,v 1.60 2004/01/16 02:11:44 nelsonb%netscape.com Exp $ * $Id: certdb.c,v 1.61 2004/01/22 22:04:54 nelsonb%netscape.com Exp $
*/ */
#include "nssilock.h" #include "nssilock.h"
@ -1213,26 +1213,37 @@ CERT_CheckKeyUsage(CERTCertificate *cert, unsigned int requiredUsage)
* type in cert * type in cert
*/ */
if ( requiredUsage & KU_KEY_AGREEMENT_OR_ENCIPHERMENT ) { if ( requiredUsage & KU_KEY_AGREEMENT_OR_ENCIPHERMENT ) {
SECKEYPublicKey *key = CERT_ExtractPublicKey(cert); KeyType keyType = CERT_GetCertKeyType(&cert->subjectPublicKeyInfo);
if (!key) /* turn off the special bit */
return SECFailure;
if ( ( key->keyType == keaKey ) || ( key->keyType == fortezzaKey ) ||
( key->keyType == dhKey ) ) {
requiredUsage |= KU_KEY_AGREEMENT;
} else {
requiredUsage |= KU_KEY_ENCIPHERMENT;
}
/* now turn off the special bit */
requiredUsage &= (~KU_KEY_AGREEMENT_OR_ENCIPHERMENT); requiredUsage &= (~KU_KEY_AGREEMENT_OR_ENCIPHERMENT);
SECKEY_DestroyPublicKey(key); switch (keyType) {
case rsaKey:
requiredUsage |= KU_KEY_ENCIPHERMENT;
break;
case dsaKey:
requiredUsage |= KU_DIGITAL_SIGNATURE;
break;
case fortezzaKey:
case keaKey:
case dhKey:
requiredUsage |= KU_KEY_AGREEMENT;
break;
case ecKey:
/* Accept either signature or agreement. */
if (!(cert->keyUsage & (KU_DIGITAL_SIGNATURE | KU_KEY_AGREEMENT)))
goto loser;
break;
default:
goto loser;
}
} }
if ( ( cert->keyUsage & requiredUsage ) != requiredUsage ) { if ( (cert->keyUsage & requiredUsage) == requiredUsage )
return(SECFailure); return SECSuccess;
} loser:
return(SECSuccess); PORT_SetError(SEC_ERROR_INADEQUATE_KEY_USAGE);
return SECFailure;
} }