Add support for Local Machine Keyset attribute in PKCS#12 files.
authorDr. Stephen Henson <steve@openssl.org>
Thu, 26 Jun 2008 23:26:52 +0000 (23:26 +0000)
committerDr. Stephen Henson <steve@openssl.org>
Thu, 26 Jun 2008 23:26:52 +0000 (23:26 +0000)
CHANGES
apps/pkcs12.c
crypto/objects/obj_dat.h
crypto/objects/obj_mac.h
crypto/objects/obj_mac.num
crypto/objects/objects.txt
crypto/pkcs12/p12_crt.c
crypto/x509/x509_att.c

diff --git a/CHANGES b/CHANGES
index b78c8d1012134c1e2d7d04e054aee5ebf895d08c..5761f74d609d5b6b6bf36eceaaadd812ed42918a 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -4,6 +4,9 @@
 
  Changes between 0.9.8h and 0.9.8i  [xx XXX xxxx]
 
+  *) Add support for Local Machine Keyset attribute in PKCS#12 files.
+     [Steve Henson]
+
   *) Fix BN_GF2m_mod_arr() top-bit cleanup code.
      [Huang Ying]
 
index 7c71b1a88fb29e17783204fb994f4e44f1a742d7..268390ebe8d8be2008144275e9b75422718a4bc4 100644 (file)
@@ -100,6 +100,7 @@ int MAIN(int argc, char **argv)
     char **args;
     char *name = NULL;
     char *csp_name = NULL;
+    int add_lmk = 0;
     PKCS12 *p12 = NULL;
     char pass[50], macpass[50];
     int export_cert = 0;
@@ -224,7 +225,9 @@ int MAIN(int argc, char **argv)
                        args++; 
                        name = *args;
                    } else badarg = 1;
-               } else if (!strcmp (*args, "-CSP")) {
+               } else if (!strcmp (*args, "-LMK"))
+                       add_lmk = 1;
+               else if (!strcmp (*args, "-CSP")) {
                    if (args[1]) {
                        args++; 
                        csp_name = *args;
@@ -338,6 +341,8 @@ int MAIN(int argc, char **argv)
        BIO_printf(bio_err,  "-rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
        BIO_printf(bio_err,  "              load the file (or the files in the directory) into\n");
        BIO_printf(bio_err,  "              the random number generator\n");
+       BIO_printf(bio_err,  "-CSP name     Microsoft CSP name\n");
+       BIO_printf(bio_err,  "-LMK          Add local machine keyset attribute to private key\n");
        goto end;
     }
 
@@ -562,7 +567,9 @@ int MAIN(int argc, char **argv)
        if (csp_name && key)
                EVP_PKEY_add1_attr_by_NID(key, NID_ms_csp_name,
                                MBSTRING_ASC, (unsigned char *)csp_name, -1);
-               
+
+       if (add_lmk && key)
+               EVP_PKEY_add1_attr_by_NID(key, NID_LocalKeySet, 0, NULL, -1);
 
 #ifdef CRYPTO_MDEBUG
        CRYPTO_pop_info();
index 576c35898f0226d02257d88997af17a79b850f19..0ccc7c62be7af8a0887e2bc1f36199fb7dc7c926 100644 (file)
  * [including the GNU Public Licence.]
  */
 
-#define NUM_NID 856
-#define NUM_SN 849
-#define NUM_LN 849
-#define NUM_OBJ 803
+#define NUM_NID 857
+#define NUM_SN 850
+#define NUM_LN 850
+#define NUM_OBJ 804
 
-static unsigned char lvalues[5702]={
+static unsigned char lvalues[5711]={
 0x00,                                        /* [  0] OBJ_undef */
 0x2A,0x86,0x48,0x86,0xF7,0x0D,               /* [  1] OBJ_rsadsi */
 0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,          /* [  7] OBJ_pkcs */
@@ -871,6 +871,7 @@ static unsigned char lvalues[5702]={
 0x2A,0x85,0x03,0x02,0x09,0x01,0x03,0x03,     /* [5677] OBJ_id_GostR3411_94_with_GostR3410_94_cc */
 0x2A,0x85,0x03,0x02,0x09,0x01,0x03,0x04,     /* [5685] OBJ_id_GostR3411_94_with_GostR3410_2001_cc */
 0x2A,0x85,0x03,0x02,0x09,0x01,0x08,0x01,     /* [5693] OBJ_id_GostR3410_2001_ParamSet_cc */
+0x2B,0x06,0x01,0x04,0x01,0x82,0x37,0x11,0x02,/* [5701] OBJ_LocalKeySet */
 };
 
 static ASN1_OBJECT nid_objs[NUM_NID]={
@@ -2253,6 +2254,8 @@ static ASN1_OBJECT nid_objs[NUM_NID]={
        "GOST R 3410-2001 Parameter Set Cryptocom",
        NID_id_GostR3410_2001_ParamSet_cc,8,&(lvalues[5693]),0},
 {"HMAC","hmac",NID_hmac,0,NULL,0},
+{"LocalKeySet","Microsoft Local Key set",NID_LocalKeySet,9,
+       &(lvalues[5701]),0},
 };
 
 static ASN1_OBJECT *sn_objs[NUM_SN]={
@@ -2347,6 +2350,7 @@ static ASN1_OBJECT *sn_objs[NUM_SN]={
 &(nid_objs[646]),/* "JOINT-ISO-ITU-T" */
 &(nid_objs[773]),/* "KISA" */
 &(nid_objs[15]),/* "L" */
+&(nid_objs[856]),/* "LocalKeySet" */
 &(nid_objs[ 3]),/* "MD2" */
 &(nid_objs[257]),/* "MD4" */
 &(nid_objs[ 4]),/* "MD5" */
@@ -3165,6 +3169,7 @@ static ASN1_OBJECT *ln_objs[NUM_LN]={
 &(nid_objs[138]),/* "Microsoft Encrypted File System" */
 &(nid_objs[171]),/* "Microsoft Extension Request" */
 &(nid_objs[134]),/* "Microsoft Individual Code Signing" */
+&(nid_objs[856]),/* "Microsoft Local Key set" */
 &(nid_objs[137]),/* "Microsoft Server Gated Crypto" */
 &(nid_objs[648]),/* "Microsoft Smartcardlogin" */
 &(nid_objs[136]),/* "Microsoft Trust List Signing" */
@@ -4550,6 +4555,7 @@ static ASN1_OBJECT *obj_objs[NUM_OBJ]={
 &(nid_objs[682]),/* OBJ_X9_62_tpBasis                1 2 840 10045 1 2 3 2 */
 &(nid_objs[683]),/* OBJ_X9_62_ppBasis                1 2 840 10045 1 2 3 3 */
 &(nid_objs[417]),/* OBJ_ms_csp_name                  1 3 6 1 4 1 311 17 1 */
+&(nid_objs[856]),/* OBJ_LocalKeySet                  1 3 6 1 4 1 311 17 2 */
 &(nid_objs[390]),/* OBJ_dcObject                     1 3 6 1 4 1 1466 344 */
 &(nid_objs[91]),/* OBJ_bf_cbc                       1 3 6 1 4 1 3029 1 2 */
 &(nid_objs[315]),/* OBJ_id_regCtrl_regToken          1 3 6 1 5 5 7 5 1 1 */
index 491a1181db7fd3da60702d97194a8ec9231e1226..05fcbe7aa1f22b5ff3f6179c2b4b8adb054a2275 100644 (file)
 #define NID_ms_csp_name                417
 #define OBJ_ms_csp_name                1L,3L,6L,1L,4L,1L,311L,17L,1L
 
+#define SN_LocalKeySet         "LocalKeySet"
+#define LN_LocalKeySet         "Microsoft Local Key set"
+#define NID_LocalKeySet                856
+#define OBJ_LocalKeySet                1L,3L,6L,1L,4L,1L,311L,17L,2L
+
 #define OBJ_certTypes          OBJ_pkcs9,22L
 
 #define LN_x509Certificate             "x509Certificate"
index 7ec6dd9936ac998cc602f379ca33cb44c2992f22..53c9cb0d6ae6a7a432daad95a34a710a0c48b55f 100644 (file)
@@ -853,3 +853,4 @@ id_GostR3411_94_with_GostR3410_94_cc                852
 id_GostR3411_94_with_GostR3410_2001_cc         853
 id_GostR3410_2001_ParamSet_cc          854
 hmac           855
+LocalKeySet            856
index 5d6b602a0206487995521374a8c102bca2938f9d..e009702e553a744864614e184814a480cfaeaccb 100644 (file)
@@ -319,6 +319,7 @@ pkcs9 20            :                       : friendlyName
 pkcs9 21               :                       : localKeyID
 !Cname ms-csp-name
 1 3 6 1 4 1 311 17 1   : CSPName               : Microsoft CSP Name
+1 3 6 1 4 1 311 17 2   : LocalKeySet           : Microsoft Local Key set
 !Alias certTypes pkcs9 22
 certTypes 1            :                       : x509Certificate
 certTypes 2            :                       : sdsiCertificate
index dbafda17b681c1711c0001757e9f91a57af09381..9748256b6fe1c95b0bbecc4ebbb60aa3795ece68 100644 (file)
 
 static int pkcs12_add_bag(STACK_OF(PKCS12_SAFEBAG) **pbags, PKCS12_SAFEBAG *bag);
 
+static int copy_bag_attr(PKCS12_SAFEBAG *bag, EVP_PKEY *pkey, int nid)
+       {
+       int idx;
+       X509_ATTRIBUTE *attr;
+       idx = EVP_PKEY_get_attr_by_NID(pkey, nid, -1);
+       if (idx < 0)
+               return 1;
+       attr = EVP_PKEY_get_attr(pkey, idx);
+       if (!X509at_add1_attr(&bag->attrib, attr))
+               return 0;
+       return 1;
+       }
+
 PKCS12 *PKCS12_create(char *pass, char *name, EVP_PKEY *pkey, X509 *cert,
             STACK_OF(X509) *ca, int nid_key, int nid_cert, int iter, int mac_iter,
             int keytype)
@@ -122,20 +135,15 @@ PKCS12 *PKCS12_create(char *pass, char *name, EVP_PKEY *pkey, X509 *cert,
 
        if (pkey)
                {
-               int cspidx;
                bag = PKCS12_add_key(&bags, pkey, keytype, iter, nid_key, pass);
 
                if (!bag)
                        goto err;
 
-               cspidx = EVP_PKEY_get_attr_by_NID(pkey, NID_ms_csp_name, -1);
-               if (cspidx >= 0)
-                       {
-                       X509_ATTRIBUTE *cspattr;
-                       cspattr = EVP_PKEY_get_attr(pkey, cspidx);
-                       if (!X509at_add1_attr(&bag->attrib, cspattr))
-                               goto err;
-                       }
+               if (!copy_bag_attr(bag, pkey, NID_ms_csp_name))
+                       goto err;
+               if (!copy_bag_attr(bag, pkey, NID_LocalKeySet))
+                       goto err;
 
                if(name && !PKCS12_add_friendlyname(bag, name, -1))
                        goto err;
index 2c9061e3d2f3e841b9b16f533d9c6bb15f2a328f..98460e8921534150003e4a9d7a1e933a10220cd5 100644 (file)
@@ -245,7 +245,7 @@ X509_ATTRIBUTE *X509_ATTRIBUTE_create_by_OBJ(X509_ATTRIBUTE **attr,
                goto err;
        if (!X509_ATTRIBUTE_set1_data(ret,atrtype,data,len))
                goto err;
-       
+
        if ((attr != NULL) && (*attr == NULL)) *attr=ret;
        return(ret);
 err:
@@ -302,6 +302,13 @@ int X509_ATTRIBUTE_set1_data(X509_ATTRIBUTE *attr, int attrtype, const void *dat
                atype = attrtype;
        }
        if(!(attr->value.set = sk_ASN1_TYPE_new_null())) goto err;
+       attr->single = 0;
+       /* This is a bit naughty because the attribute should really have
+        * at least one value but some types use and zero length SET and
+        * require this.
+        */
+       if (attrtype == 0)
+               return 1;
        if(!(ttmp = ASN1_TYPE_new())) goto err;
        if ((len == -1) && !(attrtype & MBSTRING_FLAG))
                {
@@ -311,7 +318,6 @@ int X509_ATTRIBUTE_set1_data(X509_ATTRIBUTE *attr, int attrtype, const void *dat
        else
                ASN1_TYPE_set(ttmp, atype, stmp);
        if(!sk_ASN1_TYPE_push(attr->value.set, ttmp)) goto err;
-       attr->single = 0;
        return 1;
        err:
        X509err(X509_F_X509_ATTRIBUTE_SET1_DATA, ERR_R_MALLOC_FAILURE);