19
19
Handler-calling-functions
22
#ifdef USE_PRAGMA_IMPLEMENTATION
23
#pragma implementation // gcc: Class implementation
22
26
#include <drizzled/server_includes.h>
23
#include <drizzled/rpl_filter.h>
24
#include <drizzled/error.h>
25
#include <drizzled/gettext.h>
26
#include <drizzled/data_home.h>
27
#include <drizzled/probes.h>
28
#include <drizzled/sql_parse.h>
31
#if defined(CMATH_NAMESPACE)
32
using namespace CMATH_NAMESPACE;
27
#include "rpl_filter.h"
28
#include <drizzled/drizzled_error_messages.h>
36
31
While we have legacy_db_type, we have this array to
42
37
static handlerton *installed_htons[128];
44
KEY_CREATE_INFO default_key_create_info= { HA_KEY_ALG_UNDEF, 0, {NULL,0}, {NULL,0} };
39
#define BITMAP_STACKBUF_SIZE (128/8)
41
KEY_CREATE_INFO default_key_create_info= { HA_KEY_ALG_UNDEF, 0, {NullS,0}, {NullS,0} };
46
43
/* number of entries in handlertons[] */
47
44
uint32_t total_ha= 0;
64
61
const char *tx_isolation_names[] =
65
62
{ "READ-UNCOMMITTED", "READ-COMMITTED", "REPEATABLE-READ", "SERIALIZABLE",
67
64
TYPELIB tx_isolation_typelib= {array_elements(tx_isolation_names)-1,"",
68
65
tx_isolation_names, NULL};
70
67
static TYPELIB known_extensions= {0,"known_exts", NULL, NULL};
71
uint32_t known_extensions_id= 0;
75
static plugin_ref ha_default_plugin(Session *session)
68
uint known_extensions_id= 0;
72
static plugin_ref ha_default_plugin(THD *thd)
77
if (session->variables.table_plugin)
78
return session->variables.table_plugin;
79
return my_plugin_lock(session, &global_system_variables.table_plugin);
74
if (thd->variables.table_plugin)
75
return thd->variables.table_plugin;
76
return my_plugin_lock(thd, &global_system_variables.table_plugin);
84
81
Return the default storage engine handlerton for thread
86
@param ha_default_handlerton(session)
87
@param session current thread
83
@param ha_default_handlerton(thd)
84
@param thd current thread
90
87
pointer to handlerton
92
handlerton *ha_default_handlerton(Session *session)
89
handlerton *ha_default_handlerton(THD *thd)
94
plugin_ref plugin= ha_default_plugin(session);
91
plugin_ref plugin= ha_default_plugin(thd);
96
93
handlerton *hton= plugin_data(plugin, handlerton*);
103
100
Return the storage engine handlerton for the supplied name
105
@param session current thread
102
@param thd current thread
106
103
@param name name of storage engine
109
106
pointer to storage engine plugin handle
111
plugin_ref ha_resolve_by_name(Session *session, const LEX_STRING *name)
108
plugin_ref ha_resolve_by_name(THD *thd, const LEX_STRING *name)
113
110
const LEX_STRING *table_alias;
114
111
plugin_ref plugin;
117
114
/* my_strnncoll is a macro and gcc doesn't do early expansion of macro */
118
if (session && !my_charset_utf8_general_ci.coll->strnncoll(&my_charset_utf8_general_ci,
119
(const unsigned char *)name->str, name->length,
120
(const unsigned char *)STRING_WITH_LEN("DEFAULT"), 0))
121
return ha_default_plugin(session);
115
if (thd && !my_charset_utf8_general_ci.coll->strnncoll(&my_charset_utf8_general_ci,
116
(const uchar *)name->str, name->length,
117
(const uchar *)STRING_WITH_LEN("DEFAULT"), 0))
118
return ha_default_plugin(thd);
123
if ((plugin= my_plugin_lock_by_name(session, name, DRIZZLE_STORAGE_ENGINE_PLUGIN)))
120
if ((plugin= my_plugin_lock_by_name(thd, name, DRIZZLE_STORAGE_ENGINE_PLUGIN)))
125
122
handlerton *hton= plugin_data(plugin, handlerton *);
126
123
if (!(hton->flags & HTON_NOT_USER_SELECTABLE))
138
135
for (table_alias= sys_table_aliases; table_alias->str; table_alias+= 2)
140
137
if (!my_strnncoll(&my_charset_utf8_general_ci,
141
(const unsigned char *)name->str, name->length,
142
(const unsigned char *)table_alias->str, table_alias->length))
138
(const uchar *)name->str, name->length,
139
(const uchar *)table_alias->str, table_alias->length))
144
141
name= table_alias + 1;
153
plugin_ref ha_lock_engine(Session *session, handlerton *hton)
150
plugin_ref ha_lock_engine(THD *thd, handlerton *hton)
157
154
st_plugin_int **plugin= hton2plugin + hton->slot;
159
return my_plugin_lock(session, &plugin);
156
return my_plugin_lock(thd, &plugin);
165
handlerton *ha_resolve_by_legacy_type(Session *session, enum legacy_db_type db_type)
162
handlerton *ha_resolve_by_legacy_type(THD *thd, enum legacy_db_type db_type)
167
164
plugin_ref plugin;
168
165
switch (db_type) {
169
166
case DB_TYPE_DEFAULT:
170
return ha_default_handlerton(session);
167
return ha_default_handlerton(thd);
172
169
if (db_type > DB_TYPE_UNKNOWN && db_type < DB_TYPE_DEFAULT &&
173
(plugin= ha_lock_engine(session, installed_htons[db_type])))
170
(plugin= ha_lock_engine(thd, installed_htons[db_type])))
174
171
return plugin_data(plugin, handlerton*);
175
172
/* fall through */
176
173
case DB_TYPE_UNKNOWN:
183
180
Use other database handler if databasehandler is not compiled in.
185
handlerton *ha_checktype(Session *session, enum legacy_db_type database_type,
182
handlerton *ha_checktype(THD *thd, enum legacy_db_type database_type,
186
183
bool no_substitute, bool report_error)
188
handlerton *hton= ha_resolve_by_legacy_type(session, database_type);
185
handlerton *hton= ha_resolve_by_legacy_type(thd, database_type);
189
186
if (ha_storage_engine_is_enabled(hton))
218
215
Try the default table type
219
Here the call to current_session() is ok as we call this function a lot of
216
Here the call to current_thd() is ok as we call this function a lot of
220
217
times but we enter this branch very seldom.
222
return(get_new_handler(share, alloc, ha_default_handlerton(current_session)));
219
return(get_new_handler(share, alloc, ha_default_handlerton(current_thd)));
490
487
don't bother to rollback here, it's done already
492
void ha_close_connection(Session* session)
489
void ha_close_connection(THD* thd)
494
plugin_foreach(session, closecon_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, 0);
491
plugin_foreach(thd, closecon_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, 0);
497
494
/* ========================================================================
598
595
The server stores its transaction-related data in
599
session->transaction. This structure has two members of type
600
Session_TRANS. These members correspond to the statement and
596
thd->transaction. This structure has two members of type
597
THD_TRANS. These members correspond to the statement and
601
598
normal transactions respectively:
603
- session->transaction.stmt contains a list of engines
600
- thd->transaction.stmt contains a list of engines
604
601
that are participating in the given statement
605
- session->transaction.all contains a list of engines that
602
- thd->transaction.all contains a list of engines that
606
603
have participated in any of the statement transactions started
607
604
within the context of the normal transaction.
608
605
Each element of the list contains a pointer to the storage
609
606
engine, engine-specific transactional data, and engine-specific
610
607
transaction flags.
612
In autocommit mode session->transaction.all is empty.
613
Instead, data of session->transaction.stmt is
609
In autocommit mode thd->transaction.all is empty.
610
Instead, data of thd->transaction.stmt is
614
611
used to commit/rollback the normal transaction.
616
613
The list of registered engines has a few important properties:
647
644
- if the user has requested so, by issuing ROLLBACK SQL
649
646
- if one of the storage engines requested a rollback
650
by setting session->transaction_rollback_request. This may
647
by setting thd->transaction_rollback_request. This may
651
648
happen in case, e.g., when the transaction in the engine was
652
649
chosen a victim of the internal deadlock resolution algorithm
653
650
and rolled back internally. When such a situation happens, there
753
750
---------------------------------------------------
755
752
DDLs and operations with non-transactional engines
756
do not "register" in session->transaction lists, and thus do not
753
do not "register" in thd->transaction lists, and thus do not
757
754
modify the transaction state. Besides, each DDL in
758
755
MySQL is prefixed with an implicit normal transaction commit
759
756
(a call to end_active_trans()), and thus leaves nothing
800
797
times per transaction.
803
void trans_register_ha(Session *session, bool all, handlerton *ht_arg)
800
void trans_register_ha(THD *thd, bool all, handlerton *ht_arg)
805
Session_TRANS *trans;
806
803
Ha_trx_info *ha_info;
810
trans= &session->transaction.all;
811
session->server_status|= SERVER_STATUS_IN_TRANS;
807
trans= &thd->transaction.all;
808
thd->server_status|= SERVER_STATUS_IN_TRANS;
814
trans= &session->transaction.stmt;
811
trans= &thd->transaction.stmt;
816
ha_info= session->ha_data[ht_arg->slot].ha_info + static_cast<unsigned>(all);
813
ha_info= thd->ha_data[ht_arg->slot].ha_info + static_cast<unsigned>(all);
818
815
if (ha_info->is_started())
819
816
return; /* already registered, return */
846
843
handlerton *ht= ha_info->ht();
847
status_var_increment(session->status_var.ha_prepare_count);
844
status_var_increment(thd->status_var.ha_prepare_count);
850
if ((err= ht->prepare(ht, session, all)))
847
if ((err= ht->prepare(ht, thd, all)))
852
849
my_error(ER_ERROR_DURING_COMMIT, MYF(0), err);
853
ha_rollback_trans(session, all);
850
ha_rollback_trans(thd, all);
860
push_warning_printf(session, DRIZZLE_ERROR::WARN_LEVEL_WARN,
857
push_warning_printf(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN,
861
858
ER_ILLEGAL_HA, ER(ER_ILLEGAL_HA),
862
859
ha_resolve_storage_engine_name(ht));
899
Ha_trx_info *ha_info_all= &session->ha_data[ha_info->ht()->slot].ha_info[1];
896
Ha_trx_info *ha_info_all= &thd->ha_data[ha_info->ht()->slot].ha_info[1];
900
897
assert(ha_info != ha_info_all);
902
899
Merge read-only/read-write information about statement
903
900
transaction to its enclosing normal transaction. Do this
904
901
only if in a real transaction -- that is, if we know
905
that ha_info_all is registered in session->transaction.all.
902
that ha_info_all is registered in thd->transaction.all.
906
903
Since otherwise we only clutter the normal transaction flags.
908
905
if (ha_info_all->is_started()) /* false if autocommit. */
936
933
stored functions or triggers. So we simply do nothing now.
937
934
TODO: This should be fixed in later ( >= 5.1) releases.
939
int ha_commit_trans(Session *session, bool all)
936
int ha_commit_trans(THD *thd, bool all)
941
938
int error= 0, cookie= 0;
943
940
'all' means that this is either an explicit commit issued by
944
941
user, or an implicit commit issued by a DDL.
946
Session_TRANS *trans= all ? &session->transaction.all : &session->transaction.stmt;
947
bool is_real_trans= all || session->transaction.all.ha_list == 0;
943
THD_TRANS *trans= all ? &thd->transaction.all : &thd->transaction.stmt;
944
bool is_real_trans= all || thd->transaction.all.ha_list == 0;
948
945
Ha_trx_info *ha_info= trans->ha_list;
949
my_xid xid= session->transaction.xid_state.xid.get_my_xid();
946
my_xid xid= thd->transaction.xid_state.xid.get_my_xid();
952
949
We must not commit the normal transaction if a statement
954
951
flags will not get propagated to its normal transaction's
957
assert(session->transaction.stmt.ha_list == NULL ||
958
trans == &session->transaction.stmt);
954
assert(thd->transaction.stmt.ha_list == NULL ||
955
trans == &thd->transaction.stmt);
957
if (thd->in_sub_stmt)
960
Since we don't support nested statement transactions in 5.0,
961
we can't commit or rollback stmt transactions while we are inside
962
stored functions or triggers. So we simply do nothing now.
963
TODO: This should be fixed in later ( >= 5.1) releases.
968
We assume that all statements which commit or rollback main transaction
969
are prohibited inside of stored functions or triggers. So they should
970
bail out with error even before ha_commit_trans() call. To be 100% safe
971
let us throw error in non-debug builds.
974
my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
964
if (is_real_trans && wait_if_global_read_lock(session, 0, 0))
981
if (is_real_trans && wait_if_global_read_lock(thd, 0, 0))
966
ha_rollback_trans(session, all);
983
ha_rollback_trans(thd, all);
970
987
if ( is_real_trans
972
&& ! session->slave_thread
989
&& ! thd->slave_thread
975
992
my_error(ER_OPTION_PREVENTS_STATEMENT, MYF(0), "--read-only");
976
ha_rollback_trans(session, all);
993
ha_rollback_trans(thd, all);
981
must_2pc= ha_check_and_coalesce_trx_read_only(session, ha_info, all);
998
must_2pc= ha_check_and_coalesce_trx_read_only(thd, ha_info, all);
983
1000
if (!trans->no_2pc && must_2pc)
997
1014
Sic: we know that prepare() is not NULL since otherwise
998
1015
trans->no_2pc would have been set.
1000
if ((err= ht->prepare(ht, session, all)))
1017
if ((err= ht->prepare(ht, thd, all)))
1002
1019
my_error(ER_ERROR_DURING_COMMIT, MYF(0), err);
1005
status_var_increment(session->status_var.ha_prepare_count);
1022
status_var_increment(thd->status_var.ha_prepare_count);
1007
1024
if (error || (is_real_trans && xid &&
1008
(error= !(cookie= tc_log->log_xid(session, xid)))))
1025
(error= !(cookie= tc_log->log_xid(thd, xid)))))
1010
ha_rollback_trans(session, all);
1027
ha_rollback_trans(thd, all);
1015
error=ha_commit_one_phase(session, all) ? (cookie ? 2 : 1) : 0;
1032
error=ha_commit_one_phase(thd, all) ? (cookie ? 2 : 1) : 0;
1017
1034
tc_log->unlog(cookie, xid);
1019
1036
if (is_real_trans)
1020
start_waiting_global_read_lock(session);
1037
start_waiting_global_read_lock(thd);
1027
1044
This function does not care about global read lock. A caller should.
1029
int ha_commit_one_phase(Session *session, bool all)
1046
int ha_commit_one_phase(THD *thd, bool all)
1032
Session_TRANS *trans=all ? &session->transaction.all : &session->transaction.stmt;
1033
bool is_real_trans=all || session->transaction.all.ha_list == 0;
1049
THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
1050
bool is_real_trans=all || thd->transaction.all.ha_list == 0;
1034
1051
Ha_trx_info *ha_info= trans->ha_list, *ha_info_next;
1040
1057
handlerton *ht= ha_info->ht();
1041
if ((err= ht->commit(ht, session, all)))
1058
if ((err= ht->commit(ht, thd, all)))
1043
1060
my_error(ER_ERROR_DURING_COMMIT, MYF(0), err);
1046
status_var_increment(session->status_var.ha_commit_count);
1063
status_var_increment(thd->status_var.ha_commit_count);
1047
1064
ha_info_next= ha_info->next();
1048
1065
ha_info->reset(); /* keep it conveniently zero-filled */
1050
1067
trans->ha_list= 0;
1051
1068
trans->no_2pc=0;
1052
1069
if (is_real_trans)
1053
session->transaction.xid_state.xid.null();
1070
thd->transaction.xid_state.xid.null();
1056
session->variables.tx_isolation=session->session_tx_isolation;
1057
session->transaction.cleanup();
1073
thd->variables.tx_isolation=thd->session_tx_isolation;
1074
thd->transaction.cleanup();
1064
int ha_rollback_trans(Session *session, bool all)
1081
int ha_rollback_trans(THD *thd, bool all)
1067
Session_TRANS *trans=all ? &session->transaction.all : &session->transaction.stmt;
1084
THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
1068
1085
Ha_trx_info *ha_info= trans->ha_list, *ha_info_next;
1069
bool is_real_trans=all || session->transaction.all.ha_list == 0;
1086
bool is_real_trans=all || thd->transaction.all.ha_list == 0;
1072
1089
We must not rollback the normal transaction if a statement
1073
1090
transaction is pending.
1075
assert(session->transaction.stmt.ha_list == NULL ||
1076
trans == &session->transaction.stmt);
1092
assert(thd->transaction.stmt.ha_list == NULL ||
1093
trans == &thd->transaction.stmt);
1095
if (thd->in_sub_stmt)
1098
If we are inside stored function or trigger we should not commit or
1099
rollback current statement transaction. See comment in ha_commit_trans()
1100
call for more information.
1105
my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
1080
1110
for (; ha_info; ha_info= ha_info_next)
1083
1113
handlerton *ht= ha_info->ht();
1084
if ((err= ht->rollback(ht, session, all)))
1114
if ((err= ht->rollback(ht, thd, all)))
1085
1115
{ // cannot happen
1086
1116
my_error(ER_ERROR_DURING_ROLLBACK, MYF(0), err);
1089
status_var_increment(session->status_var.ha_rollback_count);
1119
status_var_increment(thd->status_var.ha_rollback_count);
1090
1120
ha_info_next= ha_info->next();
1091
1121
ha_info->reset(); /* keep it conveniently zero-filled */
1093
1123
trans->ha_list= 0;
1094
1124
trans->no_2pc=0;
1095
1125
if (is_real_trans)
1096
session->transaction.xid_state.xid.null();
1126
thd->transaction.xid_state.xid.null();
1099
session->variables.tx_isolation=session->session_tx_isolation;
1100
session->transaction.cleanup();
1129
thd->variables.tx_isolation=thd->session_tx_isolation;
1130
thd->transaction.cleanup();
1104
session->transaction_rollback_request= false;
1134
thd->transaction_rollback_request= false;
1107
1137
If a non-transactional table was updated, warn; don't warn if this is a
1112
1142
the error log; but we don't want users to wonder why they have this
1113
1143
message in the error log, so we don't send it.
1115
if (is_real_trans && session->transaction.all.modified_non_trans_table &&
1116
!session->slave_thread && session->killed != Session::KILL_CONNECTION)
1117
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN,
1145
if (is_real_trans && thd->transaction.all.modified_non_trans_table &&
1146
!thd->slave_thread && thd->killed != THD::KILL_CONNECTION)
1147
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN,
1118
1148
ER_WARNING_NOT_COMPLETE_ROLLBACK,
1119
1149
ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
1131
1161
the user has used LOCK TABLES then that mechanism does not know to do the
1134
int ha_autocommit_or_rollback(Session *session, int error)
1164
int ha_autocommit_or_rollback(THD *thd, int error)
1136
if (session->transaction.stmt.ha_list)
1166
if (thd->transaction.stmt.ha_list)
1140
if (ha_commit_trans(session, 0))
1170
if (ha_commit_trans(thd, 0))
1145
(void) ha_rollback_trans(session, 0);
1146
if (session->transaction_rollback_request)
1147
(void) ha_rollback(session);
1175
(void) ha_rollback_trans(thd, 0);
1176
if (thd->transaction_rollback_request && !thd->in_sub_stmt)
1177
(void) ha_rollback(thd);
1150
session->variables.tx_isolation=session->session_tx_isolation;
1180
thd->variables.tx_isolation=thd->session_tx_isolation;
1315
1345
plugin_foreach(NULL, xarecover_handlerton,
1316
1346
DRIZZLE_STORAGE_ENGINE_PLUGIN, &info);
1318
free((unsigned char*)info.list);
1348
my_free((uchar*)info.list, MYF(0));
1319
1349
if (info.found_foreign_xids)
1320
1350
sql_print_warning(_("Found %d prepared XA transactions"),
1321
1351
info.found_foreign_xids);
1388
1418
This function should be called when MySQL sends rows of a SELECT result set
1389
1419
or the EOF mark to the client. It releases a possible adaptive hash index
1390
S-latch held by session in InnoDB and also releases a possible InnoDB query
1391
FIFO ticket to enter InnoDB. To save CPU time, InnoDB allows a session to
1420
S-latch held by thd in InnoDB and also releases a possible InnoDB query
1421
FIFO ticket to enter InnoDB. To save CPU time, InnoDB allows a thd to
1392
1422
keep them over several calls of the InnoDB handler interface when a join
1393
1423
is executed. But when we let the control to pass to the client they have
1394
1424
to be released because if the application program uses mysql_use_result(),
1396
1426
performs another SQL query. In MySQL-4.1 this is even more important because
1397
1427
there a connection can have several SELECT queries open at the same time.
1399
@param session the thread handle of the current connection
1429
@param thd the thread handle of the current connection
1404
static bool release_temporary_latches(Session *session, plugin_ref plugin,
1434
static bool release_temporary_latches(THD *thd, plugin_ref plugin,
1405
1435
void *unused __attribute__((unused)))
1407
1437
handlerton *hton= plugin_data(plugin, handlerton *);
1409
1439
if (hton->state == SHOW_OPTION_YES && hton->release_temporary_latches)
1410
hton->release_temporary_latches(hton, session);
1440
hton->release_temporary_latches(hton, thd);
1416
int ha_release_temporary_latches(Session *session)
1446
int ha_release_temporary_latches(THD *thd)
1418
plugin_foreach(session, release_temporary_latches, DRIZZLE_STORAGE_ENGINE_PLUGIN,
1448
plugin_foreach(thd, release_temporary_latches, DRIZZLE_STORAGE_ENGINE_PLUGIN,
1424
int ha_rollback_to_savepoint(Session *session, SAVEPOINT *sv)
1454
int ha_rollback_to_savepoint(THD *thd, SAVEPOINT *sv)
1427
Session_TRANS *trans= &session->transaction.all;
1457
THD_TRANS *trans= (thd->in_sub_stmt ? &thd->transaction.stmt :
1458
&thd->transaction.all);
1428
1459
Ha_trx_info *ha_info, *ha_info_next;
1430
1461
trans->no_2pc=0;
1438
1469
handlerton *ht= ha_info->ht();
1440
1471
assert(ht->savepoint_set != 0);
1441
if ((err= ht->savepoint_rollback(ht, session,
1442
(unsigned char *)(sv+1)+ht->savepoint_offset)))
1472
if ((err= ht->savepoint_rollback(ht, thd,
1473
(uchar *)(sv+1)+ht->savepoint_offset)))
1443
1474
{ // cannot happen
1444
1475
my_error(ER_ERROR_DURING_ROLLBACK, MYF(0), err);
1447
status_var_increment(session->status_var.ha_savepoint_rollback_count);
1478
status_var_increment(thd->status_var.ha_savepoint_rollback_count);
1448
1479
trans->no_2pc|= ht->prepare == 0;
1458
1489
handlerton *ht= ha_info->ht();
1459
if ((err= ht->rollback(ht, session, !(0))))
1490
if ((err= ht->rollback(ht, thd, !thd->in_sub_stmt)))
1460
1491
{ // cannot happen
1461
1492
my_error(ER_ERROR_DURING_ROLLBACK, MYF(0), err);
1464
status_var_increment(session->status_var.ha_rollback_count);
1495
status_var_increment(thd->status_var.ha_rollback_count);
1465
1496
ha_info_next= ha_info->next();
1466
1497
ha_info->reset(); /* keep it conveniently zero-filled */
1475
1506
section "4.33.4 SQL-statements and transaction states",
1476
1507
SAVEPOINT is *not* transaction-initiating SQL-statement
1478
int ha_savepoint(Session *session, SAVEPOINT *sv)
1509
int ha_savepoint(THD *thd, SAVEPOINT *sv)
1481
Session_TRANS *trans= &session->transaction.all;
1512
THD_TRANS *trans= (thd->in_sub_stmt ? &thd->transaction.stmt :
1513
&thd->transaction.all);
1482
1514
Ha_trx_info *ha_info= trans->ha_list;
1483
1515
for (; ha_info; ha_info= ha_info->next())
1494
if ((err= ht->savepoint_set(ht, session, (unsigned char *)(sv+1)+ht->savepoint_offset)))
1526
if ((err= ht->savepoint_set(ht, thd, (uchar *)(sv+1)+ht->savepoint_offset)))
1495
1527
{ // cannot happen
1496
1528
my_error(ER_GET_ERRNO, MYF(0), err);
1499
status_var_increment(session->status_var.ha_savepoint_count);
1531
status_var_increment(thd->status_var.ha_savepoint_count);
1502
1534
Remember the list of registered storage engines. All new
1520
1552
if (!ht->savepoint_release)
1522
if ((err= ht->savepoint_release(ht, session,
1523
(unsigned char *)(sv+1) + ht->savepoint_offset)))
1554
if ((err= ht->savepoint_release(ht, thd,
1555
(uchar *)(sv+1) + ht->savepoint_offset)))
1524
1556
{ // cannot happen
1525
1557
my_error(ER_GET_ERRNO, MYF(0), err);
1533
static bool snapshot_handlerton(Session *session, plugin_ref plugin, void *arg)
1565
static bool snapshot_handlerton(THD *thd, plugin_ref plugin, void *arg)
1535
1567
handlerton *hton= plugin_data(plugin, handlerton *);
1536
1568
if (hton->state == SHOW_OPTION_YES &&
1537
1569
hton->start_consistent_snapshot)
1539
hton->start_consistent_snapshot(hton, session);
1571
hton->start_consistent_snapshot(hton, thd);
1540
1572
*((bool *)arg)= false;
1545
int ha_start_consistent_snapshot(Session *session)
1577
int ha_start_consistent_snapshot(THD *thd)
1547
1579
bool warn= true;
1549
plugin_foreach(session, snapshot_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, &warn);
1581
plugin_foreach(thd, snapshot_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, &warn);
1552
1584
Same idea as when one wants to CREATE TABLE in one engine which does not
1556
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, ER_UNKNOWN_ERROR,
1588
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN, ER_UNKNOWN_ERROR,
1557
1589
"This MySQL server does not support any "
1558
1590
"consistent-read capable storage engine");
1563
static bool flush_handlerton(Session *session __attribute__((unused)),
1595
static bool flush_handlerton(THD *thd __attribute__((unused)),
1564
1596
plugin_ref plugin,
1565
1597
void *arg __attribute__((unused)))
1617
1649
struct Ha_delete_table_error_handler: public Internal_error_handler
1620
virtual bool handle_error(uint32_t sql_errno,
1652
virtual bool handle_error(uint sql_errno,
1621
1653
const char *message,
1622
1654
DRIZZLE_ERROR::enum_warning_level level,
1624
1656
char buff[DRIZZLE_ERRMSG_SIZE];
1629
1661
Ha_delete_table_error_handler::
1630
handle_error(uint32_t sql_errno __attribute__((unused)),
1662
handle_error(uint sql_errno __attribute__((unused)),
1631
1663
const char *message,
1632
1664
DRIZZLE_ERROR::enum_warning_level level __attribute__((unused)),
1633
Session *session __attribute__((unused)))
1665
THD *thd __attribute__((unused)))
1635
1667
/* Grab the error message */
1636
1668
strmake(buff, message, sizeof(buff)-1);
1642
1674
This should return ENOENT if the file doesn't exists.
1643
1675
The .frm file will be deleted only if we return 0 or ENOENT
1645
int ha_delete_table(Session *session, handlerton *table_type, const char *path,
1677
int ha_delete_table(THD *thd, handlerton *table_type, const char *path,
1646
1678
const char *db, const char *alias, bool generate_warning)
1683
1715
file->change_table_ptr(&dummy_table, &dummy_share);
1685
session->push_internal_handler(&ha_delete_table_error_handler);
1717
thd->push_internal_handler(&ha_delete_table_error_handler);
1686
1718
file->print_error(error, 0);
1688
session->pop_internal_handler();
1720
thd->pop_internal_handler();
1691
1723
XXX: should we convert *all* errors to warnings here?
1692
1724
What if the error is fatal?
1694
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_ERROR, error,
1726
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_ERROR, error,
1695
1727
ha_delete_table_error_handler.buff);
1709
1741
on this->table->mem_root and we will not be able to reclaim that memory
1710
1742
when the clone handler object is destroyed.
1712
if (!(new_handler->ref= (unsigned char*) alloc_root(mem_root, ALIGN_SIZE(ref_length)*2)))
1744
if (!(new_handler->ref= (uchar*) alloc_root(mem_root, ALIGN_SIZE(ref_length)*2)))
1714
1746
if (new_handler && !new_handler->ha_open(table,
1715
1747
table->s->normalized_path.str,
1726
1758
status_var_increment(table->in_use->status_var.*offset);
1729
void **handler::ha_data(Session *session) const
1761
void **handler::ha_data(THD *thd) const
1731
return session_ha_data(session, ht);
1763
return thd_ha_data(thd, ht);
1734
Session *handler::ha_session(void) const
1766
THD *handler::ha_thd(void) const
1736
assert(!table || !table->in_use || table->in_use == current_session);
1737
return (table && table->in_use) ? table->in_use : current_session;
1768
assert(!table || !table->in_use || table->in_use == current_thd);
1769
return (table && table->in_use) ? table->in_use : current_thd;
1866
1898
void handler::adjust_next_insert_id_after_explicit_value(uint64_t nr)
1869
If we have set Session::next_insert_id previously and plan to insert an
1901
If we have set THD::next_insert_id previously and plan to insert an
1870
1902
explicitely-specified value larger than this, we need to increase
1871
Session::next_insert_id to be greater than the explicit value.
1903
THD::next_insert_id to be greater than the explicit value.
1873
1905
if ((next_insert_id > 0) && (nr >= next_insert_id))
1874
1906
set_next_insert_id(compute_next_insert_id(nr, &table->in_use->variables));
1958
1990
start counting from the inserted value.
1960
1992
This function's "outputs" are: the table's auto_increment field is filled
1961
with a value, session->next_insert_id is filled with the value to use for the
1993
with a value, thd->next_insert_id is filled with the value to use for the
1962
1994
next row, if a value was autogenerated for the current row it is stored in
1963
session->insert_id_for_cur_row, if get_auto_increment() was called
1964
session->auto_inc_interval_for_cur_row is modified, if that interval is not
1965
present in session->auto_inc_intervals_in_cur_stmt_for_binlog it is added to
1995
thd->insert_id_for_cur_row, if get_auto_increment() was called
1996
thd->auto_inc_interval_for_cur_row is modified, if that interval is not
1997
present in thd->auto_inc_intervals_in_cur_stmt_for_binlog it is added to
2027
2059
handler::estimation_rows_to_insert was set by
2028
2060
handler::ha_start_bulk_insert(); if 0 it means "unknown".
2030
uint32_t nb_already_reserved_intervals=
2031
session->auto_inc_intervals_in_cur_stmt_for_binlog.nb_elements();
2062
uint nb_already_reserved_intervals=
2063
thd->auto_inc_intervals_in_cur_stmt_for_binlog.nb_elements();
2032
2064
uint64_t nb_desired_values;
2034
2066
If an estimation was given to the engine:
2107
2139
auto_inc_interval_for_cur_row.replace(nr, nb_reserved_values,
2108
2140
variables->auto_increment_increment);
2109
2141
/* Row-based replication does not need to store intervals in binlog */
2110
if (!session->current_stmt_binlog_row_based)
2111
session->auto_inc_intervals_in_cur_stmt_for_binlog.append(auto_inc_interval_for_cur_row.minimum(),
2142
if (!thd->current_stmt_binlog_row_based)
2143
thd->auto_inc_intervals_in_cur_stmt_for_binlog.append(auto_inc_interval_for_cur_row.minimum(),
2112
2144
auto_inc_interval_for_cur_row.values(),
2113
2145
variables->auto_increment_increment);
2525
2557
if (table->s->mysql_version == DRIZZLE_VERSION_ID)
2528
strxmov(path, table->s->normalized_path.str, reg_ext, NULL);
2560
strxmov(path, table->s->normalized_path.str, reg_ext, NullS);
2530
if ((file= my_open(path, O_RDWR, MYF(MY_WME))) >= 0)
2562
if ((file= my_open(path, O_RDWR|O_BINARY, MYF(MY_WME))) >= 0)
2532
unsigned char version[4];
2533
2565
char *key= table->s->table_cache_key.str;
2534
uint32_t key_length= table->s->table_cache_key.length;
2566
uint key_length= table->s->table_cache_key.length;
2536
2568
HASH_SEARCH_STATE state;
2538
2570
int4store(version, DRIZZLE_VERSION_ID);
2540
if (pwrite(file, (unsigned char*)version, 4, 51L) == 0)
2572
if (pwrite(file, (uchar*)version, 4, 51L) == 0)
2546
for (entry=(Table*) hash_first(&open_cache,(unsigned char*) key,key_length, &state);
2578
for (entry=(Table*) hash_first(&open_cache,(uchar*) key,key_length, &state);
2548
entry= (Table*) hash_next(&open_cache,(unsigned char*) key,key_length, &state))
2580
entry= (Table*) hash_next(&open_cache,(uchar*) key,key_length, &state))
2549
2581
entry->s->mysql_version= DRIZZLE_VERSION_ID;
2553
my_close(file,MYF(MY_WME));
2585
VOID(my_close(file,MYF(MY_WME)));
2554
2586
return(result);
2967
2999
is an optimization hint that storage engine is free to ignore.
2968
3000
So, let's commit an open transaction (if any) now.
2970
if (!(error= ha_commit_trans(session, 0)))
2971
error= end_trans(session, COMMIT);
3002
if (!(error= ha_commit_trans(thd, 0)))
3003
error= end_trans(thd, COMMIT);
2976
int handler::index_next_same(unsigned char *buf, const unsigned char *key, uint32_t keylen)
3008
int handler::index_next_same(uchar *buf, const uchar *key, uint keylen)
2979
3011
if (!(error=index_next(buf)))
2981
3013
my_ptrdiff_t ptrdiff= buf - table->record[0];
2982
unsigned char *save_record_0= NULL;
3014
uchar *save_record_0= NULL;
2983
3015
KEY *key_info= NULL;
2984
3016
KEY_PART_INFO *key_part;
2985
3017
KEY_PART_INFO *key_part_end= NULL;
3047
3079
const char *name;
3048
3080
TABLE_SHARE share;
3050
init_tmp_table_share(session, &share, db, 0, table_name, path);
3051
if (open_table_def(session, &share, 0) ||
3052
open_table_from_share(session, &share, "", 0, (uint) READ_ALL, 0, &table,
3082
init_tmp_table_share(thd, &share, db, 0, table_name, path);
3083
if (open_table_def(thd, &share, 0) ||
3084
open_table_from_share(thd, &share, "", 0, (uint) READ_ALL, 0, &table,
3059
3091
name= check_lowercase_names(table.file, share.path.str, name_buff);
3061
3093
error= table.file->ha_create(name, &table, create_info);
3062
closefrm(&table, 0);
3094
VOID(closefrm(&table, 0));
3065
strxmov(name_buff, db, ".", table_name, NULL);
3097
strxmov(name_buff, db, ".", table_name, NullS);
3066
3098
my_error(ER_CANT_CREATE_TABLE, MYF(ME_BELL+ME_WAITTANG), name_buff, error);
3094
3126
TABLE_SHARE share;
3096
3128
memset(&create_info, 0, sizeof(create_info));
3097
if ((error= ha_discover(session, db, name, &frmblob, &frmlen)))
3129
if ((error= ha_discover(thd, db, name, &frmblob, &frmlen)))
3099
3131
/* Table could not be discovered and thus not created */
3108
3140
build_table_filename(path, FN_REFLEN-1, db, name, "", 0);
3109
3141
// Save the frm file
3110
3142
error= writefrm(path, frmblob, frmlen);
3143
my_free(frmblob, MYF(0));
3115
init_tmp_table_share(session, &share, db, 0, name, path);
3116
if (open_table_def(session, &share, 0))
3147
init_tmp_table_share(thd, &share, db, 0, name, path);
3148
if (open_table_def(thd, &share, 0))
3120
if (open_table_from_share(session, &share, "" ,0, 0, 0, &table, OTM_OPEN))
3152
if (open_table_from_share(thd, &share, "" ,0, 0, 0, &table, OTM_OPEN))
3122
3154
free_table_share(&share);
3161
3193
pthread_mutex_lock(&LOCK_global_system_variables);
3162
3194
uint32_t tmp_buff_size= (uint32_t) key_cache->param_buff_size;
3163
uint32_t tmp_block_size= (uint) key_cache->param_block_size;
3164
uint32_t division_limit= key_cache->param_division_limit;
3165
uint32_t age_threshold= key_cache->param_age_threshold;
3195
uint tmp_block_size= (uint) key_cache->param_block_size;
3196
uint division_limit= key_cache->param_division_limit;
3197
uint age_threshold= key_cache->param_age_threshold;
3166
3198
pthread_mutex_unlock(&LOCK_global_system_variables);
3167
3199
return(!init_key_cache(key_cache,
3168
3200
tmp_block_size,
3183
3215
pthread_mutex_lock(&LOCK_global_system_variables);
3184
3216
long tmp_buff_size= (long) key_cache->param_buff_size;
3185
3217
long tmp_block_size= (long) key_cache->param_block_size;
3186
uint32_t division_limit= key_cache->param_division_limit;
3187
uint32_t age_threshold= key_cache->param_age_threshold;
3218
uint division_limit= key_cache->param_division_limit;
3219
uint age_threshold= key_cache->param_age_threshold;
3188
3220
pthread_mutex_unlock(&LOCK_global_system_variables);
3189
3221
return(!resize_key_cache(key_cache, tmp_block_size,
3202
3234
if (key_cache->key_cache_inited)
3204
3236
pthread_mutex_lock(&LOCK_global_system_variables);
3205
uint32_t division_limit= key_cache->param_division_limit;
3206
uint32_t age_threshold= key_cache->param_age_threshold;
3237
uint division_limit= key_cache->param_division_limit;
3238
uint age_threshold= key_cache->param_age_threshold;
3207
3239
pthread_mutex_unlock(&LOCK_global_system_variables);
3208
3240
change_key_cache_param(key_cache, division_limit, age_threshold);
3245
3277
const char *db;
3246
3278
const char *name;
3247
unsigned char **frmblob;
3248
3280
size_t *frmlen;
3251
static bool discover_handlerton(Session *session, plugin_ref plugin,
3283
static bool discover_handlerton(THD *thd, plugin_ref plugin,
3254
3286
st_discover_args *vargs= (st_discover_args *)arg;
3255
3287
handlerton *hton= plugin_data(plugin, handlerton *);
3256
3288
if (hton->state == SHOW_OPTION_YES && hton->discover &&
3257
(!(hton->discover(hton, session, vargs->db, vargs->name,
3289
(!(hton->discover(hton, thd, vargs->db, vargs->name,
3258
3290
vargs->frmblob,
3259
3291
vargs->frmlen))))
3265
int ha_discover(Session *session, const char *db, const char *name,
3266
unsigned char **frmblob, size_t *frmlen)
3297
int ha_discover(THD *thd, const char *db, const char *name,
3298
uchar **frmblob, size_t *frmlen)
3268
3300
int error= -1; // Table does not exist in any handler
3269
3301
st_discover_args args= {db, name, frmblob, frmlen};
3271
3303
if (is_prefix(name,tmp_file_prefix)) /* skip temporary tables */
3274
if (plugin_foreach(session, discover_handlerton,
3306
if (plugin_foreach(thd, discover_handlerton,
3275
3307
DRIZZLE_STORAGE_ENGINE_PLUGIN, &args))
3279
status_var_increment(session->status_var.ha_discover_count);
3311
status_var_increment(thd->status_var.ha_discover_count);
3332
int ha_table_exists_in_engine(Session* session, const char* db, const char* name)
3364
int ha_table_exists_in_engine(THD* thd, const char* db, const char* name)
3334
3366
st_table_exists_in_engine_args args= {db, name, HA_ERR_NO_SUCH_TABLE};
3335
plugin_foreach(session, table_exists_in_engine_handlerton,
3367
plugin_foreach(thd, table_exists_in_engine_handlerton,
3336
3368
DRIZZLE_STORAGE_ENGINE_PLUGIN, &args);
3337
3369
return(args.err);
3358
3390
Estimated cost of 'index only' scan
3361
double handler::index_only_read_time(uint32_t keynr, double records)
3393
double handler::index_only_read_time(uint keynr, double records)
3363
3395
double read_time;
3364
uint32_t keys_per_block= (stats.block_size/2/
3396
uint keys_per_block= (stats.block_size/2/
3365
3397
(table->key_info[keynr].key_length + ref_length) + 1);
3366
3398
read_time=((double) (records + keys_per_block-1) /
3367
3399
(double) keys_per_block);
3408
handler::multi_range_read_info_const(uint32_t keyno, RANGE_SEQ_IF *seq,
3440
handler::multi_range_read_info_const(uint keyno, RANGE_SEQ_IF *seq,
3409
3441
void *seq_init_param,
3410
uint32_t n_ranges_arg __attribute__((unused)),
3411
uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
3442
uint n_ranges_arg __attribute__((unused)),
3443
uint *bufsz, uint *flags, COST_VECT *cost)
3413
3445
KEY_MULTI_RANGE range;
3414
3446
range_seq_t seq_it;
3415
3447
ha_rows rows, total_rows= 0;
3416
uint32_t n_ranges=0;
3417
Session *session= current_session;
3449
THD *thd= current_thd;
3419
3451
/* Default MRR implementation doesn't need buffer */
3496
3528
other Error or can't perform the requested scan
3499
int handler::multi_range_read_info(uint32_t keyno, uint32_t n_ranges, uint32_t n_rows,
3500
uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
3531
int handler::multi_range_read_info(uint keyno, uint n_ranges, uint n_rows,
3532
uint *bufsz, uint *flags, COST_VECT *cost)
3502
3534
*bufsz= 0; /* Default implementation doesn't need a buffer */
3560
3592
handler::multi_range_read_init(RANGE_SEQ_IF *seq_funcs, void *seq_init_param,
3561
uint32_t n_ranges, uint32_t mode,
3593
uint n_ranges, uint mode,
3562
3594
HANDLER_BUFFER *buf __attribute__((unused)))
3564
3596
mrr_iter= seq_funcs->init(seq_init_param, n_ranges, mode);
3802
3834
dsmrr_eof= test(res == HA_ERR_END_OF_FILE);
3804
3836
/* Sort the buffer contents by rowid */
3805
uint32_t elem_size= h->ref_length + (int)is_mrr_assoc * sizeof(void*);
3806
uint32_t n_rowids= (rowids_buf_cur - rowids_buf) / elem_size;
3837
uint elem_size= h->ref_length + (int)is_mrr_assoc * sizeof(void*);
3838
uint n_rowids= (rowids_buf_cur - rowids_buf) / elem_size;
3808
3840
my_qsort2(rowids_buf, n_rowids, elem_size, (qsort2_cmp)rowid_cmp,
3862
3894
DS-MRR implementation: multi_range_read_info() function
3864
int DsMrr_impl::dsmrr_info(uint32_t keyno, uint32_t n_ranges, uint32_t rows, uint32_t *bufsz,
3865
uint32_t *flags, COST_VECT *cost)
3896
int DsMrr_impl::dsmrr_info(uint keyno, uint n_ranges, uint rows, uint *bufsz,
3897
uint *flags, COST_VECT *cost)
3868
uint32_t def_flags= *flags;
3869
uint32_t def_bufsz= *bufsz;
3900
uint def_flags= *flags;
3901
uint def_bufsz= *bufsz;
3871
3903
/* Get cost/flags/mem_usage of default MRR implementation */
3872
3904
res= h->handler::multi_range_read_info(keyno, n_ranges, rows, &def_bufsz,
3888
3920
DS-MRR Implementation: multi_range_read_info_const() function
3891
ha_rows DsMrr_impl::dsmrr_info_const(uint32_t keyno, RANGE_SEQ_IF *seq,
3892
void *seq_init_param, uint32_t n_ranges,
3893
uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
3923
ha_rows DsMrr_impl::dsmrr_info_const(uint keyno, RANGE_SEQ_IF *seq,
3924
void *seq_init_param, uint n_ranges,
3925
uint *bufsz, uint *flags, COST_VECT *cost)
3896
uint32_t def_flags= *flags;
3897
uint32_t def_bufsz= *bufsz;
3928
uint def_flags= *flags;
3929
uint def_bufsz= *bufsz;
3898
3930
/* Get cost/flags/mem_usage of default MRR implementation */
3899
3931
rows= h->handler::multi_range_read_info_const(keyno, seq, seq_init_param,
3900
3932
n_ranges, &def_bufsz,
3978
4010
@retval false DS-MRR implementation should be used
3981
bool DsMrr_impl::choose_mrr_impl(uint32_t keyno, ha_rows rows, uint32_t *flags,
3982
uint32_t *bufsz, COST_VECT *cost)
4013
bool DsMrr_impl::choose_mrr_impl(uint keyno, ha_rows rows, uint *flags,
4014
uint *bufsz, COST_VECT *cost)
3984
4016
COST_VECT dsmrr_cost;
3986
Session *session= current_session;
3987
if ((session->variables.optimizer_use_mrr == 2) ||
4018
THD *thd= current_thd;
4019
if ((thd->variables.optimizer_use_mrr == 2) ||
3988
4020
(*flags & HA_MRR_INDEX_ONLY) || (*flags & HA_MRR_SORTED) ||
3989
4021
(keyno == table->s->primary_key &&
3990
4022
h->primary_key_is_clustered()) ||
4045
4077
for even 1 rowid)
4048
bool DsMrr_impl::get_disk_sweep_mrr_cost(uint32_t keynr, ha_rows rows, uint32_t flags,
4049
uint32_t *buffer_size, COST_VECT *cost)
4080
bool DsMrr_impl::get_disk_sweep_mrr_cost(uint keynr, ha_rows rows, uint flags,
4081
uint *buffer_size, COST_VECT *cost)
4051
4083
uint32_t max_buff_entries, elem_size;
4052
4084
ha_rows rows_in_full_step, rows_in_last_step;
4053
uint32_t n_full_steps;
4054
4086
double index_read_cost;
4056
4088
elem_size= h->ref_length + sizeof(void*) * (!test(flags & HA_MRR_NO_ASSOCIATION));
4369
4401
handlerton *hton= plugin_data(plugin, handlerton *);
4371
4403
if (hton->state == SHOW_OPTION_YES && hton->create &&
4372
(file= hton->create(hton, (TABLE_SHARE*) 0, current_session->mem_root)))
4404
(file= hton->create(hton, (TABLE_SHARE*) 0, current_thd->mem_root)))
4374
4406
List_iterator_fast<char> it(*found_exts);
4375
4407
const char **ext, *old_ext;
4423
static bool stat_print(Session *session, const char *type, uint32_t type_len,
4424
const char *file, uint32_t file_len,
4425
const char *status, uint32_t status_len)
4455
static bool stat_print(THD *thd, const char *type, uint type_len,
4456
const char *file, uint file_len,
4457
const char *status, uint status_len)
4427
Protocol *protocol= session->protocol;
4459
Protocol *protocol= thd->protocol;
4428
4460
protocol->prepare_for_resend();
4429
4461
protocol->store(type, type_len, system_charset_info);
4430
4462
protocol->store(file, file_len, system_charset_info);
4481
4513
assert(table->s->cached_row_logging_check == 0 ||
4482
4514
table->s->cached_row_logging_check == 1);
4484
return (session->current_stmt_binlog_row_based &&
4516
return (thd->current_stmt_binlog_row_based &&
4485
4517
table->s->cached_row_logging_check &&
4486
(session->options & OPTION_BIN_LOG) &&
4518
(thd->options & OPTION_BIN_LOG) &&
4487
4519
mysql_bin_log.is_open());
4493
4525
to the binary log.
4495
4527
This function will generate and write table maps for all tables
4496
that are locked by the thread 'session'. Either manually locked
4497
(stored in Session::locked_tables) and automatically locked (stored
4498
in Session::lock) are considered.
4528
that are locked by the thread 'thd'. Either manually locked
4529
(stored in THD::locked_tables) and automatically locked (stored
4530
in THD::lock) are considered.
4500
@param session Pointer to Session structure
4532
@param thd Pointer to THD structure
4502
4534
@retval 0 All OK
4503
4535
@retval 1 Failed to write all table maps
4507
Session::locked_tables
4510
static int write_locked_table_maps(Session *session)
4542
static int write_locked_table_maps(THD *thd)
4512
if (session->get_binlog_table_maps() == 0)
4544
if (thd->get_binlog_table_maps() == 0)
4514
4546
DRIZZLE_LOCK *locks[3];
4515
locks[0]= session->extra_lock;
4516
locks[1]= session->lock;
4517
locks[2]= session->locked_tables;
4518
for (uint32_t i= 0 ; i < sizeof(locks)/sizeof(*locks) ; ++i )
4547
locks[0]= thd->extra_lock;
4548
locks[1]= thd->lock;
4549
locks[2]= thd->locked_tables;
4550
for (uint i= 0 ; i < sizeof(locks)/sizeof(*locks) ; ++i )
4520
4552
DRIZZLE_LOCK const *const lock= locks[i];
4521
4553
if (lock == NULL)
4529
4561
Table *const table= *table_ptr;
4530
4562
if (table->current_lock == F_WRLCK &&
4531
check_table_binlog_row_based(session, table))
4563
check_table_binlog_row_based(thd, table))
4533
4565
int const has_trans= table->file->has_transactions();
4534
int const error= session->binlog_write_table_map(table, has_trans);
4566
int const error= thd->binlog_write_table_map(table, has_trans);
4536
4568
If an error occurs, it is the responsibility of the caller to
4537
4569
roll back the transaction.
4549
typedef bool Log_func(Session*, Table*, bool, const unsigned char*, const unsigned char*);
4581
typedef bool Log_func(THD*, Table*, bool, const uchar*, const uchar*);
4551
4583
static int binlog_log_row(Table* table,
4552
const unsigned char *before_record,
4553
const unsigned char *after_record,
4584
const uchar *before_record,
4585
const uchar *after_record,
4554
4586
Log_func *log_func)
4556
4588
if (table->no_replicate)
4559
Session *const session= table->in_use;
4591
THD *const thd= table->in_use;
4561
if (check_table_binlog_row_based(session, table))
4593
if (check_table_binlog_row_based(thd, table))
4564
4596
If there are no table maps written to the binary log, this is
4565
4597
the first row handled in this statement. In that case, we need
4566
4598
to write table maps for all locked tables to the binary log.
4568
if (likely(!(error= write_locked_table_maps(session))))
4600
if (likely(!(error= write_locked_table_maps(thd))))
4570
4602
bool const has_trans= table->file->has_transactions();
4571
error= (*log_func)(session, table, has_trans, before_record, after_record);
4603
error= (*log_func)(thd, table, has_trans, before_record, after_record);
4574
4606
return error ? HA_ERR_RBR_LOGGING_FAILED : 0;
4577
int handler::ha_external_lock(Session *session, int lock_type)
4609
int handler::ha_external_lock(THD *thd, int lock_type)
4580
4612
Whether this is lock or unlock, this should be true, and is to verify that
4602
4634
int handler::ha_reset()
4604
4636
/* Check that we have called all proper deallocation functions */
4605
assert((unsigned char*) table->def_read_set.bitmap +
4637
assert((uchar*) table->def_read_set.bitmap +
4606
4638
table->s->column_bitmap_size ==
4607
(unsigned char*) table->def_write_set.bitmap);
4639
(uchar*) table->def_write_set.bitmap);
4608
4640
assert(bitmap_is_set_all(&table->s->all_set));
4609
4641
assert(table->key_read == 0);
4610
4642
/* ensure that ha_index_end / ha_rnd_end has been called */
4681
4713
/* fallback to use all columns in the table to identify row */
4682
4714
table->use_all_columns();
4685
void table_case_convert(char * name, uint32_t length)
4687
if (lower_case_table_names)
4688
files_charset_info->cset->casedn(files_charset_info,
4689
name, length, name, length);
4692
const char *table_case_name(HA_CREATE_INFO *info, const char *name)
4694
return ((lower_case_table_names == 2 && info->alias) ? info->alias : name);