The deprecated ASN.1 type LONG / ZLONG (incorrectly) produced zero
length INTEGER encoding for zeroes. For the sake of backward
compatibility, we allow those to be read without fault when using the
replacement types INT32 / UINT32 / INT64 / UINT64.
Fixes #7134
Reviewed-by: Tim Hudson <tjh@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/7144)
return 0;
cp = (char *)*pval;
return 0;
cp = (char *)*pval;
+
+ /*
+ * Strictly speaking, zero length is malformed. However, long_c2i
+ * (x_long.c) encodes 0 as a zero length INTEGER (wrongly, of course),
+ * so for the sake of backward compatibility, we still decode zero
+ * length INTEGERs as the number zero.
+ */
+ if (len == 0)
+ goto long_compat;
+
if (!c2i_uint64_int(&utmp, &neg, &cont, len))
return 0;
if ((it->size & INTxx_FLAG_SIGNED) == 0 && neg) {
if (!c2i_uint64_int(&utmp, &neg, &cont, len))
return 0;
if ((it->size & INTxx_FLAG_SIGNED) == 0 && neg) {
if (neg)
/* c2i_uint64_int() returns positive values */
utmp = 0 - utmp;
if (neg)
/* c2i_uint64_int() returns positive values */
utmp = 0 - utmp;
memcpy(cp, &utmp, sizeof(utmp));
return 1;
}
memcpy(cp, &utmp, sizeof(utmp));
return 1;
}
return 0;
cp = (char *)*pval;
return 0;
cp = (char *)*pval;
+
+ /*
+ * Strictly speaking, zero length is malformed. However, long_c2i
+ * (x_long.c) encodes 0 as a zero length INTEGER (wrongly, of course),
+ * so for the sake of backward compatibility, we still decode zero
+ * length INTEGERs as the number zero.
+ */
+ if (len == 0)
+ goto long_compat;
+
if (!c2i_uint64_int(&utmp, &neg, &cont, len))
return 0;
if ((it->size & INTxx_FLAG_SIGNED) == 0 && neg) {
if (!c2i_uint64_int(&utmp, &neg, &cont, len))
return 0;
if ((it->size & INTxx_FLAG_SIGNED) == 0 && neg) {
utmp2 = (uint32_t)utmp;
memcpy(cp, &utmp2, sizeof(utmp2));
return 1;
utmp2 = (uint32_t)utmp;
memcpy(cp, &utmp2, sizeof(utmp2));
return 1;