Fixed memory overrun in binlog_encryption.encrypted_master

Problem was that max_row_lengt() used different bitmap
than pack_row()
This commit is contained in:
Monty 2018-05-26 17:03:00 +03:00
parent 2d62a4cb2f
commit 13c241c64f
3 changed files with 12 additions and 8 deletions

View File

@ -6414,7 +6414,8 @@ int THD::binlog_write_row(TABLE* table, bool is_trans,
Pack records into format for transfer. We are allocating more Pack records into format for transfer. We are allocating more
memory than needed, but that doesn't matter. memory than needed, but that doesn't matter.
*/ */
Row_data_memory memory(table, max_row_length(table, record)); Row_data_memory memory(table, max_row_length(table, table->rpl_write_set,
record));
if (!memory.has_memory()) if (!memory.has_memory())
return HA_ERR_OUT_OF_MEM; return HA_ERR_OUT_OF_MEM;
@ -6451,8 +6452,10 @@ int THD::binlog_update_row(TABLE* table, bool is_trans,
DBUG_ASSERT(is_current_stmt_binlog_format_row() && DBUG_ASSERT(is_current_stmt_binlog_format_row() &&
((WSREP(this) && wsrep_emulate_bin_log) || mysql_bin_log.is_open())); ((WSREP(this) && wsrep_emulate_bin_log) || mysql_bin_log.is_open()));
size_t const before_maxlen = max_row_length(table, before_record); size_t const before_maxlen= max_row_length(table, table->read_set,
size_t const after_maxlen = max_row_length(table, after_record); before_record);
size_t const after_maxlen= max_row_length(table, table->rpl_write_set,
after_record);
Row_data_memory row_data(table, before_maxlen, after_maxlen); Row_data_memory row_data(table, before_maxlen, after_maxlen);
if (!row_data.has_memory()) if (!row_data.has_memory())
@ -6528,7 +6531,8 @@ int THD::binlog_delete_row(TABLE* table, bool is_trans,
Pack records into format for transfer. We are allocating more Pack records into format for transfer. We are allocating more
memory than needed, but that doesn't matter. memory than needed, but that doesn't matter.
*/ */
Row_data_memory memory(table, max_row_length(table, record)); Row_data_memory memory(table, max_row_length(table, table->read_set,
record));
if (unlikely(!memory.has_memory())) if (unlikely(!memory.has_memory()))
return HA_ERR_OUT_OF_MEM; return HA_ERR_OUT_OF_MEM;

View File

@ -7279,7 +7279,7 @@ bool TABLE_LIST::process_index_hints(TABLE *tbl)
} }
size_t max_row_length(TABLE *table, const uchar *data) size_t max_row_length(TABLE *table, MY_BITMAP const *cols, const uchar *data)
{ {
TABLE_SHARE *table_s= table->s; TABLE_SHARE *table_s= table->s;
size_t length= table_s->reclength + 2 * table_s->fields; size_t length= table_s->reclength + 2 * table_s->fields;
@ -7291,11 +7291,11 @@ size_t max_row_length(TABLE *table, const uchar *data)
for (uint *ptr= beg ; ptr != end ; ++ptr) for (uint *ptr= beg ; ptr != end ; ++ptr)
{ {
Field * const field= table->field[*ptr]; Field * const field= table->field[*ptr];
if (bitmap_is_set(table->read_set, field->field_index) && if (bitmap_is_set(cols, field->field_index) &&
!field->is_null(rec_offset)) !field->is_null(rec_offset))
{ {
Field_blob * const blob= (Field_blob*) field; Field_blob * const blob= (Field_blob*) field;
length+= blob->get_length(rec_offset) + HA_KEY_BLOB_LENGTH; length+= blob->get_length(rec_offset) + 8; /* max blob store length */
} }
} }
DBUG_PRINT("exit", ("length: %lld", (longlong) length)); DBUG_PRINT("exit", ("length: %lld", (longlong) length));

View File

@ -2672,7 +2672,7 @@ enum get_table_share_flags {
GTS_FORCE_DISCOVERY = 16 GTS_FORCE_DISCOVERY = 16
}; };
size_t max_row_length(TABLE *table, const uchar *data); size_t max_row_length(TABLE *table, MY_BITMAP const *cols, const uchar *data);
void init_mdl_requests(TABLE_LIST *table_list); void init_mdl_requests(TABLE_LIST *table_list);