17
17
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
20
#ifndef DRIZZLED_SESSION_H
21
#define DRIZZLED_SESSION_H
23
22
#include <algorithm>
25
24
#include <boost/make_shared.hpp>
25
#include <boost/scoped_ptr.hpp>
26
26
#include <boost/thread/condition_variable.hpp>
27
27
#include <boost/thread/mutex.hpp>
28
28
#include <boost/thread/shared_mutex.hpp>
33
33
#include <sys/resource.h>
34
34
#include <sys/time.h>
36
#include <drizzled/catalog/instance.h>
37
#include <drizzled/catalog/local.h>
38
#include <drizzled/copy_info.h>
39
#include <drizzled/cursor.h>
40
#include <drizzled/diagnostics_area.h>
41
#include <drizzled/file_exchange.h>
42
#include <drizzled/ha_data.h>
43
#include <drizzled/identifier.h>
44
#include <drizzled/lex_column.h>
45
#include <drizzled/my_hash.h>
46
#include <drizzled/named_savepoint.h>
36
#include <drizzled/global_charset_info.h>
37
#include <drizzled/base.h>
38
#include <drizzled/error.h>
47
39
#include <drizzled/open_tables_state.h>
48
#include <drizzled/plugin.h>
49
#include <drizzled/plugin/authorization.h>
50
40
#include <drizzled/pthread_globals.h>
51
#include <drizzled/query_id.h>
52
#include <drizzled/resource_context.h>
53
#include <drizzled/session/property_map.h>
54
#include <drizzled/session/state.h>
55
#include <drizzled/session/table_messages.h>
56
41
#include <drizzled/session/transactions.h>
42
#include <drizzled/sql_list.h>
57
43
#include <drizzled/sql_error.h>
58
#include <drizzled/sql_lex.h>
59
44
#include <drizzled/sql_locale.h>
60
45
#include <drizzled/statistics_variables.h>
61
46
#include <drizzled/system_variables.h>
62
#include <drizzled/system_variables.h>
63
#include <drizzled/table_ident.h>
64
#include <drizzled/transaction_context.h>
65
#include <drizzled/util/storable.h>
66
#include <drizzled/var.h>
67
47
#include <drizzled/visibility.h>
69
#define MIN_HANDSHAKE_SIZE 6
48
#include <drizzled/util/find_ptr.h>
49
#include <drizzled/util/string.h>
50
#include <drizzled/type/time.h>
51
#include <drizzled/sql_lex.h>
78
class EventObserverList;
58
class EventObserverList;
59
class MonitoredInTransaction;
88
70
namespace internal { struct st_my_thread_var; }
89
namespace table { class Placeholder; }
91
class Diagnostics_area;
93
94
class Internal_error_handler;
94
97
class Lex_input_stream;
98
class ResourceContext;
95
99
class TableShareInstance;
96
100
class Table_ident;
98
102
class select_result;
99
103
class user_var_entry;
101
108
extern char internal_table_name[2];
102
109
extern char empty_c_string[1];
204
205
void setXaId(uint64_t in_xa_id)
210
* Uniquely identifies each statement object in thread scope; change during
211
* statement lifetime.
213
* @todo should be const
217
LEX *lex; /**< parse tree descriptor */
225
enum_sql_command getSqlCommand() const
227
return lex->sql_command;
211
Diagnostics_area& main_da();
212
const LEX& lex() const;
214
enum_sql_command getSqlCommand() const;
230
216
/** query associated with this statement */
231
217
typedef boost::shared_ptr<const std::string> QueryString;
349
326
drizzle_system_variables variables; /**< Mutable local variables local to the session */
351
enum_tx_isolation getTxIsolation()
353
return (enum_tx_isolation)variables.tx_isolation;
356
struct system_status_var status_var; /**< Session-local status counters */
327
enum_tx_isolation getTxIsolation();
328
system_status_var status_var;
357
330
THR_LOCK_INFO lock_info; /**< Locking information for this session */
358
331
THR_LOCK_OWNER main_lock_id; /**< To use for conventional queries */
359
332
THR_LOCK_OWNER *lock_id; /**< If not main_lock_id, points to the lock_id of a cursor. */
365
338
char *thread_stack;
368
identifier::User::shared_ptr security_ctx;
370
int32_t scoreboard_index;
372
inline void checkSentry() const
374
assert(this->dbug_sentry == Session_SENTRY_MAGIC);
378
340
identifier::User::const_shared_ptr user() const
383
return identifier::User::const_shared_ptr();
342
return security_ctx ? security_ctx : identifier::User::const_shared_ptr();
386
345
void setUser(identifier::User::shared_ptr arg)
516
474
void **getEngineData(const plugin::MonitoredInTransaction *monitored);
517
ResourceContext *getResourceContext(const plugin::MonitoredInTransaction *monitored,
475
ResourceContext& getResourceContext(const plugin::MonitoredInTransaction&, size_t index= 0);
520
477
session::Transactions transaction;
522
479
Field *dup_field;
523
480
sigset_t signals;
525
483
// As of right now we do not allow a concurrent execute to launch itself
527
bool concurrent_execute_allowed;
531
484
void setConcurrentExecute(bool arg)
533
486
concurrent_execute_allowed= arg;
587
537
(first_successful_insert_id_in_cur_stmt == 0), but storing "INSERT_ID=3"
588
538
in the binlog is still needed; the list's minimum will contain 3.
590
Discrete_intervals_list auto_inc_intervals_in_cur_stmt_for_binlog;
591
/** Used by replication and SET INSERT_ID */
592
Discrete_intervals_list auto_inc_intervals_forced;
594
541
uint64_t limit_found_rows;
595
542
uint64_t options; /**< Bitmap of options */
770
716
bool substitute_null_with_insert_id;
771
717
bool cleanup_done;
774
bool abort_on_warning;
775
bool tablespace_op; /**< This is true in DISCARD/IMPORT TABLESPACE */
778
720
bool got_warning; /**< Set on call to push_warning() */
779
721
bool no_warnings_for_error; /**< no warnings on call to my_error() */
780
722
/** set during loop of derived table processing */
781
723
bool derived_tables_processing;
783
bool doing_tablespace_operation(void)
725
bool doing_tablespace_operation()
785
727
return tablespace_op;
916
858
if (first_successful_insert_id_in_cur_stmt == 0)
917
859
first_successful_insert_id_in_cur_stmt= id_arg;
919
inline uint64_t read_first_successful_insert_id_in_prev_stmt(void)
861
inline uint64_t read_first_successful_insert_id_in_prev_stmt()
921
863
return first_successful_insert_id_in_prev_stmt;
924
Used by Intvar_log_event::do_apply_event() and by "SET INSERT_ID=#"
925
(mysqlbinlog). We'll soon add a variant which can take many intervals in
928
inline void force_one_auto_inc_interval(uint64_t next_id)
930
auto_inc_intervals_forced.empty(); // in case of multiple SET INSERT_ID
931
auto_inc_intervals_forced.append(next_id, UINT64_MAX, 0);
934
866
Session(plugin::Client *client_arg, catalog::Instance::shared_ptr catalog);
935
867
virtual ~Session();
939
871
* Cleans up after query.
1065
997
void set_time_after_lock()
1067
boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::universal_time());
1068
utime_after_lock= (mytime - _epoch).total_microseconds();
1071
void set_end_timer()
1073
_end_timer= boost::posix_time::microsec_clock::universal_time();
1074
status_var.execution_time_nsec+=(_end_timer - _start_timer).total_microseconds();
999
utime_after_lock= (boost::posix_time::microsec_clock::universal_time() - _epoch).total_microseconds();
1002
void set_end_timer();
1077
1004
uint64_t getElapsedTime() const
1079
1006
return (_end_timer - _start_timer).total_microseconds();
1083
1010
* Returns the current micro-timestamp
1085
1012
type::Time::epoch_t getCurrentTimestamp(bool actual= true) const
1087
type::Time::epoch_t t_mark;
1091
boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::universal_time());
1092
t_mark= (mytime - _epoch).total_microseconds();
1096
t_mark= (_end_timer - _epoch).total_microseconds();
1014
return ((actual ? boost::posix_time::microsec_clock::universal_time() : _end_timer) - _epoch).total_microseconds();
1102
1017
// We may need to set user on this
1103
1018
type::Time::epoch_t getCurrentTimestampEpoch() const
1105
if (not _user_time.is_not_a_date_time())
1106
return (_user_time - _epoch).total_seconds();
1108
return (_start_timer - _epoch).total_seconds();
1020
return ((_user_time.is_not_a_date_time() ? _start_timer : _user_time) - _epoch).total_seconds();
1111
1023
type::Time::epoch_t getCurrentTimestampEpoch(type::Time::usec_t &fraction_arg) const
1113
1025
if (not _user_time.is_not_a_date_time())
1115
1027
fraction_arg= 0;
1142
1054
int send_explain_fields(select_result *result);
1145
Clear the current error, if any.
1146
We do not clear is_fatal_error or is_fatal_sub_stmt_error since we
1147
assume this is never called if the fatal error is set.
1148
@todo: To silence an error, one should use Internal_error_handler
1149
mechanism. In future this function will be removed.
1151
inline void clear_error(bool full= false)
1153
if (main_da.is_error())
1154
main_da.reset_diagnostics_area();
1158
drizzle_reset_errors(this, true);
1162
void clearDiagnostics()
1164
main_da.reset_diagnostics_area();
1168
Mark the current error as fatal. Warning: this does not
1169
set any error, it sets a property of the error, so must be
1170
followed or prefixed with my_error().
1172
inline void fatal_error()
1174
assert(main_da.is_error());
1175
is_fatal_error= true;
1178
true if there is an error in the error stack.
1180
Please use this method instead of direct access to
1183
If true, the current (sub)-statement should be aborted.
1184
The main difference between this member and is_fatal_error
1185
is that a fatal error can not be handled by a stored
1186
procedure continue handler, whereas a normal error can.
1188
To raise this flag, use my_error().
1190
inline bool is_error() const { return main_da.is_error(); }
1056
void clear_error(bool full= false);
1057
void clearDiagnostics();
1059
bool is_error() const;
1191
1061
inline const CHARSET_INFO *charset() { return default_charset_info; }
1193
void change_item_tree(Item **place, Item *new_value)
1198
1064
Cleanup statement parse state (parse tree, lex) and execution
1199
1065
state after execution of a non-prepared SQL statement.
1263
1129
@param level the error level
1264
1130
@return true if the error is handled
1266
virtual bool handle_error(drizzled::error_t sql_errno, const char *message,
1132
virtual bool handle_error(error_t sql_errno, const char *message,
1267
1133
DRIZZLE_ERROR::enum_warning_level level);
1304
1170
* @note Host, user and passwd may point to communication buffer.
1305
1171
* Current implementation does not depend on that, but future changes
1306
* should be done with this in mind;
1172
* should be done with this in mind;
1308
1174
* @param passwd Scrambled password received from client
1309
1175
* @param db Database name to connect to, may be NULL
1311
1177
bool checkUser(const std::string &passwd, const std::string &db);
1314
* Returns the timestamp (in microseconds) of when the Session
1180
* Returns the timestamp (in microseconds) of when the Session
1315
1181
* connected to the server.
1317
1183
uint64_t getConnectMicroseconds() const
1391
1257
void resetResultsetMessage()
1393
1259
resultset= NULL;
1397
/** Pointers to memory managed by the ReplicationServices component */
1398
message::Transaction *transaction_message;
1399
message::Statement *statement_message;
1400
/* Pointer to the current resultset of Select query */
1401
message::Resultset *resultset;
1402
plugin::EventObserverList *session_event_observers;
1404
/* Schema observers are mapped to databases. */
1405
std::map<std::string, plugin::EventObserverList *> schema_event_observers;
1409
plugin::EventObserverList *getSessionObservers()
1263
plugin::EventObserverList *getSessionObservers()
1411
1265
return session_event_observers;
1414
void setSessionObservers(plugin::EventObserverList *observers)
1268
void setSessionObservers(plugin::EventObserverList *observers)
1416
1270
session_event_observers= observers;
1419
1273
/* For schema event observers there is one set of observers per database. */
1420
plugin::EventObserverList *getSchemaObservers(const std::string &db_name)
1422
std::map<std::string, plugin::EventObserverList *>::iterator it;
1424
it= schema_event_observers.find(db_name);
1425
if (it == schema_event_observers.end())
1274
plugin::EventObserverList *getSchemaObservers(const std::string &db_name)
1276
if (schema_event_observers_t::mapped_type* i= find_ptr(schema_event_observers, db_name))
1431
void setSchemaObservers(const std::string &db_name, plugin::EventObserverList *observers)
1433
std::map<std::string, plugin::EventObserverList *>::iterator it;
1435
it= schema_event_observers.find(db_name);
1436
if (it != schema_event_observers.end())
1437
schema_event_observers.erase(it);;
1281
void setSchemaObservers(const std::string &db_name, plugin::EventObserverList *observers)
1283
schema_event_observers.erase(db_name);
1440
1285
schema_event_observers[db_name] = observers;
1445
const char *proc_info;
1447
1291
/** The current internal error handler for this thread, or NULL. */
1448
1292
Internal_error_handler *m_internal_handler;
1450
The lex to hold the parsed tree of conventional (non-prepared) queries.
1451
Whereas for prepared and stored procedure statements we use an own lex
1452
instance for each new query, for conventional statements we reuse
1453
the same lex. (@see mysql_parse for details).
1457
1294
This memory root is used for two purposes:
1458
1295
- for conventional queries, to allocate structures stored in main_lex
1459
1296
during parsing, and allocate runtime data (execution plan, etc.)
1475
1312
* if table->query_id != session->query_id to know if a table is in use.
1479
1316
* SELECT f1_that_uses_t1() FROM t1;
1481
1318
* In f1_that_uses_t1() we will see one instance of t1 where query_id is
1482
1319
* set to query_id of original query.
1484
1321
void mark_used_tables_as_free_for_reuse(Table *table);
1488
/** A short cut for session->main_da.set_ok_status(). */
1489
inline void my_ok(ha_rows affected_rows= 0, ha_rows found_rows_arg= 0,
1490
uint64_t passed_id= 0, const char *message= NULL)
1492
main_da.set_ok_status(this, affected_rows, found_rows_arg, passed_id, message);
1496
/** A short cut for session->main_da.set_eof_status(). */
1498
inline void my_eof()
1500
main_da.set_eof_status(this);
1503
/* Some inline functions for more speed */
1505
inline bool add_item_to_list(Item *item)
1507
return lex->current_select->add_item_to_list(this, item);
1510
inline bool add_value_to_list(Item *value)
1512
return lex->value_list.push_back(value);
1515
inline bool add_order_to_list(Item *item, bool asc)
1517
return lex->current_select->add_order_to_list(this, item, asc);
1520
inline bool add_group_to_list(Item *item, bool asc)
1522
return lex->current_select->add_group_to_list(this, item, asc);
1324
void my_ok(ha_rows affected_rows= 0, ha_rows found_rows_arg= 0, uint64_t passed_id= 0, const char *message= NULL);
1326
bool add_item_to_list(Item *item);
1327
bool add_value_to_list(Item *value);
1328
bool add_order_to_list(Item *item, bool asc);
1329
bool add_group_to_list(Item *item, bool asc);
1524
1331
void refresh_status();
1525
1332
user_var_entry *getVariable(LEX_STRING &name, bool create_if_not_exists);
1526
1333
user_var_entry *getVariable(const std::string &name, bool create_if_not_exists);
1527
1334
void setVariable(const std::string &name, const std::string &value);
1530
1337
* Closes all tables used by the current substatement, or all tables
1531
1338
* used by this thread if we are on the upper level.
1579
1381
table::Placeholder *table_cache_insert_placeholder(const identifier::Table &identifier);
1580
1382
bool lock_table_name_if_not_cached(const identifier::Table &identifier, Table **table);
1583
session::TableMessages _table_message_cache;
1586
session::TableMessages &getMessageCache()
1588
return _table_message_cache;
1384
session::TableMessages &getMessageCache();
1591
1386
/* Reopen operations */
1592
1387
bool reopen_tables();
1596
1391
int setup_conds(TableList *leaves, COND **conds);
1597
1392
int lock_tables(TableList *tables, uint32_t count, bool *need_reopen);
1599
drizzled::util::Storable *getProperty(const std::string &arg)
1395
T* getProperty(const std::string& name)
1601
return life_properties.getProperty(arg);
1397
return static_cast<T*>(getProperty0(name));
1605
bool setProperty(const std::string &arg, T *value)
1401
T setProperty(const std::string& name, T value)
1607
life_properties.setProperty(arg, value);
1403
setProperty0(name, value);
1618
1413
pointer to plugin::StorageEngine
1620
plugin::StorageEngine *getDefaultStorageEngine()
1622
if (variables.storage_engine)
1623
return variables.storage_engine;
1624
return global_system_variables.storage_engine;
1415
plugin::StorageEngine *getDefaultStorageEngine();
1627
1416
void get_xid(DrizzleXid *xid); // Innodb only
1629
1418
table::Singular *getInstanceTable();
1630
1419
table::Singular *getInstanceTable(List<CreateField> &field_list);
1635
if (getrusage(RUSAGE_THREAD, &usage))
1645
1421
void setUsage(bool arg)
1647
1423
use_usage= arg;
1650
const struct rusage &getUsage()
1426
const rusage &getUsage()
1655
1431
catalog::Instance::const_reference catalog() const
1657
return *(_catalog.get());
1660
1436
catalog::Instance::reference catalog()
1662
return *(_catalog.get());
1441
bool arg_of_last_insert_id_function; // Tells if LAST_INSERT_ID(#) was called for the current statement
1445
bool free_cached_table(boost::mutex::scoped_lock &scopedLock);
1446
drizzled::util::Storable* getProperty0(const std::string&);
1447
void setProperty0(const std::string&, drizzled::util::Storable*);
1452
return not getrusage(RUSAGE_THREAD, &usage);
1455
boost::scoped_ptr<impl_c> impl_;
1666
1456
catalog::Instance::shared_ptr _catalog;
1668
// This lives throughout the life of Session
1458
/** Pointers to memory managed by the ReplicationServices component */
1459
message::Transaction *transaction_message;
1460
message::Statement *statement_message;
1461
/* Pointer to the current resultset of Select query */
1462
message::Resultset *resultset;
1463
plugin::EventObserverList *session_event_observers;
1465
/* Schema observers are mapped to databases. */
1466
typedef std::map<std::string, plugin::EventObserverList*> schema_event_observers_t;
1467
schema_event_observers_t schema_event_observers;
1470
const char *proc_info;
1471
bool abort_on_warning;
1472
bool concurrent_execute_allowed;
1473
bool tablespace_op; /**< This is true in DISCARD/IMPORT TABLESPACE */
1669
1474
bool use_usage;
1670
session::PropertyMap life_properties;
1671
1475
std::vector<table::Singular *> temporary_shares;
1672
struct rusage usage;
1477
identifier::User::shared_ptr security_ctx;
1478
int32_t scoreboard_index;
1479
plugin::Client *client;
1675
1482
#define ESCAPE_CHARS "ntrb0ZN" // keep synchronous with READ_INFO::unescape
1677
1484
/* Bits in sql_command_flags */
1679
enum sql_command_flag_bits
1486
enum sql_command_flag_bits
1681
1488
CF_BIT_CHANGES_DATA,
1682
1489
CF_BIT_HAS_ROW_COUNT,
1692
1499
static const std::bitset<CF_BIT_SIZE> CF_SHOW_TABLE_COMMAND(1 << CF_BIT_SHOW_TABLE_COMMAND);
1693
1500
static const std::bitset<CF_BIT_SIZE> CF_WRITE_LOGS_COMMAND(1 << CF_BIT_WRITE_LOGS_COMMAND);
1696
const std::string &type(drizzled::Session::global_read_lock_t type);
1697
size_t max_string_length(drizzled::Session::global_read_lock_t type);
1504
const std::string &type(Session::global_read_lock_t);
1505
size_t max_string_length(Session::global_read_lock_t);
1699
1506
} /* namespace display */
1701
1508
} /* namespace drizzled */
1703
#endif /* DRIZZLED_SESSION_H */