fix out-of-bounds write in sm2_crypt.c
authorymlbright <yml_bright@163.com>
Wed, 22 Aug 2018 03:22:11 +0000 (11:22 +0800)
committerPauli <paul.dale@oracle.com>
Wed, 29 Aug 2018 03:47:14 +0000 (13:47 +1000)
asn1_encode has two form length octets: short form(1 byte), long form(1+n byte).

CLA: Trivial

Reviewed-by: Nicola Tuveri <nic.tuv@gmail.com>
Reviewed-by: Paul Dale <paul.dale@oracle.com>
Reviewed-by: Matt Caswell <matt@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/7027)

crypto/sm2/sm2_crypt.c

index 9e78873..9c69a45 100644 (file)
@@ -91,11 +91,18 @@ int sm2_ciphertext_size(const EC_KEY *key, const EVP_MD *digest, size_t msg_len,
 {
     const size_t field_size = ec_field_size(EC_KEY_get0_group(key));
     const int md_size = EVP_MD_size(digest);
+    size_t sz;
 
     if (field_size == 0 || md_size < 0)
         return 0;
 
-    *ct_size = 12 + 2 * field_size + (size_t)md_size + msg_len;
+    /* Integer and string are simple type; set constructed = 0, means primitive and definite length encoding. */
+    sz = 2 * ASN1_object_size(0, field_size + 1, V_ASN1_INTEGER)
+         + ASN1_object_size(0, md_size, V_ASN1_OCTET_STRING)
+         + ASN1_object_size(0, msg_len, V_ASN1_OCTET_STRING);
+    /* Sequence is structured type; set constructed = 1, means constructed and definite length encoding. */
+    *ct_size = ASN1_object_size(1, sz, V_ASN1_SEQUENCE);
+
     return 1;
 }