Commit d1e09972 authored by Sergei Golubchik's avatar Sergei Golubchik

cleanup: cache the result of Rows_log_event::find_key()

parent 6ecc90ae
...@@ -7105,67 +7105,71 @@ static bool record_compare(TABLE *table, bool vers_from_plain= false) ...@@ -7105,67 +7105,71 @@ static bool record_compare(TABLE *table, bool vers_from_plain= false)
*/ */
int Rows_log_event::find_key() int Rows_log_event::find_key()
{ {
uint i, best_key_nr, last_part; DBUG_ASSERT(m_table);
KEY *key, *UNINIT_VAR(best_key); RPL_TABLE_LIST *tl= (RPL_TABLE_LIST*)m_table->pos_in_table_list;
uint i, best_key_nr;
KEY *key;
ulong UNINIT_VAR(best_rec_per_key), tmp; ulong UNINIT_VAR(best_rec_per_key), tmp;
DBUG_ENTER("Rows_log_event::find_key"); DBUG_ENTER("Rows_log_event::find_key");
DBUG_ASSERT(m_table);
best_key_nr= MAX_KEY;
/* if ((best_key_nr= tl->cached_key_nr) != ~0U)
Keys are sorted so that any primary key is first, followed by unique keys, DBUG_ASSERT(best_key_nr <= MAX_KEY); // use the cached value
followed by any other. So we will automatically pick the primary key if else
it exists.
*/
for (i= 0, key= m_table->key_info; i < m_table->s->keys; i++, key++)
{ {
if (!m_table->s->keys_in_use.is_set(i)) best_key_nr= MAX_KEY;
continue;
/* /*
We cannot use a unique key with NULL-able columns to uniquely identify Keys are sorted so that any primary key is first, followed by unique keys,
a row (but we can still select it for range scan below if nothing better followed by any other. So we will automatically pick the primary key if
is available). it exists.
*/ */
if ((key->flags & (HA_NOSAME | HA_NULL_PART_KEY)) == HA_NOSAME) for (i= 0, key= m_table->key_info; i < m_table->s->keys; i++, key++)
{ {
best_key_nr= i; if (!m_table->s->keys_in_use.is_set(i))
best_key= key; continue;
break; /*
} We cannot use a unique key with NULL-able columns to uniquely identify
/* a row (but we can still select it for range scan below if nothing better
We can only use a non-unique key if it allows range scans (ie. skip is available).
FULLTEXT indexes and such). */
*/ if ((key->flags & (HA_NOSAME | HA_NULL_PART_KEY)) == HA_NOSAME)
last_part= key->user_defined_key_parts - 1; {
DBUG_PRINT("info", ("Index %s rec_per_key[%u]= %lu", best_key_nr= i;
key->name.str, last_part, key->rec_per_key[last_part])); break;
if (!(m_table->file->index_flags(i, last_part, 1) & HA_READ_NEXT)) }
continue; /*
We can only use a non-unique key if it allows range scans (ie. skip
FULLTEXT indexes and such).
*/
uint last_part= key->user_defined_key_parts - 1;
DBUG_PRINT("info", ("Index %s rec_per_key[%u]= %lu",
key->name.str, last_part, key->rec_per_key[last_part]));
if (!(m_table->file->index_flags(i, last_part, 1) & HA_READ_NEXT))
continue;
tmp= key->rec_per_key[last_part]; tmp= key->rec_per_key[last_part];
if (best_key_nr == MAX_KEY || (tmp > 0 && tmp < best_rec_per_key)) if (best_key_nr == MAX_KEY || (tmp > 0 && tmp < best_rec_per_key))
{ {
best_key_nr= i; best_key_nr= i;
best_key= key; best_rec_per_key= tmp;
best_rec_per_key= tmp; }
} }
tl->cached_key_nr= best_key_nr;
} }
m_key_nr= best_key_nr;
if (best_key_nr == MAX_KEY) if (best_key_nr == MAX_KEY)
{
m_key_info= NULL; m_key_info= NULL;
DBUG_RETURN(0); else
{
m_key_info= m_table->key_info + best_key_nr;
// Allocate buffer for key searches
m_key= (uchar *) my_malloc(PSI_INSTRUMENT_ME, m_key_info->key_length, MYF(MY_WME));
if (m_key == NULL)
DBUG_RETURN(HA_ERR_OUT_OF_MEM);
} }
// Allocate buffer for key searches DBUG_RETURN(0);
m_key= (uchar *) my_malloc(PSI_INSTRUMENT_ME, best_key->key_length, MYF(MY_WME));
if (m_key == NULL)
DBUG_RETURN(HA_ERR_OUT_OF_MEM);
m_key_info= best_key;
m_key_nr= best_key_nr;
DBUG_RETURN(0);;
} }
......
...@@ -249,37 +249,35 @@ class table_def ...@@ -249,37 +249,35 @@ class table_def
Extend the normal table list with a few new fields needed by the Extend the normal table list with a few new fields needed by the
slave thread, but nowhere else. slave thread, but nowhere else.
*/ */
struct RPL_TABLE_LIST struct RPL_TABLE_LIST : public TABLE_LIST
: public TABLE_LIST
{ {
bool m_tabledef_valid;
bool master_had_triggers;
table_def m_tabledef; table_def m_tabledef;
TABLE *m_conv_table; TABLE *m_conv_table;
const Copy_field *m_online_alter_copy_fields; const Copy_field *m_online_alter_copy_fields;
const Copy_field *m_online_alter_copy_fields_end; const Copy_field *m_online_alter_copy_fields_end;
uint cached_key_nr; // [0..MAX_KEY] if set, ~0U if unset
bool m_tabledef_valid;
bool master_had_triggers;
RPL_TABLE_LIST(const LEX_CSTRING *db_arg, const LEX_CSTRING *table_name_arg, RPL_TABLE_LIST(const LEX_CSTRING *db_arg, const LEX_CSTRING *table_name_arg,
thr_lock_type thr_lock_type, thr_lock_type thr_lock_type,
table_def &&tabledef, bool master_had_trigers) table_def &&tabledef, bool master_had_trigers)
: TABLE_LIST(db_arg, table_name_arg, NULL, thr_lock_type), : TABLE_LIST(db_arg, table_name_arg, NULL, thr_lock_type),
m_tabledef_valid(true), master_had_triggers(master_had_trigers),
m_tabledef(std::move(tabledef)), m_conv_table(NULL), m_tabledef(std::move(tabledef)), m_conv_table(NULL),
m_online_alter_copy_fields(NULL), m_online_alter_copy_fields(NULL), m_online_alter_copy_fields_end(NULL),
m_online_alter_copy_fields_end(NULL) cached_key_nr(~0U), m_tabledef_valid(true),
master_had_triggers(master_had_trigers)
{} {}
RPL_TABLE_LIST(TABLE *table, thr_lock_type lock_type, TABLE *conv_table, RPL_TABLE_LIST(TABLE *table, thr_lock_type lock_type, TABLE *conv_table,
table_def &&tabledef, table_def &&tabledef,
const Copy_field online_alter_copy_fields[], const Copy_field online_alter_copy_fields[],
const Copy_field *online_alter_copy_fields_end) const Copy_field *online_alter_copy_fields_end)
: TABLE_LIST(table, lock_type), : TABLE_LIST(table, lock_type),
m_tabledef_valid(true), m_tabledef(std::move(tabledef)), m_conv_table(conv_table),
master_had_triggers(false), m_online_alter_copy_fields(online_alter_copy_fields),
m_tabledef(std::move(tabledef)), m_online_alter_copy_fields_end(online_alter_copy_fields_end),
m_conv_table(conv_table), cached_key_nr(~0U), m_tabledef_valid(true), master_had_triggers(false)
m_online_alter_copy_fields(online_alter_copy_fields),
m_online_alter_copy_fields_end(online_alter_copy_fields_end)
{} {}
}; };
......
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