diff options
author | Davi Arnaut <davi.arnaut@oracle.com> | 2011-07-15 08:05:30 -0300 |
---|---|---|
committer | Davi Arnaut <davi.arnaut@oracle.com> | 2011-07-15 08:05:30 -0300 |
commit | 2aef0eda7612aac24b07a699ce62db2271cd6fd8 (patch) | |
tree | f2739d0a675d09756f7f08670dc13cbdee7ddb9a /sql/sql_error.cc | |
parent | 75ba465c361bb54db4882590ebc8879549fee15c (diff) | |
download | mariadb-git-2aef0eda7612aac24b07a699ce62db2271cd6fd8.tar.gz |
Bug#12736295 Buffer overflow for variable converted_err with
non-latin1 server error message
The problem was a one byte buffer overflow in the conversion
of a error message between character sets. Ahead of explaining
the problem further, some background information. Before an
error message is sent to the user, the message is converted
to the character set specified in the character_set_results
variable. For various reasons, this conversion might cause
the message to increase in length -- for example, if certain
characters can't be represented in the result character set.
If the final message length is greater than the maximum allowed
length of a error message (MYSQL_ERRMSG_SIZE), the message
is truncated. The message is also always null-terminated
regardless of the character set. The problem arises from this
null-termination. If a message length reached the maximum,
the terminating null character would be placed one byte past
the end of the message buffer.
The solution is to reserve the end of the message buffer for
the null character.
Diffstat (limited to 'sql/sql_error.cc')
-rw-r--r-- | sql/sql_error.cc | 4 |
1 files changed, 3 insertions, 1 deletions
diff --git a/sql/sql_error.cc b/sql/sql_error.cc index 24516f03bee..443f3b7a33e 100644 --- a/sql/sql_error.cc +++ b/sql/sql_error.cc @@ -803,14 +803,16 @@ uint32 convert_error_message(char *to, uint32 to_length, CHARSET_INFO *to_cs, my_wc_t wc; const uchar *from_end= (const uchar*) from+from_length; char *to_start= to; - uchar *to_end= (uchar*) to+to_length; + uchar *to_end; my_charset_conv_mb_wc mb_wc= from_cs->cset->mb_wc; my_charset_conv_wc_mb wc_mb; uint error_count= 0; uint length; DBUG_ASSERT(to_length > 0); + /* Make room for the null terminator. */ to_length--; + to_end= (uchar*) (to + to_length); if (!to_cs || from_cs == to_cs || to_cs == &my_charset_bin) { |