~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/sql_parse.cc

  • Committer: Daniel Nichter
  • Date: 2011-10-23 16:01:37 UTC
  • mto: This revision was merged to the branch mainline in revision 2448.
  • Revision ID: daniel@percona.com-20111023160137-7ac3blgz8z4tf8za
Add Administration Getting Started and Logging.  Capitalize SQL clause keywords.

Show diffs side-by-side

added added

removed removed

Lines of Context:
11
11
 
12
12
   You should have received a copy of the GNU General Public License
13
13
   along with this program; if not, write to the Free Software
14
 
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
 
14
   Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA */
 
15
 
 
16
#include <config.h>
15
17
 
16
18
#define DRIZZLE_LEX 1
17
 
#include <drizzled/server_includes.h>
18
 
#include <drizzled/replication/replication.h>
19
 
#include <libdrizzle/libdrizzle.h>
20
 
#include <mysys/hash.h>
21
 
#include <drizzled/replication/binlog.h>
22
 
#include <drizzled/logging.h>
23
 
#include <drizzled/db.h>
 
19
 
 
20
#include <drizzled/item/num.h>
 
21
#include <drizzled/abort_exception.h>
24
22
#include <drizzled/error.h>
25
23
#include <drizzled/nested_join.h>
26
24
#include <drizzled/query_id.h>
 
25
#include <drizzled/transaction_services.h>
27
26
#include <drizzled/sql_parse.h>
28
27
#include <drizzled/data_home.h>
29
28
#include <drizzled/sql_base.h>
30
29
#include <drizzled/show.h>
31
 
#include <drizzled/rename.h>
32
 
#include <drizzled/functions/time/unix_timestamp.h>
 
30
#include <drizzled/function/time/unix_timestamp.h>
 
31
#include <drizzled/function/get_system_var.h>
33
32
#include <drizzled/item/cmpfunc.h>
 
33
#include <drizzled/item/null.h>
34
34
#include <drizzled/session.h>
 
35
#include <drizzled/session/cache.h>
35
36
#include <drizzled/sql_load.h>
 
37
#include <drizzled/lock.h>
 
38
#include <drizzled/select_send.h>
 
39
#include <drizzled/plugin/client.h>
 
40
#include <drizzled/statement.h>
 
41
#include <drizzled/statement/alter_table.h>
 
42
#include <drizzled/probes.h>
 
43
#include <drizzled/charset.h>
 
44
#include <drizzled/plugin/logging.h>
 
45
#include <drizzled/plugin/query_rewrite.h>
 
46
#include <drizzled/plugin/query_cache.h>
 
47
#include <drizzled/plugin/authorization.h>
 
48
#include <drizzled/optimizer/explain_plan.h>
 
49
#include <drizzled/pthread_globals.h>
 
50
#include <drizzled/plugin/event_observer.h>
 
51
#include <drizzled/display.h>
 
52
#include <drizzled/visibility.h>
 
53
#include <drizzled/kill.h>
 
54
#include <drizzled/schema.h>
 
55
#include <drizzled/item/subselect.h>
 
56
#include <drizzled/diagnostics_area.h>
 
57
#include <drizzled/table_ident.h>
 
58
#include <drizzled/statistics_variables.h>
 
59
#include <drizzled/system_variables.h>
 
60
#include <drizzled/session/times.h>
 
61
#include <drizzled/session/transactions.h>
 
62
#include <drizzled/create_field.h>
 
63
#include <drizzled/lex_input_stream.h>
 
64
 
 
65
#include <limits.h>
 
66
 
36
67
#include <bitset>
 
68
#include <algorithm>
 
69
#include <boost/date_time.hpp>
 
70
#include <drizzled/internal/my_sys.h>
37
71
 
38
72
using namespace std;
39
73
 
 
74
extern int base_sql_parse(drizzled::Session *session); // from sql_yacc.cc
 
75
 
 
76
namespace drizzled {
 
77
 
 
78
/* Prototypes */
 
79
bool my_yyoverflow(short **a, ParserType **b, ulong *yystacksize);
 
80
static bool parse_sql(Session *session, Lex_input_stream *lip);
 
81
void parse(Session&, const char *inBuf, uint32_t length);
 
82
 
40
83
/**
41
84
  @defgroup Runtime_Environment Runtime Environment
42
85
  @{
43
86
*/
44
87
 
45
 
extern const CHARSET_INFO *character_set_filesystem;
46
 
const char *any_db="*any*";     // Special symbol for check_access
47
 
 
48
 
const LEX_STRING command_name[COM_END+1]={
49
 
  { C_STRING_WITH_LEN("Sleep") },
50
 
  { C_STRING_WITH_LEN("Quit") },
51
 
  { C_STRING_WITH_LEN("Init DB") },
52
 
  { C_STRING_WITH_LEN("Query") },
53
 
  { C_STRING_WITH_LEN("Field List") },
54
 
  { C_STRING_WITH_LEN("Create DB") },
55
 
  { C_STRING_WITH_LEN("Drop DB") },
56
 
  { C_STRING_WITH_LEN("Refresh") },
57
 
  { C_STRING_WITH_LEN("Shutdown") },
58
 
  { C_STRING_WITH_LEN("Processlist") },
59
 
  { C_STRING_WITH_LEN("Connect") },
60
 
  { C_STRING_WITH_LEN("Kill") },
61
 
  { C_STRING_WITH_LEN("Ping") },
62
 
  { C_STRING_WITH_LEN("Time") },
63
 
  { C_STRING_WITH_LEN("Change user") },
64
 
  { C_STRING_WITH_LEN("Binlog Dump") },
65
 
  { C_STRING_WITH_LEN("Connect Out") },
66
 
  { C_STRING_WITH_LEN("Register Slave") },
67
 
  { C_STRING_WITH_LEN("Set option") },
68
 
  { C_STRING_WITH_LEN("Daemon") },
69
 
  { C_STRING_WITH_LEN("Error") }  // Last command number
70
 
};
71
 
 
72
 
const char *xa_state_names[]={
 
88
extern size_t my_thread_stack_size;
 
89
extern const charset_info_st *character_set_filesystem;
 
90
 
 
91
namespace
 
92
{
 
93
  static const std::string command_name[]=
 
94
  {
 
95
    "Sleep",
 
96
    "Quit",
 
97
    "Init DB",
 
98
    "Query",
 
99
    "Shutdown",
 
100
    "Connect",
 
101
    "Ping",
 
102
    "Kill",
 
103
    "Error"  // Last command number
 
104
  };
 
105
}
 
106
 
 
107
const char *xa_state_names[]=
 
108
{
73
109
  "NON-EXISTING", "ACTIVE", "IDLE", "PREPARED"
74
110
};
75
111
 
76
 
static void unlock_locked_tables(Session *session)
77
 
{
78
 
  if (session->locked_tables)
79
 
  {
80
 
    session->lock=session->locked_tables;
81
 
    session->locked_tables=0;                   // Will be automatically closed
82
 
    close_thread_tables(session);                       // Free tables
83
 
  }
84
 
}
85
 
 
86
 
 
87
 
bool end_active_trans(Session *session)
88
 
{
89
 
  int error= 0;
90
 
 
91
 
  if (session->transaction.xid_state.xa_state != XA_NOTR)
92
 
  {
93
 
    my_error(ER_XAER_RMFAIL, MYF(0),
94
 
             xa_state_names[session->transaction.xid_state.xa_state]);
95
 
    return(1);
96
 
  }
97
 
  if (session->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN |
98
 
                      OPTION_TABLE_LOCK))
99
 
  {
100
 
    /* Safety if one did "drop table" on locked tables */
101
 
    if (!session->locked_tables)
102
 
      session->options&= ~OPTION_TABLE_LOCK;
103
 
    session->server_status&= ~SERVER_STATUS_IN_TRANS;
104
 
    if (ha_commit(session))
105
 
      error=1;
106
 
  }
107
 
  session->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
108
 
  session->transaction.all.modified_non_trans_table= false;
109
 
  return(error);
110
 
}
111
 
 
112
 
 
113
 
bool begin_trans(Session *session)
114
 
{
115
 
  int error= 0;
116
 
  if (session->locked_tables)
117
 
  {
118
 
    session->lock=session->locked_tables;
119
 
    session->locked_tables=0;                   // Will be automatically closed
120
 
    close_thread_tables(session);                       // Free tables
121
 
  }
122
 
  if (end_active_trans(session))
123
 
    error= -1;
124
 
  else
125
 
  {
126
 
    LEX *lex= session->lex;
127
 
    session->options|= OPTION_BEGIN;
128
 
    session->server_status|= SERVER_STATUS_IN_TRANS;
129
 
    if (lex->start_transaction_opt & DRIZZLE_START_TRANS_OPT_WITH_CONS_SNAPSHOT)
130
 
      error= ha_start_consistent_snapshot(session);
131
 
  }
132
 
  return error;
133
 
}
134
 
 
135
 
/**
136
 
  Returns true if all tables should be ignored.
137
 
*/
138
 
inline bool all_tables_not_ok(Session *, TableList *)
139
 
{
140
 
  return false;
141
 
}
142
 
 
143
 
 
144
 
static bool some_non_temp_table_to_be_updated(Session *session, TableList *tables)
145
 
{
146
 
  for (TableList *table= tables; table; table= table->next_global)
147
 
  {
148
 
    assert(table->db && table->table_name);
149
 
    if (table->updating &&
150
 
        !find_temporary_table(session, table->db, table->table_name))
151
 
      return 1;
152
 
  }
153
 
  return 0;
154
 
}
155
 
 
156
112
 
157
113
/**
158
114
  Mark all commands that somehow changes a table.
166
122
     2  - query that returns meaningful ROW_COUNT() -
167
123
          a number of modified rows
168
124
*/
169
 
 
170
125
bitset<CF_BIT_SIZE> sql_command_flags[SQLCOM_END+1];
171
126
 
 
127
const std::string &getCommandName(const enum_server_command& command)
 
128
{
 
129
  return command_name[command];
 
130
}
 
131
 
172
132
void init_update_queries(void)
173
133
{
174
 
  uint32_t x;
175
 
 
176
 
  for (x= 0; x <= SQLCOM_END; x++)
 
134
  for (uint32_t x= uint32_t(SQLCOM_SELECT); 
 
135
       x <= uint32_t(SQLCOM_END); x++)
 
136
  {
177
137
    sql_command_flags[x].reset();
 
138
  }
178
139
 
179
140
  sql_command_flags[SQLCOM_CREATE_TABLE]=   CF_CHANGES_DATA;
180
141
  sql_command_flags[SQLCOM_CREATE_INDEX]=   CF_CHANGES_DATA;
188
149
  sql_command_flags[SQLCOM_DROP_INDEX]=     CF_CHANGES_DATA;
189
150
 
190
151
  sql_command_flags[SQLCOM_UPDATE]=         CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
191
 
  sql_command_flags[SQLCOM_UPDATE_MULTI]=   CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
192
152
  sql_command_flags[SQLCOM_INSERT]=         CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
193
153
  sql_command_flags[SQLCOM_INSERT_SELECT]=  CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
194
154
  sql_command_flags[SQLCOM_DELETE]=         CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
195
 
  sql_command_flags[SQLCOM_DELETE_MULTI]=   CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
196
155
  sql_command_flags[SQLCOM_REPLACE]=        CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
197
156
  sql_command_flags[SQLCOM_REPLACE_SELECT]= CF_CHANGES_DATA | CF_HAS_ROW_COUNT;
198
157
 
199
 
  sql_command_flags[SQLCOM_SHOW_STATUS]=      CF_STATUS_COMMAND;
200
 
  sql_command_flags[SQLCOM_SHOW_DATABASES]=   CF_STATUS_COMMAND;
201
 
  sql_command_flags[SQLCOM_SHOW_OPEN_TABLES]= CF_STATUS_COMMAND;
202
 
  sql_command_flags[SQLCOM_SHOW_FIELDS]=      CF_STATUS_COMMAND;
203
 
  sql_command_flags[SQLCOM_SHOW_KEYS]=        CF_STATUS_COMMAND;
204
 
  sql_command_flags[SQLCOM_SHOW_VARIABLES]=   CF_STATUS_COMMAND;
205
 
  sql_command_flags[SQLCOM_SHOW_BINLOGS]= CF_STATUS_COMMAND;
206
158
  sql_command_flags[SQLCOM_SHOW_WARNS]= CF_STATUS_COMMAND;
207
159
  sql_command_flags[SQLCOM_SHOW_ERRORS]= CF_STATUS_COMMAND;
208
 
  sql_command_flags[SQLCOM_SHOW_ENGINE_STATUS]= CF_STATUS_COMMAND;
209
 
  sql_command_flags[SQLCOM_SHOW_PROCESSLIST]= CF_STATUS_COMMAND;
210
160
  sql_command_flags[SQLCOM_SHOW_CREATE_DB]=  CF_STATUS_COMMAND;
211
161
  sql_command_flags[SQLCOM_SHOW_CREATE]=  CF_STATUS_COMMAND;
212
 
  sql_command_flags[SQLCOM_SHOW_MASTER_STAT]=  CF_STATUS_COMMAND;
213
 
  sql_command_flags[SQLCOM_SHOW_SLAVE_STAT]=  CF_STATUS_COMMAND;
214
162
 
215
 
   sql_command_flags[SQLCOM_SHOW_TABLES]=       (CF_STATUS_COMMAND |
216
 
                                               CF_SHOW_TABLE_COMMAND);
217
 
  sql_command_flags[SQLCOM_SHOW_TABLE_STATUS]= (CF_STATUS_COMMAND |
218
 
                                                CF_SHOW_TABLE_COMMAND);
219
163
  /*
220
164
    The following admin table operations are allowed
221
165
    on log tables.
222
166
  */
223
 
  sql_command_flags[SQLCOM_REPAIR]=           CF_WRITE_LOGS_COMMAND;
224
 
  sql_command_flags[SQLCOM_OPTIMIZE]=         CF_WRITE_LOGS_COMMAND;
225
167
  sql_command_flags[SQLCOM_ANALYZE]=          CF_WRITE_LOGS_COMMAND;
226
168
}
227
169
 
228
 
 
229
 
bool is_update_query(enum enum_sql_command command)
230
 
{
231
 
  assert(command >= 0 && command <= SQLCOM_END);
232
 
  return (sql_command_flags[command].test(CF_BIT_CHANGES_DATA));
233
 
}
234
 
 
235
 
void execute_init_command(Session *session, sys_var_str *init_command_var,
236
 
                          rw_lock_t *var_mutex)
237
 
{
238
 
  Vio* save_vio;
239
 
  ulong save_client_capabilities;
240
 
 
241
 
  session->set_proc_info("Execution of init_command");
242
 
  /*
243
 
    We need to lock init_command_var because
244
 
    during execution of init_command_var query
245
 
    values of init_command_var can't be changed
246
 
  */
247
 
  rw_rdlock(var_mutex);
248
 
  save_client_capabilities= session->client_capabilities;
249
 
  session->client_capabilities|= CLIENT_MULTI_STATEMENTS;
250
 
  /*
251
 
    We don't need return result of execution to client side.
252
 
    To forbid this we should set session->net.vio to 0.
253
 
  */
254
 
  save_vio= session->net.vio;
255
 
  session->net.vio= 0;
256
 
  dispatch_command(COM_QUERY, session,
257
 
                   init_command_var->value,
258
 
                   init_command_var->value_length);
259
 
  rw_unlock(var_mutex);
260
 
  session->client_capabilities= save_client_capabilities;
261
 
  session->net.vio= save_vio;
262
 
}
263
 
 
264
 
/**
265
 
  Ends the current transaction and (maybe) begin the next.
266
 
 
267
 
  @param session            Current thread
268
 
  @param completion     Completion type
269
 
 
270
 
  @retval
271
 
    0   OK
272
 
*/
273
 
 
274
 
int end_trans(Session *session, enum enum_mysql_completiontype completion)
275
 
{
276
 
  bool do_release= 0;
277
 
  int res= 0;
278
 
 
279
 
  if (session->transaction.xid_state.xa_state != XA_NOTR)
280
 
  {
281
 
    my_error(ER_XAER_RMFAIL, MYF(0),
282
 
             xa_state_names[session->transaction.xid_state.xa_state]);
283
 
    return(1);
284
 
  }
285
 
  switch (completion) {
286
 
  case COMMIT:
287
 
    /*
288
 
     We don't use end_active_trans() here to ensure that this works
289
 
     even if there is a problem with the OPTION_AUTO_COMMIT flag
290
 
     (Which of course should never happen...)
291
 
    */
292
 
    session->server_status&= ~SERVER_STATUS_IN_TRANS;
293
 
    res= ha_commit(session);
294
 
    session->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
295
 
    session->transaction.all.modified_non_trans_table= false;
296
 
    break;
297
 
  case COMMIT_RELEASE:
298
 
    do_release= 1; /* fall through */
299
 
  case COMMIT_AND_CHAIN:
300
 
    res= end_active_trans(session);
301
 
    if (!res && completion == COMMIT_AND_CHAIN)
302
 
      res= begin_trans(session);
303
 
    break;
304
 
  case ROLLBACK_RELEASE:
305
 
    do_release= 1; /* fall through */
306
 
  case ROLLBACK:
307
 
  case ROLLBACK_AND_CHAIN:
308
 
  {
309
 
    session->server_status&= ~SERVER_STATUS_IN_TRANS;
310
 
    if (ha_rollback(session))
311
 
      res= -1;
312
 
    session->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
313
 
    session->transaction.all.modified_non_trans_table= false;
314
 
    if (!res && (completion == ROLLBACK_AND_CHAIN))
315
 
      res= begin_trans(session);
316
 
    break;
317
 
  }
318
 
  default:
319
 
    res= -1;
320
 
    my_error(ER_UNKNOWN_COM_ERROR, MYF(0));
321
 
    return(-1);
322
 
  }
323
 
 
324
 
  if (res < 0)
325
 
    my_error(session->killed_errno(), MYF(0));
326
 
  else if ((res == 0) && do_release)
327
 
    session->killed= Session::KILL_CONNECTION;
328
 
 
329
 
  return(res);
330
 
}
331
 
 
332
 
 
333
 
/**
334
 
  Read one command from connection and execute it (query or simple command).
335
 
  This function is called in loop from thread function.
336
 
 
337
 
  For profiling to work, it must never be called recursively.
338
 
 
339
 
  @retval
340
 
    0  success
341
 
  @retval
342
 
    1  request of thread shutdown (see dispatch_command() description)
343
 
*/
344
 
 
345
 
bool do_command(Session *session)
346
 
{
347
 
  bool return_value;
348
 
  char *packet= 0;
349
 
  ulong packet_length;
350
 
  NET *net= &session->net;
351
 
  enum enum_server_command command;
352
 
 
353
 
  /*
354
 
    indicator of uninitialized lex => normal flow of errors handling
355
 
    (see my_message_sql)
356
 
  */
357
 
  session->lex->current_select= 0;
358
 
 
359
 
  /*
360
 
    This thread will do a blocking read from the client which
361
 
    will be interrupted when the next command is received from
362
 
    the client, the connection is closed or "net_wait_timeout"
363
 
    number of seconds has passed
364
 
  */
365
 
  my_net_set_read_timeout(net, session->variables.net_wait_timeout);
366
 
 
367
 
  /*
368
 
    XXX: this code is here only to clear possible errors of init_connect. 
369
 
    Consider moving to init_connect() instead.
370
 
  */
371
 
  session->clear_error();                               // Clear error message
372
 
  session->main_da.reset_diagnostics_area();
373
 
 
374
 
  net_new_transaction(net);
375
 
 
376
 
  packet_length= my_net_read(net);
377
 
  if (packet_length == packet_error)
378
 
  {
379
 
    /* Check if we can continue without closing the connection */
380
 
 
381
 
    /* The error must be set. */
382
 
    assert(session->is_error());
383
 
    net_end_statement(session);
384
 
 
385
 
    if (net->error != 3)
386
 
    {
387
 
      return_value= true;                       // We have to close it.
388
 
      goto out;
389
 
    }
390
 
 
391
 
    net->error= 0;
392
 
    return_value= false;
393
 
    goto out;
394
 
  }
395
 
 
396
 
  packet= (char*) net->read_pos;
397
 
  /*
398
 
    'packet_length' contains length of data, as it was stored in packet
399
 
    header. In case of malformed header, my_net_read returns zero.
400
 
    If packet_length is not zero, my_net_read ensures that the returned
401
 
    number of bytes was actually read from network.
402
 
    There is also an extra safety measure in my_net_read:
403
 
    it sets packet[packet_length]= 0, but only for non-zero packets.
404
 
  */
405
 
  if (packet_length == 0)                       /* safety */
406
 
  {
407
 
    /* Initialize with COM_SLEEP packet */
408
 
    packet[0]= (unsigned char) COM_SLEEP;
409
 
    packet_length= 1;
410
 
  }
411
 
  /* Do not rely on my_net_read, extra safety against programming errors. */
412
 
  packet[packet_length]= '\0';                  /* safety */
413
 
 
414
 
  command= (enum enum_server_command) (unsigned char) packet[0];
415
 
 
416
 
  if (command >= COM_END)
417
 
    command= COM_END;                           // Wrong command
418
 
 
419
 
  /* Restore read timeout value */
420
 
  my_net_set_read_timeout(net, session->variables.net_read_timeout);
421
 
 
422
 
  assert(packet_length);
423
 
  return_value= dispatch_command(command, session, packet+1, (uint32_t) (packet_length-1));
424
 
 
425
 
out:
426
 
  return(return_value);
427
 
}
428
 
 
429
 
/**
430
 
  Determine if an attempt to update a non-temporary table while the
431
 
  read-only option was enabled has been made.
432
 
 
433
 
  This is a helper function to mysql_execute_command.
434
 
 
435
 
  @note SQLCOM_MULTI_UPDATE is an exception and dealt with elsewhere.
436
 
 
437
 
  @see mysql_execute_command
438
 
 
439
 
  @returns Status code
440
 
    @retval true The statement should be denied.
441
 
    @retval false The statement isn't updating any relevant tables.
442
 
*/
443
 
 
444
 
static bool deny_updates_if_read_only_option(Session *session,
445
 
                                                TableList *all_tables)
446
 
{
447
 
  if (!opt_readonly)
448
 
    return(false);
449
 
 
450
 
  LEX *lex= session->lex;
451
 
 
452
 
  if (!(sql_command_flags[lex->sql_command].test(CF_BIT_CHANGES_DATA)))
453
 
    return(false);
454
 
 
455
 
  /* Multi update is an exception and is dealt with later. */
456
 
  if (lex->sql_command == SQLCOM_UPDATE_MULTI)
457
 
    return(false);
458
 
 
459
 
  const bool create_temp_tables= 
460
 
    (lex->sql_command == SQLCOM_CREATE_TABLE) &&
461
 
    (lex->create_info.options & HA_LEX_CREATE_TMP_TABLE);
462
 
 
463
 
  const bool drop_temp_tables= 
464
 
    (lex->sql_command == SQLCOM_DROP_TABLE) &&
465
 
    lex->drop_temporary;
466
 
 
467
 
  const bool update_real_tables=
468
 
    some_non_temp_table_to_be_updated(session, all_tables) &&
469
 
    !(create_temp_tables || drop_temp_tables);
470
 
 
471
 
 
472
 
  const bool create_or_drop_databases=
473
 
    (lex->sql_command == SQLCOM_CREATE_DB) ||
474
 
    (lex->sql_command == SQLCOM_DROP_DB);
475
 
 
476
 
  if (update_real_tables || create_or_drop_databases)
477
 
  {
478
 
      /*
479
 
        An attempt was made to modify one or more non-temporary tables.
480
 
      */
481
 
      return(true);
482
 
  }
483
 
 
484
 
 
485
 
  /* Assuming that only temporary tables are modified. */
486
 
  return(false);
487
 
}
488
 
 
489
170
/**
490
171
  Perform one connection-level (COM_XXXX) command.
491
172
 
497
178
                         can be zero.
498
179
 
499
180
  @todo
500
 
    set session->lex->sql_command to SQLCOM_END here.
 
181
    set session->lex().sql_command to SQLCOM_END here.
501
182
  @todo
502
183
    The following has to be changed to an 8 byte integer
503
184
 
507
188
    1   request of thread shutdown, i. e. if command is
508
189
        COM_QUIT/COM_SHUTDOWN
509
190
*/
510
 
bool dispatch_command(enum enum_server_command command, Session *session,
511
 
                      char* packet, uint32_t packet_length)
 
191
bool dispatch_command(enum_server_command command, Session *session,
 
192
                      const char* packet, uint32_t packet_length)
512
193
{
513
 
  NET *net= &session->net;
514
 
  bool error= 0;
515
 
  Query_id &query_id= Query_id::get_query_id();
516
 
 
517
 
  session->command=command;
518
 
  session->lex->sql_command= SQLCOM_END; /* to avoid confusing VIEW detectors */
519
 
  session->set_time();
520
 
  pthread_mutex_lock(&LOCK_thread_count);
521
 
  session->query_id= query_id.value();
522
 
 
523
 
  switch( command ) {
524
 
  /* Ignore these statements. */
525
 
  case COM_PING:
526
 
    break;
527
 
  /* Increase id and count all other statements. */
528
 
  default:
529
 
    statistic_increment(session->status_var.questions, &LOCK_status);
 
194
  bool error= false;
 
195
  Query_id& query_id= Query_id::get_query_id();
 
196
 
 
197
  DRIZZLE_COMMAND_START(session->thread_id, command);
 
198
 
 
199
  session->command= command;
 
200
  session->lex().sql_command= SQLCOM_END; /* to avoid confusing VIEW detectors */
 
201
  session->times.set_time();
 
202
  session->setQueryId(query_id.value());
 
203
 
 
204
  if (command != COM_PING)
 
205
  {
 
206
    // Increase id and count all other statements
 
207
    session->status_var.questions++;
530
208
    query_id.next();
531
209
  }
532
210
 
533
 
  thread_running++;
534
 
  /* TODO: set session->lex->sql_command to SQLCOM_END here */
535
 
  pthread_mutex_unlock(&LOCK_thread_count);
536
 
 
537
 
  logging_pre_do(session);
538
 
 
539
 
  session->server_status&=
540
 
           ~(SERVER_QUERY_NO_INDEX_USED | SERVER_QUERY_NO_GOOD_INDEX_USED);
541
 
  switch (command) {
542
 
  case COM_INIT_DB:
 
211
  /* @todo set session->lex().sql_command to SQLCOM_END here */
 
212
 
 
213
  plugin::Logging::preDo(session);
 
214
  if (unlikely(plugin::EventObserver::beforeStatement(*session)))
543
215
  {
544
 
    LEX_STRING tmp;
545
 
    status_var_increment(session->status_var.com_stat[SQLCOM_CHANGE_DB]);
546
 
    session->convert_string(&tmp, system_charset_info,
547
 
                        packet, packet_length, session->charset());
548
 
    if (!mysql_change_db(session, &tmp, false))
549
 
    {
550
 
      my_ok(session);
551
 
    }
552
 
    break;
 
216
    // We should do something about an error...
553
217
  }
554
 
  case COM_CHANGE_USER:
 
218
 
 
219
  session->server_status&= ~(SERVER_QUERY_NO_INDEX_USED | SERVER_QUERY_NO_GOOD_INDEX_USED);
 
220
 
 
221
  switch (command)
555
222
  {
556
 
    status_var_increment(session->status_var.com_other);
557
 
    char *user= (char*) packet, *packet_end= packet + packet_length;
558
 
    /* Safe because there is always a trailing \0 at the end of the packet */
559
 
    char *passwd= strchr(user, '\0')+1;
560
 
 
561
 
 
562
 
    session->clear_error();                         // if errors from rollback
563
 
 
564
 
    /*
565
 
      Old clients send null-terminated string ('\0' for empty string) for
566
 
      password.  New clients send the size (1 byte) + string (not null
567
 
      terminated, so also '\0' for empty string).
568
 
 
569
 
      Cast *passwd to an unsigned char, so that it doesn't extend the sign
570
 
      for *passwd > 127 and become 2**32-127 after casting to uint32_t.
571
 
    */
572
 
    char db_buff[NAME_LEN+1];                 // buffer to store db in utf8
573
 
    char *db= passwd;
574
 
    char *save_db;
575
 
    /*
576
 
      If there is no password supplied, the packet must contain '\0',
577
 
      in any type of handshake (4.1 or pre-4.1).
578
 
     */
579
 
    if (passwd >= packet_end)
580
 
    {
581
 
      my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
582
 
      break;
583
 
    }
584
 
    uint32_t passwd_len= (session->client_capabilities & CLIENT_SECURE_CONNECTION ?
585
 
                      (unsigned char)(*passwd++) : strlen(passwd));
586
 
    uint32_t dummy_errors, save_db_length, db_length;
587
 
    int res;
588
 
    Security_context save_security_ctx= *session->security_ctx;
589
 
    USER_CONN *save_user_connect;
590
 
 
591
 
    db+= passwd_len + 1;
592
 
    /*
593
 
      Database name is always NUL-terminated, so in case of empty database
594
 
      the packet must contain at least the trailing '\0'.
595
 
    */
596
 
    if (db >= packet_end)
597
 
    {
598
 
      my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
599
 
      break;
600
 
    }
601
 
    db_length= strlen(db);
602
 
 
603
 
    char *ptr= db + db_length + 1;
604
 
    uint32_t cs_number= 0;
605
 
 
606
 
    if (ptr < packet_end)
607
 
    {
608
 
      if (ptr + 2 > packet_end)
 
223
  case COM_USE_SCHEMA:
 
224
    {
 
225
      if (packet_length == 0)
609
226
      {
610
 
        my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
 
227
        my_message(ER_NO_DB_ERROR, ER(ER_NO_DB_ERROR), MYF(0));
611
228
        break;
612
229
      }
613
 
 
614
 
      cs_number= uint2korr(ptr);
615
 
    }
616
 
 
617
 
    /* Convert database name to utf8 */
618
 
    db_buff[copy_and_convert(db_buff, sizeof(db_buff)-1,
619
 
                             system_charset_info, db, db_length,
620
 
                             session->charset(), &dummy_errors)]= 0;
621
 
    db= db_buff;
622
 
 
623
 
    /* Save user and privileges */
624
 
    save_db_length= session->db_length;
625
 
    save_db= session->db;
626
 
    save_user_connect= session->user_connect;
627
 
 
628
 
    if (!(session->security_ctx->user= my_strdup(user, MYF(0))))
629
 
    {
630
 
      session->security_ctx->user= save_security_ctx.user;
631
 
      my_message(ER_OUT_OF_RESOURCES, ER(ER_OUT_OF_RESOURCES), MYF(0));
 
230
      if (not schema::change(*session, identifier::Schema(string(packet, packet_length))))
 
231
      {
 
232
        session->my_ok();
 
233
      }
632
234
      break;
633
235
    }
634
236
 
635
 
    /* Clear variables that are allocated */
636
 
    session->user_connect= 0;
637
 
    res= check_user(session, passwd, passwd_len, db, false);
638
 
 
639
 
    if (res)
640
 
    {
641
 
      if (session->security_ctx->user)
642
 
        free(session->security_ctx->user);
643
 
      *session->security_ctx= save_security_ctx;
644
 
      session->user_connect= save_user_connect;
645
 
      session->db= save_db;
646
 
      session->db_length= save_db_length;
647
 
    }
648
 
    else
649
 
    {
650
 
      if (save_db)
651
 
        free(save_db);
652
 
      if (save_security_ctx.user)
653
 
        free(save_security_ctx.user);
654
 
 
655
 
      if (cs_number)
656
 
      {
657
 
        session_init_client_charset(session, cs_number);
658
 
        session->update_charset();
659
 
      }
660
 
    }
661
 
    break;
662
 
  }
663
237
  case COM_QUERY:
664
 
  {
665
 
    if (alloc_query(session, packet, packet_length))
666
 
      break;                                    // fatal error is set
667
 
    char *packet_end= session->query + session->query_length;
668
 
    const char* end_of_stmt= NULL;
669
 
 
670
 
    mysql_parse(session, session->query, session->query_length, &end_of_stmt);
671
 
 
672
 
    while (!session->killed && (end_of_stmt != NULL) && ! session->is_error())
673
 
    {
674
 
      char *beginning_of_next_stmt= (char*) end_of_stmt;
675
 
 
676
 
      net_end_statement(session);
677
 
      /*
678
 
        Multiple queries exits, execute them individually
679
 
      */
680
 
      close_thread_tables(session);
681
 
      ulong length= (ulong)(packet_end - beginning_of_next_stmt);
682
 
 
683
 
      log_slow_statement(session);
684
 
 
685
 
      /* Remove garbage at start of query */
686
 
      while (length > 0 && my_isspace(session->charset(), *beginning_of_next_stmt))
687
 
      {
688
 
        beginning_of_next_stmt++;
689
 
        length--;
690
 
      }
691
 
 
692
 
      pthread_mutex_lock(&LOCK_thread_count);
693
 
      session->query_length= length;
694
 
      session->query= beginning_of_next_stmt;
695
 
      /*
696
 
        Count each statement from the client.
697
 
      */
698
 
      statistic_increment(session->status_var.questions, &LOCK_status);
699
 
      session->query_id= query_id.next();
700
 
      session->set_time(); /* Reset the query start time. */
701
 
      /* TODO: set session->lex->sql_command to SQLCOM_END here */
702
 
      pthread_mutex_unlock(&LOCK_thread_count);
703
 
 
704
 
      mysql_parse(session, beginning_of_next_stmt, length, &end_of_stmt);
705
 
    }
706
 
    break;
707
 
  }
708
 
  case COM_FIELD_LIST:                          // This isn't actually needed
709
 
  {
710
 
    char *fields, *packet_end= packet + packet_length, *arg_end;
711
 
    /* Locked closure of all tables */
712
 
    TableList table_list;
713
 
    LEX_STRING conv_name;
714
 
 
715
 
    /* used as fields initializator */
716
 
    lex_start(session);
717
 
 
718
 
    status_var_increment(session->status_var.com_stat[SQLCOM_SHOW_FIELDS]);
719
 
    memset(&table_list, 0, sizeof(table_list));
720
 
    if (session->copy_db_to(&table_list.db, &table_list.db_length))
721
 
      break;
722
 
    /*
723
 
      We have name + wildcard in packet, separated by endzero
724
 
    */
725
 
    arg_end= strchr(packet, '\0');
726
 
    session->convert_string(&conv_name, system_charset_info,
727
 
                        packet, (uint32_t) (arg_end - packet), session->charset());
728
 
    table_list.alias= table_list.table_name= conv_name.str;
729
 
    packet= arg_end + 1;
730
 
 
731
 
    if (!my_strcasecmp(system_charset_info, table_list.db,
732
 
                       INFORMATION_SCHEMA_NAME.c_str()))
733
 
    {
734
 
      ST_SCHEMA_TABLE *schema_table= find_schema_table(session, table_list.alias);
735
 
      if (schema_table)
736
 
        table_list.schema_table= schema_table;
737
 
    }
738
 
 
739
 
    session->query_length= (uint32_t) (packet_end - packet); // Don't count end \0
740
 
    if (!(session->query=fields= (char*) session->memdup(packet,session->query_length+1)))
741
 
      break;
742
 
    if (lower_case_table_names)
743
 
      my_casedn_str(files_charset_info, table_list.table_name);
744
 
 
745
 
    /* init structures for VIEW processing */
746
 
    table_list.select_lex= &(session->lex->select_lex);
747
 
 
748
 
    lex_start(session);
749
 
    mysql_reset_session_for_next_command(session);
750
 
 
751
 
    session->lex->
752
 
      select_lex.table_list.link_in_list((unsigned char*) &table_list,
753
 
                                         (unsigned char**) &table_list.next_local);
754
 
    session->lex->add_to_query_tables(&table_list);
755
 
 
756
 
    /* switch on VIEW optimisation: do not fill temporary tables */
757
 
    session->lex->sql_command= SQLCOM_SHOW_FIELDS;
758
 
    mysqld_list_fields(session,&table_list,fields);
759
 
    session->lex->unit.cleanup();
760
 
    session->cleanup_after_query();
761
 
    break;
762
 
  }
 
238
    {
 
239
      session->readAndStoreQuery(packet, packet_length);
 
240
      DRIZZLE_QUERY_START(session->getQueryString()->c_str(), session->thread_id, session->schema()->c_str());
 
241
      parse(*session, session->getQueryString()->c_str(), session->getQueryString()->length());
 
242
      break;
 
243
    }
 
244
 
763
245
  case COM_QUIT:
764
246
    /* We don't calculate statistics for this command */
765
 
    net->error=0;                               // Don't give 'abort' message
766
 
    session->main_da.disable_status();              // Don't send anything back
767
 
    error=true;                                 // End server
 
247
    session->main_da().disable_status();              // Don't send anything back
 
248
    error= true;                                        // End server
768
249
    break;
769
 
  case COM_BINLOG_DUMP:
 
250
 
 
251
  case COM_KILL:
770
252
    {
771
 
      ulong pos;
772
 
      uint16_t flags;
773
 
      uint32_t slave_server_id;
774
 
 
775
 
      status_var_increment(session->status_var.com_other);
776
 
      /* TODO: The following has to be changed to an 8 byte integer */
777
 
      pos = uint4korr(packet);
778
 
      flags = uint2korr(packet + 4);
779
 
      session->server_id=0; /* avoid suicide */
780
 
      if ((slave_server_id= uint4korr(packet+6))) // mysqlbinlog.server_id==0
781
 
        kill_zombie_dump_threads(slave_server_id);
782
 
      session->server_id = slave_server_id;
783
 
 
784
 
      mysql_binlog_send(session, session->strdup(packet + 10), (my_off_t) pos, flags);
785
 
      /*  fake COM_QUIT -- if we get here, the thread needs to terminate */
786
 
      error = true;
 
253
      if (packet_length != 4)
 
254
      {
 
255
        my_error(ER_NO_SUCH_THREAD, MYF(0), 0);
 
256
        break;
 
257
      }
 
258
      else
 
259
      {
 
260
        uint32_t kill_id;
 
261
        memcpy(&kill_id, packet, sizeof(uint32_t));
 
262
 
 
263
        kill_id= ntohl(kill_id);
 
264
        (void)drizzled::kill(*session->user(), kill_id, true);
 
265
      }
 
266
      session->my_ok();
787
267
      break;
788
268
    }
 
269
 
789
270
  case COM_SHUTDOWN:
790
 
  {
791
 
    status_var_increment(session->status_var.com_other);
792
 
    my_eof(session);
793
 
    close_thread_tables(session);                       // Free before kill
794
 
    kill_drizzle();
795
 
    error=true;
796
 
    break;
797
 
  }
 
271
    {
 
272
      session->status_var.com_other++;
 
273
      session->my_eof();
 
274
      session->close_thread_tables();                   // Free before kill
 
275
      kill_drizzle();
 
276
      error= true;
 
277
      break;
 
278
    }
 
279
 
798
280
  case COM_PING:
799
 
    status_var_increment(session->status_var.com_other);
800
 
    my_ok(session);                             // Tell client we are alive
801
 
    break;
802
 
  case COM_PROCESS_INFO:
803
 
    status_var_increment(session->status_var.com_stat[SQLCOM_SHOW_PROCESSLIST]);
804
 
    mysqld_list_processes(session, NULL, 0);
805
 
    break;
806
 
  case COM_PROCESS_KILL:
807
 
  {
808
 
    status_var_increment(session->status_var.com_stat[SQLCOM_KILL]);
809
 
    ulong id=(ulong) uint4korr(packet);
810
 
    sql_kill(session,id,false);
811
 
    break;
812
 
  }
813
 
  case COM_SET_OPTION:
814
 
  {
815
 
    status_var_increment(session->status_var.com_stat[SQLCOM_SET_OPTION]);
816
 
    uint32_t opt_command= uint2korr(packet);
 
281
    session->status_var.com_other++;
 
282
    session->my_ok();                           // Tell client we are alive
 
283
    break;
817
284
 
818
 
    switch (opt_command) {
819
 
    case (int) DRIZZLE_OPTION_MULTI_STATEMENTS_ON:
820
 
      session->client_capabilities|= CLIENT_MULTI_STATEMENTS;
821
 
      my_eof(session);
822
 
      break;
823
 
    case (int) DRIZZLE_OPTION_MULTI_STATEMENTS_OFF:
824
 
      session->client_capabilities&= ~CLIENT_MULTI_STATEMENTS;
825
 
      my_eof(session);
826
 
      break;
827
 
    default:
828
 
      my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
829
 
      break;
830
 
    }
831
 
    break;
832
 
  }
833
285
  case COM_SLEEP:
834
286
  case COM_CONNECT:                             // Impossible here
835
 
  case COM_TIME:                                // Impossible from client
836
287
  case COM_END:
837
288
  default:
838
289
    my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
840
291
  }
841
292
 
842
293
  /* If commit fails, we should be able to reset the OK status. */
843
 
  session->main_da.can_overwrite_status= true;
844
 
  ha_autocommit_or_rollback(session, session->is_error());
845
 
  session->main_da.can_overwrite_status= false;
 
294
  session->main_da().can_overwrite_status= true;
 
295
  TransactionServices::autocommitOrRollback(*session, session->is_error());
 
296
  session->main_da().can_overwrite_status= false;
846
297
 
847
298
  session->transaction.stmt.reset();
848
299
 
850
301
  /* report error issued during command execution */
851
302
  if (session->killed_errno())
852
303
  {
853
 
    if (! session->main_da.is_set())
 
304
    if (not session->main_da().is_set())
854
305
      session->send_kill_message();
855
306
  }
856
 
  if (session->killed == Session::KILL_QUERY || session->killed == Session::KILL_BAD_DATA)
857
 
  {
858
 
    session->killed= Session::NOT_KILLED;
859
 
    session->mysys_var->abort= 0;
860
 
  }
861
 
 
862
 
  net_end_statement(session);
 
307
  if (session->getKilled() == Session::KILL_QUERY || session->getKilled() == Session::KILL_BAD_DATA)
 
308
  {
 
309
    session->setKilled(Session::NOT_KILLED);
 
310
    session->setAbort(false);
 
311
  }
 
312
 
 
313
  /* Can not be true, but do not take chances in production. */
 
314
  assert(! session->main_da().is_sent);
 
315
 
 
316
  switch (session->main_da().status())
 
317
  {
 
318
  case Diagnostics_area::DA_ERROR:
 
319
    /* The query failed, send error to log and abort bootstrap. */
 
320
    session->getClient()->sendError(session->main_da().sql_errno(),
 
321
                               session->main_da().message());
 
322
    break;
 
323
 
 
324
  case Diagnostics_area::DA_EOF:
 
325
    session->getClient()->sendEOF();
 
326
    break;
 
327
 
 
328
  case Diagnostics_area::DA_OK:
 
329
    session->getClient()->sendOK();
 
330
    break;
 
331
 
 
332
  case Diagnostics_area::DA_DISABLED:
 
333
    break;
 
334
 
 
335
  case Diagnostics_area::DA_EMPTY:
 
336
  default:
 
337
    session->getClient()->sendOK();
 
338
    break;
 
339
  }
 
340
 
 
341
  session->main_da().is_sent= true;
863
342
 
864
343
  session->set_proc_info("closing tables");
865
344
  /* Free tables */
866
 
  close_thread_tables(session);
867
 
 
868
 
  log_slow_statement(session);
869
 
 
 
345
  session->close_thread_tables();
 
346
 
 
347
  plugin::Logging::postDo(session);
 
348
  if (unlikely(plugin::EventObserver::afterStatement(*session)))
 
349
  {
 
350
    // We should do something about an error...
 
351
  }
 
352
 
 
353
  /* Store temp state for processlist */
870
354
  session->set_proc_info("cleaning up");
871
 
  pthread_mutex_lock(&LOCK_thread_count); // For process list
872
 
  session->set_proc_info(0);
873
 
  session->command=COM_SLEEP;
874
 
  session->query=0;
875
 
  session->query_length=0;
876
 
  thread_running--;
877
 
  pthread_mutex_unlock(&LOCK_thread_count);
878
 
  session->packet.shrink(session->variables.net_buffer_length); // Reclaim some memory
879
 
  free_root(session->mem_root,MYF(MY_KEEP_PREALLOC));
880
 
  return(error);
881
 
}
882
 
 
883
 
 
884
 
void log_slow_statement(Session *session)
885
 
{
886
 
  logging_post_do(session);
887
 
 
888
 
  return;
 
355
  session->command= COM_SLEEP;
 
356
  session->resetQueryString();
 
357
 
 
358
  session->set_proc_info(NULL);
 
359
  session->mem_root->free_root(MYF(memory::KEEP_PREALLOC));
 
360
 
 
361
  if (DRIZZLE_QUERY_DONE_ENABLED() || DRIZZLE_COMMAND_DONE_ENABLED())
 
362
  {
 
363
    if (command == COM_QUERY)
 
364
    {
 
365
      DRIZZLE_QUERY_DONE(session->is_error());
 
366
    }
 
367
    DRIZZLE_COMMAND_DONE(session->is_error());
 
368
  }
 
369
 
 
370
  return error;
889
371
}
890
372
 
891
373
 
894
376
 
895
377
    This function is used in the parser to convert a SHOW or DESCRIBE
896
378
    table_name command to a SELECT from INFORMATION_SCHEMA.
897
 
    It prepares a SELECT_LEX and a TableList object to represent the
 
379
    It prepares a Select_Lex and a TableList object to represent the
898
380
    given command as a SELECT parse tree.
899
381
 
900
 
  @param session              thread handle
901
 
  @param lex              current lex
902
 
  @param table_ident      table alias if it's used
903
 
  @param schema_table_idx the type of the INFORMATION_SCHEMA table to be
904
 
                          created
 
382
  @param session           thread handle
 
383
  @param lex               current lex
 
384
  @param table_ident       table alias if it's used
 
385
  @param schema_table_name the name of the INFORMATION_SCHEMA table to be
 
386
                           created
905
387
 
906
388
  @note
907
389
    Due to the way this function works with memory and LEX it cannot
914
396
    1                 out of memory or SHOW commands are not allowed
915
397
                      in this version of the server.
916
398
*/
917
 
 
918
 
int prepare_schema_table(Session *session, LEX *lex, Table_ident *table_ident,
919
 
                         enum enum_schema_tables schema_table_idx)
 
399
static bool _schema_select(Session& session, Select_Lex& sel, const string& schema_table_name)
920
400
{
921
 
  SELECT_LEX *schema_select_lex= NULL;
922
 
 
923
 
  switch (schema_table_idx) {
924
 
  case SCH_SCHEMATA:
925
 
    break;
926
 
  case SCH_TABLE_NAMES:
927
 
  case SCH_TABLES:
928
 
    {
929
 
      LEX_STRING db;
930
 
      size_t dummy;
931
 
      if (lex->select_lex.db == NULL &&
932
 
          lex->copy_db_to(&lex->select_lex.db, &dummy))
933
 
      {
934
 
        return(1);
935
 
      }
936
 
      schema_select_lex= new SELECT_LEX();
937
 
      db.str= schema_select_lex->db= lex->select_lex.db;
938
 
      schema_select_lex->table_list.first= NULL;
939
 
      db.length= strlen(db.str);
940
 
 
941
 
      if (check_db_name(&db))
942
 
      {
943
 
        my_error(ER_WRONG_DB_NAME, MYF(0), db.str);
944
 
        return(1);
945
 
      }
946
 
      break;
947
 
    }
948
 
  case SCH_COLUMNS:
949
 
  case SCH_STATISTICS:
950
 
  {
951
 
    assert(table_ident);
952
 
    TableList **query_tables_last= lex->query_tables_last;
953
 
    schema_select_lex= new SELECT_LEX();
954
 
    /* 'parent_lex' is used in init_query() so it must be before it. */
955
 
    schema_select_lex->parent_lex= lex;
956
 
    schema_select_lex->init_query();
957
 
    if (!schema_select_lex->add_table_to_list(session, table_ident, 0, 0, TL_READ))
958
 
      return(1);
959
 
    lex->query_tables_last= query_tables_last;
960
 
    break;
961
 
  }
962
 
  case SCH_OPEN_TABLES:
963
 
  case SCH_VARIABLES:
964
 
  case SCH_STATUS:
965
 
  case SCH_CHARSETS:
966
 
  case SCH_COLLATIONS:
967
 
  case SCH_COLLATION_CHARACTER_SET_APPLICABILITY:
968
 
  case SCH_TABLE_CONSTRAINTS:
969
 
  case SCH_KEY_COLUMN_USAGE:
970
 
  default:
971
 
    break;
972
 
  }
973
 
  
974
 
  SELECT_LEX *select_lex= lex->current_select;
975
 
  assert(select_lex);
976
 
  if (make_schema_select(session, select_lex, schema_table_idx))
977
 
  {
978
 
    return(1);
979
 
  }
980
 
  TableList *table_list= (TableList*) select_lex->table_list.first;
981
 
  assert(table_list);
982
 
  table_list->schema_select_lex= schema_select_lex;
983
 
  table_list->schema_table_reformed= 1;
984
 
  return(0);
 
401
  lex_string_t db, table;
 
402
  bitset<NUM_OF_TABLE_OPTIONS> table_options;
 
403
  /*
 
404
     We have to make non const db_name & table_name
 
405
     because of lower_case_table_names
 
406
  */
 
407
  session.make_lex_string(&db, str_ref("data_dictionary"));
 
408
  session.make_lex_string(&table, schema_table_name);
 
409
  return not sel.add_table_to_list(&session, new Table_ident(db, table), NULL, table_options, TL_READ);
985
410
}
986
411
 
987
 
 
988
 
/**
989
 
  Read query from packet and store in session->query.
990
 
  Used in COM_QUERY and COM_STMT_PREPARE.
991
 
 
992
 
    Sets the following Session variables:
993
 
  - query
994
 
  - query_length
995
 
 
996
 
  @retval
997
 
    false ok
998
 
  @retval
999
 
    true  error;  In this case session->fatal_error is set
1000
 
*/
1001
 
 
1002
 
bool alloc_query(Session *session, const char *packet, uint32_t packet_length)
 
412
int prepare_new_schema_table(Session *session, LEX& lex0, const string& schema_table_name)
1003
413
{
1004
 
  /* Remove garbage at start and end of query */
1005
 
  while (packet_length > 0 && my_isspace(session->charset(), packet[0]))
1006
 
  {
1007
 
    packet++;
1008
 
    packet_length--;
1009
 
  }
1010
 
  const char *pos= packet + packet_length;     // Point at end null
1011
 
  while (packet_length > 0 &&
1012
 
         (pos[-1] == ';' || my_isspace(session->charset() ,pos[-1])))
1013
 
  {
1014
 
    pos--;
1015
 
    packet_length--;
1016
 
  }
1017
 
  /* We must allocate some extra memory for query cache */
1018
 
  session->query_length= 0;                        // Extra safety: Avoid races
1019
 
  if (!(session->query= (char*) session->memdup_w_gap((unsigned char*) (packet),
1020
 
                                              packet_length,
1021
 
                                              session->db_length+ 1)))
1022
 
    return true;
1023
 
  session->query[packet_length]=0;
1024
 
  session->query_length= packet_length;
1025
 
 
1026
 
  /* Reclaim some memory */
1027
 
  session->packet.shrink(session->variables.net_buffer_length);
1028
 
  session->convert_buffer.shrink(session->variables.net_buffer_length);
1029
 
 
1030
 
  return false;
 
414
  Select_Lex& lex= *lex0.current_select;
 
415
  if (_schema_select(*session, lex, schema_table_name))
 
416
    return 1;
 
417
  TableList *table_list= (TableList*)lex.table_list.first;
 
418
  table_list->schema_select_lex= NULL;
 
419
  return 0;
1031
420
}
1032
421
 
1033
422
/**
1060
449
    true        Error
1061
450
*/
1062
451
 
1063
 
int
1064
 
mysql_execute_command(Session *session)
 
452
static int execute_command(Session *session)
1065
453
{
1066
 
  int res= false;
1067
 
  bool need_start_waiting= false; // have protection against global read lock
1068
 
  int  up_result= 0;
1069
 
  LEX  *lex= session->lex;
1070
 
  /* first SELECT_LEX (have special meaning for many of non-SELECTcommands) */
1071
 
  SELECT_LEX *select_lex= &lex->select_lex;
1072
 
  /* first table of first SELECT_LEX */
1073
 
  TableList *first_table= (TableList*) select_lex->table_list.first;
 
454
  bool res= false;
 
455
 
 
456
  /* first Select_Lex (have special meaning for many of non-SELECTcommands) */
 
457
  Select_Lex *select_lex= &session->lex().select_lex;
 
458
 
1074
459
  /* list of all tables in query */
1075
460
  TableList *all_tables;
1076
 
  /* most outer SELECT_LEX_UNIT of query */
1077
 
  SELECT_LEX_UNIT *unit= &lex->unit;
1078
 
  /* Saved variable value */
1079
461
 
1080
462
  /*
1081
 
    In many cases first table of main SELECT_LEX have special meaning =>
1082
 
    check that it is first table in global list and relink it first in 
 
463
    In many cases first table of main Select_Lex have special meaning =>
 
464
    check that it is first table in global list and relink it first in
1083
465
    queries_tables list if it is necessary (we need such relinking only
1084
466
    for queries with subqueries in select list, in this case tables of
1085
467
    subqueries will go to global list first)
1086
468
 
1087
 
    all_tables will differ from first_table only if most upper SELECT_LEX
 
469
    all_tables will differ from first_table only if most upper Select_Lex
1088
470
    do not contain tables.
1089
471
 
1090
472
    Because of above in place where should be at least one table in most
1091
 
    outer SELECT_LEX we have following check:
 
473
    outer Select_Lex we have following check:
1092
474
    assert(first_table == all_tables);
1093
475
    assert(first_table == all_tables && first_table != 0);
1094
476
  */
1095
 
  lex->first_lists_tables_same();
 
477
  session->lex().first_lists_tables_same();
 
478
 
1096
479
  /* should be assigned after making first tables same */
1097
 
  all_tables= lex->query_tables;
 
480
  all_tables= session->lex().query_tables;
 
481
 
1098
482
  /* set context for commands which do not use setup_tables */
1099
 
  select_lex->
1100
 
    context.resolve_in_table_list_only((TableList*)select_lex->
1101
 
                                       table_list.first);
 
483
  select_lex->context.resolve_in_table_list_only((TableList*)select_lex->table_list.first);
1102
484
 
1103
485
  /*
1104
486
    Reset warning count for each query that uses tables
1107
489
    variables, but for now this is probably good enough.
1108
490
    Don't reset warnings when executing a stored routine.
1109
491
  */
1110
 
  if (all_tables || !lex->is_single_level_stmt())
1111
 
    drizzle_reset_errors(session, 0);
1112
 
 
1113
 
  if (unlikely(session->slave_thread))
1114
 
  {
1115
 
    /*
1116
 
      Check if statment should be skipped because of slave filtering
1117
 
      rules
1118
 
 
1119
 
      Exceptions are:
1120
 
      - UPDATE MULTI: For this statement, we want to check the filtering
1121
 
        rules later in the code
1122
 
      - SET: we always execute it (Not that many SET commands exists in
1123
 
        the binary log anyway -- only 4.1 masters write SET statements,
1124
 
        in 5.0 there are no SET statements in the binary log)
1125
 
      - DROP TEMPORARY TABLE IF EXISTS: we always execute it (otherwise we
1126
 
        have stale files on slave caused by exclusion of one tmp table).
1127
 
    */
1128
 
    if (!(lex->sql_command == SQLCOM_UPDATE_MULTI) &&
1129
 
        !(lex->sql_command == SQLCOM_SET_OPTION) &&
1130
 
        !(lex->sql_command == SQLCOM_DROP_TABLE &&
1131
 
          lex->drop_temporary && lex->drop_if_exists) &&
1132
 
        all_tables_not_ok(session, all_tables))
1133
 
    {
1134
 
      /* we warn the slave SQL thread */
1135
 
      my_message(ER_SLAVE_IGNORED_TABLE, ER(ER_SLAVE_IGNORED_TABLE), MYF(0));
1136
 
      return(0);
1137
 
    }
1138
 
  }
1139
 
  else
1140
 
  {
1141
 
    /*
1142
 
      When option readonly is set deny operations which change non-temporary
1143
 
      tables. Except for the replication thread and the 'super' users.
1144
 
    */
1145
 
    if (deny_updates_if_read_only_option(session, all_tables))
1146
 
    {
1147
 
      my_error(ER_OPTION_PREVENTS_STATEMENT, MYF(0), "--read-only");
1148
 
      return(-1);
1149
 
    }
1150
 
  } /* endif unlikely slave */
1151
 
  status_var_increment(session->status_var.com_stat[lex->sql_command]);
1152
 
 
1153
 
  assert(session->transaction.stmt.modified_non_trans_table == false);
1154
 
  
1155
 
  switch (lex->sql_command) {
1156
 
  case SQLCOM_SHOW_STATUS:
1157
 
  {
1158
 
    system_status_var old_status_var= session->status_var;
1159
 
    session->initial_status_var= &old_status_var;
1160
 
    res= execute_sqlcom_select(session, all_tables);
1161
 
    /* Don't log SHOW STATUS commands to slow query log */
1162
 
    session->server_status&= ~(SERVER_QUERY_NO_INDEX_USED |
1163
 
                           SERVER_QUERY_NO_GOOD_INDEX_USED);
1164
 
    /*
1165
 
      restore status variables, as we don't want 'show status' to cause
1166
 
      changes
1167
 
    */
1168
 
    pthread_mutex_lock(&LOCK_status);
1169
 
    add_diff_to_status(&global_status_var, &session->status_var,
1170
 
                       &old_status_var);
1171
 
    session->status_var= old_status_var;
1172
 
    pthread_mutex_unlock(&LOCK_status);
1173
 
    break;
1174
 
  }
1175
 
  case SQLCOM_SHOW_DATABASES:
1176
 
  case SQLCOM_SHOW_TABLES:
1177
 
  case SQLCOM_SHOW_TABLE_STATUS:
1178
 
  case SQLCOM_SHOW_OPEN_TABLES:
1179
 
  case SQLCOM_SHOW_FIELDS:
1180
 
  case SQLCOM_SHOW_KEYS:
1181
 
  case SQLCOM_SHOW_VARIABLES:
1182
 
  case SQLCOM_SELECT:
1183
 
  {
1184
 
    session->status_var.last_query_cost= 0.0;
1185
 
    res= execute_sqlcom_select(session, all_tables);
1186
 
    break;
1187
 
  }
1188
 
  case SQLCOM_EMPTY_QUERY:
1189
 
    my_ok(session);
1190
 
    break;
1191
 
 
1192
 
  case SQLCOM_PURGE:
1193
 
  {
1194
 
    res = purge_master_logs(session, lex->to_log);
1195
 
    break;
1196
 
  }
1197
 
  case SQLCOM_PURGE_BEFORE:
1198
 
  {
1199
 
    Item *it;
1200
 
 
1201
 
    /* PURGE MASTER LOGS BEFORE 'data' */
1202
 
    it= (Item *)lex->value_list.head();
1203
 
    if ((!it->fixed && it->fix_fields(lex->session, &it)) ||
1204
 
        it->check_cols(1))
1205
 
    {
1206
 
      my_error(ER_WRONG_ARGUMENTS, MYF(0), "PURGE LOGS BEFORE");
1207
 
      goto error;
1208
 
    }
1209
 
    it= new Item_func_unix_timestamp(it);
1210
 
    /*
1211
 
      it is OK only emulate fix_fieds, because we need only
1212
 
      value of constant
1213
 
    */
1214
 
    it->quick_fix_field();
1215
 
    res = purge_master_logs_before_date(session, (ulong)it->val_int());
1216
 
    break;
1217
 
  }
1218
 
  case SQLCOM_SHOW_WARNS:
1219
 
  {
1220
 
    res= mysqld_show_warnings(session, (uint32_t)
1221
 
                              ((1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_NOTE) |
1222
 
                               (1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_WARN) |
1223
 
                               (1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_ERROR)
1224
 
                               ));
1225
 
    break;
1226
 
  }
1227
 
  case SQLCOM_SHOW_ERRORS:
1228
 
  {
1229
 
    res= mysqld_show_warnings(session, (uint32_t)
1230
 
                              (1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_ERROR));
1231
 
    break;
1232
 
  }
1233
 
  case SQLCOM_ASSIGN_TO_KEYCACHE:
1234
 
  {
1235
 
    assert(first_table == all_tables && first_table != 0);
1236
 
    res= mysql_assign_to_keycache(session, first_table, &lex->ident);
1237
 
    break;
1238
 
  }
1239
 
  case SQLCOM_CHANGE_MASTER:
1240
 
  {
1241
 
    pthread_mutex_lock(&LOCK_active_mi);
1242
 
    res = change_master(session,active_mi);
1243
 
    pthread_mutex_unlock(&LOCK_active_mi);
1244
 
    break;
1245
 
  }
1246
 
  case SQLCOM_SHOW_SLAVE_STAT:
1247
 
  {
1248
 
    pthread_mutex_lock(&LOCK_active_mi);
1249
 
    if (active_mi != NULL)
1250
 
    {
1251
 
      res = show_master_info(session, active_mi);
1252
 
    }
1253
 
    else
1254
 
    {
1255
 
      push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1256
 
                   "the master info structure does not exist");
1257
 
      my_ok(session);
1258
 
    }
1259
 
    pthread_mutex_unlock(&LOCK_active_mi);
1260
 
    break;
1261
 
  }
1262
 
  case SQLCOM_SHOW_MASTER_STAT:
1263
 
  {
1264
 
    res = show_binlog_info(session);
1265
 
    break;
1266
 
  }
1267
 
 
1268
 
  case SQLCOM_SHOW_ENGINE_STATUS:
1269
 
    {
1270
 
      res = ha_show_status(session, lex->create_info.db_type, HA_ENGINE_STATUS);
1271
 
      break;
1272
 
    }
1273
 
  case SQLCOM_CREATE_TABLE:
1274
 
  {
1275
 
    /* If CREATE TABLE of non-temporary table, do implicit commit */
1276
 
    if (!(lex->create_info.options & HA_LEX_CREATE_TMP_TABLE))
1277
 
    {
1278
 
      if (end_active_trans(session))
1279
 
      {
1280
 
        res= -1;
1281
 
        break;
1282
 
      }
1283
 
    }
1284
 
    assert(first_table == all_tables && first_table != 0);
1285
 
    bool link_to_local;
1286
 
    // Skip first table, which is the table we are creating
1287
 
    TableList *create_table= lex->unlink_first_table(&link_to_local);
1288
 
    TableList *select_tables= lex->query_tables;
1289
 
    /*
1290
 
      Code below (especially in mysql_create_table() and select_create
1291
 
      methods) may modify HA_CREATE_INFO structure in LEX, so we have to
1292
 
      use a copy of this structure to make execution prepared statement-
1293
 
      safe. A shallow copy is enough as this code won't modify any memory
1294
 
      referenced from this structure.
1295
 
    */
1296
 
    HA_CREATE_INFO create_info(lex->create_info);
1297
 
    /*
1298
 
      We need to copy alter_info for the same reasons of re-execution
1299
 
      safety, only in case of Alter_info we have to do (almost) a deep
1300
 
      copy.
1301
 
    */
1302
 
    Alter_info alter_info(lex->alter_info, session->mem_root);
1303
 
 
1304
 
    if (session->is_fatal_error)
1305
 
    {
1306
 
      /* If out of memory when creating a copy of alter_info. */
1307
 
      res= 1;
1308
 
      goto end_with_restore_list;
1309
 
    }
1310
 
 
1311
 
    if ((res= create_table_precheck(session, select_tables, create_table)))
1312
 
      goto end_with_restore_list;
1313
 
 
1314
 
    /* Might have been updated in create_table_precheck */
1315
 
    create_info.alias= create_table->alias;
1316
 
 
1317
 
#ifdef HAVE_READLINK
1318
 
    /* Fix names if symlinked tables */
1319
 
    if (append_file_to_dir(session, &create_info.data_file_name,
1320
 
                           create_table->table_name) ||
1321
 
        append_file_to_dir(session, &create_info.index_file_name,
1322
 
                           create_table->table_name))
1323
 
      goto end_with_restore_list;
1324
 
#endif
1325
 
    /*
1326
 
      If we are using SET CHARSET without DEFAULT, add an implicit
1327
 
      DEFAULT to not confuse old users. (This may change).
1328
 
    */
1329
 
    if ((create_info.used_fields &
1330
 
         (HA_CREATE_USED_DEFAULT_CHARSET | HA_CREATE_USED_CHARSET)) ==
1331
 
        HA_CREATE_USED_CHARSET)
1332
 
    {
1333
 
      create_info.used_fields&= ~HA_CREATE_USED_CHARSET;
1334
 
      create_info.used_fields|= HA_CREATE_USED_DEFAULT_CHARSET;
1335
 
      create_info.default_table_charset= create_info.table_charset;
1336
 
      create_info.table_charset= 0;
1337
 
    }
1338
 
    /*
1339
 
      The create-select command will open and read-lock the select table
1340
 
      and then create, open and write-lock the new table. If a global
1341
 
      read lock steps in, we get a deadlock. The write lock waits for
1342
 
      the global read lock, while the global read lock waits for the
1343
 
      select table to be closed. So we wait until the global readlock is
1344
 
      gone before starting both steps. Note that
1345
 
      wait_if_global_read_lock() sets a protection against a new global
1346
 
      read lock when it succeeds. This needs to be released by
1347
 
      start_waiting_global_read_lock(). We protect the normal CREATE
1348
 
      TABLE in the same way. That way we avoid that a new table is
1349
 
      created during a gobal read lock.
1350
 
    */
1351
 
    if (!session->locked_tables &&
1352
 
        !(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1353
 
    {
1354
 
      res= 1;
1355
 
      goto end_with_restore_list;
1356
 
    }
1357
 
    if (select_lex->item_list.elements)         // With select
1358
 
    {
1359
 
      select_result *result;
1360
 
 
1361
 
      select_lex->options|= SELECT_NO_UNLOCK;
1362
 
      unit->set_limit(select_lex);
1363
 
 
1364
 
      if (!(create_info.options & HA_LEX_CREATE_TMP_TABLE))
1365
 
      {
1366
 
        lex->link_first_table_back(create_table, link_to_local);
1367
 
        create_table->create= true;
1368
 
      }
1369
 
 
1370
 
      if (!(res= open_and_lock_tables(session, lex->query_tables)))
1371
 
      {
1372
 
        /*
1373
 
          Is table which we are changing used somewhere in other parts
1374
 
          of query
1375
 
        */
1376
 
        if (!(create_info.options & HA_LEX_CREATE_TMP_TABLE))
1377
 
        {
1378
 
          TableList *duplicate;
1379
 
          create_table= lex->unlink_first_table(&link_to_local);
1380
 
          if ((duplicate= unique_table(session, create_table, select_tables, 0)))
1381
 
          {
1382
 
            update_non_unique_table_error(create_table, "CREATE", duplicate);
1383
 
            res= 1;
1384
 
            goto end_with_restore_list;
1385
 
          }
1386
 
        }
1387
 
 
1388
 
        /*
1389
 
          select_create is currently not re-execution friendly and
1390
 
          needs to be created for every execution of a PS/SP.
1391
 
        */
1392
 
        if ((result= new select_create(create_table,
1393
 
                                       &create_info,
1394
 
                                       &alter_info,
1395
 
                                       select_lex->item_list,
1396
 
                                       lex->duplicates,
1397
 
                                       lex->ignore,
1398
 
                                       select_tables)))
1399
 
        {
1400
 
          /*
1401
 
            CREATE from SELECT give its SELECT_LEX for SELECT,
1402
 
            and item_list belong to SELECT
1403
 
          */
1404
 
          res= handle_select(session, lex, result, 0);
1405
 
          delete result;
1406
 
        }
1407
 
      }
1408
 
      else if (!(create_info.options & HA_LEX_CREATE_TMP_TABLE))
1409
 
        create_table= lex->unlink_first_table(&link_to_local);
1410
 
 
1411
 
    }
1412
 
    else
1413
 
    {
1414
 
      /* So that CREATE TEMPORARY TABLE gets to binlog at commit/rollback */
1415
 
      if (create_info.options & HA_LEX_CREATE_TMP_TABLE)
1416
 
        session->options|= OPTION_KEEP_LOG;
1417
 
      /* regular create */
1418
 
      if (create_info.options & HA_LEX_CREATE_TABLE_LIKE)
1419
 
        res= mysql_create_like_table(session, create_table, select_tables,
1420
 
                                     &create_info);
1421
 
      else
1422
 
      {
1423
 
        res= mysql_create_table(session, create_table->db,
1424
 
                                create_table->table_name, &create_info,
1425
 
                                &alter_info, 0, 0);
1426
 
      }
1427
 
      if (!res)
1428
 
        my_ok(session);
1429
 
    }
1430
 
 
1431
 
    /* put tables back for PS rexecuting */
1432
 
end_with_restore_list:
1433
 
    lex->link_first_table_back(create_table, link_to_local);
1434
 
    break;
1435
 
  }
1436
 
  case SQLCOM_CREATE_INDEX:
1437
 
    /* Fall through */
1438
 
  case SQLCOM_DROP_INDEX:
1439
 
  /*
1440
 
    CREATE INDEX and DROP INDEX are implemented by calling ALTER
1441
 
    TABLE with proper arguments.
1442
 
 
1443
 
    In the future ALTER TABLE will notice that the request is to
1444
 
    only add indexes and create these one by one for the existing
1445
 
    table without having to do a full rebuild.
1446
 
  */
1447
 
  {
1448
 
    /* Prepare stack copies to be re-execution safe */
1449
 
    HA_CREATE_INFO create_info;
1450
 
    Alter_info alter_info(lex->alter_info, session->mem_root);
1451
 
 
1452
 
    if (session->is_fatal_error) /* out of memory creating a copy of alter_info */
1453
 
      goto error;
1454
 
 
1455
 
    assert(first_table == all_tables && first_table != 0);
1456
 
    if (end_active_trans(session))
1457
 
      goto error;
1458
 
 
1459
 
    memset(&create_info, 0, sizeof(create_info));
1460
 
    create_info.db_type= 0;
1461
 
    create_info.row_type= ROW_TYPE_NOT_USED;
1462
 
    create_info.default_table_charset= session->variables.collation_database;
1463
 
 
1464
 
    res= mysql_alter_table(session, first_table->db, first_table->table_name,
1465
 
                           &create_info, first_table, &alter_info,
1466
 
                           0, (order_st*) 0, 0);
1467
 
    break;
1468
 
  }
1469
 
  case SQLCOM_SLAVE_START:
1470
 
  {
1471
 
    pthread_mutex_lock(&LOCK_active_mi);
1472
 
    start_slave(session,active_mi,1 /* net report*/);
1473
 
    pthread_mutex_unlock(&LOCK_active_mi);
1474
 
    break;
1475
 
  }
1476
 
  case SQLCOM_SLAVE_STOP:
1477
 
  /*
1478
 
    If the client thread has locked tables, a deadlock is possible.
1479
 
    Assume that
1480
 
    - the client thread does LOCK TABLE t READ.
1481
 
    - then the master updates t.
1482
 
    - then the SQL slave thread wants to update t,
1483
 
      so it waits for the client thread because t is locked by it.
1484
 
    - then the client thread does SLAVE STOP.
1485
 
      SLAVE STOP waits for the SQL slave thread to terminate its
1486
 
      update t, which waits for the client thread because t is locked by it.
1487
 
    To prevent that, refuse SLAVE STOP if the
1488
 
    client thread has locked tables
1489
 
  */
1490
 
  if (session->locked_tables || session->active_transaction() || session->global_read_lock)
1491
 
  {
1492
 
    my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
1493
 
               ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
1494
 
    goto error;
1495
 
  }
1496
 
  {
1497
 
    pthread_mutex_lock(&LOCK_active_mi);
1498
 
    stop_slave(session,active_mi,1/* net report*/);
1499
 
    pthread_mutex_unlock(&LOCK_active_mi);
1500
 
    break;
1501
 
  }
1502
 
 
1503
 
  case SQLCOM_ALTER_TABLE:
1504
 
    assert(first_table == all_tables && first_table != 0);
1505
 
    {
1506
 
      /*
1507
 
        Code in mysql_alter_table() may modify its HA_CREATE_INFO argument,
1508
 
        so we have to use a copy of this structure to make execution
1509
 
        prepared statement- safe. A shallow copy is enough as no memory
1510
 
        referenced from this structure will be modified.
1511
 
      */
1512
 
      HA_CREATE_INFO create_info(lex->create_info);
1513
 
      Alter_info alter_info(lex->alter_info, session->mem_root);
1514
 
 
1515
 
      if (session->is_fatal_error) /* out of memory creating a copy of alter_info */
1516
 
      {
1517
 
        goto error;
1518
 
      }
1519
 
 
1520
 
      /* Must be set in the parser */
1521
 
      assert(select_lex->db);
1522
 
 
1523
 
      { // Rename of table
1524
 
          TableList tmp_table;
1525
 
          memset(&tmp_table, 0, sizeof(tmp_table));
1526
 
          tmp_table.table_name= lex->name.str;
1527
 
          tmp_table.db=select_lex->db;
1528
 
      }
1529
 
 
1530
 
      /* Don't yet allow changing of symlinks with ALTER TABLE */
1531
 
      if (create_info.data_file_name)
1532
 
        push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1533
 
                     "DATA DIRECTORY option ignored");
1534
 
      if (create_info.index_file_name)
1535
 
        push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1536
 
                     "INDEX DIRECTORY option ignored");
1537
 
      create_info.data_file_name= create_info.index_file_name= NULL;
1538
 
      /* ALTER TABLE ends previous transaction */
1539
 
      if (end_active_trans(session))
1540
 
        goto error;
1541
 
 
1542
 
      if (!session->locked_tables &&
1543
 
          !(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1544
 
      {
1545
 
        res= 1;
1546
 
        break;
1547
 
      }
1548
 
 
1549
 
      res= mysql_alter_table(session, select_lex->db, lex->name.str,
1550
 
                             &create_info,
1551
 
                             first_table,
1552
 
                             &alter_info,
1553
 
                             select_lex->order_list.elements,
1554
 
                             (order_st *) select_lex->order_list.first,
1555
 
                             lex->ignore);
1556
 
      break;
1557
 
    }
1558
 
  case SQLCOM_RENAME_TABLE:
1559
 
  {
1560
 
    assert(first_table == all_tables && first_table != 0);
1561
 
    TableList *table;
1562
 
    for (table= first_table; table; table= table->next_local->next_local)
1563
 
    {
1564
 
      TableList old_list, new_list;
1565
 
      /*
1566
 
        we do not need initialize old_list and new_list because we will
1567
 
        come table[0] and table->next[0] there
1568
 
      */
1569
 
      old_list= table[0];
1570
 
      new_list= table->next_local[0];
1571
 
    }
1572
 
 
1573
 
    if (end_active_trans(session) || drizzle_rename_tables(session, first_table, 0))
1574
 
      {
1575
 
        goto error;
1576
 
      }
1577
 
    break;
1578
 
  }
1579
 
  case SQLCOM_SHOW_BINLOGS:
1580
 
    {
1581
 
      res = show_binlogs(session);
1582
 
      break;
1583
 
    }
1584
 
  case SQLCOM_SHOW_CREATE:
1585
 
    assert(first_table == all_tables && first_table != 0);
1586
 
    {
1587
 
      res= mysqld_show_create(session, first_table);
1588
 
      break;
1589
 
    }
1590
 
  case SQLCOM_CHECKSUM:
1591
 
  {
1592
 
    assert(first_table == all_tables && first_table != 0);
1593
 
    res = mysql_checksum_table(session, first_table, &lex->check_opt);
1594
 
    break;
1595
 
  }
1596
 
  case SQLCOM_REPAIR:
1597
 
  {
1598
 
    assert(first_table == all_tables && first_table != 0);
1599
 
    res= mysql_repair_table(session, first_table, &lex->check_opt);
1600
 
    /* ! we write after unlocking the table */
1601
 
    /*
1602
 
      Presumably, REPAIR and binlog writing doesn't require synchronization
1603
 
    */
1604
 
    write_bin_log(session, true, session->query, session->query_length);
1605
 
    select_lex->table_list.first= (unsigned char*) first_table;
1606
 
    lex->query_tables=all_tables;
1607
 
    break;
1608
 
  }
1609
 
  case SQLCOM_CHECK:
1610
 
  {
1611
 
    assert(first_table == all_tables && first_table != 0);
1612
 
    res = mysql_check_table(session, first_table, &lex->check_opt);
1613
 
    select_lex->table_list.first= (unsigned char*) first_table;
1614
 
    lex->query_tables=all_tables;
1615
 
    break;
1616
 
  }
1617
 
  case SQLCOM_ANALYZE:
1618
 
  {
1619
 
    assert(first_table == all_tables && first_table != 0);
1620
 
    res= mysql_analyze_table(session, first_table, &lex->check_opt);
1621
 
    /* ! we write after unlocking the table */
1622
 
    write_bin_log(session, true, session->query, session->query_length);
1623
 
    select_lex->table_list.first= (unsigned char*) first_table;
1624
 
    lex->query_tables=all_tables;
1625
 
    break;
1626
 
  }
1627
 
 
1628
 
  case SQLCOM_OPTIMIZE:
1629
 
  {
1630
 
    assert(first_table == all_tables && first_table != 0);
1631
 
    res= mysql_optimize_table(session, first_table, &lex->check_opt);
1632
 
    /* ! we write after unlocking the table */
1633
 
    write_bin_log(session, true, session->query, session->query_length);
1634
 
    select_lex->table_list.first= (unsigned char*) first_table;
1635
 
    lex->query_tables=all_tables;
1636
 
    break;
1637
 
  }
1638
 
  case SQLCOM_UPDATE:
1639
 
    assert(first_table == all_tables && first_table != 0);
1640
 
    if (update_precheck(session, all_tables))
1641
 
      break;
1642
 
    assert(select_lex->offset_limit == 0);
1643
 
    unit->set_limit(select_lex);
1644
 
    res= (up_result= mysql_update(session, all_tables,
1645
 
                                  select_lex->item_list,
1646
 
                                  lex->value_list,
1647
 
                                  select_lex->where,
1648
 
                                  select_lex->order_list.elements,
1649
 
                                  (order_st *) select_lex->order_list.first,
1650
 
                                  unit->select_limit_cnt,
1651
 
                                  lex->duplicates, lex->ignore));
1652
 
    /* mysql_update return 2 if we need to switch to multi-update */
1653
 
    if (up_result != 2)
1654
 
      break;
1655
 
    /* Fall through */
1656
 
  case SQLCOM_UPDATE_MULTI:
1657
 
  {
1658
 
    assert(first_table == all_tables && first_table != 0);
1659
 
    /* if we switched from normal update, rights are checked */
1660
 
    if (up_result != 2)
1661
 
    {
1662
 
      if ((res= multi_update_precheck(session, all_tables)))
1663
 
        break;
1664
 
    }
1665
 
    else
1666
 
      res= 0;
1667
 
 
1668
 
    res= mysql_multi_update_prepare(session);
1669
 
 
1670
 
    /* Check slave filtering rules */
1671
 
    if (unlikely(session->slave_thread))
1672
 
    {
1673
 
      if (all_tables_not_ok(session, all_tables))
1674
 
      {
1675
 
        if (res!= 0)
1676
 
        {
1677
 
          res= 0;             /* don't care of prev failure  */
1678
 
          session->clear_error(); /* filters are of highest prior */
1679
 
        }
1680
 
        /* we warn the slave SQL thread */
1681
 
        my_error(ER_SLAVE_IGNORED_TABLE, MYF(0));
1682
 
        break;
1683
 
      }
1684
 
      if (res)
1685
 
        break;
1686
 
    }
1687
 
    else
1688
 
    {
1689
 
      if (res)
1690
 
        break;
1691
 
      if (opt_readonly &&
1692
 
          some_non_temp_table_to_be_updated(session, all_tables))
1693
 
      {
1694
 
        my_error(ER_OPTION_PREVENTS_STATEMENT, MYF(0), "--read-only");
1695
 
        break;
1696
 
      }
1697
 
    }  /* unlikely */
1698
 
 
1699
 
    res= mysql_multi_update(session, all_tables,
1700
 
                            &select_lex->item_list,
1701
 
                            &lex->value_list,
1702
 
                            select_lex->where,
1703
 
                            select_lex->options,
1704
 
                            lex->duplicates, lex->ignore, unit, select_lex);
1705
 
    break;
1706
 
  }
1707
 
  case SQLCOM_REPLACE:
1708
 
  case SQLCOM_INSERT:
1709
 
  {
1710
 
    assert(first_table == all_tables && first_table != 0);
1711
 
    if ((res= insert_precheck(session, all_tables)))
1712
 
      break;
1713
 
 
1714
 
    if (!session->locked_tables &&
1715
 
        !(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1716
 
    {
1717
 
      res= 1;
1718
 
      break;
1719
 
    }
1720
 
 
1721
 
    res= mysql_insert(session, all_tables, lex->field_list, lex->many_values,
1722
 
                      lex->update_list, lex->value_list,
1723
 
                      lex->duplicates, lex->ignore);
1724
 
 
1725
 
    break;
1726
 
  }
1727
 
  case SQLCOM_REPLACE_SELECT:
1728
 
  case SQLCOM_INSERT_SELECT:
1729
 
  {
1730
 
    select_result *sel_result;
1731
 
    assert(first_table == all_tables && first_table != 0);
1732
 
    if ((res= insert_precheck(session, all_tables)))
1733
 
      break;
1734
 
 
1735
 
    /* Fix lock for first table */
1736
 
    if (first_table->lock_type == TL_WRITE_DELAYED)
1737
 
      first_table->lock_type= TL_WRITE;
1738
 
 
1739
 
    /* Don't unlock tables until command is written to binary log */
1740
 
    select_lex->options|= SELECT_NO_UNLOCK;
1741
 
 
1742
 
    unit->set_limit(select_lex);
1743
 
 
1744
 
    if (! session->locked_tables &&
1745
 
        ! (need_start_waiting= ! wait_if_global_read_lock(session, 0, 1)))
1746
 
    {
1747
 
      res= 1;
1748
 
      break;
1749
 
    }
1750
 
 
1751
 
    if (!(res= open_and_lock_tables(session, all_tables)))
1752
 
    {
1753
 
      /* Skip first table, which is the table we are inserting in */
1754
 
      TableList *second_table= first_table->next_local;
1755
 
      select_lex->table_list.first= (unsigned char*) second_table;
1756
 
      select_lex->context.table_list= 
1757
 
        select_lex->context.first_name_resolution_table= second_table;
1758
 
      res= mysql_insert_select_prepare(session);
1759
 
      if (!res && (sel_result= new select_insert(first_table,
1760
 
                                                 first_table->table,
1761
 
                                                 &lex->field_list,
1762
 
                                                 &lex->update_list,
1763
 
                                                 &lex->value_list,
1764
 
                                                 lex->duplicates,
1765
 
                                                 lex->ignore)))
1766
 
      {
1767
 
        res= handle_select(session, lex, sel_result, OPTION_SETUP_TABLES_DONE);
1768
 
        /*
1769
 
          Invalidate the table in the query cache if something changed
1770
 
          after unlocking when changes become visible.
1771
 
          TODO: this is workaround. right way will be move invalidating in
1772
 
          the unlock procedure.
1773
 
        */
1774
 
        if (first_table->lock_type ==  TL_WRITE_CONCURRENT_INSERT &&
1775
 
            session->lock)
1776
 
        {
1777
 
          /* INSERT ... SELECT should invalidate only the very first table */
1778
 
          TableList *save_table= first_table->next_local;
1779
 
          first_table->next_local= 0;
1780
 
          first_table->next_local= save_table;
1781
 
        }
1782
 
        delete sel_result;
1783
 
      }
1784
 
      /* revert changes for SP */
1785
 
      select_lex->table_list.first= (unsigned char*) first_table;
1786
 
    }
1787
 
 
1788
 
    break;
1789
 
  }
1790
 
  case SQLCOM_TRUNCATE:
1791
 
    if (end_active_trans(session))
1792
 
    {
1793
 
      res= -1;
1794
 
      break;
1795
 
    }
1796
 
    assert(first_table == all_tables && first_table != 0);
1797
 
    /*
1798
 
      Don't allow this within a transaction because we want to use
1799
 
      re-generate table
1800
 
    */
1801
 
    if (session->locked_tables || session->active_transaction())
1802
 
    {
1803
 
      my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
1804
 
                 ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
1805
 
      goto error;
1806
 
    }
1807
 
 
1808
 
    res= mysql_truncate(session, first_table, 0);
1809
 
 
1810
 
    break;
1811
 
  case SQLCOM_DELETE:
1812
 
  {
1813
 
    assert(first_table == all_tables && first_table != 0);
1814
 
    assert(select_lex->offset_limit == 0);
1815
 
    unit->set_limit(select_lex);
1816
 
 
1817
 
    if (!session->locked_tables &&
1818
 
        !(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1819
 
    {
1820
 
      res= 1;
1821
 
      break;
1822
 
    }
1823
 
 
1824
 
    res = mysql_delete(session, all_tables, select_lex->where,
1825
 
                       &select_lex->order_list,
1826
 
                       unit->select_limit_cnt, select_lex->options,
1827
 
                       false);
1828
 
    break;
1829
 
  }
1830
 
  case SQLCOM_DELETE_MULTI:
1831
 
  {
1832
 
    assert(first_table == all_tables && first_table != 0);
1833
 
    TableList *aux_tables=
1834
 
      (TableList *)session->lex->auxiliary_table_list.first;
1835
 
    multi_delete *del_result;
1836
 
 
1837
 
    if (!session->locked_tables &&
1838
 
        !(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1839
 
    {
1840
 
      res= 1;
1841
 
      break;
1842
 
    }
1843
 
 
1844
 
    if ((res= multi_delete_precheck(session, all_tables)))
1845
 
      break;
1846
 
 
1847
 
    /* condition will be true on SP re-excuting */
1848
 
    if (select_lex->item_list.elements != 0)
1849
 
      select_lex->item_list.empty();
1850
 
    if (add_item_to_list(session, new Item_null()))
1851
 
      goto error;
1852
 
 
1853
 
    session->set_proc_info("init");
1854
 
    if ((res= open_and_lock_tables(session, all_tables)))
1855
 
      break;
1856
 
 
1857
 
    if ((res= mysql_multi_delete_prepare(session)))
1858
 
      goto error;
1859
 
 
1860
 
    if (!session->is_fatal_error &&
1861
 
        (del_result= new multi_delete(aux_tables, lex->table_count)))
1862
 
    {
1863
 
      res= mysql_select(session, &select_lex->ref_pointer_array,
1864
 
                        select_lex->get_table_list(),
1865
 
                        select_lex->with_wild,
1866
 
                        select_lex->item_list,
1867
 
                        select_lex->where,
1868
 
                        0, (order_st *)NULL, (order_st *)NULL, (Item *)NULL,
1869
 
                        (order_st *)NULL,
1870
 
                        select_lex->options | session->options |
1871
 
                        SELECT_NO_JOIN_CACHE | SELECT_NO_UNLOCK |
1872
 
                        OPTION_SETUP_TABLES_DONE,
1873
 
                        del_result, unit, select_lex);
1874
 
      res|= session->is_error();
1875
 
      if (res)
1876
 
        del_result->abort();
1877
 
      delete del_result;
1878
 
    }
1879
 
    else
1880
 
      res= true;                                // Error
1881
 
    break;
1882
 
  }
1883
 
  case SQLCOM_DROP_TABLE:
1884
 
  {
1885
 
    assert(first_table == all_tables && first_table != 0);
1886
 
    if (!lex->drop_temporary)
1887
 
    {
1888
 
      if (end_active_trans(session))
1889
 
        goto error;
1890
 
    }
1891
 
    else
1892
 
    {
1893
 
      /*
1894
 
        If this is a slave thread, we may sometimes execute some 
1895
 
        DROP / * 40005 TEMPORARY * / TABLE
1896
 
        that come from parts of binlogs (likely if we use RESET SLAVE or CHANGE
1897
 
        MASTER TO), while the temporary table has already been dropped.
1898
 
        To not generate such irrelevant "table does not exist errors",
1899
 
        we silently add IF EXISTS if TEMPORARY was used.
1900
 
      */
1901
 
      if (session->slave_thread)
1902
 
        lex->drop_if_exists= 1;
1903
 
 
1904
 
      /* So that DROP TEMPORARY TABLE gets to binlog at commit/rollback */
1905
 
      session->options|= OPTION_KEEP_LOG;
1906
 
    }
1907
 
    /* DDL and binlog write order protected by LOCK_open */
1908
 
    res= mysql_rm_table(session, first_table, lex->drop_if_exists, lex->drop_temporary);
1909
 
  }
1910
 
  break;
1911
 
  case SQLCOM_SHOW_PROCESSLIST:
1912
 
    mysqld_list_processes(session, NULL, lex->verbose);
1913
 
    break;
1914
 
  case SQLCOM_SHOW_ENGINE_LOGS:
1915
 
    {
1916
 
      res= ha_show_status(session, lex->create_info.db_type, HA_ENGINE_LOGS);
1917
 
      break;
1918
 
    }
1919
 
  case SQLCOM_CHANGE_DB:
1920
 
  {
1921
 
    LEX_STRING db_str= { (char *) select_lex->db, strlen(select_lex->db) };
1922
 
 
1923
 
    if (!mysql_change_db(session, &db_str, false))
1924
 
      my_ok(session);
1925
 
 
1926
 
    break;
1927
 
  }
1928
 
 
1929
 
  case SQLCOM_LOAD:
1930
 
  {
1931
 
    assert(first_table == all_tables && first_table != 0);
1932
 
    if (lex->local_file)
1933
 
    {
1934
 
      if (!(session->client_capabilities & CLIENT_LOCAL_FILES) ||
1935
 
          !opt_local_infile)
1936
 
      {
1937
 
        my_message(ER_NOT_ALLOWED_COMMAND, ER(ER_NOT_ALLOWED_COMMAND), MYF(0));
1938
 
        goto error;
1939
 
      }
1940
 
    }
1941
 
 
1942
 
    res= mysql_load(session, lex->exchange, first_table, lex->field_list,
1943
 
                    lex->update_list, lex->value_list, lex->duplicates,
1944
 
                    lex->ignore, (bool) lex->local_file);
1945
 
    break;
1946
 
  }
1947
 
 
1948
 
  case SQLCOM_SET_OPTION:
1949
 
  {
1950
 
    List<set_var_base> *lex_var_list= &lex->var_list;
1951
 
 
1952
 
    if (lex->autocommit && end_active_trans(session))
1953
 
      goto error;
1954
 
 
1955
 
    if (open_and_lock_tables(session, all_tables))
1956
 
      goto error;
1957
 
    if (!(res= sql_set_variables(session, lex_var_list)))
1958
 
    {
1959
 
      my_ok(session);
1960
 
    }
1961
 
    else
1962
 
    {
1963
 
      /*
1964
 
        We encountered some sort of error, but no message was sent.
1965
 
        Send something semi-generic here since we don't know which
1966
 
        assignment in the list caused the error.
1967
 
      */
1968
 
      if (!session->is_error())
1969
 
        my_error(ER_WRONG_ARGUMENTS,MYF(0),"SET");
1970
 
      goto error;
1971
 
    }
1972
 
 
1973
 
    break;
1974
 
  }
1975
 
 
1976
 
  case SQLCOM_UNLOCK_TABLES:
1977
 
    /*
1978
 
      It is critical for mysqldump --single-transaction --master-data that
1979
 
      UNLOCK TABLES does not implicitely commit a connection which has only
1980
 
      done FLUSH TABLES WITH READ LOCK + BEGIN. If this assumption becomes
1981
 
      false, mysqldump will not work.
1982
 
    */
1983
 
    unlock_locked_tables(session);
1984
 
    if (session->options & OPTION_TABLE_LOCK)
1985
 
    {
1986
 
      end_active_trans(session);
1987
 
      session->options&= ~(OPTION_TABLE_LOCK);
1988
 
    }
1989
 
    if (session->global_read_lock)
1990
 
      unlock_global_read_lock(session);
1991
 
    my_ok(session);
1992
 
    break;
1993
 
  case SQLCOM_LOCK_TABLES:
1994
 
    /*
1995
 
      We try to take transactional locks if
1996
 
      - only transactional locks are requested (lex->lock_transactional) and
1997
 
      - no non-transactional locks exist (!session->locked_tables).
1998
 
    */
1999
 
    if (lex->lock_transactional && !session->locked_tables)
2000
 
    {
2001
 
      int rc;
2002
 
      /*
2003
 
        All requested locks are transactional and no non-transactional
2004
 
        locks exist.
2005
 
      */
2006
 
      if ((rc= try_transactional_lock(session, all_tables)) == -1)
2007
 
        goto error;
2008
 
      if (rc == 0)
2009
 
      {
2010
 
        my_ok(session);
2011
 
        break;
2012
 
      }
2013
 
      /*
2014
 
        Non-transactional locking has been requested or
2015
 
        non-transactional locks exist already or transactional locks are
2016
 
        not supported by all storage engines. Take non-transactional
2017
 
        locks.
2018
 
      */
2019
 
    }
2020
 
    /*
2021
 
      One or more requested locks are non-transactional and/or
2022
 
      non-transactional locks exist or a storage engine does not support
2023
 
      transactional locks. Check if at least one transactional lock is
2024
 
      requested. If yes, warn about the conversion to non-transactional
2025
 
      locks or abort in strict mode.
2026
 
    */
2027
 
    if (check_transactional_lock(session, all_tables))
2028
 
      goto error;
2029
 
    unlock_locked_tables(session);
2030
 
    /* we must end the trasaction first, regardless of anything */
2031
 
    if (end_active_trans(session))
2032
 
      goto error;
2033
 
    session->in_lock_tables=1;
2034
 
    session->options|= OPTION_TABLE_LOCK;
2035
 
 
2036
 
    if (!(res= simple_open_n_lock_tables(session, all_tables)))
2037
 
    {
2038
 
      session->locked_tables=session->lock;
2039
 
      session->lock=0;
2040
 
      (void) set_handler_table_locks(session, all_tables, false);
2041
 
      my_ok(session);
2042
 
    }
2043
 
    else
2044
 
    {
2045
 
      /* 
2046
 
        Need to end the current transaction, so the storage engine (InnoDB)
2047
 
        can free its locks if LOCK TABLES locked some tables before finding
2048
 
        that it can't lock a table in its list
2049
 
      */
2050
 
      ha_autocommit_or_rollback(session, 1);
2051
 
      end_active_trans(session);
2052
 
      session->options&= ~(OPTION_TABLE_LOCK);
2053
 
    }
2054
 
    session->in_lock_tables=0;
2055
 
    break;
2056
 
  case SQLCOM_CREATE_DB:
2057
 
  {
2058
 
    /*
2059
 
      As mysql_create_db() may modify HA_CREATE_INFO structure passed to
2060
 
      it, we need to use a copy of LEX::create_info to make execution
2061
 
      prepared statement- safe.
2062
 
    */
2063
 
    HA_CREATE_INFO create_info(lex->create_info);
2064
 
    if (end_active_trans(session))
2065
 
    {
2066
 
      res= -1;
2067
 
      break;
2068
 
    }
2069
 
    char *alias;
2070
 
    if (!(alias=session->strmake(lex->name.str, lex->name.length)) ||
2071
 
        check_db_name(&lex->name))
2072
 
    {
2073
 
      my_error(ER_WRONG_DB_NAME, MYF(0), lex->name.str);
2074
 
      break;
2075
 
    }
2076
 
    res= mysql_create_db(session,(lower_case_table_names == 2 ? alias :
2077
 
                              lex->name.str), &create_info, 0);
2078
 
    break;
2079
 
  }
2080
 
  case SQLCOM_DROP_DB:
2081
 
  {
2082
 
    if (end_active_trans(session))
2083
 
    {
2084
 
      res= -1;
2085
 
      break;
2086
 
    }
2087
 
    if (check_db_name(&lex->name))
2088
 
    {
2089
 
      my_error(ER_WRONG_DB_NAME, MYF(0), lex->name.str);
2090
 
      break;
2091
 
    }
2092
 
    if (session->locked_tables || session->active_transaction())
2093
 
    {
2094
 
      my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
2095
 
                 ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
2096
 
      goto error;
2097
 
    }
2098
 
    res= mysql_rm_db(session, lex->name.str, lex->drop_if_exists, 0);
2099
 
    break;
2100
 
  }
2101
 
  case SQLCOM_ALTER_DB:
2102
 
  {
2103
 
    LEX_STRING *db= &lex->name;
2104
 
    HA_CREATE_INFO create_info(lex->create_info);
2105
 
    if (check_db_name(db))
2106
 
    {
2107
 
      my_error(ER_WRONG_DB_NAME, MYF(0), db->str);
2108
 
      break;
2109
 
    }
2110
 
    if (session->locked_tables || session->active_transaction())
2111
 
    {
2112
 
      my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
2113
 
                 ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
2114
 
      goto error;
2115
 
    }
2116
 
    res= mysql_alter_db(session, db->str, &create_info);
2117
 
    break;
2118
 
  }
2119
 
  case SQLCOM_SHOW_CREATE_DB:
2120
 
  {
2121
 
    if (check_db_name(&lex->name))
2122
 
    {
2123
 
      my_error(ER_WRONG_DB_NAME, MYF(0), lex->name.str);
2124
 
      break;
2125
 
    }
2126
 
    res= mysqld_show_create_db(session, lex->name.str, &lex->create_info);
2127
 
    break;
2128
 
  }
2129
 
  case SQLCOM_RESET:
2130
 
  case SQLCOM_FLUSH:
2131
 
  {
2132
 
    bool write_to_binlog;
2133
 
 
2134
 
    /*
2135
 
      reload_cache() will tell us if we are allowed to write to the
2136
 
      binlog or not.
2137
 
    */
2138
 
    if (!reload_cache(session, lex->type, first_table, &write_to_binlog))
2139
 
    {
2140
 
      /*
2141
 
        We WANT to write and we CAN write.
2142
 
        ! we write after unlocking the table.
2143
 
      */
2144
 
      /*
2145
 
        Presumably, RESET and binlog writing doesn't require synchronization
2146
 
      */
2147
 
      write_bin_log(session, false, session->query, session->query_length);
2148
 
      my_ok(session);
2149
 
    } 
2150
 
    
2151
 
    break;
2152
 
  }
2153
 
  case SQLCOM_KILL:
2154
 
  {
2155
 
    Item *it= (Item *)lex->value_list.head();
2156
 
 
2157
 
    if (lex->table_or_sp_used())
2158
 
    {
2159
 
      my_error(ER_NOT_SUPPORTED_YET, MYF(0), "Usage of subqueries or stored "
2160
 
               "function calls as part of this statement");
2161
 
      break;
2162
 
    }
2163
 
 
2164
 
    if ((!it->fixed && it->fix_fields(lex->session, &it)) || it->check_cols(1))
2165
 
    {
2166
 
      my_message(ER_SET_CONSTANTS_ONLY, ER(ER_SET_CONSTANTS_ONLY),
2167
 
                 MYF(0));
2168
 
      goto error;
2169
 
    }
2170
 
    sql_kill(session, (ulong)it->val_int(), lex->type & ONLY_KILL_QUERY);
2171
 
    break;
2172
 
  }
2173
 
  case SQLCOM_BEGIN:
2174
 
    if (session->transaction.xid_state.xa_state != XA_NOTR)
2175
 
    {
2176
 
      my_error(ER_XAER_RMFAIL, MYF(0),
2177
 
               xa_state_names[session->transaction.xid_state.xa_state]);
2178
 
      break;
2179
 
    }
2180
 
    /*
2181
 
      Breakpoints for backup testing.
2182
 
    */
2183
 
    if (begin_trans(session))
2184
 
      goto error;
2185
 
    my_ok(session);
2186
 
    break;
2187
 
  case SQLCOM_COMMIT:
2188
 
    if (end_trans(session, lex->tx_release ? COMMIT_RELEASE :
2189
 
                              lex->tx_chain ? COMMIT_AND_CHAIN : COMMIT))
2190
 
      goto error;
2191
 
    my_ok(session);
2192
 
    break;
2193
 
  case SQLCOM_ROLLBACK:
2194
 
    if (end_trans(session, lex->tx_release ? ROLLBACK_RELEASE :
2195
 
                              lex->tx_chain ? ROLLBACK_AND_CHAIN : ROLLBACK))
2196
 
      goto error;
2197
 
    my_ok(session);
2198
 
    break;
2199
 
  case SQLCOM_RELEASE_SAVEPOINT:
2200
 
  {
2201
 
    SAVEPOINT *sv;
2202
 
    for (sv=session->transaction.savepoints; sv; sv=sv->prev)
2203
 
    {
2204
 
      if (my_strnncoll(system_charset_info,
2205
 
                       (unsigned char *)lex->ident.str, lex->ident.length,
2206
 
                       (unsigned char *)sv->name, sv->length) == 0)
2207
 
        break;
2208
 
    }
2209
 
    if (sv)
2210
 
    {
2211
 
      if (ha_release_savepoint(session, sv))
2212
 
        res= true; // cannot happen
2213
 
      else
2214
 
        my_ok(session);
2215
 
      session->transaction.savepoints=sv->prev;
2216
 
    }
2217
 
    else
2218
 
      my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
2219
 
    break;
2220
 
  }
2221
 
  case SQLCOM_ROLLBACK_TO_SAVEPOINT:
2222
 
  {
2223
 
    SAVEPOINT *sv;
2224
 
    for (sv=session->transaction.savepoints; sv; sv=sv->prev)
2225
 
    {
2226
 
      if (my_strnncoll(system_charset_info,
2227
 
                       (unsigned char *)lex->ident.str, lex->ident.length,
2228
 
                       (unsigned char *)sv->name, sv->length) == 0)
2229
 
        break;
2230
 
    }
2231
 
    if (sv)
2232
 
    {
2233
 
      if (ha_rollback_to_savepoint(session, sv))
2234
 
        res= true; // cannot happen
2235
 
      else
2236
 
      {
2237
 
        if (((session->options & OPTION_KEEP_LOG) || 
2238
 
             session->transaction.all.modified_non_trans_table) &&
2239
 
            !session->slave_thread)
2240
 
          push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN,
2241
 
                       ER_WARNING_NOT_COMPLETE_ROLLBACK,
2242
 
                       ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
2243
 
        my_ok(session);
2244
 
      }
2245
 
      session->transaction.savepoints=sv;
2246
 
    }
2247
 
    else
2248
 
      my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
2249
 
    break;
2250
 
  }
2251
 
  case SQLCOM_SAVEPOINT:
2252
 
    if (!(session->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN)) || !opt_using_transactions)
2253
 
      my_ok(session);
2254
 
    else
2255
 
    {
2256
 
      SAVEPOINT **sv, *newsv;
2257
 
      for (sv=&session->transaction.savepoints; *sv; sv=&(*sv)->prev)
2258
 
      {
2259
 
        if (my_strnncoll(system_charset_info,
2260
 
                         (unsigned char *)lex->ident.str, lex->ident.length,
2261
 
                         (unsigned char *)(*sv)->name, (*sv)->length) == 0)
2262
 
          break;
2263
 
      }
2264
 
      if (*sv) /* old savepoint of the same name exists */
2265
 
      {
2266
 
        newsv=*sv;
2267
 
        ha_release_savepoint(session, *sv); // it cannot fail
2268
 
        *sv=(*sv)->prev;
2269
 
      }
2270
 
      else if ((newsv=(SAVEPOINT *) alloc_root(&session->transaction.mem_root,
2271
 
                                               savepoint_alloc_size)) == 0)
2272
 
      {
2273
 
        my_error(ER_OUT_OF_RESOURCES, MYF(0));
2274
 
        break;
2275
 
      }
2276
 
      newsv->name=strmake_root(&session->transaction.mem_root,
2277
 
                               lex->ident.str, lex->ident.length);
2278
 
      newsv->length=lex->ident.length;
2279
 
      /*
2280
 
        if we'll get an error here, don't add new savepoint to the list.
2281
 
        we'll lose a little bit of memory in transaction mem_root, but it'll
2282
 
        be free'd when transaction ends anyway
2283
 
      */
2284
 
      if (ha_savepoint(session, newsv))
2285
 
        res= true;
2286
 
      else
2287
 
      {
2288
 
        newsv->prev=session->transaction.savepoints;
2289
 
        session->transaction.savepoints=newsv;
2290
 
        my_ok(session);
2291
 
      }
2292
 
    }
2293
 
    break;
2294
 
  case SQLCOM_BINLOG_BASE64_EVENT:
2295
 
  {
2296
 
    mysql_client_binlog_statement(session);
2297
 
    break;
2298
 
  }
2299
 
  default:
2300
 
    assert(0);                             /* Impossible */
2301
 
    my_ok(session);
2302
 
    break;
2303
 
  }
 
492
  if (all_tables || ! session->lex().is_single_level_stmt())
 
493
  {
 
494
    drizzle_reset_errors(*session, 0);
 
495
  }
 
496
 
 
497
  assert(not session->transaction.stmt.hasModifiedNonTransData());
 
498
 
 
499
  if (! (session->server_status & SERVER_STATUS_AUTOCOMMIT)
 
500
      && ! session->inTransaction()
 
501
      && session->lex().statement->isTransactional())
 
502
  {
 
503
    if (not session->startTransaction())
 
504
    {
 
505
      my_error(drizzled::ER_UNKNOWN_ERROR, MYF(0));
 
506
      return true;
 
507
    }
 
508
  }
 
509
 
 
510
  /* now we are ready to execute the statement */
 
511
  res= session->lex().statement->execute();
2304
512
  session->set_proc_info("query end");
2305
 
 
2306
513
  /*
2307
514
    The return value for ROW_COUNT() is "implementation dependent" if the
2308
515
    statement is not DELETE, INSERT or UPDATE, but -1 is what JDBC and ODBC
2309
516
    wants. We also keep the last value in case of SQLCOM_CALL or
2310
517
    SQLCOM_EXECUTE.
2311
518
  */
2312
 
  if (!(sql_command_flags[lex->sql_command].test(CF_BIT_HAS_ROW_COUNT)))
 
519
  if (! (sql_command_flags[session->lex().sql_command].test(CF_BIT_HAS_ROW_COUNT)))
 
520
  {
2313
521
    session->row_count_func= -1;
2314
 
 
2315
 
  goto finish;
2316
 
 
2317
 
error:
2318
 
  res= true;
2319
 
 
2320
 
finish:
2321
 
  if (need_start_waiting)
2322
 
  {
2323
 
    /*
2324
 
      Release the protection against the global read lock and wake
2325
 
      everyone, who might want to set a global read lock.
2326
 
    */
2327
 
    start_waiting_global_read_lock(session);
2328
522
  }
2329
 
  return(res || session->is_error());
 
523
 
 
524
  return (res || session->is_error());
2330
525
}
2331
 
 
2332
526
bool execute_sqlcom_select(Session *session, TableList *all_tables)
2333
527
{
2334
 
  LEX   *lex= session->lex;
 
528
  LEX   *lex= &session->lex();
2335
529
  select_result *result=lex->result;
2336
 
  bool res;
 
530
  bool res= false;
2337
531
  /* assign global limit variable if limit is not given */
2338
532
  {
2339
 
    SELECT_LEX *param= lex->unit.global_parameters;
 
533
    Select_Lex *param= lex->unit.global_parameters;
2340
534
    if (!param->explicit_limit)
2341
535
      param->select_limit=
2342
536
        new Item_int((uint64_t) session->variables.select_limit);
2343
537
  }
2344
 
  if (!(res= open_and_lock_tables(session, all_tables)))
 
538
 
 
539
  if (all_tables
 
540
      && ! (session->server_status & SERVER_STATUS_AUTOCOMMIT)
 
541
      && ! session->inTransaction()
 
542
      && ! lex->statement->isShow())
 
543
  {
 
544
    if (not session->startTransaction())
 
545
    {
 
546
      my_error(drizzled::ER_UNKNOWN_ERROR, MYF(0));
 
547
      return true;
 
548
    }
 
549
  }
 
550
 
 
551
  if (not (res= session->openTablesLock(all_tables)))
2345
552
  {
2346
553
    if (lex->describe)
2347
554
    {
2351
558
        to prepend EXPLAIN to any query and receive output for it,
2352
559
        even if the query itself redirects the output.
2353
560
      */
2354
 
      if (!(result= new select_send()))
2355
 
        return 1;                               /* purecov: inspected */
 
561
      result= new select_send();
2356
562
      session->send_explain_fields(result);
2357
 
      res= mysql_explain_union(session, &session->lex->unit, result);
 
563
      optimizer::ExplainPlan planner;
 
564
      res= planner.explainUnion(session, &session->lex().unit, result);
2358
565
      if (lex->describe & DESCRIBE_EXTENDED)
2359
566
      {
2360
567
        char buff[1024];
2361
568
        String str(buff,(uint32_t) sizeof(buff), system_charset_info);
2362
569
        str.length(0);
2363
 
        session->lex->unit.print(&str, QT_ORDINARY);
 
570
        session->lex().unit.print(&str);
2364
571
        str.append('\0');
2365
572
        push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
2366
573
                     ER_YES, str.ptr());
2369
576
        result->abort();
2370
577
      else
2371
578
        result->send_eof();
 
579
 
2372
580
      delete result;
2373
581
    }
2374
582
    else
2375
583
    {
2376
 
      if (!result && !(result= new select_send()))
2377
 
        return 1;                               /* purecov: inspected */
 
584
      if (not result)
 
585
        result= new select_send();
 
586
 
 
587
      /* Init the Query Cache plugin */
 
588
      plugin::QueryCache::prepareResultset(session);
2378
589
      res= handle_select(session, lex, result, 0);
 
590
      /* Send the Resultset to the cache */
 
591
      plugin::QueryCache::setResultset(session);
 
592
 
2379
593
      if (result != lex->result)
2380
594
        delete result;
2381
595
    }
2383
597
  return res;
2384
598
}
2385
599
 
2386
 
/****************************************************************************
2387
 
        Check stack size; Send error if there isn't enough stack to continue
2388
 
****************************************************************************/
2389
 
#if STACK_DIRECTION < 0
2390
 
#define used_stack(A,B) (long) (A - B)
2391
 
#else
2392
 
#define used_stack(A,B) (long) (B - A)
2393
 
#endif
2394
 
 
2395
 
/**
2396
 
  @note
2397
 
  Note: The 'buf' parameter is necessary, even if it is unused here.
2398
 
  - fix_fields functions has a "dummy" buffer large enough for the
2399
 
    corresponding exec. (Thus we only have to check in fix_fields.)
2400
 
  - Passing to check_stack_overrun() prevents the compiler from removing it.
2401
 
*/
2402
 
bool check_stack_overrun(Session *session, long margin, unsigned char *)
2403
 
{
2404
 
  long stack_used;
2405
 
  assert(session == current_session);
2406
 
  if ((stack_used=used_stack(session->thread_stack,(char*) &stack_used)) >=
2407
 
      (long) (my_thread_stack_size - margin))
2408
 
  {
2409
 
    sprintf(errbuff[0],ER(ER_STACK_OVERRUN_NEED_MORE),
2410
 
            stack_used,my_thread_stack_size,margin);
2411
 
    my_message(ER_STACK_OVERRUN_NEED_MORE,errbuff[0],MYF(ME_FATALERROR));
2412
 
    return 1;
2413
 
  }
2414
 
  return 0;
2415
 
}
2416
600
 
2417
601
#define MY_YACC_INIT 1000                       // Start with big alloc
2418
602
#define MY_YACC_MAX  32000                      // Because of 'short'
2419
603
 
2420
 
bool my_yyoverflow(short **yyss, YYSTYPE **yyvs, ulong *yystacksize)
 
604
bool my_yyoverflow(short **yyss, ParserType **yyvs, ulong *yystacksize)
2421
605
{
2422
 
  LEX   *lex= current_session->lex;
 
606
  LEX   *lex= &current_session->lex();
2423
607
  ulong old_info=0;
2424
608
  if ((uint32_t) *yystacksize >= MY_YACC_MAX)
2425
609
    return 1;
2426
610
  if (!lex->yacc_yyvs)
2427
611
    old_info= *yystacksize;
2428
612
  *yystacksize= set_zone((*yystacksize)*2,MY_YACC_INIT,MY_YACC_MAX);
2429
 
  if (!(lex->yacc_yyvs= (unsigned char*)
2430
 
        my_realloc(lex->yacc_yyvs,
2431
 
                   *yystacksize*sizeof(**yyvs),
2432
 
                   MYF(MY_ALLOW_ZERO_PTR | MY_FREE_ON_ERROR))) ||
2433
 
      !(lex->yacc_yyss= (unsigned char*)
2434
 
        my_realloc(lex->yacc_yyss,
2435
 
                   *yystacksize*sizeof(**yyss),
2436
 
                   MYF(MY_ALLOW_ZERO_PTR | MY_FREE_ON_ERROR))))
2437
 
    return 1;
 
613
  unsigned char *tmpptr= NULL;
 
614
  if (!(tmpptr= (unsigned char *)realloc(lex->yacc_yyvs,
 
615
                                         *yystacksize* sizeof(**yyvs))))
 
616
      return 1;
 
617
  lex->yacc_yyvs= tmpptr;
 
618
  tmpptr= NULL;
 
619
  if (!(tmpptr= (unsigned char*)realloc(lex->yacc_yyss,
 
620
                                        *yystacksize* sizeof(**yyss))))
 
621
      return 1;
 
622
  lex->yacc_yyss= tmpptr;
2438
623
  if (old_info)
2439
624
  {                                             // Copy old info from stack
2440
625
    memcpy(lex->yacc_yyss, *yyss, old_info*sizeof(**yyss));
2441
626
    memcpy(lex->yacc_yyvs, *yyvs, old_info*sizeof(**yyvs));
2442
627
  }
2443
628
  *yyss=(short*) lex->yacc_yyss;
2444
 
  *yyvs=(YYSTYPE*) lex->yacc_yyvs;
 
629
  *yyvs=(ParserType*) lex->yacc_yyvs;
2445
630
  return 0;
2446
631
}
2447
632
 
2448
633
 
2449
 
/**
2450
 
 Reset Session part responsible for command processing state.
2451
 
 
2452
 
   This needs to be called before execution of every statement
2453
 
   (prepared or conventional).
2454
 
   It is not called by substatements of routines.
2455
 
 
2456
 
  @todo
2457
 
   Make it a method of Session and align its name with the rest of
2458
 
   reset/end/start/init methods.
2459
 
  @todo
2460
 
   Call it after we use Session for queries, not before.
2461
 
*/
2462
 
 
2463
 
void mysql_reset_session_for_next_command(Session *session)
2464
 
{
2465
 
  session->free_list= 0;
2466
 
  session->select_number= 1;
2467
 
  /*
2468
 
    Those two lines below are theoretically unneeded as
2469
 
    Session::cleanup_after_query() should take care of this already.
2470
 
  */
2471
 
  session->auto_inc_intervals_in_cur_stmt_for_binlog.empty();
2472
 
 
2473
 
  session->query_start_used= 0;
2474
 
  session->is_fatal_error= 0;
2475
 
  session->server_status&= ~ (SERVER_MORE_RESULTS_EXISTS | 
2476
 
                          SERVER_QUERY_NO_INDEX_USED |
2477
 
                          SERVER_QUERY_NO_GOOD_INDEX_USED);
2478
 
  /*
2479
 
    If in autocommit mode and not in a transaction, reset
2480
 
    OPTION_STATUS_NO_TRANS_UPDATE | OPTION_KEEP_LOG to not get warnings
2481
 
    in ha_rollback_trans() about some tables couldn't be rolled back.
2482
 
  */
2483
 
  if (!(session->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN)))
2484
 
  {
2485
 
    session->options&= ~OPTION_KEEP_LOG;
2486
 
    session->transaction.all.modified_non_trans_table= false;
2487
 
  }
2488
 
  assert(session->security_ctx== &session->main_security_ctx);
2489
 
  session->thread_specific_used= false;
2490
 
 
2491
 
  if (opt_bin_log)
2492
 
  {
2493
 
    reset_dynamic(&session->user_var_events);
2494
 
    session->user_var_events_alloc= session->mem_root;
2495
 
  }
2496
 
  session->clear_error();
2497
 
  session->main_da.reset_diagnostics_area();
2498
 
  session->total_warn_count=0;                  // Warnings for this query
2499
 
  session->sent_row_count= session->examined_row_count= 0;
2500
 
 
2501
 
  return;
2502
 
}
2503
 
 
2504
 
 
2505
634
void
2506
 
mysql_init_select(LEX *lex)
 
635
init_select(LEX *lex)
2507
636
{
2508
 
  SELECT_LEX *select_lex= lex->current_select;
 
637
  Select_Lex *select_lex= lex->current_select;
2509
638
  select_lex->init_select();
2510
639
  lex->wild= 0;
2511
640
  if (select_lex == &lex->select_lex)
2516
645
}
2517
646
 
2518
647
 
2519
 
bool
2520
 
mysql_new_select(LEX *lex, bool move_down)
 
648
bool new_select(LEX *lex, bool move_down)
2521
649
{
2522
 
  SELECT_LEX *select_lex;
2523
 
  Session *session= lex->session;
 
650
  Session* session= lex->session;
 
651
  Select_Lex* select_lex= new (session->mem_root) Select_Lex;
2524
652
 
2525
 
  if (!(select_lex= new (session->mem_root) SELECT_LEX()))
2526
 
    return(1);
2527
653
  select_lex->select_number= ++session->select_number;
2528
654
  select_lex->parent_lex= lex; /* Used in init_query. */
2529
655
  select_lex->init_query();
2530
656
  select_lex->init_select();
2531
657
  lex->nest_level++;
 
658
 
2532
659
  if (lex->nest_level > (int) MAX_SELECT_NESTING)
2533
660
  {
2534
661
    my_error(ER_TOO_HIGH_LEVEL_OF_NESTING_FOR_SELECT,MYF(0),MAX_SELECT_NESTING);
2535
 
    return(1);
 
662
    return 1;
2536
663
  }
 
664
 
2537
665
  select_lex->nest_level= lex->nest_level;
2538
666
  if (move_down)
2539
667
  {
2540
 
    SELECT_LEX_UNIT *unit;
2541
 
    lex->subqueries= true;
2542
668
    /* first select_lex of subselect or derived table */
2543
 
    if (!(unit= new (session->mem_root) SELECT_LEX_UNIT()))
2544
 
      return(1);
 
669
    Select_Lex_Unit* unit= new (session->mem_root) Select_Lex_Unit();
2545
670
 
2546
671
    unit->init_query();
2547
672
    unit->init_select();
2562
687
    if (lex->current_select->order_list.first && !lex->current_select->braces)
2563
688
    {
2564
689
      my_error(ER_WRONG_USAGE, MYF(0), "UNION", "order_st BY");
2565
 
      return(1);
 
690
      return true;
2566
691
    }
 
692
 
2567
693
    select_lex->include_neighbour(lex->current_select);
2568
 
    SELECT_LEX_UNIT *unit= select_lex->master_unit();                              
2569
 
    if (!unit->fake_select_lex && unit->add_fake_select_lex(lex->session))
2570
 
      return(1);
2571
 
    select_lex->context.outer_context= 
 
694
    Select_Lex_Unit *unit= select_lex->master_unit();
 
695
 
 
696
    if (not unit->fake_select_lex && unit->add_fake_select_lex(lex->session))
 
697
      return true;
 
698
 
 
699
    select_lex->context.outer_context=
2572
700
                unit->first_select()->context.outer_context;
2573
701
  }
2574
702
 
2575
703
  select_lex->master_unit()->global_parameters= select_lex;
2576
 
  select_lex->include_global((st_select_lex_node**)&lex->all_selects_list);
 
704
  select_lex->include_global((Select_Lex_Node**)&lex->all_selects_list);
2577
705
  lex->current_select= select_lex;
2578
706
  /*
2579
707
    in subquery is SELECT query and we allow resolution of names in SELECT
2580
708
    list
2581
709
  */
2582
710
  select_lex->context.resolve_in_select_list= true;
2583
 
  return(0);
 
711
 
 
712
  return false;
2584
713
}
2585
714
 
2586
715
/**
2593
722
  @param var_name               Variable name
2594
723
*/
2595
724
 
2596
 
void create_select_for_variable(const char *var_name)
 
725
void create_select_for_variable(Session *session, const char *var_name)
2597
726
{
2598
 
  Session *session;
2599
 
  LEX *lex;
2600
 
  LEX_STRING tmp, null_lex_string;
2601
 
  Item *var;
2602
 
  char buff[MAX_SYS_VAR_LENGTH*2+4+8], *end;
2603
 
 
2604
 
  session= current_session;
2605
 
  lex= session->lex;
2606
 
  mysql_init_select(lex);
2607
 
  lex->sql_command= SQLCOM_SELECT;
 
727
  LEX& lex= session->lex();
 
728
  init_select(&lex);
 
729
  lex.sql_command= SQLCOM_SELECT;
 
730
  lex_string_t tmp;
2608
731
  tmp.str= (char*) var_name;
2609
732
  tmp.length=strlen(var_name);
 
733
  lex_string_t null_lex_string;
2610
734
  memset(&null_lex_string.str, 0, sizeof(null_lex_string));
2611
735
  /*
2612
736
    We set the name of Item to @@session.var_name because that then is used
2613
737
    as the column name in the output.
2614
738
  */
2615
 
  if ((var= get_system_var(session, OPT_SESSION, tmp, null_lex_string)))
 
739
  if (Item* var= get_system_var(session, OPT_SESSION, tmp, null_lex_string))
2616
740
  {
2617
 
    end= strxmov(buff, "@@session.", var_name, NULL);
2618
 
    var->set_name(buff, end-buff, system_charset_info);
2619
 
    add_item_to_list(session, var);
 
741
    char buff[MAX_SYS_VAR_LENGTH*2+4+8];
 
742
    char *end= buff;
 
743
    end+= snprintf(buff, sizeof(buff), "@@session.%s", var_name);
 
744
    var->set_name(buff, end-buff);
 
745
    session->add_item_to_list(var);
2620
746
  }
2621
 
  return;
2622
 
}
2623
 
 
2624
 
 
2625
 
void mysql_init_multi_delete(LEX *lex)
2626
 
{
2627
 
  lex->sql_command=  SQLCOM_DELETE_MULTI;
2628
 
  mysql_init_select(lex);
2629
 
  lex->select_lex.select_limit= 0;
2630
 
  lex->unit.select_limit_cnt= HA_POS_ERROR;
2631
 
  lex->select_lex.table_list.save_and_clear(&lex->auxiliary_table_list);
2632
 
  lex->lock_option= TL_READ;
2633
 
  lex->query_tables= 0;
2634
 
  lex->query_tables_last= &lex->query_tables;
2635
 
}
2636
 
 
2637
 
 
2638
 
/*
2639
 
  When you modify mysql_parse(), you may need to mofify
2640
 
  mysql_test_parse_for_slave() in this same file.
2641
 
*/
 
747
}
 
748
 
2642
749
 
2643
750
/**
2644
751
  Parse a query.
2646
753
  @param       session     Current thread
2647
754
  @param       inBuf   Begining of the query text
2648
755
  @param       length  Length of the query text
2649
 
  @param[out]  found_semicolon For multi queries, position of the character of
2650
 
                               the next query in the query text.
2651
756
*/
2652
757
 
2653
 
void mysql_parse(Session *session, const char *inBuf, uint32_t length,
2654
 
                 const char ** found_semicolon)
 
758
void parse(Session& session, const char *inBuf, uint32_t length)
2655
759
{
2656
 
  /*
2657
 
    Warning.
2658
 
    The purpose of query_cache_send_result_to_client() is to lookup the
2659
 
    query in the query cache first, to avoid parsing and executing it.
2660
 
    So, the natural implementation would be to:
2661
 
    - first, call query_cache_send_result_to_client,
2662
 
    - second, if caching failed, initialise the lexical and syntactic parser.
2663
 
    The problem is that the query cache depends on a clean initialization
2664
 
    of (among others) lex->safe_to_cache_query and session->server_status,
2665
 
    which are reset respectively in
2666
 
    - lex_start()
2667
 
    - mysql_reset_session_for_next_command()
2668
 
    So, initializing the lexical analyser *before* using the query cache
2669
 
    is required for the cache to work properly.
2670
 
    FIXME: cleanup the dependencies in the code to simplify this.
2671
 
  */
2672
 
  lex_start(session);
2673
 
  mysql_reset_session_for_next_command(session);
2674
 
 
 
760
  session.lex().start(&session);
 
761
  session.reset_for_next_command();
 
762
  /* Check if the Query is Cached if and return true if yes
 
763
   * TODO the plugin has to make sure that the query is cacheble
 
764
   * by setting the query_safe_cache param to TRUE
 
765
   */
 
766
  if (plugin::QueryCache::isCached(&session) && not plugin::QueryCache::sendCachedResultset(&session))
 
767
      return;
 
768
  Lex_input_stream lip(&session, inBuf, length);
 
769
  if (parse_sql(&session, &lip))
 
770
    assert(session.is_error());
 
771
  else if (not session.is_error())
2675
772
  {
2676
 
    LEX *lex= session->lex;
2677
 
 
2678
 
    Lex_input_stream lip(session, inBuf, length);
2679
 
 
2680
 
    bool err= parse_sql(session, &lip);
2681
 
    *found_semicolon= lip.found_semicolon;
2682
 
 
2683
 
    if (!err)
2684
 
    {
2685
 
      {
2686
 
        if (! session->is_error())
2687
 
        {
2688
 
          /*
2689
 
            Binlog logs a string starting from session->query and having length
2690
 
            session->query_length; so we set session->query_length correctly (to not
2691
 
            log several statements in one event, when we executed only first).
2692
 
            We set it to not see the ';' (otherwise it would get into binlog
2693
 
            and Query_log_event::print() would give ';;' output).
2694
 
            This also helps display only the current query in SHOW
2695
 
            PROCESSLIST.
2696
 
            Note that we don't need LOCK_thread_count to modify query_length.
2697
 
          */
2698
 
          if (*found_semicolon &&
2699
 
              (session->query_length= (ulong)(*found_semicolon - session->query)))
2700
 
            session->query_length--;
2701
 
          /* Actually execute the query */
2702
 
          mysql_execute_command(session);
2703
 
        }
2704
 
      }
2705
 
    }
2706
 
    else
2707
 
    {
2708
 
      assert(session->is_error());
2709
 
    }
2710
 
    lex->unit.cleanup();
2711
 
    session->set_proc_info("freeing items");
2712
 
    session->end_statement();
2713
 
    session->cleanup_after_query();
2714
 
    assert(session->change_list.is_empty());
 
773
    DRIZZLE_QUERY_EXEC_START(session.getQueryString()->c_str(), session.thread_id,
 
774
                             const_cast<const char *>(session.schema()->c_str()));
 
775
    // Implement Views here --Brian
 
776
    /* Actually execute the query */
 
777
    try
 
778
    {
 
779
      execute_command(&session);
 
780
    }
 
781
    catch (...)
 
782
    {
 
783
      // Just try to catch any random failures that could have come
 
784
      // during execution.
 
785
      DRIZZLE_ABORT;
 
786
    }
 
787
    DRIZZLE_QUERY_EXEC_DONE(0);
2715
788
  }
2716
 
 
2717
 
  return;
2718
 
}
2719
 
 
2720
 
 
2721
 
/*
2722
 
  Usable by the replication SQL thread only: just parse a query to know if it
2723
 
  can be ignored because of replicate-*-table rules.
2724
 
 
2725
 
  @retval
2726
 
    0   cannot be ignored
2727
 
  @retval
2728
 
    1   can be ignored
2729
 
*/
2730
 
 
2731
 
bool mysql_test_parse_for_slave(Session *session, char *inBuf, uint32_t length)
2732
 
{
2733
 
  LEX *lex= session->lex;
2734
 
  bool error= 0;
2735
 
 
2736
 
  Lex_input_stream lip(session, inBuf, length);
2737
 
  lex_start(session);
2738
 
  mysql_reset_session_for_next_command(session);
2739
 
 
2740
 
  if (!parse_sql(session, &lip) &&
2741
 
      all_tables_not_ok(session,(TableList*) lex->select_lex.table_list.first))
2742
 
    error= 1;                  /* Ignore question */
2743
 
  session->end_statement();
2744
 
  session->cleanup_after_query();
2745
 
  return(error);
2746
 
}
2747
 
 
 
789
  session.lex().unit.cleanup();
 
790
  session.set_proc_info("freeing items");
 
791
  session.end_statement();
 
792
  session.cleanup_after_query();
 
793
  session.times.set_end_timer(session);
 
794
}
2748
795
 
2749
796
 
2750
797
/**
2754
801
    Return 0 if ok
2755
802
*/
2756
803
 
2757
 
bool add_field_to_list(Session *session, LEX_STRING *field_name, enum_field_types type,
2758
 
                       char *length, char *decimals,
 
804
bool add_field_to_list(Session *session, lex_string_t *field_name, enum_field_types type,
 
805
                       const char *length, const char *decimals,
2759
806
                       uint32_t type_modifier,
2760
807
                       enum column_format_type column_format,
2761
808
                       Item *default_value, Item *on_update_value,
2762
 
                       LEX_STRING *comment,
2763
 
                       char *change,
2764
 
                       List<String> *interval_list, const CHARSET_INFO * const cs,
2765
 
                       virtual_column_info *vcol_info)
 
809
                       lex_string_t *comment,
 
810
                       const char *change,
 
811
                       List<String> *interval_list, const charset_info_st * const cs)
2766
812
{
2767
 
  register Create_field *new_field;
2768
 
  LEX  *lex= session->lex;
 
813
  register CreateField *new_field;
 
814
  LEX  *lex= &session->lex();
 
815
  statement::AlterTable *statement= (statement::AlterTable *)lex->statement;
2769
816
 
2770
817
  if (check_identifier_name(field_name, ER_TOO_LONG_IDENT))
2771
 
    return(1);                          /* purecov: inspected */
 
818
    return true;
2772
819
 
2773
820
  if (type_modifier & PRI_KEY_FLAG)
2774
821
  {
2775
822
    Key *key;
2776
823
    lex->col_list.push_back(new Key_part_spec(*field_name, 0));
2777
 
    key= new Key(Key::PRIMARY, null_lex_str,
 
824
    key= new Key(Key::PRIMARY, null_lex_string(),
2778
825
                      &default_key_create_info,
2779
826
                      0, lex->col_list);
2780
 
    lex->alter_info.key_list.push_back(key);
2781
 
    lex->col_list.empty();
 
827
    statement->alter_info.key_list.push_back(key);
 
828
    lex->col_list.clear();
2782
829
  }
2783
830
  if (type_modifier & (UNIQUE_FLAG | UNIQUE_KEY_FLAG))
2784
831
  {
2785
832
    Key *key;
2786
833
    lex->col_list.push_back(new Key_part_spec(*field_name, 0));
2787
 
    key= new Key(Key::UNIQUE, null_lex_str,
 
834
    key= new Key(Key::UNIQUE, null_lex_string(),
2788
835
                 &default_key_create_info, 0,
2789
836
                 lex->col_list);
2790
 
    lex->alter_info.key_list.push_back(key);
2791
 
    lex->col_list.empty();
 
837
    statement->alter_info.key_list.push_back(key);
 
838
    lex->col_list.clear();
2792
839
  }
2793
840
 
2794
841
  if (default_value)
2795
842
  {
2796
 
    /* 
 
843
    /*
2797
844
      Default value should be literal => basic constants =>
2798
845
      no need fix_fields()
2799
 
      
2800
 
      We allow only one function as part of default value - 
 
846
 
 
847
      We allow only one function as part of default value -
2801
848
      NOW() as default for TIMESTAMP type.
2802
849
    */
2803
 
    if (default_value->type() == Item::FUNC_ITEM && 
 
850
    if (default_value->type() == Item::FUNC_ITEM &&
2804
851
        !(((Item_func*)default_value)->functype() == Item_func::NOW_FUNC &&
2805
 
         type == DRIZZLE_TYPE_TIMESTAMP))
 
852
         (type == DRIZZLE_TYPE_TIMESTAMP or type == DRIZZLE_TYPE_MICROTIME)))
2806
853
    {
2807
854
      my_error(ER_INVALID_DEFAULT, MYF(0), field_name->str);
2808
 
      return(1);
 
855
      return true;
2809
856
    }
2810
857
    else if (default_value->type() == Item::NULL_ITEM)
2811
858
    {
2812
859
      default_value= 0;
2813
 
      if ((type_modifier & (NOT_NULL_FLAG | AUTO_INCREMENT_FLAG)) ==
2814
 
          NOT_NULL_FLAG)
 
860
      if ((type_modifier & (NOT_NULL_FLAG | AUTO_INCREMENT_FLAG)) == NOT_NULL_FLAG)
2815
861
      {
2816
862
        my_error(ER_INVALID_DEFAULT, MYF(0), field_name->str);
2817
 
        return(1);
 
863
        return true;
2818
864
      }
2819
865
    }
2820
866
    else if (type_modifier & AUTO_INCREMENT_FLAG)
2821
867
    {
2822
868
      my_error(ER_INVALID_DEFAULT, MYF(0), field_name->str);
2823
 
      return(1);
 
869
      return true;
2824
870
    }
2825
871
  }
2826
872
 
2827
 
  if (on_update_value && type != DRIZZLE_TYPE_TIMESTAMP)
 
873
  if (on_update_value && (type != DRIZZLE_TYPE_TIMESTAMP and type != DRIZZLE_TYPE_MICROTIME))
2828
874
  {
2829
875
    my_error(ER_INVALID_ON_UPDATE, MYF(0), field_name->str);
2830
 
    return(1);
 
876
    return true;
2831
877
  }
2832
878
 
2833
 
  if (!(new_field= new Create_field()) ||
2834
 
      new_field->init(session, field_name->str, type, length, decimals, type_modifier,
2835
 
                      default_value, on_update_value, comment, change,
2836
 
                      interval_list, cs, 0, column_format,
2837
 
                      vcol_info))
2838
 
    return(1);
 
879
  new_field= new CreateField;
 
880
  if (new_field->init(session, field_name->str, type, length, decimals,
 
881
                         type_modifier, comment, change, interval_list, cs, 0, column_format)
 
882
      || new_field->setDefaultValue(default_value, on_update_value))
 
883
    return true;
2839
884
 
2840
 
  lex->alter_info.create_list.push_back(new_field);
 
885
  statement->alter_info.create_list.push_back(new_field);
2841
886
  lex->last_field=new_field;
2842
 
  return(0);
2843
 
}
2844
 
 
2845
 
 
2846
 
/** Store position for column in ALTER TABLE .. ADD column. */
2847
 
 
2848
 
void store_position_for_column(const char *name)
2849
 
{
2850
 
  current_session->lex->last_field->after=const_cast<char*> (name);
2851
 
}
2852
 
 
2853
 
bool
2854
 
add_proc_to_list(Session* session, Item *item)
2855
 
{
2856
 
  order_st *order;
2857
 
  Item  **item_ptr;
2858
 
 
2859
 
  if (!(order = (order_st *) session->alloc(sizeof(order_st)+sizeof(Item*))))
2860
 
    return 1;
2861
 
  item_ptr = (Item**) (order+1);
2862
 
  *item_ptr= item;
2863
 
  order->item=item_ptr;
2864
 
  order->free_me=0;
2865
 
  session->lex->proc_list.link_in_list((unsigned char*) order,(unsigned char**) &order->next);
2866
 
  return 0;
2867
 
}
2868
 
 
2869
 
 
2870
 
/**
2871
 
  save order by and tables in own lists.
2872
 
*/
2873
 
 
2874
 
bool add_to_list(Session *session, SQL_LIST &list,Item *item,bool asc)
2875
 
{
2876
 
  order_st *order;
2877
 
  if (!(order = (order_st *) session->alloc(sizeof(order_st))))
2878
 
    return(1);
2879
 
  order->item_ptr= item;
2880
 
  order->item= &order->item_ptr;
2881
 
  order->asc = asc;
2882
 
  order->free_me=0;
2883
 
  order->used=0;
2884
 
  order->counter_used= 0;
2885
 
  list.link_in_list((unsigned char*) order,(unsigned char**) &order->next);
2886
 
  return(0);
 
887
 
 
888
  return false;
2887
889
}
2888
890
 
2889
891
 
2906
908
    \#  Pointer to TableList element added to the total table list
2907
909
*/
2908
910
 
2909
 
TableList *st_select_lex::add_table_to_list(Session *session,
2910
 
                                             Table_ident *table,
2911
 
                                             LEX_STRING *alias,
2912
 
                                             uint32_t table_options,
2913
 
                                             thr_lock_type lock_type,
2914
 
                                             List<Index_hint> *index_hints_arg,
2915
 
                                             LEX_STRING *option)
 
911
TableList *Select_Lex::add_table_to_list(Session *session,
 
912
                                         Table_ident *table,
 
913
                                         lex_string_t *alias,
 
914
                                         const bitset<NUM_OF_TABLE_OPTIONS>& table_options,
 
915
                                         thr_lock_type lock_type,
 
916
                                         List<Index_hint> *index_hints_arg,
 
917
                                         lex_string_t *option)
2916
918
{
2917
 
  register TableList *ptr;
2918
919
  TableList *previous_table_ref; /* The table preceding the current one. */
2919
 
  char *alias_str;
2920
 
  LEX *lex= session->lex;
 
920
  LEX *lex= &session->lex();
2921
921
 
2922
922
  if (!table)
2923
 
    return(0);                          // End of memory
2924
 
  alias_str= alias ? alias->str : table->table.str;
2925
 
  if (!test(table_options & TL_OPTION_ALIAS) && 
 
923
    return NULL;                                // End of memory
 
924
  const char* alias_str= alias ? alias->str : table->table.str;
 
925
  if (! table_options.test(TL_OPTION_ALIAS) &&
2926
926
      check_table_name(table->table.str, table->table.length))
2927
927
  {
2928
928
    my_error(ER_WRONG_TABLE_NAME, MYF(0), table->table.str);
2929
 
    return(0);
 
929
    return NULL;
2930
930
  }
2931
931
 
2932
 
  if (table->is_derived_table() == false && table->db.str &&
2933
 
      check_db_name(&table->db))
 
932
  if (not table->is_derived_table() && table->db.str)
2934
933
  {
2935
 
    my_error(ER_WRONG_DB_NAME, MYF(0), table->db.str);
2936
 
    return(0);
 
934
    my_casedn_str(files_charset_info, table->db.str);
 
935
 
 
936
    identifier::Schema schema_identifier(string(table->db.str));
 
937
    if (not schema::check(*session, schema_identifier))
 
938
    {
 
939
      my_error(ER_WRONG_DB_NAME, MYF(0), table->db.str);
 
940
      return NULL;
 
941
    }
2937
942
  }
2938
943
 
2939
944
  if (!alias)                                   /* Alias is case sensitive */
2940
945
  {
2941
946
    if (table->sel)
2942
947
    {
2943
 
      my_message(ER_DERIVED_MUST_HAVE_ALIAS,
2944
 
                 ER(ER_DERIVED_MUST_HAVE_ALIAS), MYF(0));
2945
 
      return(0);
 
948
      my_message(ER_DERIVED_MUST_HAVE_ALIAS, ER(ER_DERIVED_MUST_HAVE_ALIAS), MYF(0));
 
949
      return NULL;
2946
950
    }
2947
 
    if (!(alias_str= (char*) session->memdup(alias_str,table->table.length+1)))
2948
 
      return(0);
 
951
    alias_str= (char*) session->mem.memdup(alias_str,table->table.length+1);
2949
952
  }
2950
 
  if (!(ptr = (TableList *) session->calloc(sizeof(TableList))))
2951
 
    return(0);                          /* purecov: inspected */
 
953
  TableList *ptr = (TableList *) session->mem.calloc(sizeof(TableList));
 
954
 
 
955
  char* name;
 
956
  size_t name_size;
2952
957
  if (table->db.str)
2953
958
  {
2954
 
    ptr->is_fqtn= true;
2955
 
    ptr->db= table->db.str;
2956
 
    ptr->db_length= table->db.length;
 
959
    ptr->setIsFqtn(true);
 
960
    ptr->setSchemaName(table->db.str);
2957
961
  }
2958
 
  else if (lex->copy_db_to(&ptr->db, &ptr->db_length))
2959
 
    return(0);
 
962
  else if (lex->session->copy_db_to(name, name_size))
 
963
    return NULL;
2960
964
  else
2961
 
    ptr->is_fqtn= false;
 
965
  {
 
966
    ptr->setIsFqtn(false);
 
967
    ptr->setSchemaName(name);
 
968
  }
2962
969
 
2963
970
  ptr->alias= alias_str;
2964
 
  ptr->is_alias= alias ? true : false;
2965
 
  if (lower_case_table_names && table->table.length)
2966
 
    table->table.length= my_casedn_str(files_charset_info, table->table.str);
2967
 
  ptr->table_name=table->table.str;
2968
 
  ptr->table_name_length=table->table.length;
 
971
  ptr->setIsAlias(alias ? true : false);
 
972
  ptr->setTableName(table->table.str);
2969
973
  ptr->lock_type=   lock_type;
2970
 
  ptr->lock_timeout= -1;      /* default timeout */
2971
 
  ptr->lock_transactional= 1; /* allow transactional locks */
2972
 
  ptr->updating=    test(table_options & TL_OPTION_UPDATING);
2973
 
  ptr->force_index= test(table_options & TL_OPTION_FORCE_INDEX);
2974
 
  ptr->ignore_leaves= test(table_options & TL_OPTION_IGNORE_LEAVES);
 
974
  ptr->force_index= table_options.test(TL_OPTION_FORCE_INDEX);
 
975
  ptr->ignore_leaves= table_options.test(TL_OPTION_IGNORE_LEAVES);
2975
976
  ptr->derived=     table->sel;
2976
 
  if (!ptr->derived && !my_strcasecmp(system_charset_info, ptr->db,
2977
 
                                      INFORMATION_SCHEMA_NAME.c_str()))
2978
 
  {
2979
 
    ST_SCHEMA_TABLE *schema_table= find_schema_table(session, ptr->table_name);
2980
 
    if (!schema_table ||
2981
 
        (schema_table->hidden && 
2982
 
         ((sql_command_flags[lex->sql_command].test(CF_BIT_STATUS_COMMAND)) == 0 ||
2983
 
          /*
2984
 
            this check is used for show columns|keys from I_S hidden table
2985
 
          */
2986
 
          lex->sql_command == SQLCOM_SHOW_FIELDS ||
2987
 
          lex->sql_command == SQLCOM_SHOW_KEYS)))
2988
 
    {
2989
 
      my_error(ER_UNKNOWN_TABLE, MYF(0),
2990
 
               ptr->table_name, INFORMATION_SCHEMA_NAME.c_str());
2991
 
      return(0);
2992
 
    }
2993
 
    ptr->schema_table_name= ptr->table_name;
2994
 
    ptr->schema_table= schema_table;
2995
 
  }
2996
977
  ptr->select_lex=  lex->current_select;
2997
 
  ptr->cacheable_table= 1;
2998
978
  ptr->index_hints= index_hints_arg;
2999
979
  ptr->option= option ? option->str : 0;
3000
980
  /* check that used name is unique */
3001
981
  if (lock_type != TL_IGNORE)
3002
982
  {
3003
983
    TableList *first_table= (TableList*) table_list.first;
3004
 
    for (TableList *tables= first_table ;
3005
 
         tables ;
3006
 
         tables=tables->next_local)
 
984
    for (TableList *tables= first_table; tables; tables= tables->next_local)
3007
985
    {
3008
 
      if (!my_strcasecmp(table_alias_charset, alias_str, tables->alias) &&
3009
 
          !strcmp(ptr->db, tables->db))
 
986
      if (not my_strcasecmp(table_alias_charset, alias_str, tables->alias) &&
 
987
        not my_strcasecmp(system_charset_info, ptr->getSchemaName(), tables->getSchemaName()))
3010
988
      {
3011
 
        my_error(ER_NONUNIQ_TABLE, MYF(0), alias_str); /* purecov: tested */
3012
 
        return(0);                              /* purecov: tested */
 
989
        my_error(ER_NONUNIQ_TABLE, MYF(0), alias_str);
 
990
        return NULL;
3013
991
      }
3014
992
    }
3015
993
  }
3016
994
  /* Store the table reference preceding the current one. */
3017
 
  if (table_list.elements > 0)
 
995
  if (table_list.size() > 0)
3018
996
  {
3019
997
    /*
3020
998
      table_list.next points to the last inserted TableList->next_local'
3044
1022
  ptr->next_name_resolution_table= NULL;
3045
1023
  /* Link table in global list (all used tables) */
3046
1024
  lex->add_to_query_tables(ptr);
3047
 
  return(ptr);
 
1025
  return ptr;
3048
1026
}
3049
1027
 
3050
1028
 
3054
1032
    The function initializes a structure of the TableList type
3055
1033
    for a nested join. It sets up its nested join list as empty.
3056
1034
    The created structure is added to the front of the current
3057
 
    join list in the st_select_lex object. Then the function
 
1035
    join list in the Select_Lex object. Then the function
3058
1036
    changes the current nest level for joins to refer to the newly
3059
1037
    created empty list after having saved the info on the old level
3060
1038
    in the initialized structure.
3067
1045
    1   otherwise
3068
1046
*/
3069
1047
 
3070
 
bool st_select_lex::init_nested_join(Session *session)
 
1048
void Select_Lex::init_nested_join(Session& session)
3071
1049
{
3072
 
  TableList *ptr;
3073
 
  nested_join_st *nested_join;
3074
 
 
3075
 
  if (!(ptr= (TableList*) session->calloc(ALIGN_SIZE(sizeof(TableList))+
3076
 
                                       sizeof(nested_join_st))))
3077
 
    return(1);
3078
 
  nested_join= ptr->nested_join=
3079
 
    ((nested_join_st*) ((unsigned char*) ptr + ALIGN_SIZE(sizeof(TableList))));
3080
 
 
 
1050
  TableList* ptr= (TableList*) session.mem.calloc(ALIGN_SIZE(sizeof(TableList)) + sizeof(NestedJoin));
 
1051
  ptr->setNestedJoin(((NestedJoin*) ((unsigned char*) ptr + ALIGN_SIZE(sizeof(TableList)))));
 
1052
  NestedJoin* nested_join= ptr->getNestedJoin();
3081
1053
  join_list->push_front(ptr);
3082
 
  ptr->embedding= embedding;
3083
 
  ptr->join_list= join_list;
 
1054
  ptr->setEmbedding(embedding);
 
1055
  ptr->setJoinList(join_list);
3084
1056
  ptr->alias= (char*) "(nested_join)";
3085
1057
  embedding= ptr;
3086
1058
  join_list= &nested_join->join_list;
3087
 
  join_list->empty();
3088
 
  return(0);
 
1059
  join_list->clear();
3089
1060
}
3090
1061
 
3091
1062
 
3103
1074
    - 0, otherwise
3104
1075
*/
3105
1076
 
3106
 
TableList *st_select_lex::end_nested_join(Session *)
 
1077
TableList *Select_Lex::end_nested_join(Session *)
3107
1078
{
3108
1079
  TableList *ptr;
3109
 
  nested_join_st *nested_join;
 
1080
  NestedJoin *nested_join;
3110
1081
 
3111
1082
  assert(embedding);
3112
1083
  ptr= embedding;
3113
 
  join_list= ptr->join_list;
3114
 
  embedding= ptr->embedding;
3115
 
  nested_join= ptr->nested_join;
3116
 
  if (nested_join->join_list.elements == 1)
 
1084
  join_list= ptr->getJoinList();
 
1085
  embedding= ptr->getEmbedding();
 
1086
  nested_join= ptr->getNestedJoin();
 
1087
  if (nested_join->join_list.size() == 1)
3117
1088
  {
3118
 
    TableList *embedded= nested_join->join_list.head();
 
1089
    TableList *embedded= &nested_join->join_list.front();
3119
1090
    join_list->pop();
3120
 
    embedded->join_list= join_list;
3121
 
    embedded->embedding= embedding;
 
1091
    embedded->setJoinList(join_list);
 
1092
    embedded->setEmbedding(embedding);
3122
1093
    join_list->push_front(embedded);
3123
1094
    ptr= embedded;
3124
1095
  }
3125
 
  else if (nested_join->join_list.elements == 0)
 
1096
  else if (nested_join->join_list.size() == 0)
3126
1097
  {
3127
1098
    join_list->pop();
3128
 
    ptr= 0;                                     // return value
 
1099
    ptr= NULL;                                     // return value
3129
1100
  }
3130
 
  return(ptr);
 
1101
  return ptr;
3131
1102
}
3132
1103
 
3133
1104
 
3144
1115
    \#  Pointer to TableList element created for the new nested join
3145
1116
*/
3146
1117
 
3147
 
TableList *st_select_lex::nest_last_join(Session *session)
 
1118
TableList *Select_Lex::nest_last_join(Session *session)
3148
1119
{
3149
 
  TableList *ptr;
3150
 
  nested_join_st *nested_join;
3151
 
  List<TableList> *embedded_list;
3152
 
 
3153
 
  if (!(ptr= (TableList*) session->calloc(ALIGN_SIZE(sizeof(TableList))+
3154
 
                                       sizeof(nested_join_st))))
3155
 
    return(0);
3156
 
  nested_join= ptr->nested_join=
3157
 
    ((nested_join_st*) ((unsigned char*) ptr + ALIGN_SIZE(sizeof(TableList))));
3158
 
 
3159
 
  ptr->embedding= embedding;
3160
 
  ptr->join_list= join_list;
 
1120
  TableList* ptr= (TableList*) session->mem.calloc(ALIGN_SIZE(sizeof(TableList)) + sizeof(NestedJoin));
 
1121
  ptr->setNestedJoin(((NestedJoin*) ((unsigned char*) ptr + ALIGN_SIZE(sizeof(TableList)))));
 
1122
  NestedJoin* nested_join= ptr->getNestedJoin();
 
1123
  ptr->setEmbedding(embedding);
 
1124
  ptr->setJoinList(join_list);
3161
1125
  ptr->alias= (char*) "(nest_last_join)";
3162
 
  embedded_list= &nested_join->join_list;
3163
 
  embedded_list->empty();
 
1126
  List<TableList>* embedded_list= &nested_join->join_list;
 
1127
  embedded_list->clear();
3164
1128
 
3165
1129
  for (uint32_t i=0; i < 2; i++)
3166
1130
  {
3167
1131
    TableList *table= join_list->pop();
3168
 
    table->join_list= embedded_list;
3169
 
    table->embedding= ptr;
 
1132
    table->setJoinList(embedded_list);
 
1133
    table->setEmbedding(ptr);
3170
1134
    embedded_list->push_back(table);
3171
1135
    if (table->natural_join)
3172
1136
    {
3181
1145
  }
3182
1146
  join_list->push_front(ptr);
3183
1147
  nested_join->used_tables= nested_join->not_null_tables= (table_map) 0;
3184
 
  return(ptr);
 
1148
  return ptr;
3185
1149
}
3186
1150
 
3187
1151
 
3189
1153
  Add a table to the current join list.
3190
1154
 
3191
1155
    The function puts a table in front of the current join list
3192
 
    of st_select_lex object.
 
1156
    of Select_Lex object.
3193
1157
    Thus, joined tables are put into this list in the reverse order
3194
1158
    (the most outer join operation follows first).
3195
1159
 
3199
1163
    None
3200
1164
*/
3201
1165
 
3202
 
void st_select_lex::add_joined_table(TableList *table)
 
1166
void Select_Lex::add_joined_table(TableList *table)
3203
1167
{
3204
1168
  join_list->push_front(table);
3205
 
  table->join_list= join_list;
3206
 
  table->embedding= embedding;
3207
 
  return;
 
1169
  table->setJoinList(join_list);
 
1170
  table->setEmbedding(embedding);
3208
1171
}
3209
1172
 
3210
1173
 
3239
1202
    - 0, otherwise
3240
1203
*/
3241
1204
 
3242
 
TableList *st_select_lex::convert_right_join()
 
1205
TableList *Select_Lex::convert_right_join()
3243
1206
{
3244
1207
  TableList *tab2= join_list->pop();
3245
1208
  TableList *tab1= join_list->pop();
3248
1211
  join_list->push_front(tab1);
3249
1212
  tab1->outer_join|= JOIN_TYPE_RIGHT;
3250
1213
 
3251
 
  return(tab1);
 
1214
  return tab1;
3252
1215
}
3253
1216
 
3254
1217
/**
3262
1225
    query
3263
1226
*/
3264
1227
 
3265
 
void st_select_lex::set_lock_for_tables(thr_lock_type lock_type)
 
1228
void Select_Lex::set_lock_for_tables(thr_lock_type lock_type)
3266
1229
{
3267
 
  bool for_update= lock_type >= TL_READ_NO_INSERT;
3268
 
 
3269
1230
  for (TableList *tables= (TableList*) table_list.first;
3270
1231
       tables;
3271
1232
       tables= tables->next_local)
3272
1233
  {
3273
1234
    tables->lock_type= lock_type;
3274
 
    tables->updating=  for_update;
3275
1235
  }
3276
 
  return;
3277
1236
}
3278
1237
 
3279
1238
 
3280
1239
/**
3281
 
  Create a fake SELECT_LEX for a unit.
 
1240
  Create a fake Select_Lex for a unit.
3282
1241
 
3283
 
    The method create a fake SELECT_LEX object for a unit.
 
1242
    The method create a fake Select_Lex object for a unit.
3284
1243
    This object is created for any union construct containing a union
3285
1244
    operation and also for any single select union construct of the form
3286
1245
    @verbatim
3287
 
    (SELECT ... order_st BY order_list [LIMIT n]) order_st BY ... 
 
1246
    (SELECT ... ORDER BY order_list [LIMIT n]) ORDER BY ...
3288
1247
    @endvarbatim
3289
1248
    or of the form
3290
1249
    @varbatim
3291
 
    (SELECT ... order_st BY LIMIT n) order_st BY ...
 
1250
    (SELECT ... ORDER BY LIMIT n) ORDER BY ...
3292
1251
    @endvarbatim
3293
 
  
 
1252
 
3294
1253
  @param session_arg               thread handle
3295
1254
 
3296
1255
  @note
3303
1262
    0     on success
3304
1263
*/
3305
1264
 
3306
 
bool st_select_lex_unit::add_fake_select_lex(Session *session_arg)
 
1265
bool Select_Lex_Unit::add_fake_select_lex(Session *session_arg)
3307
1266
{
3308
 
  SELECT_LEX *first_sl= first_select();
 
1267
  Select_Lex *first_sl= first_select();
3309
1268
  assert(!fake_select_lex);
3310
1269
 
3311
 
  if (!(fake_select_lex= new (session_arg->mem_root) SELECT_LEX()))
3312
 
      return(1);
3313
 
  fake_select_lex->include_standalone(this, 
3314
 
                                      (SELECT_LEX_NODE**)&fake_select_lex);
 
1270
  fake_select_lex= new (session_arg->mem_root) Select_Lex();
 
1271
  fake_select_lex->include_standalone(this, (Select_Lex_Node**)&fake_select_lex);
3315
1272
  fake_select_lex->select_number= INT_MAX;
3316
 
  fake_select_lex->parent_lex= session_arg->lex; /* Used in init_query. */
 
1273
  fake_select_lex->parent_lex= &session_arg->lex(); /* Used in init_query. */
3317
1274
  fake_select_lex->make_empty_select();
3318
1275
  fake_select_lex->linkage= GLOBAL_OPTIONS_TYPE;
3319
1276
  fake_select_lex->select_limit= 0;
3320
1277
 
3321
1278
  fake_select_lex->context.outer_context=first_sl->context.outer_context;
3322
 
  /* allow item list resolving in fake select for order_st BY */
 
1279
  /* allow item list resolving in fake select for ORDER BY */
3323
1280
  fake_select_lex->context.resolve_in_select_list= true;
3324
1281
  fake_select_lex->context.select_lex= fake_select_lex;
3325
1282
 
3326
1283
  if (!is_union())
3327
1284
  {
3328
 
    /* 
3329
 
      This works only for 
3330
 
      (SELECT ... order_st BY list [LIMIT n]) order_st BY order_list [LIMIT m],
3331
 
      (SELECT ... LIMIT n) order_st BY order_list [LIMIT m]
 
1285
    /*
 
1286
      This works only for
 
1287
      (SELECT ... ORDER BY list [LIMIT n]) ORDER BY order_list [LIMIT m],
 
1288
      (SELECT ... LIMIT n) ORDER BY order_list [LIMIT m]
3332
1289
      just before the parser starts processing order_list
3333
 
    */ 
 
1290
    */
3334
1291
    global_parameters= fake_select_lex;
3335
1292
    fake_select_lex->no_table_names_allowed= 1;
3336
 
    session_arg->lex->current_select= fake_select_lex;
 
1293
    session_arg->lex().current_select= fake_select_lex;
3337
1294
  }
3338
 
  session_arg->lex->pop_context();
3339
 
  return(0);
 
1295
  session_arg->lex().pop_context();
 
1296
  return 0;
3340
1297
}
3341
1298
 
3342
1299
 
3359
1316
    true   if a memory allocation error occured
3360
1317
*/
3361
1318
 
3362
 
bool
3363
 
push_new_name_resolution_context(Session *session,
3364
 
                                 TableList *left_op, TableList *right_op)
 
1319
void push_new_name_resolution_context(Session& session, TableList& left_op, TableList& right_op)
3365
1320
{
3366
 
  Name_resolution_context *on_context;
3367
 
  if (!(on_context= new (session->mem_root) Name_resolution_context))
3368
 
    return true;
 
1321
  Name_resolution_context *on_context= new (session.mem_root) Name_resolution_context;
3369
1322
  on_context->init();
3370
 
  on_context->first_name_resolution_table=
3371
 
    left_op->first_leaf_for_name_resolution();
3372
 
  on_context->last_name_resolution_table=
3373
 
    right_op->last_leaf_for_name_resolution();
3374
 
  return session->lex->push_context(on_context);
 
1323
  on_context->first_name_resolution_table= left_op.first_leaf_for_name_resolution();
 
1324
  on_context->last_name_resolution_table= right_op.last_leaf_for_name_resolution();
 
1325
  session.lex().push_context(on_context);
3375
1326
}
3376
1327
 
3377
1328
 
3443
1394
*/
3444
1395
 
3445
1396
void add_join_natural(TableList *a, TableList *b, List<String> *using_fields,
3446
 
                      SELECT_LEX *lex)
 
1397
                      Select_Lex *lex)
3447
1398
{
3448
1399
  b->natural_join= a;
3449
1400
  lex->prev_join_using= using_fields;
3451
1402
 
3452
1403
 
3453
1404
/**
3454
 
  Reload/resets privileges and the different caches.
3455
 
 
3456
 
  @param session Thread handler (can be NULL!)
3457
 
  @param options What should be reset/reloaded (tables, privileges, slave...)
3458
 
  @param tables Tables to flush (if any)
3459
 
  @param write_to_binlog True if we can write to the binlog.
3460
 
               
3461
 
  @note Depending on 'options', it may be very bad to write the
3462
 
    query to the binlog (e.g. FLUSH SLAVE); this is a
3463
 
    pointer where reload_cache() will put 0 if
3464
 
    it thinks we really should not write to the binlog.
3465
 
    Otherwise it will put 1.
3466
 
 
3467
 
  @return Error status code
3468
 
    @retval 0 Ok
3469
 
    @retval !=0  Error; session->killed is set or session->is_error() is true
3470
 
*/
3471
 
 
3472
 
bool reload_cache(Session *session, ulong options, TableList *tables,
3473
 
                          bool *write_to_binlog)
3474
 
{
3475
 
  bool result=0;
3476
 
  select_errors=0;                              /* Write if more errors */
3477
 
  bool tmp_write_to_binlog= 1;
3478
 
 
3479
 
  if (options & REFRESH_LOG)
3480
 
  {
3481
 
    /*
3482
 
      Flush the normal query log, the update log, the binary log,
3483
 
      the slow query log, the relay log (if it exists) and the log
3484
 
      tables.
3485
 
    */
3486
 
 
3487
 
    /*
3488
 
      Writing this command to the binlog may result in infinite loops
3489
 
      when doing mysqlbinlog|mysql, and anyway it does not really make
3490
 
      sense to log it automatically (would cause more trouble to users
3491
 
      than it would help them)
3492
 
    */
3493
 
    tmp_write_to_binlog= 0;
3494
 
    if (drizzle_bin_log.is_open())
3495
 
    {
3496
 
      drizzle_bin_log.rotate_and_purge(RP_FORCE_ROTATE);
3497
 
    }
3498
 
    pthread_mutex_lock(&LOCK_active_mi);
3499
 
    rotate_relay_log(active_mi);
3500
 
    pthread_mutex_unlock(&LOCK_active_mi);
3501
 
 
3502
 
    /* flush slow and general logs */
3503
 
    logger.flush_logs(session);
3504
 
 
3505
 
    if (ha_flush_logs(NULL))
3506
 
      result=1;
3507
 
    if (flush_error_log())
3508
 
      result=1;
3509
 
  }
3510
 
  /*
3511
 
    Note that if REFRESH_READ_LOCK bit is set then REFRESH_TABLES is set too
3512
 
    (see sql_yacc.yy)
3513
 
  */
3514
 
  if (options & (REFRESH_TABLES | REFRESH_READ_LOCK)) 
3515
 
  {
3516
 
    if ((options & REFRESH_READ_LOCK) && session)
3517
 
    {
3518
 
      /*
3519
 
        We must not try to aspire a global read lock if we have a write
3520
 
        locked table. This would lead to a deadlock when trying to
3521
 
        reopen (and re-lock) the table after the flush.
3522
 
      */
3523
 
      if (session->locked_tables)
3524
 
      {
3525
 
        THR_LOCK_DATA **lock_p= session->locked_tables->locks;
3526
 
        THR_LOCK_DATA **end_p= lock_p + session->locked_tables->lock_count;
3527
 
 
3528
 
        for (; lock_p < end_p; lock_p++)
3529
 
        {
3530
 
          if ((*lock_p)->type >= TL_WRITE_ALLOW_WRITE)
3531
 
          {
3532
 
            my_error(ER_LOCK_OR_ACTIVE_TRANSACTION, MYF(0));
3533
 
            return 1;
3534
 
          }
3535
 
        }
3536
 
      }
3537
 
      /*
3538
 
        Writing to the binlog could cause deadlocks, as we don't log
3539
 
        UNLOCK TABLES
3540
 
      */
3541
 
      tmp_write_to_binlog= 0;
3542
 
      if (lock_global_read_lock(session))
3543
 
        return 1;                               // Killed
3544
 
      result= close_cached_tables(session, tables, false, (options & REFRESH_FAST) ?
3545
 
                                  false : true, true);
3546
 
      if (make_global_read_lock_block_commit(session)) // Killed
3547
 
      {
3548
 
        /* Don't leave things in a half-locked state */
3549
 
        unlock_global_read_lock(session);
3550
 
        return 1;
3551
 
      }
3552
 
    }
3553
 
    else
3554
 
      result= close_cached_tables(session, tables, false, (options & REFRESH_FAST) ?
3555
 
                                  false : true, false);
3556
 
    my_dbopt_cleanup();
3557
 
  }
3558
 
  if (session && (options & REFRESH_STATUS))
3559
 
    refresh_status(session);
3560
 
  if (options & REFRESH_MASTER)
3561
 
  {
3562
 
    assert(session);
3563
 
    tmp_write_to_binlog= 0;
3564
 
    if (reset_master(session))
3565
 
    {
3566
 
      result=1;
3567
 
    }
3568
 
  }
3569
 
 if (options & REFRESH_SLAVE)
3570
 
 {
3571
 
   tmp_write_to_binlog= 0;
3572
 
   pthread_mutex_lock(&LOCK_active_mi);
3573
 
   if (reset_slave(session, active_mi))
3574
 
     result=1;
3575
 
   pthread_mutex_unlock(&LOCK_active_mi);
3576
 
 }
3577
 
 *write_to_binlog= tmp_write_to_binlog;
3578
 
 return result;
3579
 
}
3580
 
 
3581
 
 
3582
 
/**
3583
 
  kill on thread.
3584
 
 
3585
 
  @param session                        Thread class
3586
 
  @param id                     Thread id
3587
 
  @param only_kill_query        Should it kill the query or the connection
3588
 
 
3589
 
  @note
3590
 
    This is written such that we have a short lock on LOCK_thread_count
3591
 
*/
3592
 
 
3593
 
static unsigned int
3594
 
kill_one_thread(Session *, ulong id, bool only_kill_query)
3595
 
{
3596
 
  Session *tmp;
3597
 
  uint32_t error=ER_NO_SUCH_THREAD;
3598
 
  pthread_mutex_lock(&LOCK_thread_count); // For unlink from list
3599
 
  I_List_iterator<Session> it(threads);
3600
 
  while ((tmp=it++))
3601
 
  {
3602
 
    if (tmp->command == COM_DAEMON)
3603
 
      continue;
3604
 
    if (tmp->thread_id == id)
3605
 
    {
3606
 
      pthread_mutex_lock(&tmp->LOCK_delete);    // Lock from delete
3607
 
      break;
3608
 
    }
3609
 
  }
3610
 
  pthread_mutex_unlock(&LOCK_thread_count);
3611
 
  if (tmp)
3612
 
  {
3613
 
    tmp->awake(only_kill_query ? Session::KILL_QUERY : Session::KILL_CONNECTION);
3614
 
    error=0;
3615
 
    pthread_mutex_unlock(&tmp->LOCK_delete);
3616
 
  }
3617
 
  return(error);
3618
 
}
3619
 
 
3620
 
 
3621
 
/*
3622
 
  kills a thread and sends response
3623
 
 
3624
 
  SYNOPSIS
3625
 
    sql_kill()
3626
 
    session                     Thread class
3627
 
    id                  Thread id
3628
 
    only_kill_query     Should it kill the query or the connection
3629
 
*/
3630
 
 
3631
 
void sql_kill(Session *session, ulong id, bool only_kill_query)
3632
 
{
3633
 
  uint32_t error;
3634
 
  if (!(error= kill_one_thread(session, id, only_kill_query)))
3635
 
    my_ok(session);
3636
 
  else
3637
 
    my_error(error, MYF(0), id);
3638
 
}
3639
 
 
3640
 
 
3641
 
/** If pointer is not a null pointer, append filename to it. */
3642
 
 
3643
 
bool append_file_to_dir(Session *session, const char **filename_ptr,
3644
 
                        const char *table_name)
3645
 
{
3646
 
  char buff[FN_REFLEN],*ptr, *end;
3647
 
  if (!*filename_ptr)
3648
 
    return 0;                                   // nothing to do
3649
 
 
3650
 
  /* Check that the filename is not too long and it's a hard path */
3651
 
  if (strlen(*filename_ptr)+strlen(table_name) >= FN_REFLEN-1 ||
3652
 
      !test_if_hard_path(*filename_ptr))
3653
 
  {
3654
 
    my_error(ER_WRONG_TABLE_NAME, MYF(0), *filename_ptr);
3655
 
    return 1;
3656
 
  }
3657
 
  /* Fix is using unix filename format on dos */
3658
 
  my_stpcpy(buff,*filename_ptr);
3659
 
  end=convert_dirname(buff, *filename_ptr, NULL);
3660
 
  if (!(ptr= (char*) session->alloc((size_t) (end-buff) + strlen(table_name)+1)))
3661
 
    return 1;                                   // End of memory
3662
 
  *filename_ptr=ptr;
3663
 
  strxmov(ptr,buff,table_name,NULL);
3664
 
  return 0;
3665
 
}
3666
 
 
3667
 
 
3668
 
/**
3669
1405
  Check if the select is a simple select (not an union).
3670
1406
 
3671
1407
  @retval
3674
1410
    1   error   ; In this case the error messege is sent to the client
3675
1411
*/
3676
1412
 
3677
 
bool check_simple_select()
 
1413
bool check_simple_select(Session* session)
3678
1414
{
3679
 
  Session *session= current_session;
3680
 
  LEX *lex= session->lex;
3681
 
  if (lex->current_select != &lex->select_lex)
 
1415
  if (session->lex().current_select != &session->lex().select_lex)
3682
1416
  {
3683
1417
    char command[80];
3684
1418
    Lex_input_stream *lip= session->m_lip;
3685
 
    strmake(command, lip->yylval->symbol.str,
3686
 
            cmin((ulong)lip->yylval->symbol.length, sizeof(command)-1));
 
1419
    strncpy(command, lip->yylval->symbol.str,
 
1420
            min(lip->yylval->symbol.length, (uint32_t)(sizeof(command)-1)));
 
1421
    command[min(lip->yylval->symbol.length, (uint32_t)(sizeof(command)-1))]=0;
3687
1422
    my_error(ER_CANT_USE_OPTION_HERE, MYF(0), command);
3688
1423
    return 1;
3689
1424
  }
3705
1440
Item * all_any_subquery_creator(Item *left_expr,
3706
1441
                                chooser_compare_func_creator cmp,
3707
1442
                                bool all,
3708
 
                                SELECT_LEX *select_lex)
 
1443
                                Select_Lex *select_lex)
3709
1444
{
3710
1445
  if ((cmp == &comp_eq_creator) && !all)       //  = ANY <=> IN
3711
1446
    return new Item_in_subselect(left_expr, select_lex);
3723
1458
 
3724
1459
 
3725
1460
/**
3726
 
  Multi update query pre-check.
 
1461
  Update query pre-check.
3727
1462
 
3728
1463
  @param session                Thread handler
3729
1464
  @param tables Global/local table list (have to be the same)
3734
1469
    true  Error
3735
1470
*/
3736
1471
 
3737
 
bool multi_update_precheck(Session *session, TableList *)
 
1472
bool update_precheck(Session *session, TableList *)
3738
1473
{
3739
1474
  const char *msg= 0;
3740
 
  LEX *lex= session->lex;
3741
 
  SELECT_LEX *select_lex= &lex->select_lex;
3742
 
 
3743
 
  if (select_lex->item_list.elements != lex->value_list.elements)
3744
 
  {
3745
 
    my_message(ER_WRONG_VALUE_COUNT, ER(ER_WRONG_VALUE_COUNT), MYF(0));
3746
 
    return(true);
3747
 
  }
3748
 
 
3749
 
  if (select_lex->order_list.elements)
3750
 
    msg= "ORDER BY";
3751
 
  else if (select_lex->select_limit)
3752
 
    msg= "LIMIT";
3753
 
  if (msg)
3754
 
  {
3755
 
    my_error(ER_WRONG_USAGE, MYF(0), "UPDATE", msg);
3756
 
    return(true);
3757
 
  }
3758
 
  return(false);
3759
 
}
3760
 
 
3761
 
/**
3762
 
  Multi delete query pre-check.
3763
 
 
3764
 
  @param session                        Thread handler
3765
 
  @param tables         Global/local table list
3766
 
 
3767
 
  @retval
3768
 
    false OK
3769
 
  @retval
3770
 
    true  error
3771
 
*/
3772
 
 
3773
 
bool multi_delete_precheck(Session *session, TableList *)
3774
 
{
3775
 
  SELECT_LEX *select_lex= &session->lex->select_lex;
3776
 
  TableList **save_query_tables_own_last= session->lex->query_tables_own_last;
3777
 
 
3778
 
  session->lex->query_tables_own_last= 0;
3779
 
  session->lex->query_tables_own_last= save_query_tables_own_last;
3780
 
 
3781
 
  if ((session->options & OPTION_SAFE_UPDATES) && !select_lex->where)
3782
 
  {
3783
 
    my_message(ER_UPDATE_WITHOUT_KEY_IN_SAFE_MODE,
3784
 
               ER(ER_UPDATE_WITHOUT_KEY_IN_SAFE_MODE), MYF(0));
3785
 
    return(true);
3786
 
  }
3787
 
  return(false);
3788
 
}
3789
 
 
3790
 
 
3791
 
/*
3792
 
  Given a table in the source list, find a correspondent table in the
3793
 
  table references list.
3794
 
 
3795
 
  @param lex Pointer to LEX representing multi-delete.
3796
 
  @param src Source table to match.
3797
 
  @param ref Table references list.
3798
 
 
3799
 
  @remark The source table list (tables listed before the FROM clause
3800
 
  or tables listed in the FROM clause before the USING clause) may
3801
 
  contain table names or aliases that must match unambiguously one,
3802
 
  and only one, table in the target table list (table references list,
3803
 
  after FROM/USING clause).
3804
 
 
3805
 
  @return Matching table, NULL otherwise.
3806
 
*/
3807
 
 
3808
 
static TableList *multi_delete_table_match(LEX *, TableList *tbl,
3809
 
                                           TableList *tables)
3810
 
{
3811
 
  TableList *match= NULL;
3812
 
 
3813
 
  for (TableList *elem= tables; elem; elem= elem->next_local)
3814
 
  {
3815
 
    int cmp;
3816
 
 
3817
 
    if (tbl->is_fqtn && elem->is_alias)
3818
 
      continue; /* no match */
3819
 
    if (tbl->is_fqtn && elem->is_fqtn)
3820
 
      cmp= my_strcasecmp(table_alias_charset, tbl->table_name, elem->table_name) ||
3821
 
           strcmp(tbl->db, elem->db);
3822
 
    else if (elem->is_alias)
3823
 
      cmp= my_strcasecmp(table_alias_charset, tbl->alias, elem->alias);
3824
 
    else
3825
 
      cmp= my_strcasecmp(table_alias_charset, tbl->table_name, elem->table_name) ||
3826
 
           strcmp(tbl->db, elem->db);
3827
 
 
3828
 
    if (cmp)
3829
 
      continue;
3830
 
 
3831
 
    if (match)
3832
 
    {
3833
 
      my_error(ER_NONUNIQ_TABLE, MYF(0), elem->alias);
3834
 
      return(NULL);
3835
 
    }
3836
 
 
3837
 
    match= elem;
3838
 
  }
3839
 
 
3840
 
  if (!match)
3841
 
    my_error(ER_UNKNOWN_TABLE, MYF(0), tbl->table_name, "MULTI DELETE");
3842
 
 
3843
 
  return(match);
3844
 
}
3845
 
 
3846
 
 
3847
 
/**
3848
 
  Link tables in auxilary table list of multi-delete with corresponding
3849
 
  elements in main table list, and set proper locks for them.
3850
 
 
3851
 
  @param lex   pointer to LEX representing multi-delete
3852
 
 
3853
 
  @retval
3854
 
    false   success
3855
 
  @retval
3856
 
    true    error
3857
 
*/
3858
 
 
3859
 
bool multi_delete_set_locks_and_link_aux_tables(LEX *lex)
3860
 
{
3861
 
  TableList *tables= (TableList*)lex->select_lex.table_list.first;
3862
 
  TableList *target_tbl;
3863
 
 
3864
 
  lex->table_count= 0;
3865
 
 
3866
 
  for (target_tbl= (TableList *)lex->auxiliary_table_list.first;
3867
 
       target_tbl; target_tbl= target_tbl->next_local)
3868
 
  {
3869
 
    lex->table_count++;
3870
 
    /* All tables in aux_tables must be found in FROM PART */
3871
 
    TableList *walk= multi_delete_table_match(lex, target_tbl, tables);
3872
 
    if (!walk)
3873
 
      return(true);
3874
 
    if (!walk->derived)
3875
 
    {
3876
 
      target_tbl->table_name= walk->table_name;
3877
 
      target_tbl->table_name_length= walk->table_name_length;
3878
 
    }
3879
 
    walk->updating= target_tbl->updating;
3880
 
    walk->lock_type= target_tbl->lock_type;
3881
 
    target_tbl->correspondent_table= walk;      // Remember corresponding table
3882
 
  }
3883
 
  return(false);
3884
 
}
3885
 
 
3886
 
 
3887
 
/**
3888
 
  simple UPDATE query pre-check.
3889
 
 
3890
 
  @param session                Thread handler
3891
 
  @param tables Global table list
3892
 
 
3893
 
  @retval
3894
 
    false OK
3895
 
  @retval
3896
 
    true  Error
3897
 
*/
3898
 
 
3899
 
bool update_precheck(Session *session, TableList *)
3900
 
{
3901
 
  if (session->lex->select_lex.item_list.elements != session->lex->value_list.elements)
3902
 
  {
3903
 
    my_message(ER_WRONG_VALUE_COUNT, ER(ER_WRONG_VALUE_COUNT), MYF(0));
3904
 
    return(true);
3905
 
  }
3906
 
  return(false);
 
1475
  Select_Lex *select_lex= &session->lex().select_lex;
 
1476
 
 
1477
  if (session->lex().select_lex.item_list.size() != session->lex().value_list.size())
 
1478
  {
 
1479
    my_message(ER_WRONG_VALUE_COUNT, ER(ER_WRONG_VALUE_COUNT), MYF(0));
 
1480
    return true;
 
1481
  }
 
1482
 
 
1483
  if (session->lex().select_lex.table_list.size() > 1)
 
1484
  {
 
1485
    if (select_lex->order_list.size())
 
1486
      msg= "ORDER BY";
 
1487
    else if (select_lex->select_limit)
 
1488
      msg= "LIMIT";
 
1489
    if (msg)
 
1490
    {
 
1491
      my_error(ER_WRONG_USAGE, MYF(0), "UPDATE", msg);
 
1492
      return true;
 
1493
    }
 
1494
  }
 
1495
  return false;
3907
1496
}
3908
1497
 
3909
1498
 
3921
1510
 
3922
1511
bool insert_precheck(Session *session, TableList *)
3923
1512
{
3924
 
  LEX *lex= session->lex;
3925
 
 
3926
1513
  /*
3927
1514
    Check that we have modify privileges for the first table and
3928
1515
    select privileges for the rest
3929
1516
  */
3930
 
  if (lex->update_list.elements != lex->value_list.elements)
 
1517
  if (session->lex().update_list.size() != session->lex().value_list.size())
3931
1518
  {
3932
1519
    my_message(ER_WRONG_VALUE_COUNT, ER(ER_WRONG_VALUE_COUNT), MYF(0));
3933
 
    return(true);
3934
 
  }
3935
 
  return(false);
3936
 
}
3937
 
 
3938
 
 
3939
 
/**
3940
 
  CREATE TABLE query pre-check.
3941
 
 
3942
 
  @param session                        Thread handler
3943
 
  @param tables         Global table list
3944
 
  @param create_table           Table which will be created
3945
 
 
3946
 
  @retval
3947
 
    false   OK
3948
 
  @retval
3949
 
    true   Error
3950
 
*/
3951
 
 
3952
 
bool create_table_precheck(Session *, TableList *,
3953
 
                           TableList *create_table)
3954
 
{
3955
 
  bool error= true;                                 // Error message is given
3956
 
 
3957
 
  if (create_table && (strcmp(create_table->db, "information_schema") == 0))
3958
 
  {
3959
 
    my_error(ER_DBACCESS_DENIED_ERROR, MYF(0), "", "", INFORMATION_SCHEMA_NAME.c_str());
3960
 
    return(true);
3961
 
  }
3962
 
 
3963
 
  error= false;
3964
 
 
3965
 
  return(error);
 
1520
    return true;
 
1521
  }
 
1522
  return false;
3966
1523
}
3967
1524
 
3968
1525
 
3984
1541
  {
3985
1542
    /* it is NOT(NOT( ... )) */
3986
1543
    Item *arg= ((Item_func *) expr)->arguments()[0];
3987
 
    enum_parsing_place place= session->lex->current_select->parsing_place;
 
1544
    enum_parsing_place place= session->lex().current_select->parsing_place;
3988
1545
    if (arg->is_bool_func() || place == IN_WHERE || place == IN_HAVING)
3989
1546
      return arg;
3990
1547
    /*
4016
1573
*/
4017
1574
 
4018
1575
 
4019
 
bool check_string_char_length(LEX_STRING *str, const char *err_msg,
4020
 
                              uint32_t max_char_length, const CHARSET_INFO * const cs,
 
1576
bool check_string_char_length(lex_string_t *str, const char *err_msg,
 
1577
                              uint32_t max_char_length, const charset_info_st * const cs,
4021
1578
                              bool no_error)
4022
1579
{
4023
1580
  int well_formed_error;
4033
1590
}
4034
1591
 
4035
1592
 
4036
 
bool check_identifier_name(LEX_STRING *str, uint32_t err_code,
 
1593
bool check_identifier_name(lex_string_t *str, error_t err_code,
4037
1594
                           uint32_t max_char_length,
4038
1595
                           const char *param_for_err_msg)
4039
1596
{
4040
 
#ifdef HAVE_CHARSET_utf8mb3
4041
1597
  /*
4042
1598
    We don't support non-BMP characters in identifiers at the moment,
4043
1599
    so they should be prohibited until such support is done.
4044
1600
    This is why we use the 3-byte utf8 to check well-formedness here.
4045
1601
  */
4046
 
  const CHARSET_INFO * const cs= &my_charset_utf8mb3_general_ci;
4047
 
#else
4048
 
  const CHARSET_INFO * const cs= system_charset_info;
4049
 
#endif
 
1602
  const charset_info_st * const cs= &my_charset_utf8mb4_general_ci;
 
1603
 
4050
1604
  int well_formed_error;
4051
1605
  uint32_t res= cs->cset->well_formed_len(cs, str->str, str->str + str->length,
4052
1606
                                      max_char_length, &well_formed_error);
4056
1610
    my_error(ER_INVALID_CHARACTER_STRING, MYF(0), "identifier", str->str);
4057
1611
    return true;
4058
1612
  }
4059
 
  
 
1613
 
4060
1614
  if (str->length == res)
4061
1615
    return false;
4062
1616
 
4063
1617
  switch (err_code)
4064
1618
  {
4065
 
  case 0:
 
1619
  case EE_OK:
4066
1620
    break;
4067
1621
  case ER_WRONG_STRING_LENGTH:
4068
1622
    my_error(err_code, MYF(0), str->str, param_for_err_msg, max_char_length);
4074
1628
    assert(0);
4075
1629
    break;
4076
1630
  }
 
1631
 
4077
1632
  return true;
4078
1633
}
4079
1634
 
4080
1635
 
4081
 
/*
4082
 
  Check if path does not contain mysql data home directory
4083
 
  SYNOPSIS
4084
 
    test_if_data_home_dir()
4085
 
    dir                     directory
4086
 
    conv_home_dir           converted data home directory
4087
 
    home_dir_len            converted data home directory length
4088
 
 
4089
 
  RETURN VALUES
4090
 
    0   ok
4091
 
    1   error  
4092
 
*/
4093
 
 
4094
 
bool test_if_data_home_dir(const char *dir)
4095
 
{
4096
 
  char path[FN_REFLEN], conv_path[FN_REFLEN];
4097
 
  uint32_t dir_len, home_dir_len= strlen(drizzle_unpacked_real_data_home);
4098
 
 
4099
 
  if (!dir)
4100
 
    return(0);
4101
 
 
4102
 
  (void) fn_format(path, dir, "", "",
4103
 
                   (MY_RETURN_REAL_PATH|MY_RESOLVE_SYMLINKS));
4104
 
  dir_len= unpack_dirname(conv_path, dir);
4105
 
 
4106
 
  if (home_dir_len < dir_len)
4107
 
  {
4108
 
    if (!my_strnncoll(character_set_filesystem,
4109
 
                      (const unsigned char*) conv_path, home_dir_len,
4110
 
                      (const unsigned char*) drizzle_unpacked_real_data_home,
4111
 
                      home_dir_len))
4112
 
      return(1);
4113
 
  }
4114
 
  return(0);
4115
 
}
4116
 
 
4117
 
 
4118
 
extern int DRIZZLEparse(void *session); // from sql_yacc.cc
4119
 
 
4120
 
 
4121
1636
/**
4122
1637
  This is a wrapper of DRIZZLEparse(). All the code should call parse_sql()
4123
1638
  instead of DRIZZLEparse().
4130
1645
    @retval true on parsing error.
4131
1646
*/
4132
1647
 
4133
 
bool parse_sql(Session *session, Lex_input_stream *lip)
 
1648
static bool parse_sql(Session *session, Lex_input_stream *lip)
4134
1649
{
4135
1650
  assert(session->m_lip == NULL);
4136
1651
 
 
1652
  DRIZZLE_QUERY_PARSE_START(session->getQueryString()->c_str());
 
1653
 
4137
1654
  /* Set Lex_input_stream. */
4138
1655
 
4139
1656
  session->m_lip= lip;
4140
1657
 
4141
1658
  /* Parse the query. */
4142
1659
 
4143
 
  bool mysql_parse_status= DRIZZLEparse(session) != 0;
 
1660
  bool parse_status= base_sql_parse(session) != 0;
4144
1661
 
4145
1662
  /* Check that if DRIZZLEparse() failed, session->is_error() is set. */
4146
1663
 
4147
 
  assert(!mysql_parse_status || session->is_error());
 
1664
  assert(!parse_status || session->is_error());
4148
1665
 
4149
1666
  /* Reset Lex_input_stream. */
4150
1667
 
4151
1668
  session->m_lip= NULL;
4152
1669
 
 
1670
  DRIZZLE_QUERY_PARSE_DONE(parse_status || session->is_fatal_error);
 
1671
 
4153
1672
  /* That's it. */
4154
1673
 
4155
 
  return mysql_parse_status || session->is_fatal_error;
 
1674
  return parse_status || session->is_fatal_error;
4156
1675
}
4157
1676
 
4158
1677
/**
4159
1678
  @} (end of group Runtime_Environment)
4160
1679
*/
 
1680
 
 
1681
} /* namespace drizzled */