24
24
/* Classes in mysql */
26
#include "drizzled/plugin.h"
26
#include "drizzled/sql_plugin.h"
27
#include <drizzled/plugin/protocol.h>
28
#include <drizzled/plugin/scheduler.h>
27
29
#include <drizzled/sql_locale.h>
28
#include "drizzled/resource_context.h"
29
#include <drizzled/cursor.h>
30
#include <drizzled/ha_trx_info.h>
31
#include <mysys/my_alloc.h>
32
#include <mysys/my_tree.h>
33
#include <drizzled/handler.h>
30
34
#include <drizzled/current_session.h>
31
35
#include <drizzled/sql_error.h>
32
36
#include <drizzled/file_exchange.h>
33
37
#include <drizzled/select_result_interceptor.h>
38
#include <drizzled/authentication.h>
39
#include <drizzled/db.h>
34
40
#include <drizzled/xid.h>
35
#include "drizzled/query_id.h"
36
#include "drizzled/named_savepoint.h"
37
#include "drizzled/transaction_context.h"
45
#include <drizzled/security_context.h>
46
#include <drizzled/open_tables_state.h>
48
#include <drizzled/internal_error_handler.h>
49
#include <drizzled/diagnostics_area.h>
51
#include <drizzled/plugin/authorization.h>
53
46
#define MIN_HANDSHAKE_SIZE 6
70
struct st_my_thread_var;
73
48
class Lex_input_stream;
74
49
class user_var_entry;
191
157
size_t range_alloc_block_size;
192
158
uint32_t query_alloc_block_size;
193
159
uint32_t query_prealloc_size;
160
uint32_t trans_alloc_block_size;
161
uint32_t trans_prealloc_size;
194
162
uint64_t group_concat_max_len;
163
/* TODO: change this to my_thread_id - but have to fix set_var first */
195
164
uint64_t pseudo_thread_id;
197
plugin::StorageEngine *storage_engine;
166
StorageEngine *storage_engine;
199
168
/* Only charset part of these variables is sensible */
200
169
const CHARSET_INFO *character_set_filesystem;
312
* Resource contexts for both the "statement" and "normal"
315
* Resource context at index 0:
317
* Life time: one statement within a transaction. If @@autocommit is
318
* on, also represents the entire transaction.
320
* Resource context at index 1:
322
* Life time: one transaction within a connection.
326
* If the storage engine does not participate in a transaction,
327
* there will not be a resource context.
329
drizzled::ResourceContext resource_context[2];
291
0: Life time: one statement within a transaction. If @@autocommit is
292
on, also represents the entire transaction.
293
@sa trans_register_ha()
295
1: Life time: one transaction within a connection.
296
If the storage engine does not participate in a transaction,
297
this should not be used.
298
@sa trans_register_ha()
300
Ha_trx_info ha_info[2];
331
302
Ha_data() :ha_ptr(NULL) {}
413
384
LEX *lex; /**< parse tree descriptor */
414
/** query associated with this statement */
386
Points to the query associated with this statement. It's const, but
387
we need to declare it char * because all table handlers are written
388
in C and need to point to it.
390
Note that (A) if we set query = NULL, we must at the same time set
391
query_length = 0, and protect the whole operation with the
392
LOCK_thread_count mutex. And (B) we are ONLY allowed to set query to a
393
non-NULL value if its previous value is NULL. We do not need to protect
394
operation (B) with any mutex. To avoid crashes in races, if we do not
395
know that session->query cannot change at the moment, one should print
396
session->query like this:
397
(1) reserve the LOCK_thread_count mutex;
398
(2) check if session->query is NULL;
399
(3) if not NULL, then print at most session->query_length characters from
400
it. We will see the query_length field as either 0, or the right value
402
Assuming that the write and read of an n-bit memory field in an n-bit
403
computer is atomic, we can avoid races in the above way.
404
This printing is needed at least in SHOW PROCESSLIST and SHOW INNODB
408
uint32_t query_length; /**< current query length */
418
411
Name of the current (default) database.
437
431
static const char * const DEFAULT_WHERE;
439
memory::Root warn_root; /**< Allocation area for warnings and errors */
440
plugin::Client *client; /**< Pointer to client object */
441
plugin::Scheduler *scheduler; /**< Pointer to scheduler object */
433
MEM_ROOT warn_root; /**< Allocation area for warnings and errors */
434
drizzled::plugin::Protocol *protocol; /**< Pointer to protocol object */
435
drizzled::plugin::Scheduler *scheduler; /**< Pointer to scheduler object */
442
436
void *scheduler_arg; /**< Pointer to the optional scheduler argument */
443
437
HASH user_vars; /**< Hash of user variables defined during the session's lifetime */
438
String packet; /**< dynamic buffer for network I/O */
439
String convert_buffer; /**< A buffer for charset conversions */
444
440
struct system_variables variables; /**< Mutable local variables local to the session */
445
441
struct system_status_var status_var; /**< Session-local status counters */
446
442
struct system_status_var *initial_status_var; /* used by show status */
462
458
char *thread_stack;
465
SecurityContext security_ctx;
467
inline void checkSentry() const
469
assert(this->dbug_sentry == Session_SENTRY_MAGIC);
472
const SecurityContext& getSecurityContext() const
477
SecurityContext& getSecurityContext()
483
* Is this session viewable by the current user?
485
bool isViewable() const
487
return plugin::Authorization::isAuthorized(current_session->getSecurityContext(),
462
Some members of Session (currently 'Statement::db',
463
'query') are set and alloced by the slave SQL thread
464
(for the Session of that thread); that thread is (and must remain, for now)
465
the only responsible for freeing these 3 members. If you add members
466
here, and you add code to set them in replication, don't forget to
467
free_them_and_set_them_to_0 in replication properly. For details see
468
the 'err:' label of the handle_slave_sql() in sql/slave.cc.
470
@see handle_slave_sql
472
Security_context security_ctx;
493
475
Used in error messages to tell user in what part of MySQL we found an
502
484
chapter 'Miscellaneous functions', for functions GET_LOCK, RELEASE_LOCK.
504
486
uint32_t dbug_sentry; /**< watch for memory corruption */
505
internal::st_my_thread_var *mysys_var;
487
struct st_my_thread_var *mysys_var;
507
489
* Type of current query: COM_STMT_PREPARE, COM_QUERY, etc. Set from
508
490
* first byte of the packet in executeStatement()
510
492
enum enum_server_command command;
511
493
uint32_t file_id; /**< File ID for LOAD DATA INFILE */
512
/* @note the following three members should likely move to Client */
494
/* @note the following three members should likely move to Protocol */
495
uint16_t peer_port; /**< The remote (peer) port */
513
496
uint32_t max_client_packet_length; /**< Maximum number of bytes a client can send in a single packet */
514
497
time_t start_time;
515
498
time_t user_time;
523
506
Both of the following container points in session will be converted to an API.
527
509
/* container for handler's private per-connection data */
528
std::vector<Ha_data> ha_data;
530
Id of current query. Statement can be reused to execute several queries
531
query_id is global in context of the whole MySQL server.
532
ID is automatically generated from an atomic counter.
533
It's used in Cursor code for various purposes: to check which columns
534
from table are necessary for this select, to check if it's necessary to
535
update auto-updatable fields (like auto_increment and timestamp).
538
query_id_t warn_query_id;
540
void **getEngineData(const plugin::MonitoredInTransaction *monitored);
541
ResourceContext *getResourceContext(const plugin::MonitoredInTransaction *monitored,
510
Ha_data ha_data[MAX_HA];
512
/* container for replication data */
513
void *replication_data;
544
515
struct st_transactions {
545
std::deque<NamedSavepoint> savepoints;
546
TransactionContext all; ///< Trans since BEGIN WORK
547
TransactionContext stmt; ///< Trans for current statement
516
SAVEPOINT *savepoints;
517
Session_TRANS all; // Trans since BEGIN WORK
518
Session_TRANS stmt; // Trans for current statement
519
bool on; // see ha_enable_transaction()
548
520
XID_STATE xid_state;
523
Tables changed in transaction (that must be invalidated in query cache).
524
List contain only transactional tables, that not invalidated in query
525
cache (instead of full list of changed in transaction tables).
527
CHANGED_TableList* changed_tables;
528
MEM_ROOT mem_root; // Transaction-life memory allocation pool
533
free_root(&mem_root,MYF(MY_KEEP_PREALLOC));
537
memset(this, 0, sizeof(*this));
538
xid_state.xid.null();
539
init_sql_alloc(&mem_root, ALLOC_ROOT_MIN_BLOCK_SIZE, 0);
562
542
Field *dup_field;
563
543
sigset_t signals;
654
634
uint32_t total_warn_count;
655
635
Diagnostics_area main_da;
638
Id of current query. Statement can be reused to execute several queries
639
query_id is global in context of the whole MySQL server.
640
ID is automatically generated from mutex-protected counter.
641
It's used in handler code for various purposes: to check which columns
642
from table are necessary for this select, to check if it's necessary to
643
update auto-updatable fields (like auto_increment and timestamp).
657
647
ulong col_access;
649
#ifdef ERROR_INJECT_SUPPORT
650
ulong error_inject_value;
659
652
/* Statement id is thread-wide. This counter is used to generate ids */
660
653
uint32_t statement_id_counter;
661
654
uint32_t rand_saved_seed1;
989
962
enter_cond(); this mutex is then released by exit_cond().
990
963
Usage must be: lock mutex; enter_cond(); your code; exit_cond().
992
const char* enter_cond(pthread_cond_t *cond, pthread_mutex_t* mutex, const char* msg);
993
void exit_cond(const char* old_msg);
965
inline const char* enter_cond(pthread_cond_t *cond, pthread_mutex_t* mutex, const char* msg)
967
const char* old_msg = get_proc_info();
968
safe_mutex_assert_owner(mutex);
969
mysys_var->current_mutex = mutex;
970
mysys_var->current_cond = cond;
971
this->set_proc_info(msg);
974
inline void exit_cond(const char* old_msg)
977
Putting the mutex unlock in exit_cond() ensures that
978
mysys_var->current_mutex is always unlocked _before_ mysys_var->mutex is
979
locked (if that would not be the case, you'll get a deadlock if someone
980
does a Session::awake() on you).
982
pthread_mutex_unlock(mysys_var->current_mutex);
983
pthread_mutex_lock(&mysys_var->mutex);
984
mysys_var->current_mutex = 0;
985
mysys_var->current_cond = 0;
986
this->set_proc_info(old_msg);
987
pthread_mutex_unlock(&mysys_var->mutex);
995
989
inline time_t query_start() { return start_time; }
996
990
inline void set_time()
1031
1025
return !lex->only_view_structure();
1027
inline void* trans_alloc(unsigned int size)
1029
return alloc_root(&transaction.mem_root,size);
1034
1032
LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1035
1033
const char* str, uint32_t length,
1036
1034
bool allocate_lex_string);
1037
LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1038
const std::string &str,
1039
bool allocate_lex_string);
1036
void add_changed_table(Table *table);
1037
void add_changed_table(const char *key, long key_length);
1038
CHANGED_TableList * changed_table_dup(const char *key, long key_length);
1041
1039
int send_explain_fields(select_result *result);
1043
1041
Clear the current error, if any.
1128
1126
@retval false Success
1129
1127
@retval true Out-of-memory error
1131
bool set_db(const std::string &new_db);
1129
bool set_db(const char *new_db, size_t new_db_len);
1132
Set the current database; use shallow copy of C-string.
1134
@param new_db a pointer to the new database name.
1135
@param new_db_len length of the new database name.
1137
@note This operation just sets {db, db_length}. Switching the current
1138
database usually involves other actions, like switching other database
1139
attributes including security context. In the future, this operation
1140
will be made private and more convenient interface will be provided.
1142
void reset_db(char *new_db, size_t new_db_len)
1145
db_length= new_db_len;
1134
1148
Copy the current database to the argument. Use the current arena to
1135
1149
allocate memory for a deep copy: current database may be freed after
1208
1222
return connect_microseconds;
1212
* Returns a pointer to the active Transaction message for this
1213
* Session being managed by the ReplicationServices component, or
1214
* NULL if no active message.
1216
message::Transaction *getTransactionMessage() const
1218
return transaction_message;
1222
* Returns a pointer to the active Statement message for this
1223
* Session, or NULL if no active message.
1225
message::Statement *getStatementMessage() const
1227
return statement_message;
1231
* Sets the active transaction message used by the ReplicationServices
1234
* @param[in] Pointer to the message
1236
void setTransactionMessage(message::Transaction *in_message)
1238
transaction_message= in_message;
1242
* Sets the active statement message used by the ReplicationServices
1245
* @param[in] Pointer to the message
1247
void setStatementMessage(message::Statement *in_message)
1249
statement_message= in_message;
1252
/** Pointers to memory managed by the ReplicationServices component */
1253
message::Transaction *transaction_message;
1254
message::Statement *statement_message;
1255
1226
/** Microsecond timestamp of when Session connected */
1256
1227
uint64_t connect_microseconds;
1257
1228
const char *proc_info;
1412
1382
Table *openTable(TableList *table_list, bool *refresh, uint32_t flags= 0);
1414
1384
void unlink_open_table(Table *find);
1415
void drop_open_table(Table *table, TableIdentifier &identifier);
1385
void drop_open_table(Table *table, const char *db_name,
1386
const char *table_name);
1416
1387
void close_cached_table(Table *table);
1418
1389
/* Create a lock in the cache */
1419
1390
Table *table_cache_insert_placeholder(const char *key, uint32_t key_length);
1420
bool lock_table_name_if_not_cached(TableIdentifier &identifier, Table **table);
1421
bool lock_table_name_if_not_cached(const char *db,
1391
bool lock_table_name_if_not_cached(const char *db,
1422
1392
const char *table_name, Table **table);
1424
typedef drizzled::hash_map<std::string, message::Table> TableMessageCache;
1425
TableMessageCache table_message_cache;
1427
bool storeTableMessage(TableIdentifier &identifier, message::Table &table_message);
1428
bool removeTableMessage(TableIdentifier &identifier);
1429
bool getTableMessage(TableIdentifier &identifier, message::Table &table_message);
1430
bool doesTableMessageExist(TableIdentifier &identifier);
1431
bool renameTableMessage(TableIdentifier &from, TableIdentifier &to);
1433
1394
/* Work with temporary tables */
1434
1395
Table *find_temporary_table(TableList *table_list);
1435
1396
Table *find_temporary_table(const char *db, const char *table_name);
1436
Table *find_temporary_table(TableIdentifier &identifier);
1438
void doGetTableNames(CachedDirectory &directory,
1439
SchemaIdentifier &schema_identifier,
1440
std::set<std::string>& set_of_names);
1441
void doGetTableNames(SchemaIdentifier &schema_identifier,
1442
std::set<std::string>& set_of_names);
1444
void doGetTableIdentifiers(CachedDirectory &directory,
1445
SchemaIdentifier &schema_identifier,
1446
TableIdentifiers &set_of_identifiers);
1447
void doGetTableIdentifiers(SchemaIdentifier &schema_identifier,
1448
TableIdentifiers &set_of_identifiers);
1450
int doGetTableDefinition(drizzled::TableIdentifier &identifier,
1451
message::Table &table_proto);
1452
bool doDoesTableExist(TableIdentifier &identifier);
1454
1397
void close_temporary_tables();
1455
void close_temporary_table(Table *table);
1456
// The method below just handles the de-allocation of the table. In
1457
// a better memory type world, this would not be needed.
1459
void nukeTable(Table *table);
1462
void dumpTemporaryTableNames(const char *id);
1398
void close_temporary_table(Table *table, bool free_share, bool delete_table);
1399
void close_temporary(Table *table, bool free_share, bool delete_table);
1463
1400
int drop_temporary_table(TableList *table_list);
1464
bool rm_temporary_table(plugin::StorageEngine *base, TableIdentifier &identifier);
1465
bool rm_temporary_table(TableIdentifier &identifier);
1466
Table *open_temporary_table(TableIdentifier &identifier,
1467
bool link_in_list= true);
1401
bool rm_temporary_table(StorageEngine *base, char *path);
1402
Table *open_temporary_table(const char *path, const char *db,
1403
const char *table_name, bool link_in_list,
1404
open_table_mode open_mode);
1469
1406
/* Reopen operations */
1470
1407
bool reopen_tables(bool get_locks, bool mark_share_as_old);
1471
1408
bool reopen_name_locked_table(TableList* table_list, bool link_in);
1474
1411
void wait_for_condition(pthread_mutex_t *mutex, pthread_cond_t *cond);
1475
1412
int setup_conds(TableList *leaves, COND **conds);
1476
1413
int lock_tables(TableList *tables, uint32_t count, bool *need_reopen);
1480
Return the default storage engine
1482
@param getDefaultStorageEngine()
1485
pointer to plugin::StorageEngine
1487
plugin::StorageEngine *getDefaultStorageEngine()
1489
if (variables.storage_engine)
1490
return variables.storage_engine;
1491
return global_system_variables.storage_engine;
1494
static void unlink(Session *session);
1500
1418
#define ESCAPE_CHARS "ntrb0ZN" // keep synchronous with READ_INFO::unescape
1502
} /* namespace drizzled */
1504
/** @TODO why is this in the middle of the file */
1505
1420
#include <drizzled/select_to_file.h>
1506
1421
#include <drizzled/select_export.h>
1507
1422
#include <drizzled/select_dump.h>
1508
1423
#include <drizzled/select_insert.h>
1509
1424
#include <drizzled/select_create.h>
1425
#include <plugin/myisam/myisam.h>
1510
1426
#include <drizzled/tmp_table_param.h>
1511
1427
#include <drizzled/select_union.h>
1512
1428
#include <drizzled/select_subselect.h>
1573
1479
static const std::bitset<CF_BIT_SIZE> CF_WRITE_LOGS_COMMAND(1 << CF_BIT_WRITE_LOGS_COMMAND);
1575
1481
/* Functions in sql_class.cc */
1576
void add_to_status(system_status_var *to_var, system_status_var *from_var);
1578
void add_diff_to_status(system_status_var *to_var, system_status_var *from_var,
1579
system_status_var *dec_var);
1581
} /* namespace drizzled */
1482
void add_to_status(STATUS_VAR *to_var, STATUS_VAR *from_var);
1484
void add_diff_to_status(STATUS_VAR *to_var, STATUS_VAR *from_var,
1485
STATUS_VAR *dec_var);
1583
1487
#endif /* DRIZZLED_SESSION_H */