[openssl-dev] Heap corruption in asn1_item_ex_combine_new()

Julien Kauffmann julien.kauffmann at freelan.org
Tue Mar 31 12:36:37 UTC 2015


Hi,

I've been hunting down a heap corruption bug in OpenSSL for the past few 
days and I found the guilty instruction. At this point, I know what 
causes the problem but I am unsure how to solve it nicely.

Here is the minimal sample I used to reproduce the issue on the latest 
1.0.2a (happens on every run, on all platforms in 64 bits):

int main()
{
     ERR_load_crypto_strings(); OpenSSL_add_all_algorithms(); 
ENGINE_load_builtin_engines();

     EC_GROUP* group = EC_GROUP_new_by_curve_name(NID_sect571k1);
     EC_GROUP_set_point_conversion_form(group, 
POINT_CONVERSION_UNCOMPRESSED);

     EC_KEY* eckey = EC_KEY_new();
     EC_KEY_set_group(eckey, group);
     EC_KEY_generate_key(eckey);

     BIO* out = BIO_new(BIO_s_file());
     BIO_set_fp(out, stdout, BIO_NOCLOSE);

     PEM_write_bio_ECPrivateKey(out, eckey, NULL, NULL, 0, NULL, NULL);
}

Basically what happens is that, somewhere inside the call to 
PEM_write_bio_ECPrivateKey(), an ASN1 sequence of 3 elements is 
allocated. The corresponding code is as follow (in 
crypto/asn1/tasn_new.c:181):

if (!combine) {
     *pval = OPENSSL_malloc(it->size);
     if (!*pval)
         goto memerr;
     memset(*pval, 0, it->size);
     asn1_do_lock(pval, 0, it);
     asn1_enc_init(pval, it);
}
for (i = 0, tt = it->templates; i < it->tcount; tt++, i++) {
     pseqval = asn1_get_field_ptr(pval, tt);
     if (!ASN1_template_new(pseqval, tt))
         goto memerr;
}

In the sample I gave, at some point OPENSSL_malloc allocates 12 bytes 
for a 3-elements ASN1 SEQUENCE. The for-loop then initializes every 
element: ASN1_template_new() calls in turn asn1_item_ex_combine_new() 
which, at line 103, does:

if (!combine)
     *pval = NULL;

The problem is that pval at this point points to an element of the 
SEQUENCE that is only 4 bytes long. On 64 bits systems this causes the 
next 4 bytes to be set to 0x00000000. For the first two elements of the 
sequence, this gets recovered by the next element being initialized. 
However for the last element, this affectation happens to write 4 bytes 
past the allocated memory, corrupting the heap.

I'm not sure what is the best place to fix this. Do you have any hints ?

Julien Kauffmann.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mta.openssl.org/pipermail/openssl-dev/attachments/20150331/2cd75b80/attachment-0001.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/pkcs7-signature
Size: 4276 bytes
Desc: Signature cryptographique S/MIME
URL: <http://mta.openssl.org/pipermail/openssl-dev/attachments/20150331/2cd75b80/attachment-0001.bin>


More information about the openssl-dev mailing list