17
17
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21
20
#ifndef DRIZZLED_SESSION_H
22
21
#define DRIZZLED_SESSION_H
24
/* Classes in mysql */
25
#include <boost/make_shared.hpp>
26
#include <boost/thread/condition_variable.hpp>
27
#include <boost/thread/mutex.hpp>
28
#include <boost/thread/shared_mutex.hpp>
29
#include <boost/thread/thread.hpp>
33
#include <sys/resource.h>
26
#include "drizzled/plugin.h"
27
#include <drizzled/sql_locale.h>
28
#include "drizzled/resource_context.h"
36
#include <drizzled/catalog/instance.h>
37
#include <drizzled/catalog/local.h>
38
#include <drizzled/copy_info.h>
29
39
#include <drizzled/cursor.h>
30
#include <drizzled/current_session.h>
31
#include <drizzled/sql_error.h>
40
#include <drizzled/diagnostics_area.h>
32
41
#include <drizzled/file_exchange.h>
33
#include <drizzled/select_result_interceptor.h>
34
#include <drizzled/statistics_variables.h>
35
#include <drizzled/xid.h>
36
#include "drizzled/query_id.h"
37
#include "drizzled/named_savepoint.h"
38
#include "drizzled/transaction_context.h"
39
#include "drizzled/util/storable.h"
41
#include "drizzled/my_hash.h"
49
#include "drizzled/internal/getrusage.h"
51
#include <drizzled/security_context.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>
52
47
#include <drizzled/open_tables_state.h>
54
#include <drizzled/internal_error_handler.h>
55
#include <drizzled/diagnostics_area.h>
48
#include <drizzled/plugin.h>
57
49
#include <drizzled/plugin/authorization.h>
59
#include <boost/unordered_map.hpp>
60
#include <boost/thread/mutex.hpp>
61
#include <boost/thread/shared_mutex.hpp>
62
#include <boost/thread/condition_variable.hpp>
50
#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
#include <drizzled/session/transactions.h>
57
#include <drizzled/sql_error.h>
58
#include <drizzled/sql_lex.h>
59
#include <drizzled/sql_locale.h>
60
#include <drizzled/statistics_variables.h>
61
#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
#include <drizzled/visibility.h>
64
69
#define MIN_HANDSHAKE_SIZE 6
99
106
#define TC_HEURISTIC_RECOVER_ROLLBACK 2
100
107
extern uint32_t tc_heuristic_recover;
104
Local storage for proto that are tmp table. This should be enlarged
105
to hande the entire table-share for a local table. Once Hash is done,
106
we should consider exchanging the map for it.
108
typedef std::map <std::string, message::Table> ProtoCache;
111
The COPY_INFO structure is used by INSERT/REPLACE code.
112
The schema of the row counting by the INSERT/INSERT ... ON DUPLICATE KEY
114
If a row is inserted then the copied variable is incremented.
115
If a row is updated by the INSERT ... ON DUPLICATE KEY UPDATE and the
116
new data differs from the old one then the copied and the updated
117
variables are incremented.
118
The touched variable is incremented if a row was touched by the update part
119
of the INSERT ... ON DUPLICATE KEY UPDATE no matter whether the row
120
was actually changed or not.
124
ha_rows records; /**< Number of processed records */
125
ha_rows deleted; /**< Number of deleted records */
126
ha_rows updated; /**< Number of updated records */
127
ha_rows copied; /**< Number of copied records */
129
ha_rows touched; /* Number of touched records */
130
enum enum_duplicates handle_duplicates;
131
int escape_char, last_errno;
133
/* for INSERT ... UPDATE */
134
List<Item> *update_fields;
135
List<Item> *update_values;
136
/* for VIEW ... WITH CHECK OPTION */
157
uint32_t table_count;
159
THR_LOCK_DATA **locks;
170
} /* namespace drizzled */
172
/** @TODO why is this in the middle of the file */
173
#include <drizzled/lex_column.h>
181
109
#define Session_SENTRY_MAGIC 0xfeedd1ff
182
110
#define Session_SENTRY_GONE 0xdeadbeef
184
struct system_variables
186
system_variables() {};
188
How dynamically allocated system variables are handled:
190
The global_system_variables and max_system_variables are "authoritative"
191
They both should have the same 'version' and 'size'.
192
When attempting to access a dynamic variable, if the session version
193
is out of date, then the session version is updated and realloced if
194
neccessary and bytes copied from global to make up for missing data.
196
ulong dynamic_variables_version;
197
char * dynamic_variables_ptr;
198
uint32_t dynamic_variables_head; /* largest valid variable offset */
199
uint32_t dynamic_variables_size; /* how many bytes are in use */
201
uint64_t myisam_max_extra_sort_file_size;
202
uint64_t max_heap_table_size;
203
uint64_t tmp_table_size;
204
ha_rows select_limit;
205
ha_rows max_join_size;
206
uint64_t auto_increment_increment;
207
uint64_t auto_increment_offset;
208
uint64_t bulk_insert_buff_size;
209
uint64_t join_buff_size;
210
uint32_t max_allowed_packet;
211
uint64_t max_error_count;
212
uint64_t max_length_for_sort_data;
213
size_t max_sort_length;
214
uint64_t min_examined_row_limit;
215
bool optimizer_prune_level;
218
uint32_t optimizer_search_depth;
219
uint32_t div_precincrement;
220
uint64_t preload_buff_size;
221
uint32_t read_buff_size;
222
uint32_t read_rnd_buff_size;
223
size_t sortbuff_size;
224
uint32_t thread_handling;
225
uint32_t tx_isolation;
226
size_t transaction_message_threshold;
227
uint32_t completion_type;
228
/* Determines which non-standard SQL behaviour should be enabled */
230
uint64_t max_seeks_for_key;
231
size_t range_alloc_block_size;
232
uint32_t query_alloc_block_size;
233
uint32_t query_prealloc_size;
234
uint64_t group_concat_max_len;
235
uint64_t pseudo_thread_id;
237
plugin::StorageEngine *storage_engine;
239
/* Only charset part of these variables is sensible */
240
const CHARSET_INFO *character_set_filesystem;
242
/* Both charset and collation parts of these variables are important */
243
const CHARSET_INFO *collation_server;
245
inline const CHARSET_INFO *getCollation(void)
247
return collation_server;
251
MY_LOCALE *lc_time_names;
253
Time_zone *time_zone;
256
extern struct system_variables global_system_variables;
258
} /* namespace drizzled */
260
#include "drizzled/sql_lex.h"
265
void mark_transaction_to_rollback(Session *session, bool all);
268
Storage engine specific thread local data.
273
Storage engine specific thread local data.
274
Lifetime: one user connection.
278
* Resource contexts for both the "statement" and "normal"
281
* Resource context at index 0:
283
* Life time: one statement within a transaction. If @@autocommit is
284
* on, also represents the entire transaction.
286
* Resource context at index 1:
288
* Life time: one transaction within a connection.
292
* If the storage engine does not participate in a transaction,
293
* there will not be a resource context.
295
drizzled::ResourceContext resource_context[2];
297
Ha_data() :ha_ptr(NULL) {}
112
extern DRIZZLED_API struct drizzle_system_variables global_system_variables;
301
115
* Represents a client connection to the database server.
316
130
* all member variables that are not critical to non-internal operations of the
317
131
* session object.
319
class Session : public Open_tables_state
134
class DRIZZLED_API Session : public Open_tables_state
322
137
// Plugin storage in Session.
323
typedef boost::unordered_map<std::string, util::Storable *, util::insensitive_hash, util::insensitive_equal_to> PropertyMap;
138
typedef boost::shared_ptr<Session> shared_ptr;
139
typedef Session& reference;
140
typedef const Session& const_reference;
141
typedef const Session* const_pointer;
142
typedef Session* pointer;
144
static shared_ptr make_shared(plugin::Client *client, catalog::Instance::shared_ptr instance_arg)
146
assert(instance_arg);
147
return boost::make_shared<Session>(client, instance_arg);
326
151
MARK_COLUMNS_NONE: Means mark_used_colums is not set and no indicator to
385
213
* @todo should be const
388
217
LEX *lex; /**< parse tree descriptor */
225
enum_sql_command getSqlCommand() const
227
return lex->sql_command;
394
230
/** query associated with this statement */
231
typedef boost::shared_ptr<const std::string> QueryString;
234
boost::shared_ptr<std::string> query;
236
// Never allow for a modification of this outside of the class. c_str()
237
// requires under some setup non const, you must copy the QueryString in
240
QueryString getQueryString() const
245
void resetQueryString()
252
We need to copy the lock on the string in order to make sure we have a stable string.
253
Once this is done we can use it to build a const char* which can be handed off for
254
a method to use (Innodb is currently the only engine using this).
256
const char *getQueryStringCopy(size_t &length)
258
QueryString tmp_string(getQueryString());
266
length= tmp_string->length();
267
char *to_return= strmake(tmp_string->c_str(), tmp_string->length());
272
session::State::shared_ptr _state;
276
session::State::const_shared_ptr state()
398
282
Name of the current (default) database.
418
314
static const char * const DEFAULT_WHERE;
420
316
memory::Root warn_root; /**< Allocation area for warnings and errors */
421
318
plugin::Client *client; /**< Pointer to client object */
322
void setClient(plugin::Client *client_arg);
324
plugin::Client *getClient()
329
plugin::Client *getClient() const
422
334
plugin::Scheduler *scheduler; /**< Pointer to scheduler object */
423
335
void *scheduler_arg; /**< Pointer to the optional scheduler argument */
425
337
typedef boost::unordered_map< std::string, user_var_entry *, util::insensitive_hash, util::insensitive_equal_to> UserVars;
426
340
typedef std::pair< UserVars::iterator, UserVars::iterator > UserVarsRange;
427
341
UserVars user_vars; /**< Hash of user variables defined during the session's lifetime */
430
struct system_variables variables; /**< Mutable local variables local to the session */
344
const UserVars &getUserVariables() const
349
drizzle_system_variables variables; /**< Mutable local variables local to the session */
351
enum_tx_isolation getTxIsolation()
353
return (enum_tx_isolation)variables.tx_isolation;
431
356
struct system_status_var status_var; /**< Session-local status counters */
432
357
THR_LOCK_INFO lock_info; /**< Locking information for this session */
433
358
THR_LOCK_OWNER main_lock_id; /**< To use for conventional queries */
434
359
THR_LOCK_OWNER *lock_id; /**< If not main_lock_id, points to the lock_id of a cursor. */
436
boost::mutex LOCK_delete; /**< Locked before session is deleted */
444
void unlockForDelete()
446
LOCK_delete.unlock();
450
* A peek into the query string for the session. This is a best effort
451
* delivery, there is no guarantee whether the content is meaningful.
453
char process_list_info[PROCESS_LIST_WIDTH+1];
456
362
* A pointer to the stack frame of the scheduler thread
532
466
uint32_t file_id; /**< File ID for LOAD DATA INFILE */
533
467
/* @note the following three members should likely move to Client */
534
468
uint32_t max_client_packet_length; /**< Maximum number of bytes a client can send in a single packet */
537
uint64_t thr_create_utime; /**< track down slow pthread_create */
538
uint64_t start_utime;
539
uint64_t utime_after_lock;
471
boost::posix_time::ptime _epoch;
472
boost::posix_time::ptime _connect_time;
473
boost::posix_time::ptime _start_timer;
474
boost::posix_time::ptime _end_timer;
476
boost::posix_time::ptime _user_time;
478
uint64_t utime_after_lock; // This used by Innodb.
482
_user_time= boost::posix_time::not_a_date_time;
485
const boost::posix_time::ptime &start_timer() const
490
void getTimeDifference(boost::posix_time::time_duration &result_arg, const boost::posix_time::ptime &arg) const
492
result_arg= arg - _start_timer;
541
495
thr_lock_type update_lock_default;
558
512
query_id_t query_id;
559
513
query_id_t warn_query_id;
561
516
void **getEngineData(const plugin::MonitoredInTransaction *monitored);
562
517
ResourceContext *getResourceContext(const plugin::MonitoredInTransaction *monitored,
563
518
size_t index= 0);
565
struct st_transactions {
566
std::deque<NamedSavepoint> savepoints;
567
TransactionContext all; ///< Trans since BEGIN WORK
568
TransactionContext stmt; ///< Trans for current statement
520
session::Transactions transaction;
583
522
Field *dup_field;
584
523
sigset_t signals;
525
// As of right now we do not allow a concurrent execute to launch itself
527
bool concurrent_execute_allowed;
531
void setConcurrentExecute(bool arg)
533
concurrent_execute_allowed= arg;
536
bool isConcurrentExecuteAllowed() const
538
return concurrent_execute_allowed;
586
541
/* Tells if LAST_INSERT_ID(#) was called for the current statement */
587
542
bool arg_of_last_insert_id_function;
589
545
ALL OVER THIS FILE, "insert_id" means "*automatically generated* value for
590
546
insertion into an auto_increment column".
686
648
create_sort_index(); may differ from examined_row_count.
688
650
uint32_t row_count;
652
uint32_t getRowCount() const
657
session_id_t thread_id;
690
658
uint32_t tmp_table;
691
uint32_t global_read_lock;
659
enum global_read_lock_t
662
GOT_GLOBAL_READ_LOCK= 1,
663
MADE_GLOBAL_READ_LOCK_BLOCK_COMMIT= 2
666
global_read_lock_t _global_read_lock;
670
global_read_lock_t isGlobalReadLock() const
672
return _global_read_lock;
675
void setGlobalReadLock(global_read_lock_t arg)
677
_global_read_lock= arg;
680
DrizzleLock *lockTables(Table **tables, uint32_t count, uint32_t flags);
681
bool lockGlobalReadLock();
682
bool lock_table_names(TableList *table_list);
683
bool lock_table_names_exclusively(TableList *table_list);
684
bool makeGlobalReadLockBlockCommit();
685
bool abortLockForThread(Table *table);
686
bool wait_if_global_read_lock(bool abort_on_refresh, bool is_not_commit);
687
int lock_table_name(TableList *table_list);
688
void abortLock(Table *table);
689
void removeLock(Table *table);
690
void unlockReadTables(DrizzleLock *sql_lock);
691
void unlockSomeTables(Table **table, uint32_t count);
692
void unlockTables(DrizzleLock *sql_lock);
693
void startWaitingGlobalReadLock();
694
void unlockGlobalReadLock();
697
int unlock_external(Table **table, uint32_t count);
698
int lock_external(Table **tables, uint32_t count);
699
bool wait_for_locked_table_names(TableList *table_list);
700
DrizzleLock *get_lock_data(Table **table_ptr, uint32_t count,
701
bool should_lock, Table **write_lock_used);
692
704
uint32_t server_status;
693
705
uint32_t open_options;
694
706
uint32_t select_number; /**< number of select (used for EXPLAIN) */
1012
1046
const char* enter_cond(boost::condition_variable_any &cond, boost::mutex &mutex, const char* msg);
1013
1047
void exit_cond(const char* old_msg);
1015
inline time_t query_start() { return start_time; }
1016
inline void set_time()
1020
start_time= user_time;
1021
connect_microseconds= start_utime= utime_after_lock= my_micro_time();
1024
start_utime= utime_after_lock= my_micro_time_and_time(&start_time);
1026
inline void set_current_time() { start_time= time(NULL); }
1027
inline void set_time(time_t t)
1029
start_time= user_time= t;
1030
start_utime= utime_after_lock= my_micro_time();
1032
void set_time_after_lock() { utime_after_lock= my_micro_time(); }
1049
type::Time::epoch_t query_start()
1051
return getCurrentTimestampEpoch();
1056
_end_timer= _start_timer= boost::posix_time::microsec_clock::universal_time();
1057
utime_after_lock= (_start_timer - _epoch).total_microseconds();
1060
void set_time(time_t t) // This is done by a sys_var, as long as user_time is set, we will use that for all references to time
1062
_user_time= boost::posix_time::from_time_t(t);
1065
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();
1077
uint64_t getElapsedTime() const
1079
return (_end_timer - _start_timer).total_microseconds();
1034
1083
* Returns the current micro-timestamp
1036
inline uint64_t getCurrentTimestamp()
1038
return my_micro_time();
1040
inline uint64_t found_rows(void)
1085
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();
1102
// We may need to set user on this
1103
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();
1111
type::Time::epoch_t getCurrentTimestampEpoch(type::Time::usec_t &fraction_arg) const
1113
if (not _user_time.is_not_a_date_time())
1116
return (_user_time - _epoch).total_seconds();
1119
fraction_arg= _start_timer.time_of_day().fractional_seconds() % 1000000;
1120
return (_start_timer - _epoch).total_seconds();
1123
uint64_t found_rows(void) const
1042
1125
return limit_found_rows;
1044
1128
/** Returns whether the session is currently inside a transaction */
1045
inline bool inTransaction()
1129
bool inTransaction() const
1047
1131
return server_status & SERVER_STATUS_IN_TRANS;
1049
1134
LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1050
1135
const char* str, uint32_t length,
1051
1136
bool allocate_lex_string);
1052
1138
LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1053
1139
const std::string &str,
1054
1140
bool allocate_lex_string);
1056
1142
int send_explain_fields(select_result *result);
1058
1145
Clear the current error, if any.
1059
1146
We do not clear is_fatal_error or is_fatal_sub_stmt_error since we
1209
1305
* Current implementation does not depend on that, but future changes
1210
1306
* should be done with this in mind;
1212
* @param Scrambled password received from client
1213
* @param Length of scrambled password
1214
* @param Database name to connect to, may be NULL
1308
* @param passwd Scrambled password received from client
1309
* @param db Database name to connect to, may be NULL
1216
bool checkUser(const char *passwd, uint32_t passwd_len, const char *db);
1311
bool checkUser(const std::string &passwd, const std::string &db);
1219
1314
* Returns the timestamp (in microseconds) of when the Session
1220
1315
* connected to the server.
1222
inline uint64_t getConnectMicroseconds() const
1224
return connect_microseconds;
1317
uint64_t getConnectMicroseconds() const
1319
return (_connect_time - _epoch).total_microseconds();
1322
uint64_t getConnectSeconds() const
1324
return (_connect_time - _epoch).total_seconds();
1481
1572
Table *openTable(TableList *table_list, bool *refresh, uint32_t flags= 0);
1483
1574
void unlink_open_table(Table *find);
1484
void drop_open_table(Table *table, TableIdentifier &identifier);
1575
void drop_open_table(Table *table, const identifier::Table &identifier);
1485
1576
void close_cached_table(Table *table);
1487
1578
/* Create a lock in the cache */
1488
Table *table_cache_insert_placeholder(const char *db_name, const char *table_name);
1489
bool lock_table_name_if_not_cached(TableIdentifier &identifier, Table **table);
1491
typedef boost::unordered_map<std::string, message::Table, util::insensitive_hash, util::insensitive_equal_to> TableMessageCache;
1492
TableMessageCache table_message_cache;
1494
bool storeTableMessage(const TableIdentifier &identifier, message::Table &table_message);
1495
bool removeTableMessage(const TableIdentifier &identifier);
1496
bool getTableMessage(const TableIdentifier &identifier, message::Table &table_message);
1497
bool doesTableMessageExist(const TableIdentifier &identifier);
1498
bool renameTableMessage(const TableIdentifier &from, const TableIdentifier &to);
1500
/* Work with temporary tables */
1501
Table *find_temporary_table(TableList *table_list);
1502
Table *find_temporary_table(const char *db, const char *table_name);
1503
Table *find_temporary_table(TableIdentifier &identifier);
1505
void doGetTableNames(CachedDirectory &directory,
1506
const SchemaIdentifier &schema_identifier,
1507
std::set<std::string>& set_of_names);
1508
void doGetTableNames(const SchemaIdentifier &schema_identifier,
1509
std::set<std::string>& set_of_names);
1511
void doGetTableIdentifiers(CachedDirectory &directory,
1512
const SchemaIdentifier &schema_identifier,
1513
TableIdentifiers &set_of_identifiers);
1514
void doGetTableIdentifiers(const SchemaIdentifier &schema_identifier,
1515
TableIdentifiers &set_of_identifiers);
1517
int doGetTableDefinition(const drizzled::TableIdentifier &identifier,
1518
message::Table &table_proto);
1519
bool doDoesTableExist(const drizzled::TableIdentifier &identifier);
1521
void close_temporary_tables();
1522
void close_temporary_table(Table *table);
1523
// The method below just handles the de-allocation of the table. In
1524
// a better memory type world, this would not be needed.
1579
table::Placeholder *table_cache_insert_placeholder(const identifier::Table &identifier);
1580
bool lock_table_name_if_not_cached(const identifier::Table &identifier, Table **table);
1526
void nukeTable(Table *table);
1583
session::TableMessages _table_message_cache;
1529
void dumpTemporaryTableNames(const char *id);
1530
int drop_temporary_table(TableList *table_list);
1531
bool rm_temporary_table(plugin::StorageEngine *base, TableIdentifier &identifier);
1532
bool rm_temporary_table(TableIdentifier &identifier, bool best_effort= false);
1533
Table *open_temporary_table(TableIdentifier &identifier,
1534
bool link_in_list= true);
1586
session::TableMessages &getMessageCache()
1588
return _table_message_cache;
1536
1591
/* Reopen operations */
1537
bool reopen_tables(bool get_locks, bool mark_share_as_old);
1538
bool reopen_name_locked_table(TableList* table_list, bool link_in);
1592
bool reopen_tables();
1539
1593
bool close_cached_tables(TableList *tables, bool wait_for_refresh, bool wait_for_placeholders);
1541
1595
void wait_for_condition(boost::mutex &mutex, boost::condition_variable_any &cond);
1542
1596
int setup_conds(TableList *leaves, COND **conds);
1543
1597
int lock_tables(TableList *tables, uint32_t count, bool *need_reopen);
1545
Table *create_virtual_tmp_table(List<CreateField> &field_list);
1547
1599
drizzled::util::Storable *getProperty(const std::string &arg)
1549
return life_properties[arg];
1601
return life_properties.getProperty(arg);
1552
1604
template<class T>
1553
1605
bool setProperty(const std::string &arg, T *value)
1555
life_properties[arg]= value;
1607
life_properties.setProperty(arg, value);
1655
catalog::Instance::const_reference catalog() const
1657
return *(_catalog.get());
1660
catalog::Instance::reference catalog()
1662
return *(_catalog.get());
1666
catalog::Instance::shared_ptr _catalog;
1604
1668
// This lives throughout the life of Session
1605
1669
bool use_usage;
1606
PropertyMap life_properties;
1607
std::vector<TableShareInstance *> temporary_shares;
1670
session::PropertyMap life_properties;
1671
std::vector<table::Singular *> temporary_shares;
1608
1672
struct rusage usage;
1613
1675
#define ESCAPE_CHARS "ntrb0ZN" // keep synchronous with READ_INFO::unescape
1615
} /* namespace drizzled */
1617
/** @TODO why is this in the middle of the file */
1618
#include <drizzled/select_to_file.h>
1619
#include <drizzled/select_export.h>
1620
#include <drizzled/select_dump.h>
1621
#include <drizzled/select_insert.h>
1622
#include <drizzled/select_create.h>
1623
#include <drizzled/tmp_table_param.h>
1624
#include <drizzled/select_union.h>
1625
#include <drizzled/select_subselect.h>
1626
#include <drizzled/select_singlerow_subselect.h>
1627
#include <drizzled/select_max_min_finder_subselect.h>
1628
#include <drizzled/select_exists_subselect.h>
1634
* A structure used to describe sort information
1635
* for a field or item used in ORDER BY.
1639
Field *field; /**< Field to sort */
1640
Item *item; /**< Item if not sorting fields */
1641
size_t length; /**< Length of sort field */
1642
uint32_t suffix_length; /**< Length suffix (0-4) */
1643
Item_result result_type; /**< Type of item */
1644
bool reverse; /**< if descending sort */
1645
bool need_strxnfrm; /**< If we have to use strxnfrm() */
1652
result_type(STRING_RESULT),
1659
} /* namespace drizzled */
1661
/** @TODO why is this in the middle of the file */
1663
#include <drizzled/table_ident.h>
1664
#include <drizzled/user_var_entry.h>
1665
#include <drizzled/unique.h>
1666
#include <drizzled/var.h>
1667
#include <drizzled/select_dumpvar.h>
1672
1677
/* Bits in sql_command_flags */
1674
1679
enum sql_command_flag_bits