Closed Bug 434099 Opened 16 years ago Closed 16 years ago

NSS relies on unchecked PKCS#11 object attribute values

Categories

(NSS :: Libraries, defect, P2)

defect

Tracking

(Not tracked)

RESOLVED FIXED
3.12.1

People

(Reporter: julio.maranhao, Assigned: nelson)

Details

Attachments

(8 files)

User-Agent:       Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9b5) Gecko/2008032620 Firefox/3.0b5
Build Identifier: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9b5) Gecko/2008032620 Firefox/3.0b5

Actually I don't know if I chose the correct Product/Component.

I have an USB Token (iKey 2032). It works with MS Cripto API, but I can't make it work with Firefox or Thunderbird (2.0.0.14 and Trunk). The Token has a PKCS#11 module (API 2.01). The module is dkck201.dll.

I can load the module and login correctly. But I can't see the 3 certs inside it (only 2). The second cert is duplicated (view attachment). When I try to configure an account to use certificates I raise an strange error (view attachment). That's it.

Reproducible: Always

Steps to Reproduce:
1. Load an iKey 2032 USB Token using its PKCS#11 module (dkck201.dll)
2. View the certificates in the Certificate Manager. I have 3 unique certs but TB shows 3 certs (1 duplicated). View the attachments.
3. I cannot set any cert for my account. View the attachments for the error dialog.
Actual Results:  
I cannot use certs with my Token with Thunderbird.

Expected Results:  
Just work. ;-)

I discovered the OpenSC site and I made some tests. Here it goes.

C:\>pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --show-info
Cryptoki version 2.1
Manufacturer     Copyright (c) SafeNet Inc.
Library          SafeNet Cryptoki DLL V-2.01 (ver 7.0)

C:\>pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --list-slots
Available slots:
Slot 10          Rainbow Technologies iKeyVirtualReader 0
  token state:   uninitialized
Slot 11          (empty)
Slot 12          (empty)
Slot 13          (empty)

C:\>pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --list-mechanisms
Supported mechanisms:
  RSA-PKCS, sign, verify, wrap, unwrap, encrypt, decrypt, other flags=0x25000
  SHA1-RSA-PKCS, sign, verify
  RSA-PKCS-KEY-PAIR-GEN, keypairgen
  MD2, digest
  MD5, digest
  SHA-1, digest
  SHA256, digest
  DSA-KEY-PAIR-GEN, keypairgen
  DSA, sign, verify
  RC2-KEY-GEN, other flags=0x8000
  RC2-ECB, wrap, unwrap, encrypt, decrypt, other flags=0x20000
  RC2-CBC, encrypt, decrypt
  RC2-MAC, sign, verify
  RC4-KEY-GEN, other flags=0x8000
  RC4, encrypt, decrypt
  DES-MAC, sign, verify
  DES3-MAC, sign, verify
  DES-KEY-GEN, other flags=0x8000
  DES-ECB, wrap, unwrap, encrypt, decrypt, other flags=0x20000
  DES-CBC, encrypt, decrypt
  DES2-KEY-GEN, other flags=0x8000
  DES3-KEY-GEN, other flags=0x8000
  DES3-ECB, wrap, unwrap, encrypt, decrypt, other flags=0x20000
  DES3-CBC, encrypt, decrypt
  DH-PKCS-KEY-PAIR-GEN, keypairgen
  DH-PKCS-DERIVE, other flags=0x80000

C:\>pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --list-objects
Public Key Object; RSA 2048 bits
  label:      Comodo_IEAv
  ID:         63f3afb9bee9f557572c9722efbb4bc9277a8e34
  Usage:      encrypt, verify, wrap
Certificate Object, type = X.509 cert
  label:      Comodo_IEAv
  ID:         63f3afb9bee9f557572c9722efbb4bc9277a8e34
Public Key Object; RSA 1024 bits
  label:      Certisign
  ID:         342b8df0abafd88ad7ba1473ebbdba3611b71259
  Usage:      encrypt, verify, wrap
Certificate Object, type = X.509 cert
  label:      Certisign
  ID:         342b8df0abafd88ad7ba1473ebbdba3611b71259
Public Key Object; RSA 2048 bits
  label:      Comodo_Maranhao.us
  ID:         7790656d2d528fbf15256058f6864290be2bc920
  Usage:      encrypt, verify, wrap
Certificate Object, type = X.509 cert
  label:      Comodo_Maranhao.us
  ID:         7790656d2d528fbf15256058f6864290be2bc920

Using the following command I can extract the 3 certificates:
pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --read-object --type=cert --label=XXXXXXX --output-file=XXXXXXX

The following test does not work:

C:\>pkcs11-tool.exe --module c:\Windows\system32\dkck201.dll --pin=XXXXXXXXXX --test
C_SeedRandom() and C_GenerateRandom():
  seems to be OK
Digests:
  all 4 digest functions seem to work
  MD5: OK
  SHA-1: OK
Signatures (currently only RSA signatures)
  testing key 0 (Comodo_IEAv)
error: PKCS11 function C_SignUpdate failed: rv = CKR_MECHANISM_INVALID (0x70)

Aborting.
Thunderbird Build Identifier: version 3.0a2pre (2008051603)
Attached image Device Manager Dialog
Comment on attachment 321330 [details]
Certificate Manager Dialog

Looks to me like you may have two certificates with the same issuer name and serial number.  
(I can't tell for sure because the serial number is truncated in the screen shot.)
Is that the case? 
Do you have two different certs with the same issuer and serial number? 
If so, that's the problem.  Certificate issuers are required by the standards to never use the same serial number in two different certificates.  Consequently, the combination of issuer name and serial number suffices to uniquely identify any standards-conforming cert.  NSS identifies certs by issuer and serial.  If you have two certs with the same issuer and serial, NSS will not be able to access both of them.
Comment on attachment 321331 [details]
Trying to select a certificate to Digital Sign (Select button)

You're trying to configure a certificate for signing in email.  You're using either Thunderbird or SeaMonkey.  The email client is trying to find certificates that are valid for your email account.  That means that: 
1) the email certificate must be issued by a trusted issuer, 
2) if any intermediate CA certificates are required to validate your certificate, the email client must have access to them, also.
3) the certificate must have your email address in it (the email address for the account that you're trying to configure).
4) the email certificate must not have any extensions that effectively prohibit it from being used for signatures or for email protection.
5) the cert must not be expired or revoked.
As I mentioned above, if you've got two certs with the same issuer name and 
serial number, NSS will only be able to use one of them.  If one of them is 
your email signing cert, and it's the one that NSS can't use, then that's 
your problem.  In that case, getting certs with unique serial numbers is the 
solution.  But I'm guessing that it is unlikely that that is the cause.  
Most professional CAs that issue certs understand the requirement for unique
serial numbers and get it right.

I'm guessing that your problem is one or more of these:
a) one or more of the CA certificates in the chain for validating your email 
cert is not present in your token or in the email client's DB, so the email
client doesn't have access to it.  You'll have to get those certs into the 
email client somehow, to correct that.

b) The "root CA" certificate, the top level CA cert in the chain for your
email cert, did not come with the email client, but rather was loaded into 
the client or is present in the token.  It is not trusted as an email root 
CA cert by the client.  You'll have to mark it trusted in the client's certificate manager dialog.

c) The email address for the account that you're trying to configure isn't 
present in your email certificate in a place where NSS recognizes it.  
You'll need to either change the email address associated with the email
account in the email client, or get a cert with that email address in it.

d) Your cert has an extension in it that says it's not good for signing 
email.  That might be a "Key Usage" extension that lacks the "signing" 
attribute, or it might be an "Extended Key Usage" extension that lacks
the "e-mail protection" attribute.  The solution for that problem is to 
get a new cert.
(In reply to comment #7)
> As I mentioned above, if you've got two certs with the same issuer name and 
> serial number, NSS will only be able to use one of them.  If one of them is 
> your email signing cert, and it's the one that NSS can't use, then that's 
> your problem.  In that case, getting certs with unique serial numbers is the 
> solution.  But I'm guessing that it is unlikely that that is the cause.  
> Most professional CAs that issue certs understand the requirement for unique
> serial numbers and get it right.

A lot of replies! It´s good. :-). The 3 certs have unique serial numbers and fingerprints. One is from Certisign, it has no e-mail associated and it is expired. The two other, apart from serials, only differ by associated e-mail (Subject) and are from Comodo. Both are valid. Tomorrow I will upload de certs.

> 
> I'm guessing that your problem is one or more of these:
> a) one or more of the CA certificates in the chain for validating your email 
> cert is not present in your token or in the email client's DB, so the email
> client doesn't have access to it.  You'll have to get those certs into the 
> email client somehow, to correct that.

I will check this. Tomorrow.

> 
> b) The "root CA" certificate, the top level CA cert in the chain for your
> email cert, did not come with the email client, but rather was loaded into 
> the client or is present in the token.  It is not trusted as an email root 
> CA cert by the client.  You'll have to mark it trusted in the client's
> certificate manager dialog.

I will check this. Tomorrow.

> 
> c) The email address for the account that you're trying to configure isn't 
> present in your email certificate in a place where NSS recognizes it.  
> You'll need to either change the email address associated with the email
> account in the email client, or get a cert with that email address in it.

This is new for me. My expired cert does not have e-mail associated. It is to use with any e-mail. It worked with Outlook and Live Mail. It should work with any e-mail client because it has that "e-mail signing purpose". 

> 
> d) Your cert has an extension in it that says it's not good for signing 
> email.  That might be a "Key Usage" extension that lacks the "signing" 
> attribute, or it might be an "Extended Key Usage" extension that lacks
> the "e-mail protection" attribute.  The solution for that problem is to 
> get a new cert.
> 

I will double-check this.

Cheers. You gave me many hints.
Trunk update applied -> version 3.0a2pre (2008051703)

1) The certs are in the attachments certs.zip and CAs.zip;

2) All chains are currently installed.

CN="AAA Certificate Services" is in the "Builtin Object Token" (TB 2.0.0.14 and Trunk). It's not included in the CAs.zip file;

The following CNs were installed by me in the "Software Security Device" of NSS Internal PKCS #11 module:

CN="UTN-USERFirst-Client Authentication and Email"
CN="Autoridade Certificadora Raiz Brasileira"
CN="Autoridade Certificadora da Secretaria da Receita Federal v1"
CN="AC CertiSign SRF V3"

BUT I forgot to edit the previous 4 CAs to mark the 3 Trust settings. NOW, it is done. I restarted TB (Trunk). Unfortunately nothing changed. So, the a and b items can be forgotten.

2) For the Comodo_IEAv cert, wich is for my only e-mail account in TB:

Subject:
    E = julio@ieav.cta.br
    CN = Julio Mendes de Albuquerque Maranhao
    OU = (c)2003 Comodo Limited
    OU = Terms and Conditions of use: http://www.comodo.net/repository
    OU = Comodo Trust Network - PERSONA NOT VALIDATED
Certificate Key Usage:
    Critical
    Signing
    Key Encipherment
Extended Key Usage:
    Not Critical
    E-mail protection (1.3.6.1.5.5.7.3.4)
    1.3.6.1.4.1.6449.1.3.5.2

So items c and d can be forgotten.

3) For the Certisign cert:

Subject:
    CN = JULIO MENDES DE ALBUQUERQUE MARANHAO:02122516437
    OU = SRF e-CPF
    OU = Secretaria da Receita Federal-SRF
    O = ICP-Brasil
    C = BR
Certificate Key Usage:
    Critical
    Signing
    Non-repudiation
    Key Encipherment
Extended Key Usage:
    Not Critical
    E-mail protection (1.3.6.1.5.5.7.3.4)
    TLS Web Client Authentication (1.3.6.1.5.5.7.3.2)

It worked very well with Firefox (Web auth) and Outlook (e-mail signing).

4) I noticed other bugs in "Certificate Manager" dialog and "Certificate Viewer" dialog (Details Tab). But, one issue per time. :-). When this one is solved, I'll focus on them (search bugzilla for duplicates, create a new, etc). You may tell me if NSS (Libraries) is the proper product to create a new issue about those dialogs.

Cheers.
Just to remember. The Certisign cert already expired.
Thunderbird is from thrunk (1st June 2008)
I got the tracing log using:
set NSS_DEBUG_PKCS11_MODULE=Test
set NSPR_LOG_MODULES=nss_mod_log:4
set NSPR_LOG_FILE=NSS_2_Module.log
Thanks to N. B. Bolyard for pointing out:
http://www.mozilla.org/projects/security/pki/nss/tech-notes/tn2.html
While debugging Thunderbird, I found that many UTF-8 errors were raised because the token name is "Júlio Maranhão" (Latin1).

From pipnss.dll
nsPKCS11Slot::GetToken calls nsPK11Token::nsPK11Token (constructor)
nsPK11Token::nsPK11Token calls nsPK11Token::refreshTokenInfo
nsPK11Token::refreshTokenInfo does:
mTokenName = NS_ConvertUTF8toUTF16(PK11_GetTokenName(mSlot));

PK11_GetTokenName is from nss3.dll

Question 1: Should it be ASCII (0-127)? Does my USB token software was wrong when allowed me to enter non-ascii letters for the token's name?
Question 2: What about certs? Is UTF-8 used? Or Is only the ASCII compatible part really allowed? My certs only have ASCII chars (Julio Maranhao).

I changed the token name to "Julio Maranhao". Now I see NO UTF-8 ASSERTION errors in the console window. This is good. But I see NO difference in the "bug". I will continue my debug tomorrow.
Júlio,
It should be OK for your token to contain non-ASCII characters in the token 
name, module name, slot name, and in the CKA_LABEL attribute of objects on 
the token, but they must be encoded in UTF8, not ISO-Latin-1.
> NSS identifies certs by issuer and serial.

Today I found that this is the reason. But there are not two identical serials. There are two NULL serials. The details are:

static PLHashNumber
nss_certificate_hash (
  const void *key
)
{
    unsigned int i;
    PLHashNumber h;
    NSSCertificate *c = (NSSCertificate *)key;
    h = 0;
    for (i=0; i<c->issuer.size; i++)
	h = PR_ROTATE_LEFT32(h, 4) ^ ((unsigned char *)c->issuer.data)[i];
    for (i=0; i<c->serial.size; i++)
	h = PR_ROTATE_LEFT32(h, 4) ^ ((unsigned char *)c->serial.data)[i];
    return h;
}

The second for loop is not executed.
c->serial.data is NULL
c->serial.size is 0

After detecting the reason for the equality I discovered where serial is defined/attributed as NULL.

The file is ckhelper.c
The function is nssCKObject_GetAttributes(...)
The call is
ckrv = CKAPI(epv)->C_GetAttributeValue(hSession, object, obj_template, count);
count is 6
ckrv return 0 (No error?)

obj_template has 6 itens.
The size and meaning are: 
4      type
20     id
1306   encoding
112    issuer
0      serial
160    subject

As I presume that CKAPI(epv)->C_GetAttributeValue is a direct call to the PKCS#11 module (DLL), I do not know what to do now.

Question: How TB collect the serial that is shown in the dialog?

Cheers.
A certificate with an empty serial number is invalid. 
One might argue that NSS should do a better job of detecting & reporting it,
but in no case is it proper for NSS to treat the cert as valid. 
So, I think this bug can now be resolved as invalid. 
The cause is an invalid cert.
> So, I think this bug can now be resolved as invalid.

Not so fast. The 3 certs have serials, BUT all of them have a NULL serial return from the function CKAPI(epv)->C_GetAttributeValue. So this is at least a module bug. BUT again there is the question: What are the serials showed by TB? Where did it get from? Another module call that worked? I need more time to answer that.

Do not close this bug because it is VALID. The certs are PERFECT as I already showed (see the attachments). Maybe the fault is only from the module, but again the NSS code is wrong because if the cert has no serial (NULL) it cannot be included in the cache ring (Closed Linked List) and showed to the user. The 3 certs are included as two objects which one has two instances. That is totally wrong (a bug).

It is clear this is a valid bug. "Thunderbird cannot use certificates from dkck201.dll" because the module returns NULL serials but TB shows serials. !?!?

I would not close this bug. It needs to be fixed.

Cheers.
If thunderbird's behavior is correct in the presence of a correctly working 
PKCS#11 module, and is only apparently incorrect in the presence of an incorrectly working PKCS#11 module, then there is arguably no TB bug here. 
Even if you think there is, it is very low priority, not likely to get 
worked on soon, or ever.

The CKA_VALUE attribute of a cert object is the entire DER-encoded cert.
Once NSS has fetched that value, it tends to use the information found in
the cert itself, rather than in other PKCS#11 attributes whose values are
derived from the cert.  NSS decodes the cert and uses the info from the 
decoding.  If the cert cannot be decoded (say, because the cert is 
improperly encoded) then parts of it may appear to be zero length in 
the structure containing the decoded parts of the cert.  

c->issuer usually comes from the decoding of the cert itself, not from 
another PKCS#11 attribute, such as CKA_SERIAL.  
Here is a pretty-printed dump of the two certs from Comodo.  
As I understand it, you only see one of these, and not the other. 
You want to be able to pick a specific one of these but cannot.
Is that correct?
What are the "friendly names" that your module gives to these certs?
(The "Friendly Name" is the value of the CKA_LABEL attribute.)
Does it give them both the same CKA_LABEL attribute value?
(In reply to comment #20)
> Here is a pretty-printed dump of the two certs from Comodo. 
> As I understand it, you only see one of these, and not the other.
> You want to be able to pick a specific one of these but cannot.
> Is that correct?

Yes. But it is worse. From program launch, the first time I load the cert manager dialog I see duplicated certs. The second time, the duplicate disappears (only Certisign and ComodoIEAv are shown). And I cannot use the showed cert (julio@ieav.cta.br) in my account (same e-mail). These are the issues.

(In reply to comment #21)
> What are the "friendly names" that your module gives to these certs?
> (The "Friendly Name" is the value of the CKA_LABEL attribute.)
> Does it give them both the same CKA_LABEL attribute value?
>

No, the CKA_LABEL values are different. I do not know the difference between CKA_ and CK_. But here is the debugged info:

from pkibase.c

from nssPKIObjectCollection_AddInstanceAsObject function

nssCryptokiObject *instance

uid size is 1621 (data is 0x08548b88) -> from CK_ENCODING
instance->handle = 2359296 -> from CK_OBJECT_HANDLE
instance->label = "ComodoIEAv" -> from CK_LABEL

uid size is 1306 (data is 0x08557548)
instance->handle = 2686976
instance->label = "Certisign"

uid size is 1620 (data is 0x085625b8)
instance->handle = 3014656
instance->label = "ComodoMaranhaous"

// foundIt is zero for the 3 certs
node = add_object_instance(collection, instance, &foundIt);

//buggy! It adds "ComodoMaranhaous" as a second instance of the "ComodoIEAv" node. It should be in its own new node. After this line, instance has bogus data only for "ComodoMaranhaous". Reason: CK_SERIAL is NULL for the 3 certs.
node->object = (*collection->createObject)(node->object);

(In reply to comment #19)
> c->issuer usually comes from the decoding of the cert itself, not from 
> another PKCS#11 attribute, such as CKA_SERIAL.  

After getting CK_OBJECT_HANDLE, CK_LABEL and CK_ENCODING the code try to get the CKA_ data. 

The c->issuer comes from certificate.c :

Function nssCertificate_Create()
status = nssCryptokiCertificate_GetAttributes(object->instances[0],
                                                  NULL,  /* XXX sessionOpt */
                                                  arena,
                                                  &rvCert->type,
                                                  &rvCert->id,
                                                  &rvCert->encoding,
                                                  &rvCert->issuer,
                                                  &rvCert->serial,
                                                  &rvCert->subject);

The symbols used to compound the template are:
CKA_CERTIFICATE_TYPE
CKA_ID
CKA_VALUE
CKA_ISSUER -> The issuer comes from here. At least initially, as the issuer/serial uniqueness formula.
CKA_SERIAL_NUMBER
CKA_SUBJECT

Only CKA_SERIAL_NUMBER returns NULL.

(In reply to comment #19)
> If thunderbird's behavior is correct in the presence of a correctly working 
> PKCS#11 module, and is only apparently incorrect in the presence of an
> incorrectly working PKCS#11 module, then there is arguably no TB bug here. 
> Even if you think there is, it is very low priority, not likely to get 
> worked on soon, or ever.

Ok, I got it. I just feel that the "issue" should be closed as WONTFIX because NSS behaves wrongly with a NULL cert serial. If NSS refused to manage the 3 certs, then the bug should be INVALID.

Cheers.
Julio, the reason I have not resolved this bug is this:
I am not convinced that the empty serial number is relevant to the problem
you are having.  It could be that, even with non-empty serial numbers,
the problem would exist.  

I believe the problem you're seeing is related to the fact that the two 
certs have identical subject names.  If you were using NSS's built-in 
software PKCS#11 module to hold those certs (and their private keys), 
I would be certain that the problem is due to identical subject names,
but since you are using a third party PKCS#11 module, I am not entirely
certain.  
(In reply to comment #23)
> I believe the problem you're seeing is related to the fact that the two 
> certs have identical subject names.

Are you talking about the CN (Common Name)? Or is it the OUs? The Subjects, strictly speaking, are different (E part).

Subject: "E=julio@ieav.cta.br,CN=Julio Mendes de Albuquerque Maranhao
            ,OU=(c)2003 Comodo Limited,OU=Terms and Conditions of use: http:/
            /www.comodo.net/repository,OU=Comodo Trust Network - PERSONA NOT 
            VALIDATED"
Subject: "E=julio@maranhao.us,CN=Julio Mendes de Albuquerque Maranhao
            ,OU=(c)2003 Comodo Limited,OU=Terms and Conditions of use: http:/
            /www.comodo.net/repository,OU=Comodo Trust Network - PERSONA NOT 
            VALIDATED"

You're right.  The subjects are not identical.  I figured that out yesterday
but somehow forgot it overnight. :( 

One way to tell if the issue is really in the module you're using or not,
is to export the two Comodo certs into PKCS#12 files (if you can), and then 
import them into NSS's cert DB, and run the test with the certs in NSS's
built-in PKS#11 module.  If they work that way, then the problem is with 
your module.  If they fail that way too, then the problem is independent of
your module, and is in NSS.
There are strong similarities between the symptoms reported in this bug,
and those reported in bug 435314.  I was thinking that perhaps they have
the same (or similar causes), but they do not, because your subject names
are NOT identical.
(In reply to comment #25)
> One way to tell if the issue is really in the module you're using or not,
> is to export the two Comodo certs into PKCS#12 files (if you can), and then 
> import them into NSS's cert DB, and run the test with the certs in NSS's
> built-in PKS#11 module.  If they work that way, then the problem is with 
> your module.  If they fail that way too, then the problem is independent of
> your module, and is in NSS.
> 

I cannot export to PKCS#12. But I don't need to do this test. I already did it before adding the certs to the USB Token. And it worked.

Now I understand that the code that manage internal certificates is the same that manages USB Tokens. The only difference is the Vendor PKCS#11 module.

So I agree with you. This is NOT an NSS bug. Feel free to finish this bug register.

I only recommend to also check that the issuer and serial are not NULL in the following function (certificate.c) because that data are used to create a hash table and to uniquely identify the cert. What do you think?

Cheers. (I will hack NSS only for me, just to overcome the PKCS#11 module bug) 

/* Creates a certificate from a base object */
NSS_IMPLEMENT NSSCertificate *
nssCertificate_Create (
  nssPKIObject *object
)
{
    PRStatus status;
    NSSCertificate *rvCert;
    /* mark? */
    NSSArena *arena = object->arena;
    PR_ASSERT(object->instances != NULL && object->numInstances > 0);
    PR_ASSERT(object->lockType == nssPKIMonitor);
    rvCert = nss_ZNEW(arena, NSSCertificate);
    if (!rvCert) {
	return (NSSCertificate *)NULL;
    }
    rvCert->object = *object;
    /* XXX should choose instance based on some criteria */
    status = nssCryptokiCertificate_GetAttributes(object->instances[0],
                                                  NULL,  /* XXX sessionOpt */
                                                  arena,
                                                  &rvCert->type,
                                                  &rvCert->id,
                                                  &rvCert->encoding,
                                                  &rvCert->issuer,
                                                  &rvCert->serial,
                                                  &rvCert->subject);
    if (status != PR_SUCCESS) {
	return (NSSCertificate *)NULL;
    }
    /* all certs need an encoding value */
    if (rvCert->encoding.data == NULL) {
	return (NSSCertificate *)NULL;
    }
    return rvCert;
}
Julio, if you have a patch that you believe improves NSS's reliability, go 
ahead and submit the patch for review.  Here's a chance for fame and glory!
:)
\mozilla\security\nss\lib\pki\certificate.c

At line 96:
-    if (status != PR_SUCCESS) {
+    if (status != PR_SUCCESS || 
+        rvCert->issuer.size == 0 || 
+        rvCert->serial.size == 0) {

The issuer name array is not the only required component.  
nssCertificate_Create should check all the required components for being 
empty or missing.  We need to determine exactly which ones are required.
Certainly issuer name and serial number are both among them.

The callers of nssCertificate_Create must all check the return value to 
see if it is NULL, but one of those callers, cert_createObject, does not, 
which is also a bug.
Assignee: nobody → nelson
Status: UNCONFIRMED → NEW
Ever confirmed: true
OS: Windows XP → All
Priority: -- → P2
Hardware: PC → All
Summary: Thunderbird cannot use certificates from a PKCS#11 module (USB Token iKey 2032 dkck201.dll) → NSS relies on unchecked PKCS#11 object attribute values
Target Milestone: --- → 3.12.1
These bugs have been present since NSS 3.5.
Version: unspecified → 3.5
Bob, I have a question for you, related to Stan.

Function nssCertificate_Create *could* detect that some of the certificate object's attribute values (from the PKCS#11 module) are missing, and could
then parse the certificate (from the CKA_VALUE attribute) and get the
values for the missing attributes, e.g. the issuer name, serial number, etc.,
rather than simply declaring an error when some of those values are absent.

The question is: Does NSS ever try to search for certs in the PKCS#11 token, based on any of those attribute values?  

Given the following scenario:
NSS gets a cert from a flawed PKCS#11 module where some of the cert object 
attributes (such as issuer name and serial number) are not implemented or 
are empty.  NSS then parses the cert and fills in the missing attribute 
values (in the NSSCertificate) from the parsed cert.  

I'm wondering if NSS would then try to search for that cert object again, 
trying to find it by searching for an object that matches on some combination 
of those attribute values.  Presumably, such a search would fail.  What would
happen then?
it really depends.

If the cert is in the cache, then we would find it. If it's not in the cache it won't be found.

In addition, there is code in NSS that caches all the certs from (removable/hardware?) tokens that have less then some number (I think 10) certs. It's been a while since I looked at the details, but the idea is a token only has a few certs it's better to just keep those certs around than to try to search for them each time. It also allows us to be tolerant of problems (like missing attributes) on these tokens.

I don't remember exactly what conditions trigger a token for 'caching all it's certs'.

bob
I could imagine writing a second alternative that called the appropriate 
Stan function (name unknown) to decode the cert and then get the values
of issuer, serial and subject from that decoding.  But I suspect that 
will just lead to more problems down the line.
Attachment #324994 - Flags: review?(rrelyea)
Comment on attachment 324994 [details] [diff] [review]
patch alternative 1: reject cert for missing attributes

r+ rrelyea.
Attachment #324994 - Flags: review?(rrelyea) → review+
lib/pki/certificate.c; new revision: 1.65; previous revision: 1.64
Status: NEW → RESOLVED
Closed: 16 years ago
Resolution: --- → FIXED
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: