110
void write_bin_log(Session *session, const std::string &query)
108
void write_bin_log(Session *session,
112
111
TransactionServices &transaction_services= TransactionServices::singleton();
113
112
transaction_services.rawStatement(session, query);
116
/* Should should be refactored to go away */
117
void write_bin_log_drop_table(Session *session, bool if_exists, const char *db_name, const char *table_name)
119
TransactionServices &transaction_services= TransactionServices::singleton();
123
built_query.append("DROP TABLE IF EXISTS ");
125
built_query.append("DROP TABLE ");
127
built_query.append("`");
128
if (session->db.empty() || strcmp(db_name, session->db.c_str()) != 0)
130
built_query.append(db_name);
131
built_query.append("`.`");
134
built_query.append(table_name);
135
built_query.append("`");
136
transaction_services.rawStatement(session, built_query);
117
140
Execute the drop of a normal or temporary table
149
172
bool foreign_key_error= false;
152
table::Cache::singleton().mutex().lock(); /* Part 2 of rm a table */
154
if (not drop_temporary && session->lock_table_names_exclusively(tables))
156
table::Cache::singleton().mutex().unlock();
160
/* Don't give warnings for not found errors, as we already generate notes */
161
session->no_warnings_for_error= 1;
163
for (table= tables; table; table= table->next_local)
165
TableIdentifier tmp_identifier(table->getSchemaName(), table->getTableName());
167
error= session->drop_temporary_table(tmp_identifier);
171
// removed temporary table
174
pthread_mutex_lock(&LOCK_open); /* Part 2 of rm a table */
177
If we have the table in the definition cache, we don't have to check the
178
.frm cursor to find if the table is a normal table (not view) and what
182
for (table= tables; table; table= table->next_local)
184
TableIdentifier identifier(table->db, table->table_name);
186
table->setDbType(NULL);
188
if ((share= TableShare::getShare(identifier)))
190
table->setDbType(share->db_type());
194
if (not drop_temporary && lock_table_names_exclusively(session, tables))
196
pthread_mutex_unlock(&LOCK_open);
200
/* Don't give warnings for not found errors, as we already generate notes */
201
session->no_warnings_for_error= 1;
203
for (table= tables; table; table= table->next_local)
207
error= session->drop_temporary_table(table);
211
// removed temporary table
215
goto err_with_placeholders;
217
// temporary table not found
221
if (drop_temporary == false)
224
abort_locked_tables(session, db, table->table_name);
225
TableIdentifier identifier(db, table->table_name);
226
remove_table_from_cache(session, identifier,
227
RTFC_WAIT_OTHER_THREAD_FLAG |
228
RTFC_CHECK_KILLED_FLAG);
230
If the table was used in lock tables, remember it so that
231
unlock_table_names can free it
233
if ((locked_table= drop_locked_tables(session, db, table->table_name)))
234
table->table= locked_table;
239
goto err_with_placeholders;
242
TableIdentifier identifier(db, table->table_name, table->getInternalTmpTable() ? message::Table::INTERNAL : message::Table::STANDARD);
244
if (drop_temporary || not plugin::StorageEngine::doesTableExist(*session, identifier))
246
// Table was not found on disk and table can't be created from engine
248
push_warning_printf(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
249
ER_BAD_TABLE_ERROR, ER(ER_BAD_TABLE_ERROR),
175
goto err_with_placeholders;
177
// temporary table not found
256
error= plugin::StorageEngine::dropTable(*session, identifier);
258
if ((error == ENOENT || error == HA_ERR_NO_SUCH_TABLE) && if_exists)
181
if (drop_temporary == false)
184
abort_locked_tables(session, tmp_identifier);
185
table::Cache::singleton().removeTable(session, tmp_identifier,
186
RTFC_WAIT_OTHER_THREAD_FLAG |
187
RTFC_CHECK_KILLED_FLAG);
189
If the table was used in lock tables, remember it so that
190
unlock_table_names can free it
192
if ((locked_table= drop_locked_tables(session, tmp_identifier)))
193
table->table= locked_table;
195
if (session->getKilled())
198
goto err_with_placeholders;
201
TableIdentifier identifier(table->getSchemaName(), table->getTableName(), table->getInternalTmpTable() ? message::Table::INTERNAL : message::Table::STANDARD);
203
if (drop_temporary || not plugin::StorageEngine::doesTableExist(*session, identifier))
205
// Table was not found on disk and table can't be created from engine
207
push_warning_printf(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
208
ER_BAD_TABLE_ERROR, ER(ER_BAD_TABLE_ERROR),
209
table->getTableName());
215
error= plugin::StorageEngine::dropTable(*session, identifier);
217
if ((error == ENOENT || error == HA_ERR_NO_SUCH_TABLE) && if_exists)
220
session->clear_error();
223
if (error == HA_ERR_ROW_IS_REFERENCED)
225
/* the table is referenced by a foreign key constraint */
226
foreign_key_error= true;
230
if (error == 0 || (if_exists && foreign_key_error == false))
232
TransactionServices &transaction_services= TransactionServices::singleton();
233
transaction_services.dropTable(session, string(table->getSchemaName()), string(table->getTableName()), if_exists);
238
if (wrong_tables.length())
239
wrong_tables.append(',');
240
wrong_tables.append(String(table->getTableName(), system_charset_info));
244
It's safe to unlock table::Cache::singleton().mutex(): we have an exclusive lock
247
table::Cache::singleton().mutex().unlock();
261
session->clear_error();
264
if (error == HA_ERR_ROW_IS_REFERENCED)
266
/* the table is referenced by a foreign key constraint */
267
foreign_key_error= true;
271
if (error == 0 || (if_exists && foreign_key_error == false))
273
TransactionServices &transaction_services= TransactionServices::singleton();
274
transaction_services.dropTable(session, string(db), string(table->table_name), if_exists);
279
if (wrong_tables.length())
280
wrong_tables.append(',');
281
wrong_tables.append(String(table->table_name,system_charset_info));
285
It's safe to unlock LOCK_open: we have an exclusive lock
288
pthread_mutex_unlock(&LOCK_open);
251
291
if (wrong_tables.length())
1423
1466
assert(identifier.getTableName() == table_proto.name());
1424
1467
db_options= create_info->table_options;
1469
if (create_info->row_type == ROW_TYPE_DYNAMIC)
1470
db_options|=HA_OPTION_PACK_RECORD;
1426
1472
set_table_default_charset(create_info, identifier.getSchemaName().c_str());
1428
1474
/* Build a Table object to pass down to the engine, and the do the actual create. */
1429
1475
if (not mysql_prepare_create_table(session, create_info, table_proto, alter_info,
1432
&key_info_buffer, &key_count,
1433
select_field_count))
1478
&key_info_buffer, &key_count,
1479
select_field_count))
1435
boost_unique_lock_t lock(table::Cache::singleton().mutex()); /* CREATE TABLE (some confussion on naming, double check) */
1481
pthread_mutex_lock(&LOCK_open); /* CREATE TABLE (some confussion on naming, double check) */
1436
1482
error= locked_create_event(session,
1822
1864
/* Close all instances of the table to allow repair to rename files */
1823
1865
if (lock_type == TL_WRITE && table->table->getShare()->getVersion())
1825
table::Cache::singleton().mutex().lock(); /* Lock type is TL_WRITE and we lock to repair the table */
1826
const char *old_message=session->enter_cond(COND_refresh, table::Cache::singleton().mutex(),
1827
"Waiting to get writelock");
1828
session->abortLock(table->table);
1829
TableIdentifier identifier(table->table->getShare()->getSchemaName(), table->table->getShare()->getTableName());
1830
table::Cache::singleton().removeTable(session, identifier, RTFC_WAIT_OTHER_THREAD_FLAG | RTFC_CHECK_KILLED_FLAG);
1867
pthread_mutex_lock(&LOCK_open); /* Lock type is TL_WRITE and we lock to repair the table */
1868
const char *old_message=session->enter_cond(&COND_refresh, &LOCK_open,
1869
"Waiting to get writelock");
1870
mysql_lock_abort(session,table->table);
1871
TableIdentifier identifier(table->table->getMutableShare()->getSchemaName(), table->table->getMutableShare()->getTableName());
1872
remove_table_from_cache(session, identifier,
1873
RTFC_WAIT_OTHER_THREAD_FLAG |
1874
RTFC_CHECK_KILLED_FLAG);
1831
1875
session->exit_cond(old_message);
1832
if (session->getKilled())
1876
if (session->killed)
1834
1878
open_for_modify= 0;
1959
2004
Altough exclusive name-lock on target table protects us from concurrent
1960
2005
DML and DDL operations on it we still want to wrap .FRM creation and call
1961
2006
to plugin::StorageEngine::createTable() in critical section protected by
1962
table::Cache::singleton().mutex() in order to provide minimal atomicity against operations which
2007
LOCK_open in order to provide minimal atomicity against operations which
1963
2008
disregard name-locks, like I_S implementation, for example. This is a
1964
2009
temporary and should not be copied. Instead we should fix our code to
1965
2010
always honor name-locks.
1967
Also some engines (e.g. NDB cluster) require that table::Cache::singleton().mutex() should be held
2012
Also some engines (e.g. NDB cluster) require that LOCK_open should be held
1968
2013
during the call to plugin::StorageEngine::createTable().
1969
2014
See bug #28614 for more info.
1971
2016
static bool create_table_wrapper(Session &session, const message::Table& create_table_proto,
1972
const TableIdentifier &destination_identifier,
1973
const TableIdentifier &src_table,
2017
TableIdentifier &destination_identifier,
2018
TableIdentifier &src_table,
1974
2019
bool is_engine_set)
1976
2021
int protoerr= EEXIST;
1977
2022
message::Table new_proto;
1978
message::table::shared_ptr src_proto;
2023
message::Table src_proto;
1980
2025
protoerr= plugin::StorageEngine::getTableDefinition(session,
1983
new_proto.CopyFrom(*src_proto);
2028
new_proto.CopyFrom(src_proto);
1985
2030
if (destination_identifier.isTmp())