63
63
void table_cache_free(void)
65
DBUG_ENTER("table_cache_free");
66
65
if (table_def_inited)
68
67
close_cached_tables(NULL, NULL, false, false, false);
69
68
if (!open_cache.records) // Safety first
70
69
hash_free(&open_cache);
75
74
uint cached_open_tables(void)
77
76
return open_cache.records;
82
static void check_unused(void)
84
uint count= 0, open_files= 0, idx= 0;
85
TABLE *cur_link,*start_link;
87
if ((start_link=cur_link=unused_tables))
91
if (cur_link != cur_link->next->prev || cur_link != cur_link->prev->next)
93
DBUG_PRINT("error",("Unused_links aren't linked properly")); /* purecov: inspected */
94
return; /* purecov: inspected */
96
} while (count++ < open_cache.records &&
97
(cur_link=cur_link->next) != start_link);
98
if (cur_link != start_link)
100
DBUG_PRINT("error",("Unused_links aren't connected")); /* purecov: inspected */
103
for (idx=0 ; idx < open_cache.records ; idx++)
105
TABLE *entry=(TABLE*) hash_element(&open_cache,idx);
113
DBUG_PRINT("error",("Unused_links doesn't match open_cache: diff: %d", /* purecov: inspected */
114
count)); /* purecov: inspected */
117
#ifdef NOT_SAFE_FOR_REPAIR
119
check that open cache and table definition cache has same number of
123
for (idx=0 ; idx < table_def_cache.records ; idx++)
125
TABLE_SHARE *entry= (TABLE_SHARE*) hash_element(&table_def_cache,idx);
126
count+= entry->ref_count;
128
if (count != open_files)
130
DBUG_PRINT("error", ("table_def ref_count: %u open_cache: %u",
132
DBUG_ASSERT(count == open_files);
137
#define check_unused()
142
80
Create a table cache key
307
242
if (my_hash_insert(&table_def_cache, (uchar*) share))
309
244
free_table_share(share);
310
DBUG_RETURN(0); // return error
245
return(0); // return error
312
247
if (open_table_def(thd, share, db_flags))
314
249
*error= share->error;
315
250
(void) hash_delete(&table_def_cache, (uchar*) share);
318
253
share->ref_count++; // Mark in use
319
DBUG_PRINT("exit", ("share: 0x%lx ref_count: %u",
320
(ulong) share, share->ref_count));
321
254
(void) pthread_mutex_unlock(&share->mutex);
334
267
/* Table definition contained an error */
335
268
open_table_error(share, share->error, share->open_errno, share->errarg);
336
269
(void) pthread_mutex_unlock(&share->mutex);
340
273
if (!share->ref_count++ && share->prev)
343
276
Share was not used before and it was in the old_unused_share list
344
277
Unlink share from this list
346
DBUG_PRINT("info", ("Unlinking from not used list"));
347
279
pthread_mutex_lock(&LOCK_table_share);
348
280
*share->prev= share->next;
349
281
share->next->prev= share->prev;
361
293
VOID(hash_delete(&table_def_cache, (uchar*) oldest_unused_share));
364
DBUG_PRINT("exit", ("share: 0x%lx ref_count: %u",
365
(ulong) share, share->ref_count));
381
311
TABLE_SHARE *share;
383
DBUG_ENTER("get_table_share_with_create");
385
314
share= get_table_share(thd, table_list, key, key_length, db_flags, error);
405
334
if (share || (thd->is_error() && (thd->main_da.sql_errno() != ER_NO_SUCH_TABLE)))
409
338
/* Table didn't exist. Check if some engine can provide it */
410
339
if ((tmp= ha_create_table_from_engine(thd, table_list->db,
423
352
thd->clear_error();
424
353
my_error(ER_VIEW_INVALID, MYF(0), "", "");
430
359
/* Give right error message */
431
360
thd->clear_error();
432
DBUG_PRINT("error", ("Discovery of %s/%s failed", table_list->db,
433
table_list->table_name));
434
361
my_printf_error(ER_UNKNOWN_ERROR,
435
362
"Failed to open '%-.64s', error while "
436
363
"unpacking from engine",
437
364
MYF(0), table_list->table_name);
440
367
/* Table existed in engine. Let's open it */
441
368
mysql_reset_errors(thd, 1); // Clear warnings
442
369
thd->clear_error(); // Clear error message
443
DBUG_RETURN(get_table_share(thd, table_list, key, key_length,
370
return(get_table_share(thd, table_list, key, key_length,
444
371
db_flags, error));
470
397
enum release_type type __attribute__((__unused__)))
472
399
bool to_be_deleted= 0;
473
DBUG_ENTER("release_table_share");
475
("share: 0x%lx table: %s.%s ref_count: %u version: %lu",
476
(ulong) share, share->db.str, share->table_name.str,
477
share->ref_count, share->version));
479
401
safe_mutex_assert_owner(&LOCK_open);
488
410
/* Link share last in used_table_share list */
489
DBUG_PRINT("info",("moving share to unused list"));
491
DBUG_ASSERT(share->next == 0);
411
assert(share->next == 0);
492
412
pthread_mutex_lock(&LOCK_table_share);
493
413
share->prev= end_of_unused_share.prev;
494
414
*end_of_unused_share.prev= share;
561
480
TABLE_SHARE *share, *old_share= table->s;
563
482
MEM_ROOT *mem_root= &table->mem_root;
564
DBUG_ENTER("close_handle_and_leave_table_as_lock");
566
DBUG_ASSERT(table->db_stat);
484
assert(table->db_stat);
569
487
Make a local copy of the table share and free the current one.
617
535
OPEN_TABLE_LIST **start_list, *open_list;
618
536
TABLE_LIST table_list;
619
DBUG_ENTER("list_open_tables");
621
538
VOID(pthread_mutex_lock(&LOCK_open));
622
539
bzero((char*) &table_list,sizeof(table_list));
680
597
void intern_close_table(TABLE *table)
681
598
{ // Free all structures
682
DBUG_ENTER("intern_close_table");
683
DBUG_PRINT("tcache", ("table: '%s'.'%s' 0x%lx",
684
table->s ? table->s->db.str : "?",
685
table->s ? table->s->table_name.str : "?",
688
599
free_io_cache(table);
689
600
if (table->file) // Not true if name lock
690
601
VOID(closefrm(table, 1)); // close file
717
626
if (table == unused_tables)
720
check_unused(); // consisty check
722
630
my_free((uchar*) table,MYF(0));
726
634
/* Free resources allocated by filesort() and read_record() */
728
636
void free_io_cache(TABLE *table)
730
DBUG_ENTER("free_io_cache");
731
638
if (table->sort.io_cache)
733
640
close_cached_file(table->sort.io_cache);
734
641
my_free((uchar*) table->sort.io_cache,MYF(0));
735
642
table->sort.io_cache=0;
757
664
bool wait_for_refresh, bool wait_for_placeholders)
760
DBUG_ENTER("close_cached_tables");
761
DBUG_ASSERT(thd || (!wait_for_refresh && !tables));
667
assert(thd || (!wait_for_refresh && !tables));
764
670
VOID(pthread_mutex_lock(&LOCK_open));
780
686
pthread_mutex_lock(&oldest_unused_share->mutex);
781
687
VOID(hash_delete(&table_def_cache, (uchar*) oldest_unused_share));
783
DBUG_PRINT("tcache", ("incremented global refresh_version to: %lu",
785
689
if (wait_for_refresh)
1066
966
VOID(pthread_mutex_lock(&LOCK_open));
1068
DBUG_PRINT("info", ("thd->open_tables: 0x%lx", (long) thd->open_tables));
1070
968
while (thd->open_tables)
1071
969
found_old_table|= close_thread_table(thd, &thd->open_tables);
1072
970
thd->some_tables_deleted= 0;
1074
972
/* Free tables to hold down open files */
1075
973
while (open_cache.records > table_cache_size && unused_tables)
1076
974
VOID(hash_delete(&open_cache,(uchar*) unused_tables)); /* purecov: tested */
1078
975
if (found_old_table)
1080
977
/* Tell threads waiting for refresh that something has happened */
1202
1098
bool found_old_table= 0;
1203
1099
TABLE *table= *table_ptr;
1204
DBUG_ENTER("close_thread_table");
1205
DBUG_ASSERT(table->key_read == 0);
1206
DBUG_ASSERT(!table->file || table->file->inited == handler::NONE);
1207
DBUG_PRINT("tcache", ("table: '%s'.'%s' 0x%lx", table->s->db.str,
1208
table->s->table_name.str, (long) table));
1101
assert(table->key_read == 0);
1102
assert(!table->file || table->file->inited == handler::NONE);
1210
1104
*table_ptr=table->next;
1221
1115
Open placeholders have TABLE::db_stat set to 0, so they should be
1222
1116
handled by the first alternative.
1224
DBUG_ASSERT(!table->open_placeholder);
1118
assert(!table->open_placeholder);
1226
1120
/* Free memory and reset for next loop */
1227
1121
table->file->ha_reset();
1468
1362
TABLE_LIST *res;
1469
1363
const char *d_name, *t_name, *t_alias;
1470
DBUG_ENTER("unique_table");
1471
DBUG_PRINT("enter", ("table alias: %s", table->alias));
1474
1366
If this function called for query which update table (INSERT/UPDATE/...)
1485
1377
/* temporary table is always unique */
1486
1378
if (table->table && table->table->s->tmp_table != NO_TMP_TABLE)
1488
1380
table= table->find_underlying_table(table->table);
1490
1382
as far as we have table->table we have to find real TABLE_LIST of
1491
1383
it in underlying tables
1495
1387
d_name= table->db;
1496
1388
t_name= table->table_name;
1497
1389
t_alias= table->alias;
1499
DBUG_PRINT("info", ("real table: %s.%s", d_name, t_name));
1502
1393
if (((! (res= find_table_in_global_list(table_list, d_name, t_name))) &&
1557
1446
char key[MAX_DBKEY_LENGTH];
1558
1447
uint key_length;
1560
DBUG_ENTER("find_temporary_table");
1561
DBUG_PRINT("enter", ("table: '%s'.'%s'",
1562
table_list->db, table_list->table_name));
1564
1450
key_length= create_table_def_key(thd, key, table_list, 1);
1565
1451
for (table=thd->temporary_tables ; table ; table= table->next)
1567
1453
if (table->s->table_cache_key.length == key_length &&
1568
1454
!memcmp(table->s->table_cache_key.str, key, key_length))
1571
("Found table. server_id: %u pseudo_thread_id: %lu",
1572
(uint) thd->server_id,
1573
(ulong) thd->variables.pseudo_thread_id));
1577
DBUG_RETURN(0); // Not a temporary table
1457
return(0); // Not a temporary table
1607
1487
int drop_temporary_table(THD *thd, TABLE_LIST *table_list)
1610
DBUG_ENTER("drop_temporary_table");
1611
DBUG_PRINT("tmptable", ("closing table: '%s'.'%s'",
1612
table_list->db, table_list->table_name));
1614
1491
if (!(table= find_temporary_table(thd, table_list)))
1617
1494
/* Table might be in use by some outer statement. */
1618
1495
if (table->query_id && table->query_id != thd->query_id)
1620
1497
my_error(ER_CANT_REOPEN_TABLE, MYF(0), table->alias);
1628
1505
mysql_lock_remove(thd, thd->locked_tables, table, false);
1629
1506
close_temporary_table(thd, table, 1, 1);
1637
1514
void close_temporary_table(THD *thd, TABLE *table,
1638
1515
bool free_share, bool delete_table)
1640
DBUG_ENTER("close_temporary_table");
1641
DBUG_PRINT("tmptable", ("closing table: '%s'.'%s' 0x%lx alias: '%s'",
1642
table->s->db.str, table->s->table_name.str,
1643
(long) table, table->alias));
1645
1517
if (table->prev)
1647
1519
table->prev->next= table->next;
1653
1525
/* removing the item from the list */
1654
DBUG_ASSERT(table == thd->temporary_tables);
1526
assert(table == thd->temporary_tables);
1656
1528
slave must reset its temporary list pointer to zero to exclude
1657
1529
passing non-zero value to end_slave via rli->save_temporary_tables
1664
1536
if (thd->slave_thread)
1666
1538
/* natural invariant of temporary_tables */
1667
DBUG_ASSERT(slave_open_temp_tables || !thd->temporary_tables);
1539
assert(slave_open_temp_tables || !thd->temporary_tables);
1668
1540
slave_open_temp_tables--;
1670
1542
close_temporary(table, free_share, delete_table);
1683
1555
void close_temporary(TABLE *table, bool free_share, bool delete_table)
1685
1557
handlerton *table_type= table->s->db_type();
1686
DBUG_ENTER("close_temporary");
1687
DBUG_PRINT("tmptable", ("closing table: '%s'.'%s'",
1688
table->s->db.str, table->s->table_name.str));
1690
1559
free_io_cache(table);
1691
1560
closefrm(table, 0);
1720
1589
uint key_length;
1721
1590
TABLE_SHARE *share= table->s;
1722
1591
TABLE_LIST table_list;
1723
DBUG_ENTER("rename_temporary_table");
1725
1593
if (!(key=(char*) alloc_root(&share->mem_root, MAX_DBKEY_LENGTH)))
1726
DBUG_RETURN(1); /* purecov: inspected */
1594
return(1); /* purecov: inspected */
1728
1596
table_list.db= (char*) db;
1729
1597
table_list.table_name= (char*) table_name;
1730
1598
key_length= create_table_def_key(thd, key, &table_list, 1);
1731
1599
share->set_table_cache_key(key, key_length);
1869
1735
thd->mysys_var->current_cond= cond;
1870
1736
proc_info=thd->proc_info;
1871
1737
thd_proc_info(thd, "Waiting for table");
1872
DBUG_ENTER("wait_for_condition");
1873
1738
if (!thd->killed)
1874
1739
(void) pthread_cond_wait(cond, mutex);
1907
1772
bool name_lock_locked_table(THD *thd, TABLE_LIST *tables)
1909
DBUG_ENTER("name_lock_locked_table");
1911
1774
/* Under LOCK TABLES we must only accept write locked tables. */
1912
1775
tables->table= find_locked_table(thd, tables->db, tables->table_name);
2097
1957
char key[MAX_DBKEY_LENGTH];
2098
1958
uint key_length;
2099
DBUG_ENTER("lock_table_name_if_not_cached");
2101
1960
key_length= (uint)(strmov(strmov(key, db) + 1, table_name) - key) + 1;
2102
1961
VOID(pthread_mutex_lock(&LOCK_open));
2104
1963
if (hash_search(&open_cache, (uchar *)key, key_length))
2106
1965
VOID(pthread_mutex_unlock(&LOCK_open));
2107
DBUG_PRINT("info", ("Table is cached, name-lock is not obtained"));
2111
1969
if (!(*table= table_cache_insert_placeholder(thd, key, key_length)))
2113
1971
VOID(pthread_mutex_unlock(&LOCK_open));
2116
1974
(*table)->open_placeholder= 1;
2117
1975
(*table)->next= thd->open_tables;
2118
1976
thd->open_tables= *table;
2119
1977
VOID(pthread_mutex_unlock(&LOCK_open));
2147
2005
char path[FN_REFLEN];
2149
DBUG_ENTER("check_if_table_exists");
2151
2008
safe_mutex_assert_owner(&LOCK_open);
2155
2012
if (get_cached_table_share(table->db, table->table_name))
2158
2015
build_table_filename(path, sizeof(path) - 1, table->db, table->table_name,
2161
2018
if (!access(path, F_OK))
2164
2021
/* .FRM file doesn't exist. Check if some engine can provide it. */
2170
2027
/* Table does not exists in engines as well. */
2171
2028
*exists= false;
2176
2033
/* Table exists in some engine and .FRM for it was created. */
2179
2036
else /* (rc > 0) */
2181
2038
my_printf_error(ER_UNKNOWN_ERROR, "Failed to open '%-.64s', error while "
2182
2039
"unpacking from engine", MYF(0), table->table_name);
2226
2083
unsigned int key_length;
2227
2084
char *alias= table_list->alias;
2228
2085
HASH_SEARCH_STATE state;
2229
DBUG_ENTER("open_table");
2231
2087
/* Parsing of partitioning information from .frm needs thd->lex set up. */
2232
DBUG_ASSERT(thd->lex->is_lex_started);
2088
assert(thd->lex->is_lex_started);
2234
2090
/* find a unused table in the open table cache */
2238
2094
/* an open table operation needs a lot of the stack space */
2239
2095
if (check_stack_overrun(thd, STACK_MIN_SIZE_FOR_OPEN, (uchar *)&alias))
2242
2098
if (thd->killed)
2245
2101
key_length= (create_table_def_key(thd, key, table_list, 1) -
2246
2102
TMP_TABLE_KEY_EXTRA);
2269
2125
if (table->query_id)
2272
("query_id: %lu server_id: %u pseudo_thread_id: %lu",
2273
(ulong) table->query_id, (uint) thd->server_id,
2274
(ulong) thd->variables.pseudo_thread_id));
2275
2127
my_error(ER_CANT_REOPEN_TABLE, MYF(0), table->alias);
2278
2130
table->query_id= thd->query_id;
2279
2131
thd->thread_specific_used= true;
2280
DBUG_PRINT("info",("Using temporary table"));
2318
2169
my_error(ER_CANT_UPDATE_USED_TABLE_IN_SF_OR_TRG, MYF(0),
2319
2170
table->s->table_name.str);
2323
2174
When looking for a usable TABLE, ignore MERGE children, as they
2440
2290
table= (TABLE*) hash_next(&open_cache, (uchar*) key, key_length,
2443
DBUG_PRINT("tcache", ("in_use table: '%s'.'%s' 0x%lx", table->s->db.str,
2444
table->s->table_name.str, (long) table));
2446
2294
Here we flush tables marked for flush.
2447
2295
Normally, table->s->version contains the value of
2463
2311
if (table->needs_reopen_or_name_lock())
2466
("Found table '%s.%s' with different refresh version",
2467
table_list->db, table_list->table_name));
2469
2313
if (flags & MYSQL_LOCK_IGNORE_FLUSH)
2471
2315
/* Force close at once after usage */
2533
DBUG_PRINT("tcache", ("unused table: '%s'.'%s' 0x%lx", table->s->db.str,
2534
table->s->table_name.str, (long) table));
2535
2377
/* Unlink the table from "unused_tables" list. */
2536
2378
if (table == unused_tables)
2537
2379
{ // First unused
2548
2390
/* Insert a new TABLE instance into the open cache */
2550
DBUG_PRINT("tcache", ("opening new table"));
2551
2392
/* Free cache if too big */
2552
2393
while (open_cache.records > table_cache_size && unused_tables)
2553
2394
VOID(hash_delete(&open_cache,(uchar*) unused_tables)); /* purecov: tested */
2590
2431
if (!(table=(TABLE*) my_malloc(sizeof(*table),MYF(MY_WME))))
2592
2433
VOID(pthread_mutex_unlock(&LOCK_open));
2596
2437
error= open_unireg_entry(thd, table, table_list, alias, key, key_length,
2601
2442
my_free((uchar*)table, MYF(0));
2602
2443
VOID(pthread_mutex_unlock(&LOCK_open));
2607
2448
my_free((uchar*)table, MYF(0));
2608
2449
VOID(pthread_mutex_unlock(&LOCK_open));
2609
DBUG_RETURN(0); // VIEW
2611
DBUG_PRINT("info", ("inserting table '%s'.'%s' 0x%lx into the cache",
2612
table->s->db.str, table->s->table_name.str,
2614
2452
VOID(my_hash_insert(&open_cache,(uchar*) table));
2617
check_unused(); // Debugging call
2619
2455
VOID(pthread_mutex_unlock(&LOCK_open));
2625
2461
table->reginfo.lock_type=TL_READ; /* Assume read */
2628
DBUG_ASSERT(table->s->ref_count > 0 || table->s->tmp_table != NO_TMP_TABLE);
2464
assert(table->s->ref_count > 0 || table->s->tmp_table != NO_TMP_TABLE);
2630
2466
if (thd->lex->need_correct_ident())
2631
2467
table->alias_name_used= my_strcasecmp(table_alias_charset,
2648
2484
table->fulltext_searched= 0;
2649
2485
table->file->ft_handler= 0;
2650
2486
/* Catch wrong handling of the auto_increment_field_not_null. */
2651
DBUG_ASSERT(!table->auto_increment_field_not_null);
2487
assert(!table->auto_increment_field_not_null);
2652
2488
table->auto_increment_field_not_null= false;
2653
2489
if (table->timestamp_field)
2654
2490
table->timestamp_field_type= table->timestamp_field->get_auto_set_type();
2655
2491
table->pos_in_table_list= table_list;
2656
2492
table->clear_column_bitmaps();
2657
DBUG_ASSERT(table->key_read == 0);
2493
assert(table->key_read == 0);
2699
2535
TABLE_LIST table_list;
2700
2536
THD *thd= table->in_use;
2701
DBUG_ENTER("reopen_table");
2702
DBUG_PRINT("tcache", ("table: '%s'.'%s' 0x%lx", table->s->db.str,
2703
table->s->table_name.str, (long) table));
2705
DBUG_ASSERT(table->s->ref_count == 0);
2706
DBUG_ASSERT(!table->sort.io_cache);
2538
assert(table->s->ref_count == 0);
2539
assert(!table->sort.io_cache);
2708
2541
#ifdef EXTRA_DEBUG
2709
2542
if (table->db_stat)
2716
2549
table_list.table= table;
2718
2551
if (wait_for_locked_table_names(thd, &table_list))
2719
DBUG_RETURN(1); // Thread was killed
2552
return(1); // Thread was killed
2721
2554
if (open_unireg_entry(thd, &tmp, &table_list,
2750
2583
table->default_column_bitmaps();
2751
2584
table->file->change_table_ptr(table, table->s);
2753
DBUG_ASSERT(table->alias != 0);
2586
assert(table->alias != 0);
2754
2587
for (field=table->field ; *field ; field++)
2756
2589
(*field)->table= (*field)->orig_table= table;
2963
2790
bool send_refresh)
2965
2792
bool found= send_refresh;
2966
DBUG_ENTER("close_old_data_files");
2968
2794
for (; table ; table=table->next)
2970
DBUG_PRINT("tcache", ("checking table: '%s'.'%s' 0x%lx",
2971
table->s->db.str, table->s->table_name.str,
2973
DBUG_PRINT("tcache", ("needs refresh: %d is open: %u",
2974
table->needs_reopen_or_name_lock(), table->db_stat));
2976
2797
Reopen marked for flush.
3046
2867
bool table_is_used(TABLE *table, bool wait_for_name_lock)
3048
DBUG_ENTER("table_is_used");
3051
2871
char *key= table->s->table_cache_key.str;
3052
2872
uint key_length= table->s->table_cache_key.length;
3054
DBUG_PRINT("loop", ("table_name: %s", table->alias));
3055
2874
HASH_SEARCH_STATE state;
3056
2875
for (TABLE *search= (TABLE*) hash_first(&open_cache, (uchar*) key,
3057
2876
key_length, &state);
3059
2878
search= (TABLE*) hash_next(&open_cache, (uchar*) key,
3060
2879
key_length, &state))
3062
DBUG_PRINT("info", ("share: 0x%lx "
3063
"open_placeholder: %d locked_by_name: %d "
3064
"db_stat: %u version: %lu",
3066
search->open_placeholder, search->locked_by_name,
3068
search->s->version));
3069
2881
if (search->in_use == table->in_use)
3070
2882
continue; // Name locked by this thread
3089
2901
bool wait_for_tables(THD *thd)
3092
DBUG_ENTER("wait_for_tables");
3094
2905
thd_proc_info(thd, "Waiting for tables");
3095
2906
pthread_mutex_lock(&LOCK_open);
3146
2957
TABLE *table,*next,**prev, *found= 0;
3147
2958
prev= &thd->open_tables;
3148
DBUG_ENTER("drop_locked_tables");
3151
2961
Note that we need to hold LOCK_open while changing the
3252
3062
static ulong last_table_id= ~0UL;
3254
DBUG_ENTER("assign_new_table_id");
3256
3064
/* Preconditions */
3257
DBUG_ASSERT(share != NULL);
3065
assert(share != NULL);
3258
3066
safe_mutex_assert_owner(&LOCK_open);
3260
3068
ulong tid= ++last_table_id; /* get next id */
3265
3073
if (unlikely(tid == ~0UL))
3266
3074
tid= ++last_table_id;
3267
3075
share->table_map_id= tid;
3268
DBUG_PRINT("info", ("table_id=%lu", tid));
3270
3077
/* Post conditions */
3271
DBUG_ASSERT(share->table_map_id != ~0UL);
3078
assert(share->table_map_id != ~0UL);
3316
3122
table_list->i_s_requested_object,
3320
3126
while ((error= open_table_from_share(thd, share, alias,
3321
3127
(uint) (HA_OPEN_KEYFILE |
3508
3313
for (tables= *start; tables ;tables= tables->next_global)
3510
DBUG_PRINT("tcache", ("opening table: '%s'.'%s' item: 0x%lx",
3511
tables->db, tables->table_name, (long) tables));
3513
3315
safe_to_ignore_table= false;
3541
3343
not opened yet. Try to open the table.
3543
3345
if (!tables->table)
3545
3346
tables->table= open_table(thd, tables, &new_frm_mem, &refresh, flags);
3548
DBUG_PRINT("tcache", ("referenced table: '%s'.'%s' 0x%lx",
3549
tables->db, tables->table_name,
3550
(long) tables->table));
3552
3348
if (!tables->table)
3576
3372
if (safe_to_ignore_table)
3578
DBUG_PRINT("info", ("open_table: ignoring table '%s'.'%s'",
3579
tables->db, tables->alias));
3583
3375
result= -1; // Fatal error
3629
3420
thr_lock_type lock_type)
3632
DBUG_ENTER("check_lock_and_start_stmt");
3634
3424
if ((int) lock_type >= (int) TL_WRITE_ALLOW_READ &&
3635
3425
(int) table->reginfo.lock_type < (int) TL_WRITE_ALLOW_READ)
3637
3427
my_error(ER_TABLE_NOT_LOCKED_FOR_WRITE, MYF(0),table->alias);
3640
3430
if ((error=table->file->start_stmt(thd, lock_type)))
3642
3432
table->file->print_error(error,MYF(0));
3756
DBUG_ASSERT(thd->lock == 0); // You must lock everything at once
3544
assert(thd->lock == 0); // You must lock everything at once
3757
3545
if ((table->reginfo.lock_type= lock_type) != TL_UNLOCK)
3758
3546
if (! (thd->lock= mysql_lock_tables(thd, &table_list->table, 1,
3759
3547
lock_flags, &refresh)))
3796
3584
bool need_reopen;
3797
DBUG_ENTER("open_and_lock_tables_derived");
3798
DBUG_PRINT("enter", ("derived handling: %d", derived));
3802
3588
if (open_tables(thd, &tables, &counter, 0))
3805
DBUG_EXECUTE_IF("sleep_open_and_lock_after_open", {
3806
const char *old_proc_info= thd->proc_info;
3807
thd->proc_info= "DBUG sleep";
3809
thd->proc_info= old_proc_info;});
3811
3591
if (!lock_tables(thd, tables, counter, &need_reopen))
3813
3593
if (!need_reopen)
3815
3595
close_tables_for_reopen(thd, &tables);
3818
3598
(mysql_handle_derived(thd->lex, &mysql_derived_prepare) ||
3819
3599
(thd->fill_derived_tables() &&
3820
3600
mysql_handle_derived(thd->lex, &mysql_derived_filling))))
3821
DBUG_RETURN(true); /* purecov: inspected */
3601
return(true); /* purecov: inspected */
3846
3626
bool open_normal_and_derived_tables(THD *thd, TABLE_LIST *tables, uint flags)
3849
DBUG_ENTER("open_normal_and_derived_tables");
3850
DBUG_ASSERT(!thd->fill_derived_tables());
3629
assert(!thd->fill_derived_tables());
3851
3630
if (open_tables(thd, &tables, &counter, flags) ||
3852
3631
mysql_handle_derived(thd->lex, &mysql_derived_prepare))
3853
DBUG_RETURN(true); /* purecov: inspected */
3632
return(true); /* purecov: inspected */
3905
3684
if (!table->placeholder() && table->lock_type >= TL_WRITE_ALLOW_WRITE)
3907
3686
ulonglong const flags= table->table->file->ha_table_flags();
3908
DBUG_PRINT("info", ("table: %s; ha_table_flags: %s%s",
3910
FLAGSTR(flags, HA_BINLOG_STMT_CAPABLE),
3911
FLAGSTR(flags, HA_BINLOG_ROW_CAPABLE)));
3912
3687
if (prev_ht && prev_ht != table->table->file->ht)
3913
3688
multi_engine= true;
3914
3689
prev_ht= table->table->file->ht;
3920
DBUG_PRINT("info", ("flags_all_set: %s%s",
3921
FLAGSTR(flags_all_set, HA_BINLOG_STMT_CAPABLE),
3922
FLAGSTR(flags_all_set, HA_BINLOG_ROW_CAPABLE)));
3923
DBUG_PRINT("info", ("flags_some_set: %s%s",
3924
FLAGSTR(flags_some_set, HA_BINLOG_STMT_CAPABLE),
3925
FLAGSTR(flags_some_set, HA_BINLOG_ROW_CAPABLE)));
3926
DBUG_PRINT("info", ("thd->variables.binlog_format: %ld",
3927
thd->variables.binlog_format));
3928
DBUG_PRINT("info", ("multi_engine: %s",
3929
multi_engine ? "true" : "false"));
3932
3696
if (flags_all_set == 0)
4034
3795
*need_reopen= false;
4037
DBUG_RETURN(decide_logging_format(thd, tables));
3798
return(decide_logging_format(thd, tables));
4039
3800
if (!thd->locked_tables)
4041
DBUG_ASSERT(thd->lock == 0); // You must lock everything at once
3802
assert(thd->lock == 0); // You must lock everything at once
4042
3803
TABLE **start,**ptr;
4043
3804
uint lock_flag= MYSQL_LOCK_NOTIFY_IF_NEED_REOPEN;
4045
3806
if (!(ptr=start=(TABLE**) thd->alloc(sizeof(TABLE*)*count)))
4047
3808
for (table= tables; table; table= table->next_global)
4049
3810
if (!table->placeholder())
4074
3835
if (!table->placeholder() &&
4075
3836
check_lock_and_start_stmt(thd, table->table, table->lock_type))
4082
DBUG_RETURN(decide_logging_format(thd, tables));
3843
return(decide_logging_format(thd, tables));
4138
3899
char cache_key[MAX_DBKEY_LENGTH], *saved_cache_key, *tmp_path;
4139
3900
uint key_length;
4140
3901
TABLE_LIST table_list;
4141
DBUG_ENTER("open_temporary_table");
4143
("table: '%s'.'%s' path: '%s' server_id: %u "
4144
"pseudo_thread_id: %lu",
4145
db, table_name, path,
4146
(uint) thd->server_id, (ulong) thd->variables.pseudo_thread_id));
4148
3903
table_list.db= (char*) db;
4149
3904
table_list.table_name= (char*) table_name;
4153
3908
if (!(tmp_table= (TABLE*) my_malloc(sizeof(*tmp_table) + sizeof(*share) +
4154
3909
strlen(path)+1 + key_length,
4156
DBUG_RETURN(0); /* purecov: inspected */
3911
return(0); /* purecov: inspected */
4158
3913
share= (TABLE_SHARE*) (tmp_table+1);
4159
3914
tmp_path= (char*) (share+1);
4206
3961
slave_open_temp_tables++;
4208
3963
tmp_table->pos_in_table_list= 0;
4209
DBUG_PRINT("tmptable", ("opened table: '%s'.'%s' 0x%lx", tmp_table->s->db.str,
4210
tmp_table->s->table_name.str, (long) tmp_table));
4211
DBUG_RETURN(tmp_table);
4253
4005
static void update_field_dependencies(THD *thd, Field *field, TABLE *table)
4255
DBUG_ENTER("update_field_dependencies");
4256
4007
if (thd->mark_used_columns != MARK_COLUMNS_NONE)
4258
4009
MY_BITMAP *current_bitmap, *other_bitmap;
4279
4030
if (bitmap_fast_test_and_set(current_bitmap, field->field_index))
4281
4032
if (thd->mark_used_columns == MARK_COLUMNS_WRITE)
4283
DBUG_PRINT("warning", ("Found duplicated field"));
4284
4033
thd->dup_field= field;
4288
DBUG_PRINT("note", ("Field found before"));
4292
4036
if (table->get_fields_in_item_tree)
4293
4037
field->flags|= GET_FIXED_FIELDS_FLAG;
4328
4072
bool register_tree_change __attribute__((__unused__)))
4330
DBUG_ENTER("find_field_in_view");
4332
("view: '%s', field name: '%s', item name: '%s', ref 0x%lx",
4333
table_list->alias, name, item_name, (ulong) ref));
4334
4074
Field_iterator_view field_it;
4335
4075
field_it.set(table_list);
4337
DBUG_ASSERT(table_list->schema_table_reformed ||
4077
assert(table_list->schema_table_reformed ||
4338
4078
(ref != 0 && (0) != 0));
4339
4079
for (; !field_it.end_of_fields(); field_it.next())
4411
4151
field_it(*(table_ref->join_columns));
4412
4152
Natural_join_column *nj_col, *curr_nj_col;
4413
4153
Field *found_field;
4414
DBUG_ENTER("find_field_in_natural_join");
4415
DBUG_PRINT("enter", ("field name: '%s', ref 0x%lx",
4416
name, (ulong) ref));
4417
DBUG_ASSERT(table_ref->is_natural_join && table_ref->join_columns);
4418
DBUG_ASSERT(*actual_table == NULL);
4155
assert(table_ref->is_natural_join && table_ref->join_columns);
4156
assert(*actual_table == NULL);
4420
4158
for (nj_col= NULL, curr_nj_col= field_it++; curr_nj_col;
4421
4159
curr_nj_col= field_it++)
4465
4203
already('mysql_schema_table' function). So we can return
4466
4204
->field. It is used only for 'show & where' commands.
4468
DBUG_RETURN(((Item_field*) (nj_col->view_field->item))->field);
4206
return(((Item_field*) (nj_col->view_field->item))->field);
4470
4208
if (register_tree_change)
4471
4209
thd->change_item_tree(ref, item);
4478
4216
/* This is a base table. */
4479
DBUG_ASSERT(nj_col->view_field == NULL);
4480
DBUG_ASSERT(nj_col->table_ref->table == nj_col->table_field->table);
4217
assert(nj_col->view_field == NULL);
4218
assert(nj_col->table_ref->table == nj_col->table_field->table);
4481
4219
found_field= nj_col->table_field;
4482
4220
update_field_dependencies(thd, found_field, nj_col->table_ref->table);
4485
4223
*actual_table= nj_col->table_ref;
4487
DBUG_RETURN(found_field);
4225
return(found_field);
4513
4251
Field **field_ptr, *field;
4514
4252
uint cached_field_index= *cached_field_index_ptr;
4515
DBUG_ENTER("find_field_in_table");
4516
DBUG_PRINT("enter", ("table: '%s', field name: '%s'", table->alias, name));
4518
4254
/* We assume here that table->field < NO_CACHED_FIELD_INDEX = UINT_MAX */
4519
4255
if (cached_field_index < table->s->fields &&
4552
4288
if (!allow_rowid ||
4553
4289
my_strcasecmp(system_charset_info, name, "_rowid") ||
4554
4290
table->s->rowid_field_offset == 0)
4555
DBUG_RETURN((Field*) 0);
4556
4292
field= table->field[table->s->rowid_field_offset-1];
4559
4295
update_field_dependencies(thd, field, table);
4614
4350
bool register_tree_change, TABLE_LIST **actual_table)
4617
DBUG_ENTER("find_field_in_table_ref");
4618
DBUG_ASSERT(table_list->alias);
4620
DBUG_ASSERT(item_name);
4622
("table: '%s' field name: '%s' item name: '%s' ref 0x%lx",
4623
table_list->alias, name, item_name, (ulong) ref));
4354
assert(table_list->alias);
4626
4359
Check that the table and database that qualify the current field name
4651
4384
(my_strcasecmp(table_alias_charset, table_list->alias, table_name) ||
4652
4385
(db_name && db_name[0] && table_list->db && table_list->db[0] &&
4653
4386
strcmp(db_name, table_list->db))))
4656
4389
*actual_table= NULL;
4665
4398
else if (!table_list->nested_join)
4667
4400
/* 'table_list' is a stored table. */
4668
DBUG_ASSERT(table_list->table);
4401
assert(table_list->table);
4669
4402
if ((fld= find_field_in_table(thd, table_list->table, name, length,
4671
4404
cached_field_index_ptr)))
4691
4424
check_privileges, allow_rowid,
4692
4425
cached_field_index_ptr,
4693
4426
register_tree_change, actual_table)))
4699
4432
Non-qualified field, search directly in the result columns of the
5381
5114
!table_ref_2->is_natural_join) ?
5382
5115
NULL : table_ref_2;
5384
DBUG_ENTER("mark_common_columns");
5385
DBUG_PRINT("info", ("operand_1: %s operand_2: %s",
5386
table_ref_1->alias, table_ref_2->alias));
5388
5117
*found_using_fields= 0;
5390
5119
for (it_1.set(table_ref_1); !it_1.end_of_fields(); it_1.next())
5398
5127
field_name_1= nj_col_1->name();
5399
5128
is_using_column_1= using_fields &&
5400
5129
test_if_string_in_list(field_name_1, using_fields);
5401
DBUG_PRINT ("info", ("field_name_1=%s.%s",
5402
nj_col_1->table_name() ? nj_col_1->table_name() : "",
5406
5132
Find a field with the same name in table_ref_2.
5417
5143
if (!(cur_nj_col_2= it_2.get_or_create_column_ref(leaf_2)))
5419
5145
cur_field_name_2= cur_nj_col_2->name();
5420
DBUG_PRINT ("info", ("cur_field_name_2=%s.%s",
5421
cur_nj_col_2->table_name() ?
5422
cur_nj_col_2->table_name() : "",
5426
5148
Compare the two columns and check for duplicate common fields.
5436
5158
if (!my_strcasecmp(system_charset_info, field_name_1, cur_field_name_2))
5438
DBUG_PRINT ("info", ("match c1.is_common=%d", nj_col_1->is_common));
5439
5160
if (cur_nj_col_2->is_common ||
5440
5161
(found && (!using_fields || is_using_column_1)))
5479
5200
The following assert checks that the two created items are of
5480
5201
type Item_ident.
5482
DBUG_ASSERT(!thd->lex->current_select->no_wrap_view_item);
5203
assert(!thd->lex->current_select->no_wrap_view_item);
5484
5205
In the case of no_wrap_view_item == 0, the created items must be
5485
5206
of sub-classes of Item_ident.
5487
DBUG_ASSERT(item_1->type() == Item::FIELD_ITEM ||
5208
assert(item_1->type() == Item::FIELD_ITEM ||
5488
5209
item_1->type() == Item::REF_ITEM);
5489
DBUG_ASSERT(item_2->type() == Item::FIELD_ITEM ||
5210
assert(item_2->type() == Item::FIELD_ITEM ||
5490
5211
item_2->type() == Item::REF_ITEM);
5520
5241
nj_col_1->is_common= nj_col_2->is_common= true;
5521
DBUG_PRINT ("info", ("%s.%s and %s.%s are common",
5522
nj_col_1->table_name() ?
5523
nj_col_1->table_name() : "",
5525
nj_col_2->table_name() ?
5526
nj_col_2->table_name() : "",
5612
5326
Natural_join_column *nj_col_1, *nj_col_2;
5613
5327
bool result= true;
5614
5328
List<Natural_join_column> *non_join_columns;
5615
DBUG_ENTER("store_natural_using_join_columns");
5617
DBUG_ASSERT(!natural_using_join->join_columns);
5330
assert(!natural_using_join->join_columns);
5619
5332
if (!(non_join_columns= new List<Natural_join_column>) ||
5620
5333
!(natural_using_join->join_columns= new List<Natural_join_column>))
5757
5468
cur_table_ref->outer_join & JOIN_TYPE_RIGHT)
5759
5470
/* This can happen only for JOIN ... ON. */
5760
DBUG_ASSERT(table_ref->nested_join->join_list.elements == 2);
5471
assert(table_ref->nested_join->join_list.elements == 2);
5761
5472
swap_variables(TABLE_LIST*, same_level_left_neighbor, cur_table_ref);
5785
5496
if (table_ref->is_natural_join)
5787
DBUG_ASSERT(table_ref->nested_join &&
5498
assert(table_ref->nested_join &&
5788
5499
table_ref->nested_join->join_list.elements == 2);
5789
5500
List_iterator_fast<TABLE_LIST> operand_it(table_ref->nested_join->join_list);
6006
5716
nesting_map save_allow_sum_func= thd->lex->allow_sum_func;
6007
5717
List_iterator<Item> it(fields);
6008
5718
bool save_is_item_list_lookup;
6009
DBUG_ENTER("setup_fields");
6011
5720
thd->mark_used_columns= mark_used_columns;
6012
DBUG_PRINT("info", ("thd->mark_used_columns: %d", thd->mark_used_columns));
6013
5721
if (allow_sum_func)
6014
5722
thd->lex->allow_sum_func|= 1 << thd->lex->current_select->nest_level;
6015
5723
thd->where= THD::DEFAULT_WHERE;
6039
5747
thd->lex->current_select->is_item_list_lookup= save_is_item_list_lookup;
6040
5748
thd->lex->allow_sum_func= save_allow_sum_func;
6041
5749
thd->mark_used_columns= save_mark_used_columns;
6042
DBUG_PRINT("info", ("thd->mark_used_columns: %d", thd->mark_used_columns));
6043
DBUG_RETURN(true); /* purecov: inspected */
5750
return(true); /* purecov: inspected */
6046
5753
*(ref++)= item;
6056
5763
thd->lex->allow_sum_func= save_allow_sum_func;
6057
5764
thd->mark_used_columns= save_mark_used_columns;
6058
DBUG_PRINT("info", ("thd->mark_used_columns: %d", thd->mark_used_columns));
6059
DBUG_RETURN(test(thd->is_error()));
5765
return(test(thd->is_error()));
6116
5822
TABLE_LIST **leaves, bool select_insert)
6118
5824
uint tablenr= 0;
6119
DBUG_ENTER("setup_tables");
6121
DBUG_ASSERT ((select_insert && !tables->next_name_resolution_table) || !tables ||
5826
assert ((select_insert && !tables->next_name_resolution_table) || !tables ||
6122
5827
(context->table_list && context->first_name_resolution_table));
6124
5829
this is used for INSERT ... SELECT.
6147
5852
setup_table_map(table, table_list, tablenr);
6148
5853
if (table_list->process_index_hints(table))
6151
5856
if (tablenr > MAX_TABLES)
6153
5858
my_error(ER_TOO_MANY_TABLES,MYF(0),MAX_TABLES);
6157
5862
/* Precompute and store the row types of NATURAL/USING joins. */
6158
5863
if (setup_natural_join_row_types(thd, from_clause, context))
6312
6016
TABLE *table= tables->table;
6314
DBUG_ASSERT(tables->is_leaf_for_name_resolution());
6018
assert(tables->is_leaf_for_name_resolution());
6316
6020
if ((table_name && my_strcasecmp(table_alias_charset, table_name, tables->alias)) ||
6317
6021
(db_name && strcmp(tables->db,db_name)))
6366
6070
Natural_join_column *nj_col;
6367
6071
if (!(nj_col= field_iterator.get_natural_column_ref()))
6369
DBUG_ASSERT(nj_col->table_field);
6073
assert(nj_col->table_field);
6370
6074
field_table= nj_col->table_ref->table;
6371
6075
if (field_table)
6443
6147
bool save_is_item_list_lookup= select_lex->is_item_list_lookup;
6444
6148
select_lex->is_item_list_lookup= 0;
6445
DBUG_ENTER("setup_conds");
6447
6150
thd->mark_used_columns= MARK_COLUMNS_READ;
6448
DBUG_PRINT("info", ("thd->mark_used_columns: %d", thd->mark_used_columns));
6449
6151
select_lex->cond_count= 0;
6450
6152
select_lex->between_count= 0;
6451
6153
select_lex->max_equal_elems= 0;
6490
6192
thd->thd_marker= save_thd_marker;
6492
6194
thd->lex->current_select->is_item_list_lookup= save_is_item_list_lookup;
6493
DBUG_RETURN(test(thd->is_error()));
6195
return(test(thd->is_error()));
6496
6198
select_lex->is_item_list_lookup= save_is_item_list_lookup;
6789
6488
TABLE_SHARE *share;
6790
6489
bool result= 0, signalled= 0;
6791
DBUG_ENTER("remove_table_from_cache");
6792
DBUG_PRINT("enter", ("table: '%s'.'%s' flags: %u", db, table_name, flags));
6794
6491
key_length=(uint) (strmov(strmov(key,db)+1,table_name)-key)+1;
6807
DBUG_PRINT("tcache", ("found table: '%s'.'%s' 0x%lx", table->s->db.str,
6808
table->s->table_name.str, (long) table));
6810
6505
table->s->version=0L; /* Free when thread is ready */
6811
6506
if (!(in_use=table->in_use))
6813
DBUG_PRINT("info",("Table was not in use"));
6814
6508
relink_unused(table);
6816
6510
else if (in_use != thd)
6818
DBUG_PRINT("info", ("Table was in use by other thread"));
6820
6513
Mark that table is going to be deleted from cache. This will
6821
6514
force threads that are in mysql_lock_tables() (but not yet
6824
6517
in_use->some_tables_deleted= 1;
6825
6518
if (table->is_name_opened())
6827
DBUG_PRINT("info", ("Found another active instance of the table"));
6830
6522
/* Kill delayed insert threads */
6865
DBUG_PRINT("info", ("Table was in use by current thread. db_stat: %u",
6867
6556
result= result || (flags & RTFC_OWNED_BY_THD_FLAG);
6870
6558
while (unused_tables && !unused_tables->s->version)
6871
6559
VOID(hash_delete(&open_cache,(uchar*) unused_tables));
6873
DBUG_PRINT("info", ("Removing table from table_def_cache"));
6874
6561
/* Remove table from table definition cache if it's not in use */
6875
6562
if ((share= (TABLE_SHARE*) hash_search(&table_def_cache,(uchar*) key,
6878
DBUG_PRINT("info", ("share version: %lu ref_count: %u",
6879
share->version, share->ref_count));
6880
6565
share->version= 0; // Mark for delete
6881
6566
if (share->ref_count == 0)
6958
6642
open_system_tables_for_read(THD *thd, TABLE_LIST *table_list,
6959
6643
Open_tables_state *backup)
6961
DBUG_ENTER("open_system_tables_for_read");
6963
6645
thd->reset_n_backup_open_tables_state(backup);
7037
6719
open_system_table_for_update(THD *thd, TABLE_LIST *one_table)
7039
DBUG_ENTER("open_system_table_for_update");
7041
6721
TABLE *table= open_ltable(thd, one_table, one_table->lock_type, 0);
7044
DBUG_ASSERT(table->s->table_category == TABLE_CATEGORY_SYSTEM);
6724
assert(table->s->table_category == TABLE_CATEGORY_SYSTEM);
7045
6725
table->use_all_columns();