udf: Prevent buffer overrun with multi-byte characters
udf_CS0toUTF8 function stops the conversion when the output buffer length reaches UDF_NAME_LEN-2, which is correct maximum name length, but, when checking, it leaves the space for a single byte only, while multi-bytes output characters can take more space, causing buffer overflow. Similar error exists in udf_CS0toNLS function, that restricts the output length to UDF_NAME_LEN, while actual maximum allowed length is UDF_NAME_LEN-2. In these cases the output can override not only the current buffer length field, causing corruption of the name buffer itself, but also following allocation structures, causing kernel crash. Adjust the output length checks in both functions to prevent buffer overruns in case of multi-bytes UTF8 or NLS characters. CC: stable@vger.kernel.org Signed-off-by: Andrew Gabbasov <andrew_gabbasov@mentor.com> Signed-off-by: Jan Kara <jack@suse.cz>
This commit is contained in:
parent
d1b98c23f7
commit
ad402b265e
|
@ -128,11 +128,15 @@ int udf_CS0toUTF8(struct ustr *utf_o, const struct ustr *ocu_i)
|
|||
if (c < 0x80U)
|
||||
utf_o->u_name[utf_o->u_len++] = (uint8_t)c;
|
||||
else if (c < 0x800U) {
|
||||
if (utf_o->u_len > (UDF_NAME_LEN - 4))
|
||||
break;
|
||||
utf_o->u_name[utf_o->u_len++] =
|
||||
(uint8_t)(0xc0 | (c >> 6));
|
||||
utf_o->u_name[utf_o->u_len++] =
|
||||
(uint8_t)(0x80 | (c & 0x3f));
|
||||
} else {
|
||||
if (utf_o->u_len > (UDF_NAME_LEN - 5))
|
||||
break;
|
||||
utf_o->u_name[utf_o->u_len++] =
|
||||
(uint8_t)(0xe0 | (c >> 12));
|
||||
utf_o->u_name[utf_o->u_len++] =
|
||||
|
@ -277,7 +281,7 @@ static int udf_CS0toNLS(struct nls_table *nls, struct ustr *utf_o,
|
|||
c = (c << 8) | ocu[i++];
|
||||
|
||||
len = nls->uni2char(c, &utf_o->u_name[utf_o->u_len],
|
||||
UDF_NAME_LEN - utf_o->u_len);
|
||||
UDF_NAME_LEN - 2 - utf_o->u_len);
|
||||
/* Valid character? */
|
||||
if (len >= 0)
|
||||
utf_o->u_len += len;
|
||||
|
|
Loading…
Reference in a new issue