Commit a63a250d authored by Neha Kumari's avatar Neha Kumari

BUG#23509275 :DBUG_PRINT in THD::decide_logging_format prints incorrectly, access out-of-bound

Problem:
In debug builds, there is a chance that an out-of-bounds
read is performed when tables are locked in
LTM_PRELOCKED_UNDER_LOCK_TABLES mode. It can happen because
the debug code uses enum values as index for an array of
mode descriptions, but it only takes into consideration 3
out of 4 of the enum values.

Fix:
This patch fixes it by implementing a getter for the enum which
returns a string representation of the enum,
effectively removing the out-of-bounds read.

Moreover, it also fixes the lock mode descriptions that
would be print out in debug builds.
parent 2674cf91
/* /*
Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.
This program is free software; you can redistribute it and/or modify This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by it under the terms of the GNU General Public License as published by
...@@ -4246,6 +4246,25 @@ has_write_table_auto_increment_not_first_in_pk(TABLE_LIST *tables) ...@@ -4246,6 +4246,25 @@ has_write_table_auto_increment_not_first_in_pk(TABLE_LIST *tables)
return 0; return 0;
} }
#ifndef DBUG_OFF
const char * get_locked_tables_mode_name(enum_locked_tables_mode locked_tables_mode)
{
switch (locked_tables_mode)
{
case LTM_NONE:
return "LTM_NONE";
case LTM_LOCK_TABLES:
return "LTM_LOCK_TABLES";
case LTM_PRELOCKED:
return "LTM_PRELOCKED";
case LTM_PRELOCKED_UNDER_LOCK_TABLES:
return "LTM_PRELOCKED_UNDER_LOCK_TABLES";
default:
return "Unknown table lock mode";
}
}
#endif
/** /**
Decide on logging format to use for the statement and issue errors Decide on logging format to use for the statement and issue errors
or warnings as needed. The decision depends on the following or warnings as needed. The decision depends on the following
...@@ -4397,15 +4416,8 @@ int THD::decide_logging_format(TABLE_LIST *tables) ...@@ -4397,15 +4416,8 @@ int THD::decide_logging_format(TABLE_LIST *tables)
TABLE* prev_access_table= NULL; TABLE* prev_access_table= NULL;
#ifndef DBUG_OFF #ifndef DBUG_OFF
{ DBUG_PRINT("debug", ("prelocked_mode: %s",
static const char *prelocked_mode_name[] = { get_locked_tables_mode_name(locked_tables_mode)));
"NON_PRELOCKED",
"PRELOCKED",
"PRELOCKED_UNDER_LOCK_TABLES",
};
DBUG_PRINT("debug", ("prelocked_mode: %s",
prelocked_mode_name[locked_tables_mode]));
}
#endif #endif
if (variables.binlog_format != BINLOG_FORMAT_ROW && tables) if (variables.binlog_format != BINLOG_FORMAT_ROW && tables)
......
...@@ -963,6 +963,8 @@ typedef I_List<Item_change_record> Item_change_list; ...@@ -963,6 +963,8 @@ typedef I_List<Item_change_record> Item_change_list;
/** /**
Type of locked tables mode. Type of locked tables mode.
See comment for THD::locked_tables_mode for complete description. See comment for THD::locked_tables_mode for complete description.
While adding new enum values add them to the getter method for this enum
declared below and defined in sql_class.cc as well.
*/ */
enum enum_locked_tables_mode enum enum_locked_tables_mode
...@@ -973,6 +975,15 @@ enum enum_locked_tables_mode ...@@ -973,6 +975,15 @@ enum enum_locked_tables_mode
LTM_PRELOCKED_UNDER_LOCK_TABLES LTM_PRELOCKED_UNDER_LOCK_TABLES
}; };
#ifndef DBUG_OFF
/**
Getter for the enum enum_locked_tables_mode
@param locked_tables_mode enum for types of locked tables mode
@return The string represantation of that enum value
*/
const char * get_locked_tables_mode_name(enum_locked_tables_mode locked_tables_mode);
#endif
/** /**
Class that holds information about tables which were opened and locked Class that holds information about tables which were opened and locked
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment