In adding gost support to BIND and I was running with the following
openssl.cnf (yes I know it needs "default_algorithms = ALL" to be
added) and encountered a NULL pointer dereference in the gost code
due to a undetected EVP_PKEY_assign() failure in pkey_gost01_paramgen().

openssl_conf = openssl_def
[openssl_def]
engines = engine_section
[engine_section]
gost = gost_section
[gost_section]
dynamic_path = /opt/local/lib/engines/libgost.so
engine_id = gost

The attach patch against openssl-1.0.0a checks that EVP_PKEY_assign()
succeeds, where appropriate.  It also removes some memory leaks.

Mark
-- 
Mark Andrews, ISC
1 Seymour St., Dundas Valley, NSW 2117, Australia
PHONE:  +61 2 9871 4742                  INTERNET: [email protected]

diff -ru orig/openssl-1.0.0a/engines/ccgost/gost_ameth.c 
openssl-1.0.0a/engines/ccgost/gost_ameth.c
--- orig/openssl-1.0.0a/engines/ccgost/gost_ameth.c     2010-04-08 
20:54:54.000000000 +1000
+++ openssl-1.0.0a/engines/ccgost/gost_ameth.c  2010-12-16 11:37:42.000000000 
+1100
@@ -127,7 +127,12 @@
                if (!dsa) 
                        {
                        dsa = DSA_new();
-                       if (!EVP_PKEY_assign(pkey,pkey_nid,dsa)) return 0;
+                       if (!dsa) return 0;
+                       if (!EVP_PKEY_assign(pkey,pkey_nid,dsa))
+                               {
+                               DSA_free(dsa);
+                               return 0;
+                               }
                        }
                if (!fill_GOST94_params(dsa,param_nid)) return 0;
                break;
@@ -138,7 +143,12 @@
                if (!ec) 
                        {
                        ec = EC_KEY_new();
-                       if (!EVP_PKEY_assign(pkey,pkey_nid,ec)) return 0;
+                       if (!ec) return 0;
+                       if (!EVP_PKEY_assign(pkey,pkey_nid,ec))
+                               {
+                               EC_KEY_free(ec);
+                               return 0;
+                               }
                        }
                if (!fill_GOST2001_params(ec,param_nid)) return 0;
                }
@@ -157,7 +167,12 @@
                if (!dsa) 
                        {
                        dsa = DSA_new();
-                       EVP_PKEY_assign(pkey,EVP_PKEY_base_id(pkey),dsa);
+                       if (!dsa) return 0;
+                       if (!EVP_PKEY_assign(pkey,EVP_PKEY_base_id(pkey),dsa))
+                               {
+                               DSA_free(dsa);
+                               return 0;
+                               }
                        }       
                dsa->priv_key = BN_dup(priv);
                if (!EVP_PKEY_missing_parameters(pkey)) 
@@ -170,7 +185,12 @@
                if (!ec) 
                        {
                        ec = EC_KEY_new();
-                       EVP_PKEY_assign(pkey,EVP_PKEY_base_id(pkey),ec);
+                       if (!ec) return 0;
+                       if (!EVP_PKEY_assign(pkey,EVP_PKEY_base_id(pkey),ec))
+                               {
+                               EC_KEY_free(ec);
+                               return 0;
+                               }
                        }       
                if (!EC_KEY_set_private_key(ec,priv)) return 0;
                if (!EVP_PKEY_missing_parameters(pkey)) 
@@ -508,7 +528,12 @@
        if (!dto) 
                {
                dto = DSA_new();
-               EVP_PKEY_assign(to,EVP_PKEY_base_id(from),dto);
+               if (!dto) return 0;
+               if (!EVP_PKEY_assign(to,EVP_PKEY_base_id(from),dto))
+                       {
+                       DSA_free(dto);
+                       return 0;
+                       }
                }       
 #define COPYBIGNUM(a,b,x) if (a->x) BN_free(a->x); a->x=BN_dup(b->x);  
        COPYBIGNUM(dto,dfrom,p)
@@ -538,7 +563,12 @@
        if (!eto) 
                {
                eto = EC_KEY_new();
-               EVP_PKEY_assign(to,EVP_PKEY_base_id(from),eto);
+               if (!eto) return 0;
+               if (!EVP_PKEY_assign(to,EVP_PKEY_base_id(from),eto))
+                       {
+                       EC_KEY_free(eto);
+                       return 0;
+                       }
                }       
        EC_KEY_set_group(eto,EC_KEY_get0_group(efrom));
        if (EC_KEY_get0_private_key(eto)) 
@@ -831,7 +861,12 @@
        if (!dsa) 
                {
                dsa=DSA_new();
-               if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_94,dsa)) return 0;
+               if (!dsa) return 0;
+               if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_94,dsa))
+                       {
+                       DSA_free(dsa);
+                       return 0;
+                       }
                }
        if (!fill_GOST94_params(dsa,nid)) return 0;
        return 1;
@@ -849,7 +884,12 @@
        if (!ec) 
                {
                ec = EC_KEY_new();
-               if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_2001,ec)) return 0;
+               if (!ec) return 0;
+               if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_2001,ec))
+                       {
+                       EC_KEY_free(ec);
+                       return 0;
+                       }
                }       
        if (!fill_GOST2001_params(ec, nid)) return 0;
        return 1;
diff -ru orig/openssl-1.0.0a/engines/ccgost/gost_pmeth.c 
openssl-1.0.0a/engines/ccgost/gost_pmeth.c
--- orig/openssl-1.0.0a/engines/ccgost/gost_pmeth.c     2009-06-17 
02:39:20.000000000 +1000
+++ openssl-1.0.0a/engines/ccgost/gost_pmeth.c  2010-12-16 12:08:12.000000000 
+1100
@@ -36,6 +36,7 @@
                   data->sign_param_nid = 
EC_GROUP_get_curve_name(EC_KEY_get0_group(EVP_PKEY_get0((EVP_PKEY *)pkey)));
                break;
                default:
+                       OPENSSL_free(data);
                        return 0;
                }         
                }
@@ -274,12 +275,17 @@
                        return 0;
                }
        dsa = DSA_new();
+       if (!dsa) return 0;
        if (!fill_GOST94_params(dsa,data->sign_param_nid))
                {
                DSA_free(dsa);
                return 0;
                }
-       EVP_PKEY_assign(pkey,NID_id_GostR3410_94,dsa);
+       if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_94,dsa))
+               {
+               DSA_free(dsa);
+               return 0;
+               }
        return 1;
        }
 static int pkey_gost01_paramgen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
@@ -294,13 +300,20 @@
                        return 0;
                }
        if (!ec)        
+               {
                ec = EC_KEY_new();
+               if (!ec) return 0;
+               }
        if (!fill_GOST2001_params(ec,data->sign_param_nid))
                {
                EC_KEY_free(ec);
                return 0;
                }
-       EVP_PKEY_assign(pkey,NID_id_GostR3410_2001,ec);
+       if (!EVP_PKEY_assign(pkey,NID_id_GostR3410_2001,ec))
+               {
+               EC_KEY_free(ec);
+               return (0);
+               }
        return 1;
        }
 
@@ -542,8 +555,13 @@
                        return 0;
                }
                keydata = OPENSSL_malloc(32);
+               if (!keydata) return 0;
                memcpy(keydata,data->key,32);
-               EVP_PKEY_assign(pkey, NID_id_Gost28147_89_MAC, keydata);
+               if (!EVP_PKEY_assign(pkey, NID_id_Gost28147_89_MAC, keydata))
+                       {
+                       OPENSSL_free(keydata);
+                       return 0;
+                       }
                return 1;
        }
 

Reply via email to