~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/session.h

Merge with trunk.

Show diffs side-by-side

added added

removed removed

Lines of Context:
17
17
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18
18
 */
19
19
 
20
 
 
21
20
#ifndef DRIZZLED_SESSION_H
22
21
#define DRIZZLED_SESSION_H
23
22
 
24
 
#include "drizzled/plugin.h"
25
 
#include "drizzled/sql_locale.h"
26
 
#include "drizzled/resource_context.h"
27
 
#include "drizzled/cursor.h"
28
 
#include "drizzled/current_session.h"
29
 
#include "drizzled/sql_error.h"
30
 
#include "drizzled/file_exchange.h"
31
 
#include "drizzled/select_result_interceptor.h"
32
 
#include "drizzled/statistics_variables.h"
33
 
#include "drizzled/xid.h"
34
 
#include "drizzled/query_id.h"
35
 
#include "drizzled/named_savepoint.h"
36
 
#include "drizzled/transaction_context.h"
37
 
#include "drizzled/util/storable.h"
38
 
#include "drizzled/my_hash.h"
39
 
#include "drizzled/pthread_globals.h"
 
23
#include <drizzled/cursor.h>
 
24
#include <drizzled/diagnostics_area.h>
 
25
#include <drizzled/file_exchange.h>
 
26
#include <drizzled/identifier.h>
 
27
#include <drizzled/lex_column.h>
 
28
#include <drizzled/my_hash.h>
 
29
#include <drizzled/named_savepoint.h>
 
30
#include <drizzled/open_tables_state.h>
 
31
#include <drizzled/plugin.h>
 
32
#include <drizzled/plugin/authorization.h>
 
33
#include <drizzled/pthread_globals.h>
 
34
#include <drizzled/query_id.h>
 
35
#include <drizzled/resource_context.h>
 
36
#include <drizzled/sql_error.h>
 
37
#include <drizzled/sql_lex.h>
 
38
#include <drizzled/sql_locale.h>
 
39
#include <drizzled/statistics_variables.h>
 
40
#include <drizzled/table_ident.h>
 
41
#include <drizzled/transaction_context.h>
 
42
#include <drizzled/util/storable.h>
 
43
#include <drizzled/var.h>
 
44
 
 
45
 
40
46
#include <netdb.h>
41
47
#include <sys/time.h>
42
48
#include <sys/resource.h>
43
49
 
44
50
#include <algorithm>
45
51
#include <bitset>
46
 
#include <deque>
47
52
#include <map>
48
53
#include <string>
49
54
 
50
 
#include "drizzled/identifier.h"
51
 
#include "drizzled/open_tables_state.h"
52
 
#include "drizzled/internal_error_handler.h"
53
 
#include "drizzled/diagnostics_area.h"
54
 
#include "drizzled/plugin/authorization.h"
 
55
#include <drizzled/catalog/instance.h>
 
56
#include <drizzled/catalog/local.h>
55
57
 
56
 
#include <boost/unordered_map.hpp>
 
58
#include <drizzled/copy_info.h>
 
59
#include <drizzled/ha_data.h>
 
60
#include <drizzled/session/property_map.h>
 
61
#include <drizzled/session/state.h>
 
62
#include <drizzled/session/table_messages.h>
 
63
#include <drizzled/session/transactions.h>
 
64
#include <drizzled/system_variables.h>
 
65
#include <drizzled/system_variables.h>
57
66
 
58
67
#include <boost/thread/thread.hpp>
59
68
#include <boost/thread/mutex.hpp>
61
70
#include <boost/thread/condition_variable.hpp>
62
71
#include <boost/make_shared.hpp>
63
72
 
 
73
#include "drizzled/visibility.h"
64
74
 
65
75
#define MIN_HANDSHAKE_SIZE      6
66
76
 
81
91
class Resultset;
82
92
}
83
93
 
84
 
namespace internal
85
 
{
86
 
struct st_my_thread_var;
87
 
}
88
 
 
89
 
namespace table
90
 
{
91
 
class Placeholder;
92
 
}
93
 
 
 
94
namespace internal { struct st_my_thread_var; }
 
95
namespace table { class Placeholder; }
 
96
 
 
97
class CopyField;
 
98
class DrizzleXid;
 
99
class Internal_error_handler;
94
100
class Lex_input_stream;
 
101
class TableShareInstance;
 
102
class Table_ident;
 
103
class Time_zone;
 
104
class select_result;
95
105
class user_var_entry;
96
 
class CopyField;
97
 
class Table_ident;
98
 
 
99
 
class TableShareInstance;
100
106
 
101
107
extern char internal_table_name[2];
102
108
extern char empty_c_string[1];
106
112
#define TC_HEURISTIC_RECOVER_ROLLBACK 2
107
113
extern uint32_t tc_heuristic_recover;
108
114
 
109
 
/**
110
 
  @brief
111
 
  Local storage for proto that are tmp table. This should be enlarged
112
 
  to hande the entire table-share for a local table. Once Hash is done,
113
 
  we should consider exchanging the map for it.
114
 
*/
115
 
typedef std::map <std::string, message::Table> ProtoCache;
116
 
 
117
 
/**
118
 
  The COPY_INFO structure is used by INSERT/REPLACE code.
119
 
  The schema of the row counting by the INSERT/INSERT ... ON DUPLICATE KEY
120
 
  UPDATE code:
121
 
    If a row is inserted then the copied variable is incremented.
122
 
    If a row is updated by the INSERT ... ON DUPLICATE KEY UPDATE and the
123
 
      new data differs from the old one then the copied and the updated
124
 
      variables are incremented.
125
 
    The touched variable is incremented if a row was touched by the update part
126
 
      of the INSERT ... ON DUPLICATE KEY UPDATE no matter whether the row
127
 
      was actually changed or not.
128
 
*/
129
 
class CopyInfo 
130
 
{
131
 
public:
132
 
  ha_rows records; /**< Number of processed records */
133
 
  ha_rows deleted; /**< Number of deleted records */
134
 
  ha_rows updated; /**< Number of updated records */
135
 
  ha_rows copied;  /**< Number of copied records */
136
 
  ha_rows error_count;
137
 
  ha_rows touched; /* Number of touched records */
138
 
  enum enum_duplicates handle_duplicates;
139
 
  int escape_char, last_errno;
140
 
  bool ignore;
141
 
  /* for INSERT ... UPDATE */
142
 
  List<Item> *update_fields;
143
 
  List<Item> *update_values;
144
 
  /* for VIEW ... WITH CHECK OPTION */
145
 
 
146
 
  CopyInfo() :
147
 
    records(0),
148
 
    deleted(0),
149
 
    updated(0),
150
 
    copied(0),
151
 
    error_count(0),
152
 
    touched(0),
153
 
    escape_char(0),
154
 
    last_errno(0),
155
 
    ignore(0),
156
 
    update_fields(0),
157
 
    update_values(0)
158
 
  { }
159
 
 
160
 
};
161
 
 
162
 
} /* namespace drizzled */
163
 
 
164
 
/** @TODO why is this in the middle of the file */
165
 
#include <drizzled/lex_column.h>
166
 
 
167
 
namespace drizzled
168
 
{
169
 
 
170
 
class select_result;
171
 
class Time_zone;
172
 
 
173
115
#define Session_SENTRY_MAGIC 0xfeedd1ff
174
116
#define Session_SENTRY_GONE  0xdeadbeef
175
117
 
176
 
struct drizzle_system_variables
177
 
{
178
 
  drizzle_system_variables()
179
 
  {}
180
 
  /*
181
 
    How dynamically allocated system variables are handled:
182
 
 
183
 
    The global_system_variables and max_system_variables are "authoritative"
184
 
    They both should have the same 'version' and 'size'.
185
 
    When attempting to access a dynamic variable, if the session version
186
 
    is out of date, then the session version is updated and realloced if
187
 
    neccessary and bytes copied from global to make up for missing data.
188
 
  */
189
 
  ulong dynamic_variables_version;
190
 
  char * dynamic_variables_ptr;
191
 
  uint32_t dynamic_variables_head;  /* largest valid variable offset */
192
 
  uint32_t dynamic_variables_size;  /* how many bytes are in use */
193
 
 
194
 
  uint64_t myisam_max_extra_sort_file_size;
195
 
  uint64_t max_heap_table_size;
196
 
  uint64_t tmp_table_size;
197
 
  ha_rows select_limit;
198
 
  ha_rows max_join_size;
199
 
  uint64_t auto_increment_increment;
200
 
  uint64_t auto_increment_offset;
201
 
  uint64_t bulk_insert_buff_size;
202
 
  uint64_t join_buff_size;
203
 
  uint32_t max_allowed_packet;
204
 
  uint64_t max_error_count;
205
 
  uint64_t max_length_for_sort_data;
206
 
  size_t max_sort_length;
207
 
  uint64_t min_examined_row_limit;
208
 
  bool optimizer_prune_level;
209
 
  bool log_warnings;
210
 
 
211
 
  uint32_t optimizer_search_depth;
212
 
  uint32_t div_precincrement;
213
 
  uint64_t preload_buff_size;
214
 
  uint32_t read_buff_size;
215
 
  uint32_t read_rnd_buff_size;
216
 
  bool replicate_query;
217
 
  size_t sortbuff_size;
218
 
  uint32_t thread_handling;
219
 
  uint32_t tx_isolation;
220
 
  size_t transaction_message_threshold;
221
 
  uint32_t completion_type;
222
 
  /* Determines which non-standard SQL behaviour should be enabled */
223
 
  uint32_t sql_mode;
224
 
  uint64_t max_seeks_for_key;
225
 
  size_t range_alloc_block_size;
226
 
  uint32_t query_alloc_block_size;
227
 
  uint32_t query_prealloc_size;
228
 
  uint64_t group_concat_max_len;
229
 
  uint64_t pseudo_thread_id;
230
 
 
231
 
  plugin::StorageEngine *storage_engine;
232
 
 
233
 
  /* Only charset part of these variables is sensible */
234
 
  const CHARSET_INFO  *character_set_filesystem;
235
 
 
236
 
  /* Both charset and collation parts of these variables are important */
237
 
  const CHARSET_INFO    *collation_server;
238
 
 
239
 
  inline const CHARSET_INFO  *getCollation(void) 
240
 
  {
241
 
    return collation_server;
242
 
  }
243
 
 
244
 
  /* Locale Support */
245
 
  MY_LOCALE *lc_time_names;
246
 
 
247
 
  Time_zone *time_zone;
248
 
};
249
 
 
250
 
extern struct drizzle_system_variables global_system_variables;
251
 
 
252
 
} /* namespace drizzled */
253
 
 
254
 
#include "drizzled/sql_lex.h"
255
 
 
256
 
namespace drizzled
257
 
{
258
 
 
259
 
void mark_transaction_to_rollback(Session *session, bool all);
260
 
 
261
 
/**
262
 
  Storage engine specific thread local data.
263
 
*/
264
 
struct Ha_data
265
 
{
266
 
  /**
267
 
    Storage engine specific thread local data.
268
 
    Lifetime: one user connection.
269
 
  */
270
 
  void *ha_ptr;
271
 
  /**
272
 
   * Resource contexts for both the "statement" and "normal"
273
 
   * transactions.
274
 
   *
275
 
   * Resource context at index 0:
276
 
   *
277
 
   * Life time: one statement within a transaction. If @@autocommit is
278
 
   * on, also represents the entire transaction.
279
 
   *
280
 
   * Resource context at index 1:
281
 
   *
282
 
   * Life time: one transaction within a connection. 
283
 
   *
284
 
   * @note
285
 
   *
286
 
   * If the storage engine does not participate in a transaction, 
287
 
   * there will not be a resource context.
288
 
   */
289
 
  drizzled::ResourceContext resource_context[2];
290
 
 
291
 
  Ha_data() :ha_ptr(NULL) {}
292
 
};
 
118
extern DRIZZLED_API struct drizzle_system_variables global_system_variables;
293
119
 
294
120
/**
295
121
 * Represents a client connection to the database server.
310
136
 * all member variables that are not critical to non-internal operations of the
311
137
 * session object.
312
138
 */
313
 
typedef int64_t session_id_t;
314
139
 
315
 
class Session : public Open_tables_state
 
140
class DRIZZLED_API Session : public Open_tables_state
316
141
{
317
142
public:
318
143
  // Plugin storage in Session.
319
 
  typedef boost::unordered_map<std::string, util::Storable *, util::insensitive_hash, util::insensitive_equal_to> PropertyMap;
320
 
  typedef Session* Ptr;
321
144
  typedef boost::shared_ptr<Session> shared_ptr;
 
145
  typedef Session& reference;
 
146
  typedef const Session& const_reference;
 
147
  typedef const Session* const_pointer;
 
148
  typedef Session* pointer;
 
149
 
 
150
  static shared_ptr make_shared(plugin::Client *client, catalog::Instance::shared_ptr instance_arg)
 
151
  {
 
152
    assert(instance_arg);
 
153
    return boost::make_shared<Session>(client, instance_arg);
 
154
  }
322
155
 
323
156
  /*
324
157
    MARK_COLUMNS_NONE:  Means mark_used_colums is not set and no indicator to
332
165
                        and update_row.
333
166
  */
334
167
  enum enum_mark_columns mark_used_columns;
335
 
  inline void* alloc(size_t size)
336
 
  {
337
 
    return mem_root->alloc_root(size);
338
 
  }
339
168
  inline void* calloc(size_t size)
340
169
  {
341
170
    void *ptr;
343
172
      memset(ptr, 0, size);
344
173
    return ptr;
345
174
  }
346
 
  inline char *strdup(const char *str)
347
 
  {
348
 
    return mem_root->strdup_root(str);
349
 
  }
350
175
  inline char *strmake(const char *str, size_t size)
351
176
  {
352
177
    return mem_root->strmake_root(str,size);
353
178
  }
354
 
  inline void *memdup(const void *str, size_t size)
355
 
  {
356
 
    return mem_root->memdup_root(str, size);
357
 
  }
 
179
 
358
180
  inline void *memdup_w_gap(const void *str, size_t size, uint32_t gap)
359
181
  {
360
182
    void *ptr;
364
186
  }
365
187
  /** Frees all items attached to this Statement */
366
188
  void free_items();
 
189
 
367
190
  /**
368
191
   * List of items created in the parser for this query. Every item puts
369
192
   * itself to the list on creation (see Item::Item() for details))
402
225
  {
403
226
    return lex;
404
227
  }
 
228
 
 
229
  enum_sql_command getSqlCommand() const
 
230
  {
 
231
    return lex->sql_command;
 
232
  }
 
233
 
405
234
  /** query associated with this statement */
406
235
  typedef boost::shared_ptr<const std::string> QueryString;
 
236
 
407
237
private:
408
238
  boost::shared_ptr<std::string> query;
409
239
 
442
272
    return to_return;
443
273
  }
444
274
 
445
 
  class State {
446
 
    std::vector <char> _query;
447
 
 
448
 
  public:
449
 
    typedef boost::shared_ptr<State> const_shared_ptr;
450
 
 
451
 
    State(const char *in_packet, size_t in_packet_length)
452
 
    {
453
 
      if (in_packet_length)
454
 
      {
455
 
        size_t minimum= std::min(in_packet_length, static_cast<size_t>(PROCESS_LIST_WIDTH));
456
 
        _query.resize(minimum + 1);
457
 
        memcpy(&_query[0], in_packet, minimum);
458
 
      }
459
 
      else
460
 
      {
461
 
        _query.resize(0);
462
 
      }
463
 
    }
464
 
 
465
 
    const char *query() const
466
 
    {
467
 
      if (_query.size())
468
 
        return &_query[0];
469
 
 
470
 
      return "";
471
 
    }
472
 
 
473
 
    const char *query(size_t &size) const
474
 
    {
475
 
      if (_query.size())
476
 
      {
477
 
        size= _query.size() -1;
478
 
        return &_query[0];
479
 
      }
480
 
 
481
 
      size= 0;
482
 
      return "";
483
 
    }
484
 
  protected:
485
 
    friend class Session;
486
 
    typedef boost::shared_ptr<State> shared_ptr;
487
 
  };
488
275
private:
489
 
  State::shared_ptr  _state; 
 
276
  session::State::shared_ptr  _state; 
 
277
 
490
278
public:
491
279
 
492
 
  State::const_shared_ptr state()
 
280
  session::State::const_shared_ptr state()
493
281
  {
494
282
    return _state;
495
283
  }
508
296
  */
509
297
private:
510
298
  util::string::shared_ptr _schema;
 
299
 
511
300
public:
512
301
 
513
302
  util::string::const_shared_ptr schema() const
517
306
 
518
307
    return util::string::const_shared_ptr(new std::string(""));
519
308
  }
520
 
  std::string catalog;
 
309
 
521
310
  /* current cache key */
522
311
  std::string query_cache_key;
523
312
  /**
529
318
  static const char * const DEFAULT_WHERE;
530
319
 
531
320
  memory::Root warn_root; /**< Allocation area for warnings and errors */
 
321
private:
532
322
  plugin::Client *client; /**< Pointer to client object */
533
323
 
 
324
public:
 
325
 
534
326
  void setClient(plugin::Client *client_arg);
535
327
 
536
328
  plugin::Client *getClient()
538
330
    return client;
539
331
  }
540
332
 
 
333
  plugin::Client *getClient() const
 
334
  {
 
335
    return client;
 
336
  }
 
337
 
541
338
  plugin::Scheduler *scheduler; /**< Pointer to scheduler object */
542
339
  void *scheduler_arg; /**< Pointer to the optional scheduler argument */
543
340
 
544
341
  typedef boost::unordered_map< std::string, user_var_entry *, util::insensitive_hash, util::insensitive_equal_to> UserVars;
 
342
 
545
343
private:
546
344
  typedef std::pair< UserVars::iterator, UserVars::iterator > UserVarsRange;
547
345
  UserVars user_vars; /**< Hash of user variables defined during the session's lifetime */
548
346
 
549
347
public:
550
 
 
551
348
  const UserVars &getUserVariables() const
552
349
  {
553
350
    return user_vars;
554
351
  }
555
352
 
556
353
  drizzle_system_variables variables; /**< Mutable local variables local to the session */
 
354
 
 
355
  enum_tx_isolation getTxIsolation()
 
356
  {
 
357
    return (enum_tx_isolation)variables.tx_isolation;
 
358
  }
 
359
 
557
360
  struct system_status_var status_var; /**< Session-local status counters */
558
361
  THR_LOCK_INFO lock_info; /**< Locking information for this session */
559
362
  THR_LOCK_OWNER main_lock_id; /**< To use for conventional queries */
574
377
  {
575
378
    assert(this->dbug_sentry == Session_SENTRY_MAGIC);
576
379
  }
 
380
 
577
381
public:
578
382
  identifier::User::const_shared_ptr user() const
579
383
  {
601
405
  /**
602
406
   * Is this session viewable by the current user?
603
407
   */
604
 
  bool isViewable() const;
 
408
  bool isViewable(identifier::User::const_reference) const;
605
409
 
 
410
private:
606
411
  /**
607
412
    Used in error messages to tell user in what part of MySQL we found an
608
413
    error. E. g. when where= "having clause", if fix_fields() fails, user
609
414
    will know that the error was in having clause.
610
415
  */
611
 
  const char *where;
 
416
  const char *_where;
 
417
 
 
418
public:
 
419
  const char *where()
 
420
  {
 
421
    return _where;
 
422
  }
 
423
 
 
424
  void setWhere(const char *arg)
 
425
  {
 
426
    _where= arg;
 
427
  }
612
428
 
613
429
  /*
614
430
    One thread can hold up to one named user-level lock. This variable
616
432
    chapter 'Miscellaneous functions', for functions GET_LOCK, RELEASE_LOCK.
617
433
  */
618
434
  uint32_t dbug_sentry; /**< watch for memory corruption */
 
435
 
619
436
private:
620
437
  boost::thread::id boost_thread_id;
621
438
  boost_thread_shared_ptr _thread;
622
439
  boost::this_thread::disable_interruption *interrupt;
623
440
 
624
441
  internal::st_my_thread_var *mysys_var;
 
442
 
625
443
public:
626
 
 
627
444
  boost_thread_shared_ptr &getThread()
628
445
  {
629
446
    return _thread;
653
470
  uint32_t file_id;     /**< File ID for LOAD DATA INFILE */
654
471
  /* @note the following three members should likely move to Client */
655
472
  uint32_t max_client_packet_length; /**< Maximum number of bytes a client can send in a single packet */
656
 
  time_t start_time;
657
 
  time_t user_time;
658
 
  uint64_t thr_create_utime; /**< track down slow pthread_create */
659
 
  uint64_t start_utime;
660
 
  uint64_t utime_after_lock;
 
473
 
 
474
private:
 
475
  boost::posix_time::ptime _epoch;
 
476
  boost::posix_time::ptime _connect_time;
 
477
  boost::posix_time::ptime _start_timer;
 
478
  boost::posix_time::ptime _end_timer;
 
479
 
 
480
  boost::posix_time::ptime _user_time;
 
481
public:
 
482
  uint64_t utime_after_lock; // This used by Innodb.
 
483
 
 
484
  void resetUserTime()
 
485
  {
 
486
    _user_time= boost::posix_time::not_a_date_time;
 
487
  }
 
488
 
 
489
  const boost::posix_time::ptime &start_timer() const
 
490
  {
 
491
    return _start_timer;
 
492
  }
 
493
 
 
494
  void getTimeDifference(boost::posix_time::time_duration &result_arg, const boost::posix_time::ptime &arg) const
 
495
  {
 
496
    result_arg=  arg - _start_timer;
 
497
  }
661
498
 
662
499
  thr_lock_type update_lock_default;
663
500
 
678
515
  */
679
516
  query_id_t query_id;
680
517
  query_id_t warn_query_id;
 
518
 
681
519
public:
682
520
  void **getEngineData(const plugin::MonitoredInTransaction *monitored);
683
521
  ResourceContext *getResourceContext(const plugin::MonitoredInTransaction *monitored,
684
522
                                      size_t index= 0);
685
523
 
686
 
  /**
687
 
   * Structure used to manage "statement transactions" and
688
 
   * "normal transactions". In autocommit mode, the normal transaction is
689
 
   * equivalent to the statement transaction.
690
 
   *
691
 
   * Storage engines will be registered here when they participate in
692
 
   * a transaction. No engine is registered more than once.
693
 
   */
694
 
  struct st_transactions {
695
 
    std::deque<NamedSavepoint> savepoints;
696
 
 
697
 
    /**
698
 
     * The normal transaction (since BEGIN WORK).
699
 
     *
700
 
     * Contains a list of all engines that have participated in any of the
701
 
     * statement transactions started within the context of the normal
702
 
     * transaction.
703
 
     *
704
 
     * @note In autocommit mode, this is empty.
705
 
     */
706
 
    TransactionContext all;
707
 
 
708
 
    /**
709
 
     * The statment transaction.
710
 
     *
711
 
     * Contains a list of all engines participating in the given statement.
712
 
     *
713
 
     * @note In autocommit mode, this will be used to commit/rollback the
714
 
     * normal transaction.
715
 
     */
716
 
    TransactionContext stmt;
717
 
 
718
 
    XID_STATE xid_state;
719
 
 
720
 
    void cleanup()
721
 
    {
722
 
      savepoints.clear();
723
 
    }
724
 
    st_transactions() :
725
 
      savepoints(),
726
 
      all(),
727
 
      stmt(),
728
 
      xid_state()
729
 
    { }
730
 
  } transaction;
 
524
  session::Transactions transaction;
731
525
 
732
526
  Field *dup_field;
733
527
  sigset_t signals;
735
529
  // As of right now we do not allow a concurrent execute to launch itself
736
530
private:
737
531
  bool concurrent_execute_allowed;
 
532
 
738
533
public:
739
534
 
740
535
  void setConcurrentExecute(bool arg)
803
598
  uint64_t limit_found_rows;
804
599
  uint64_t options; /**< Bitmap of options */
805
600
  int64_t row_count_func; /**< For the ROW_COUNT() function */
 
601
 
 
602
  int64_t rowCount() const
 
603
  {
 
604
    return row_count_func;
 
605
  }
 
606
 
806
607
  ha_rows cuted_fields; /**< Count of "cut" or truncated fields. @todo Kill this friggin thing. */
807
608
 
808
609
  /** 
851
652
    create_sort_index(); may differ from examined_row_count.
852
653
  */
853
654
  uint32_t row_count;
 
655
 
 
656
  uint32_t getRowCount() const
 
657
  {
 
658
    return row_count;
 
659
  }
 
660
 
854
661
  session_id_t thread_id;
855
662
  uint32_t tmp_table;
856
663
  enum global_read_lock_t
874
681
    _global_read_lock= arg;
875
682
  }
876
683
 
877
 
  DrizzleLock *lockTables(Table **tables, uint32_t count, uint32_t flags, bool *need_reopen);
 
684
  DrizzleLock *lockTables(Table **tables, uint32_t count, uint32_t flags);
878
685
  bool lockGlobalReadLock();
879
686
  bool lock_table_names(TableList *table_list);
880
687
  bool lock_table_names_exclusively(TableList *table_list);
942
749
    can not continue. In particular, disables activation of
943
750
    CONTINUE or EXIT handlers of stored routines.
944
751
    Reset in the end of processing of the current user request, in
945
 
    @see mysql_reset_session_for_next_command().
 
752
    @see reset_session_for_next_command().
946
753
  */
947
754
  bool is_fatal_error;
948
755
  /**
967
774
  bool substitute_null_with_insert_id;
968
775
  bool cleanup_done;
969
776
 
 
777
private:
970
778
  bool abort_on_warning;
 
779
  bool tablespace_op; /**< This is true in DISCARD/IMPORT TABLESPACE */
 
780
 
 
781
public:
971
782
  bool got_warning; /**< Set on call to push_warning() */
972
783
  bool no_warnings_for_error; /**< no warnings on call to my_error() */
973
784
  /** set during loop of derived table processing */
974
785
  bool derived_tables_processing;
975
 
  bool tablespace_op; /**< This is true in DISCARD/IMPORT TABLESPACE */
 
786
 
 
787
  bool doing_tablespace_operation(void)
 
788
  {
 
789
    return tablespace_op;
 
790
  }
 
791
 
 
792
  void setDoingTablespaceOperation(bool doing)
 
793
  {
 
794
    tablespace_op= doing;
 
795
  }
 
796
 
976
797
 
977
798
  /** Used by the sys_var class to store temporary values */
978
799
  union
1114
935
    auto_inc_intervals_forced.append(next_id, UINT64_MAX, 0);
1115
936
  }
1116
937
 
1117
 
  Session(plugin::Client *client_arg);
 
938
  Session(plugin::Client *client_arg, catalog::Instance::shared_ptr catalog);
1118
939
  virtual ~Session();
1119
940
 
1120
941
  void cleanup(void);
1197
1018
  bool endTransaction(enum enum_mysql_completiontype completion);
1198
1019
  bool endActiveTransaction();
1199
1020
  bool startTransaction(start_transaction_option_t opt= START_TRANS_NO_OPTIONS);
 
1021
  void markTransactionForRollback(bool all);
1200
1022
 
1201
1023
  /**
1202
1024
   * Authenticates users, with error reporting.
1217
1039
   */
1218
1040
  static bool schedule(Session::shared_ptr&);
1219
1041
 
 
1042
  static void unlink(session_id_t &session_id);
1220
1043
  static void unlink(Session::shared_ptr&);
1221
1044
 
1222
1045
  /*
1227
1050
  const char* enter_cond(boost::condition_variable_any &cond, boost::mutex &mutex, const char* msg);
1228
1051
  void exit_cond(const char* old_msg);
1229
1052
 
1230
 
  inline time_t query_start() { return start_time; }
1231
 
  inline void set_time()
1232
 
  {
1233
 
    boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::local_time());
1234
 
    boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1));
1235
 
    start_utime= utime_after_lock= (mytime-epoch).total_microseconds();
1236
 
 
1237
 
    if (user_time)
1238
 
    {
1239
 
      start_time= user_time;
1240
 
      connect_microseconds= start_utime;
1241
 
    }
1242
 
    else 
1243
 
      start_time= (mytime-epoch).total_seconds();
1244
 
  }
1245
 
  inline void   set_current_time()    { start_time= time(NULL); }
1246
 
  inline void   set_time(time_t t)
1247
 
  {
1248
 
    start_time= user_time= t;
1249
 
    boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::local_time());
1250
 
    boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1));
1251
 
    uint64_t t_mark= (mytime-epoch).total_microseconds();
1252
 
 
1253
 
    start_utime= utime_after_lock= t_mark;
1254
 
  }
1255
 
  void set_time_after_lock()  { 
1256
 
     boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::local_time());
1257
 
     boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1));
1258
 
     utime_after_lock= (mytime-epoch).total_microseconds();
1259
 
  }
 
1053
  type::Time::epoch_t query_start()
 
1054
  {
 
1055
    return getCurrentTimestampEpoch();
 
1056
  }
 
1057
 
 
1058
  void set_time()
 
1059
  {
 
1060
    _end_timer= _start_timer= boost::posix_time::microsec_clock::universal_time();
 
1061
    utime_after_lock= (_start_timer - _epoch).total_microseconds();
 
1062
  }
 
1063
 
 
1064
  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
 
1065
  {
 
1066
    _user_time= boost::posix_time::from_time_t(t);
 
1067
  }
 
1068
 
 
1069
  void set_time_after_lock()
 
1070
  { 
 
1071
    boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::universal_time());
 
1072
    utime_after_lock= (mytime - _epoch).total_microseconds();
 
1073
  }
 
1074
 
 
1075
  void set_end_timer()
 
1076
  {
 
1077
    _end_timer= boost::posix_time::microsec_clock::universal_time();
 
1078
    status_var.execution_time_nsec+=(_end_timer - _start_timer).total_microseconds();
 
1079
  }
 
1080
 
 
1081
  uint64_t getElapsedTime() const
 
1082
  {
 
1083
    return (_end_timer - _start_timer).total_microseconds();
 
1084
  }
 
1085
 
1260
1086
  /**
1261
1087
   * Returns the current micro-timestamp
1262
1088
   */
1263
 
  inline uint64_t getCurrentTimestamp()  
 
1089
  type::Time::epoch_t getCurrentTimestamp(bool actual= true) const
1264
1090
  { 
1265
 
    boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::local_time());
1266
 
    boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1));
1267
 
    uint64_t t_mark= (mytime-epoch).total_microseconds();
 
1091
    type::Time::epoch_t t_mark;
 
1092
 
 
1093
    if (actual)
 
1094
    {
 
1095
      boost::posix_time::ptime mytime(boost::posix_time::microsec_clock::universal_time());
 
1096
      t_mark= (mytime - _epoch).total_microseconds();
 
1097
    }
 
1098
    else
 
1099
    {
 
1100
      t_mark= (_end_timer - _epoch).total_microseconds();
 
1101
    }
1268
1102
 
1269
1103
    return t_mark; 
1270
1104
  }
1271
 
  inline uint64_t found_rows(void)
 
1105
 
 
1106
  // We may need to set user on this
 
1107
  type::Time::epoch_t getCurrentTimestampEpoch() const
 
1108
  { 
 
1109
    if (not _user_time.is_not_a_date_time())
 
1110
      return (_user_time - _epoch).total_seconds();
 
1111
 
 
1112
    return (_start_timer - _epoch).total_seconds();
 
1113
  }
 
1114
 
 
1115
  type::Time::epoch_t getCurrentTimestampEpoch(type::Time::usec_t &fraction_arg) const
 
1116
  { 
 
1117
    if (not _user_time.is_not_a_date_time())
 
1118
    {
 
1119
      fraction_arg= 0;
 
1120
      return (_user_time - _epoch).total_seconds();
 
1121
    }
 
1122
 
 
1123
    fraction_arg= _start_timer.time_of_day().fractional_seconds() % 1000000;
 
1124
    return (_start_timer - _epoch).total_seconds();
 
1125
  }
 
1126
 
 
1127
  uint64_t found_rows(void) const
1272
1128
  {
1273
1129
    return limit_found_rows;
1274
1130
  }
 
1131
 
1275
1132
  /** Returns whether the session is currently inside a transaction */
1276
 
  inline bool inTransaction()
 
1133
  bool inTransaction() const
1277
1134
  {
1278
1135
    return server_status & SERVER_STATUS_IN_TRANS;
1279
1136
  }
 
1137
 
1280
1138
  LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1281
1139
                              const char* str, uint32_t length,
1282
1140
                              bool allocate_lex_string);
 
1141
 
1283
1142
  LEX_STRING *make_lex_string(LEX_STRING *lex_str,
1284
1143
                              const std::string &str,
1285
1144
                              bool allocate_lex_string);
1286
1145
 
1287
1146
  int send_explain_fields(select_result *result);
 
1147
 
1288
1148
  /**
1289
1149
    Clear the current error, if any.
1290
1150
    We do not clear is_fatal_error or is_fatal_sub_stmt_error since we
1354
1214
  }
1355
1215
  void send_kill_message() const;
1356
1216
  /* return true if we will abort query if we make a warning now */
1357
 
  inline bool really_abort_on_warning()
1358
 
  {
1359
 
    return (abort_on_warning);
 
1217
  inline bool abortOnWarning()
 
1218
  {
 
1219
    return abort_on_warning;
 
1220
  }
 
1221
 
 
1222
  inline void setAbortOnWarning(bool arg)
 
1223
  {
 
1224
    abort_on_warning= arg;
1360
1225
  }
1361
1226
 
1362
1227
  void setAbort(bool arg);
1402
1267
    @param level the error level
1403
1268
    @return true if the error is handled
1404
1269
  */
1405
 
  virtual bool handle_error(uint32_t sql_errno, const char *message,
 
1270
  virtual bool handle_error(drizzled::error_t sql_errno, const char *message,
1406
1271
                            DRIZZLE_ERROR::enum_warning_level level);
1407
1272
 
1408
1273
  /**
1430
1295
   * updates any status variables necessary.
1431
1296
   *
1432
1297
   * @param errcode     Error code to print to console
1433
 
   * @param should_lock 1 if we have have to lock LOCK_thread_count
1434
1298
   *
1435
1299
   * @note  For the connection that is doing shutdown, this is called twice
1436
1300
   */
1437
 
  void disconnect(uint32_t errcode, bool lock);
 
1301
  void disconnect(enum error_t errcode= EE_OK);
1438
1302
 
1439
1303
  /**
1440
1304
   * Check if user exists and the password supplied is correct.
1454
1318
   * Returns the timestamp (in microseconds) of when the Session 
1455
1319
   * connected to the server.
1456
1320
   */
1457
 
  inline uint64_t getConnectMicroseconds() const
1458
 
  {
1459
 
    return connect_microseconds;
 
1321
  uint64_t getConnectMicroseconds() const
 
1322
  {
 
1323
    return (_connect_time - _epoch).total_microseconds();
 
1324
  }
 
1325
 
 
1326
  uint64_t getConnectSeconds() const
 
1327
  {
 
1328
    return (_connect_time - _epoch).total_seconds();
1460
1329
  }
1461
1330
 
1462
1331
  /**
1577
1446
  
1578
1447
  
1579
1448
 private:
1580
 
 /** Microsecond timestamp of when Session connected */
1581
 
  uint64_t connect_microseconds;
1582
1449
  const char *proc_info;
1583
1450
 
1584
1451
  /** The current internal error handler for this thread, or NULL. */
1671
1538
  void close_old_data_files(bool morph_locks= false,
1672
1539
                            bool send_refresh= false);
1673
1540
  void close_open_tables();
1674
 
  void close_data_files_and_morph_locks(const TableIdentifier &identifier);
 
1541
  void close_data_files_and_morph_locks(const identifier::Table &identifier);
1675
1542
 
1676
1543
private:
1677
 
  bool free_cached_table();
 
1544
  bool free_cached_table(boost::mutex::scoped_lock &scopedLock);
 
1545
 
1678
1546
public:
1679
1547
 
1680
1548
  /**
1708
1576
  Table *openTable(TableList *table_list, bool *refresh, uint32_t flags= 0);
1709
1577
 
1710
1578
  void unlink_open_table(Table *find);
1711
 
  void drop_open_table(Table *table, const TableIdentifier &identifier);
 
1579
  void drop_open_table(Table *table, const identifier::Table &identifier);
1712
1580
  void close_cached_table(Table *table);
1713
1581
 
1714
1582
  /* Create a lock in the cache */
1715
 
  table::Placeholder *table_cache_insert_placeholder(const TableIdentifier &identifier);
1716
 
  bool lock_table_name_if_not_cached(const TableIdentifier &identifier, Table **table);
1717
 
 
1718
 
  typedef boost::unordered_map<std::string, message::Table, util::insensitive_hash, util::insensitive_equal_to> TableMessageCache;
1719
 
 
1720
 
  class TableMessages
1721
 
  {
1722
 
    TableMessageCache table_message_cache;
1723
 
 
1724
 
  public:
1725
 
    bool storeTableMessage(const TableIdentifier &identifier, message::Table &table_message);
1726
 
    bool removeTableMessage(const TableIdentifier &identifier);
1727
 
    bool getTableMessage(const TableIdentifier &identifier, message::Table &table_message);
1728
 
    bool doesTableMessageExist(const TableIdentifier &identifier);
1729
 
    bool renameTableMessage(const TableIdentifier &from, const TableIdentifier &to);
1730
 
 
1731
 
  };
 
1583
  table::Placeholder *table_cache_insert_placeholder(const identifier::Table &identifier);
 
1584
  bool lock_table_name_if_not_cached(const identifier::Table &identifier, Table **table);
 
1585
 
1732
1586
private:
1733
 
  TableMessages _table_message_cache;
 
1587
  session::TableMessages _table_message_cache;
1734
1588
 
1735
1589
public:
1736
 
  TableMessages &getMessageCache()
 
1590
  session::TableMessages &getMessageCache()
1737
1591
  {
1738
1592
    return _table_message_cache;
1739
1593
  }
1740
1594
 
1741
1595
  /* Reopen operations */
1742
 
  bool reopen_tables(bool get_locks, bool mark_share_as_old);
 
1596
  bool reopen_tables();
1743
1597
  bool close_cached_tables(TableList *tables, bool wait_for_refresh, bool wait_for_placeholders);
1744
1598
 
1745
1599
  void wait_for_condition(boost::mutex &mutex, boost::condition_variable_any &cond);
1748
1602
 
1749
1603
  drizzled::util::Storable *getProperty(const std::string &arg)
1750
1604
  {
1751
 
    return life_properties[arg];
 
1605
    return life_properties.getProperty(arg);
1752
1606
  }
1753
1607
 
1754
1608
  template<class T>
1755
1609
  bool setProperty(const std::string &arg, T *value)
1756
1610
  {
1757
 
    life_properties[arg]= value;
 
1611
    life_properties.setProperty(arg, value);
1758
1612
 
1759
1613
    return true;
1760
1614
  }
1774
1628
    return global_system_variables.storage_engine;
1775
1629
  }
1776
1630
 
1777
 
  void get_xid(DRIZZLE_XID *xid); // Innodb only
 
1631
  void get_xid(DrizzleXid *xid); // Innodb only
1778
1632
 
1779
 
  table::Instance *getInstanceTable();
1780
 
  table::Instance *getInstanceTable(List<CreateField> &field_list);
 
1633
  table::Singular *getInstanceTable();
 
1634
  table::Singular *getInstanceTable(List<CreateField> &field_list);
1781
1635
 
1782
1636
private:
1783
1637
  bool resetUsage()
1789
1643
 
1790
1644
    return true;
1791
1645
  }
 
1646
 
1792
1647
public:
1793
1648
 
1794
1649
  void setUsage(bool arg)
1801
1656
    return usage;
1802
1657
  }
1803
1658
 
 
1659
  catalog::Instance::const_reference catalog() const
 
1660
  {
 
1661
    return *(_catalog.get());
 
1662
  }
 
1663
 
 
1664
  catalog::Instance::reference catalog()
 
1665
  {
 
1666
    return *(_catalog.get());
 
1667
  }
 
1668
 
1804
1669
private:
 
1670
  catalog::Instance::shared_ptr _catalog;
 
1671
 
1805
1672
  // This lives throughout the life of Session
1806
1673
  bool use_usage;
1807
 
  PropertyMap life_properties;
1808
 
  std::vector<table::Instance *> temporary_shares;
 
1674
  session::PropertyMap life_properties;
 
1675
  std::vector<table::Singular *> temporary_shares;
1809
1676
  struct rusage usage;
1810
1677
};
1811
1678
 
1812
 
class Join;
1813
 
 
1814
1679
#define ESCAPE_CHARS "ntrb0ZN" // keep synchronous with READ_INFO::unescape
1815
1680
 
1816
 
} /* namespace drizzled */
1817
 
 
1818
 
/** @TODO why is this in the middle of the file */
1819
 
#include <drizzled/select_to_file.h>
1820
 
#include <drizzled/select_export.h>
1821
 
#include <drizzled/select_dump.h>
1822
 
#include <drizzled/select_insert.h>
1823
 
#include <drizzled/select_create.h>
1824
 
#include <drizzled/tmp_table_param.h>
1825
 
#include <drizzled/select_union.h>
1826
 
#include <drizzled/select_subselect.h>
1827
 
#include <drizzled/select_singlerow_subselect.h>
1828
 
#include <drizzled/select_max_min_finder_subselect.h>
1829
 
#include <drizzled/select_exists_subselect.h>
1830
 
 
1831
 
namespace drizzled
1832
 
{
1833
 
 
1834
 
/**
1835
 
 * A structure used to describe sort information
1836
 
 * for a field or item used in ORDER BY.
1837
 
 */
1838
 
class SortField 
1839
 
{
1840
 
public:
1841
 
  Field *field; /**< Field to sort */
1842
 
  Item  *item; /**< Item if not sorting fields */
1843
 
  size_t length; /**< Length of sort field */
1844
 
  uint32_t suffix_length; /**< Length suffix (0-4) */
1845
 
  Item_result result_type; /**< Type of item */
1846
 
  bool reverse; /**< if descending sort */
1847
 
  bool need_strxnfrm;   /**< If we have to use strxnfrm() */
1848
 
 
1849
 
  SortField() :
1850
 
    field(0),
1851
 
    item(0),
1852
 
    length(0),
1853
 
    suffix_length(0),
1854
 
    result_type(STRING_RESULT),
1855
 
    reverse(0),
1856
 
    need_strxnfrm(0)
1857
 
  { }
1858
 
 
1859
 
};
1860
 
 
1861
 
} /* namespace drizzled */
1862
 
 
1863
 
/** @TODO why is this in the middle of the file */
1864
 
 
1865
 
#include <drizzled/table_ident.h>
1866
 
#include <drizzled/user_var_entry.h>
1867
 
#include <drizzled/unique.h>
1868
 
#include <drizzled/var.h>
1869
 
#include <drizzled/select_dumpvar.h>
1870
 
 
1871
 
namespace drizzled
1872
 
{
1873
 
 
1874
1681
/* Bits in sql_command_flags */
1875
1682
 
1876
1683
enum sql_command_flag_bits 
1892
1699
namespace display  {
1893
1700
const std::string &type(drizzled::Session::global_read_lock_t type);
1894
1701
size_t max_string_length(drizzled::Session::global_read_lock_t type);
 
1702
 
1895
1703
} /* namespace display */
1896
1704
 
1897
1705
} /* namespace drizzled */