From fd0186ebfc32ac2cebff60eb035b9e6ce93b9b5e Mon Sep 17 00:00:00 2001 From: Nalin Dahyabhai Date: Thu, 2 Dec 2010 13:38:03 -0500 Subject: [PATCH 114/150] - go ahead and encode the content-info ourselves, to get the client side of anonymous working --- src/plugins/preauth/pkinit/pkinit_crypto_nss.c | 109 +++++++++++++++-------- 1 files changed, 71 insertions(+), 38 deletions(-) diff --git a/src/plugins/preauth/pkinit/pkinit_crypto_nss.c b/src/plugins/preauth/pkinit/pkinit_crypto_nss.c index 15dc387..9824185 100644 --- a/src/plugins/preauth/pkinit/pkinit_crypto_nss.c +++ b/src/plugins/preauth/pkinit/pkinit_crypto_nss.c @@ -371,6 +371,35 @@ kerberos_principal_name_template[] = { {0, 0, NULL, 0}, }; +/* ContentInfo: RFC 3852, 3. */ +struct content_info { + SECItem content_type, content; +}; +static const SEC_ASN1Template +content_info_template[] = { + { + .kind = SEC_ASN1_SEQUENCE, + .offset = 0, + .sub = NULL, + .size = sizeof(struct content_info), + }, + { + .kind = SEC_ASN1_OBJECT_ID, + .offset = offsetof(struct content_info, content_type), + .sub = &SEC_ObjectIDTemplate, + .size = sizeof(SECItem), + }, + { + .kind = SEC_ASN1_CONTEXT_SPECIFIC | 0 | + SEC_ASN1_CONSTRUCTED | + SEC_ASN1_EXPLICIT, + .offset = offsetof(struct content_info, content), + .sub = &SEC_OctetStringTemplate, + .size = sizeof(SECItem), + }, + { 0, 0, NULL, 0 }, +}; + /* OIDs. */ static unsigned char oid_pkinit_key_purpose_client_bytes[] = {0x2b, 0x06, 0x01, 0x05, 0x02, 0x03, 0x04}; @@ -426,6 +455,28 @@ get_pkinit_data_auth_data_tag(void) } static SECOidTag +get_pkinit_data_auth_data9_tag(void) +{ + static unsigned char oid_pkinit_auth_data9_bytes[] = + {0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01}; + static SECOidData oid_pkinit_auth_data9 = { + .oid = { + .data = oid_pkinit_auth_data9_bytes, + .len = 9, + }, + .offset = SEC_OID_UNKNOWN, + .desc = "PKINIT Client Authentication Data (Draft 9)", + .mechanism = CKM_INVALID_MECHANISM, + .supportedExtension = UNSUPPORTED_CERT_EXTENSION, + }; + if (oid_pkinit_auth_data9.offset == SEC_OID_UNKNOWN) { + oid_pkinit_auth_data9.offset = + SECOID_AddEntry(&oid_pkinit_auth_data9); + } + return oid_pkinit_auth_data9.offset; +} + +static SECOidTag get_pkinit_data_rkey_data_tag(void) { static unsigned char oid_pkinit_rkey_data_bytes[] = @@ -813,6 +864,11 @@ pkinit_init_plg_crypto(pkinit_plg_crypto_context *plg_cryptoctx) NSS_INIT_FORCEOPEN | NSS_INIT_PK11RELOAD); if ((*plg_cryptoctx)->ncontext != NULL) { + tag = get_pkinit_data_auth_data9_tag(); + if (crypto_register_any(tag) != SECSuccess) { + PORT_FreeArena(pool, PR_TRUE); + return ENOMEM; + } tag = get_pkinit_data_auth_data_tag(); if (crypto_register_any(tag) != SECSuccess) { PORT_FreeArena(pool, PR_TRUE); @@ -4060,15 +4116,14 @@ cms_contentinfo_create(krb5_context context, unsigned char *in_data, unsigned int in_length, unsigned char **out_data, unsigned int *out_data_len) { - NSSCMSMessage *msg; - NSSCMSContentInfo *info; PLArenaPool *pool; - SECItem plain, encoded; + SECItem *oid, encoded; SECOidTag encapsulated_tag; + struct content_info cinfo; switch (cms_msg_type) { case CMS_SIGN_DRAFT9: - encapsulated_tag = get_pkinit_data_auth_data_tag(); + encapsulated_tag = get_pkinit_data_auth_data9_tag(); break; case CMS_SIGN_CLIENT: encapsulated_tag = get_pkinit_data_auth_data_tag(); @@ -4084,51 +4139,30 @@ cms_contentinfo_create(krb5_context context, break; } - pool = PORT_NewArena(sizeof(double)); - if (pool == NULL) { - return ENOMEM; - } - - msg = NSS_CMSMessage_Create(pool); - if (msg == NULL) { - PORT_FreeArena(pool, PR_TRUE); + oid = get_oid_from_tag(encapsulated_tag); + if (oid == NULL) { return ENOMEM; } - info = NSS_CMSMessage_GetContentInfo(msg); - if (info == NULL) { - NSS_CMSMessage_Destroy(msg); - PORT_FreeArena(pool, PR_TRUE); - return ENOMEM; - } - if (NSS_CMSContentInfo_SetDontStream(info, PR_TRUE) != SECSuccess) { - pkiDebug("%s: error turning off streaming\n", __FUNCTION__); - NSS_CMSMessage_Destroy(msg); - PORT_FreeArena(pool, PR_TRUE); + pool = PORT_NewArena(sizeof(double)); + if (pool == NULL) { return ENOMEM; } - if (NSS_CMSContentInfo_SetContent(msg, info, encapsulated_tag, - NULL) != SECSuccess) { - pkiDebug("%s: error setting encapsulated data\n", __FUNCTION__); - NSS_CMSMessage_Destroy(msg); - PORT_FreeArena(pool, PR_TRUE); - return ENOMEM; - } + memset(&cinfo, 0, sizeof(cinfo)); + cinfo.content_type = *oid; + cinfo.content.data = in_data; + cinfo.content.len = in_length; - memset(&plain, 0, sizeof(plain)); - plain.data = in_data; - plain.len = in_length; memset(&encoded, 0, sizeof(encoded)); - if (NSS_CMSDEREncode(msg, &plain, &encoded, pool) != SECSuccess) { - NSS_CMSMessage_Destroy(msg); + if (SEC_ASN1EncodeItem(pool, &encoded, &cinfo, + content_info_template) != &encoded) { PORT_FreeArena(pool, PR_TRUE); pkiDebug("%s: error encoding data\n", __FUNCTION__); return ENOMEM; } if (secitem_to_buf_len(&encoded, out_data, out_data_len) != 0) { - NSS_CMSMessage_Destroy(msg); PORT_FreeArena(pool, PR_TRUE); return ENOMEM; } @@ -4140,7 +4174,6 @@ cms_contentinfo_create(krb5_context context, cmsdump(*out_data, *out_data_len); #endif - NSS_CMSMessage_Destroy(msg); PORT_FreeArena(pool, PR_TRUE); return 0; @@ -4635,7 +4668,7 @@ cms_signeddata_create(krb5_context context, case CMS_SIGN_DRAFT9: digest = SEC_OID_MD5; add_signed_attributes = PR_FALSE; - encapsulated_tag = get_pkinit_data_auth_data_tag(); + encapsulated_tag = get_pkinit_data_auth_data9_tag(); break; case CMS_SIGN_CLIENT: digest = SEC_OID_SHA1; @@ -4782,7 +4815,7 @@ cms_signeddata_verify(krb5_context context, switch (cms_msg_type) { case CMS_SIGN_DRAFT9: usage = certUsageSSLClient; - expected_tag = get_pkinit_data_auth_data_tag(); + expected_tag = get_pkinit_data_auth_data9_tag(); break; case CMS_SIGN_CLIENT: usage = certUsageSSLClient; -- 1.7.6.4