diff options
author | unknown <bell@sanja.is.com.ua> | 2004-10-21 23:56:12 +0300 |
---|---|---|
committer | unknown <bell@sanja.is.com.ua> | 2004-10-21 23:56:12 +0300 |
commit | b50b1dd3a4b9cf5e4e9a6c33961b007becbda6bc (patch) | |
tree | adba151b89c3f3b0d8b6812947bd34aa47f36a7d | |
parent | 0a505ccc080eca79903103d081da8214bcd51d47 (diff) | |
download | mariadb-git-b50b1dd3a4b9cf5e4e9a6c33961b007becbda6bc.tar.gz |
Check of temporary tables hiding for query fetched from QC (BUG#6084)
mysql-test/r/query_cache.result:
hiding real table stored in query cache by temporary table
mysql-test/t/query_cache.test:
hiding real table stored in query cache by temporary table
sql/sql_cache.cc:
Check of temporary tables hiding for query fetched from QC
sql/sql_cache.h:
Key length now stored in table record of query cache
-rw-r--r-- | mysql-test/r/query_cache.result | 13 | ||||
-rw-r--r-- | mysql-test/t/query_cache.test | 12 | ||||
-rw-r--r-- | sql/sql_cache.cc | 32 | ||||
-rw-r--r-- | sql/sql_cache.h | 3 |
4 files changed, 59 insertions, 1 deletions
diff --git a/mysql-test/r/query_cache.result b/mysql-test/r/query_cache.result index a9e9f167e5f..85fe77b1f10 100644 --- a/mysql-test/r/query_cache.result +++ b/mysql-test/r/query_cache.result @@ -704,4 +704,17 @@ Qcache_queries_in_cache 1 unlock table; drop table t1,t2; set query_cache_wlock_invalidate=default; +CREATE TABLE t1 (id INT PRIMARY KEY); +insert into t1 values (1),(2),(3); +select * from t1; +id +1 +2 +3 +create temporary table t1 (a int not null auto_increment +primary key); +select * from t1; +a +drop table t1; +drop table t1; set GLOBAL query_cache_size=0; diff --git a/mysql-test/t/query_cache.test b/mysql-test/t/query_cache.test index 8a07c0a53a0..61fbadde1e1 100644 --- a/mysql-test/t/query_cache.test +++ b/mysql-test/t/query_cache.test @@ -521,4 +521,16 @@ unlock table; drop table t1,t2; set query_cache_wlock_invalidate=default; +# +# hiding real table stored in query cache by temporary table +# +CREATE TABLE t1 (id INT PRIMARY KEY); +insert into t1 values (1),(2),(3); +select * from t1; +create temporary table t1 (a int not null auto_increment +primary key); +select * from t1; +drop table t1; +drop table t1; + set GLOBAL query_cache_size=0; diff --git a/sql/sql_cache.cc b/sql/sql_cache.cc index 60f0cfadc8e..8e953e223a9 100644 --- a/sql/sql_cache.cc +++ b/sql/sql_cache.cc @@ -971,9 +971,38 @@ Query_cache::send_result_to_client(THD *thd, char *sql, uint query_length) for (; block_table != block_table_end; block_table++) { TABLE_LIST table_list; - bzero((char*) &table_list,sizeof(table_list)); + TABLE *tmptable; Query_cache_table *table = block_table->parent; + + /* + Check that we have not temporary tables with same names of tables + of this query. If we have such tables, we will not send data from + query cache, because temporary tables hide real tables by which + query in query cache was made. + */ + for (tmptable= thd->temporary_tables; tmptable ; tmptable= tmptable->next) + { + if (tmptable->key_length - 8 == table->key_len() && + !memcmp(tmptable->table_cache_key, table->data(), + table->key_len())) + { + DBUG_PRINT("qcache", + ("Temporary table detected: '%s.%s'", + table_list.db, table_list.alias)); + STRUCT_UNLOCK(&structure_guard_mutex); + /* + We should not store result of this query because it contain + temporary tables => assign following wariable to make check + faster. + */ + thd->safe_to_cache_query=0; + BLOCK_UNLOCK_RD(query_block); + DBUG_RETURN(-1); + } + } + + bzero((char*) &table_list,sizeof(table_list)); table_list.db = table->db(); table_list.alias= table_list.real_name= table->table(); if (check_table_access(thd,SELECT_ACL,&table_list,1)) @@ -2066,6 +2095,7 @@ Query_cache::insert_table(uint key_len, char *key, } char *db = header->db(); header->table(db + db_length + 1); + header->key_len(key_len); } Query_cache_block_table *list_root = table_block->table(0); diff --git a/sql/sql_cache.h b/sql/sql_cache.h index 0c6579250ab..454f0318c12 100644 --- a/sql/sql_cache.h +++ b/sql/sql_cache.h @@ -144,10 +144,13 @@ struct Query_cache_query struct Query_cache_table { char *tbl; + uint32 key_length; inline char *db() { return (char *) data(); } inline char *table() { return tbl; } inline void table(char *table) { tbl = table; } + inline uint32 key_len() { return key_length; } + inline void key_len(uint32 len) { key_length= len; } inline gptr data() { return (gptr)(((byte*)this)+ |