60
57
"NON-EXISTING", "ACTIVE", "IDLE", "PREPARED"
63
static void unlock_locked_tables(Session *session)
60
static void unlock_locked_tables(THD *thd)
65
if (session->locked_tables)
62
if (thd->locked_tables)
67
session->lock=session->locked_tables;
68
session->locked_tables=0; // Will be automatically closed
69
close_thread_tables(session); // Free tables
64
thd->lock=thd->locked_tables;
65
thd->locked_tables=0; // Will be automatically closed
66
close_thread_tables(thd); // Free tables
74
bool end_active_trans(Session *session)
71
bool end_active_trans(THD *thd)
78
if (session->transaction.xid_state.xa_state != XA_NOTR)
74
if (unlikely(thd->in_sub_stmt))
76
my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
79
if (thd->transaction.xid_state.xa_state != XA_NOTR)
80
81
my_error(ER_XAER_RMFAIL, MYF(0),
81
xa_state_names[session->transaction.xid_state.xa_state]);
82
xa_state_names[thd->transaction.xid_state.xa_state]);
84
if (session->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN |
85
if (thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN |
85
86
OPTION_TABLE_LOCK))
87
88
/* Safety if one did "drop table" on locked tables */
88
if (!session->locked_tables)
89
session->options&= ~OPTION_TABLE_LOCK;
90
session->server_status&= ~SERVER_STATUS_IN_TRANS;
91
if (ha_commit(session))
89
if (!thd->locked_tables)
90
thd->options&= ~OPTION_TABLE_LOCK;
91
thd->server_status&= ~SERVER_STATUS_IN_TRANS;
94
session->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
95
session->transaction.all.modified_non_trans_table= false;
95
thd->options&= ~(OPTION_BEGIN | OPTION_KEEP_LOG);
96
thd->transaction.all.modified_non_trans_table= false;
100
bool begin_trans(Session *session)
101
bool begin_trans(THD *thd)
103
if (session->locked_tables)
105
session->lock=session->locked_tables;
106
session->locked_tables=0; // Will be automatically closed
107
close_thread_tables(session); // Free tables
109
if (end_active_trans(session))
104
if (unlikely(thd->in_sub_stmt))
106
my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
109
if (thd->locked_tables)
111
thd->lock=thd->locked_tables;
112
thd->locked_tables=0; // Will be automatically closed
113
close_thread_tables(thd); // Free tables
115
if (end_active_trans(thd))
113
LEX *lex= session->lex;
114
session->options|= OPTION_BEGIN;
115
session->server_status|= SERVER_STATUS_IN_TRANS;
116
if (lex->start_transaction_opt & DRIZZLE_START_TRANS_OPT_WITH_CONS_SNAPSHOT)
117
error= ha_start_consistent_snapshot(session);
120
thd->options|= OPTION_BEGIN;
121
thd->server_status|= SERVER_STATUS_IN_TRANS;
122
if (lex->start_transaction_opt & MYSQL_START_TRANS_OPT_WITH_CONS_SNAPSHOT)
123
error= ha_start_consistent_snapshot(thd);
217
227
return (sql_command_flags[command] & CF_CHANGES_DATA) != 0;
220
void execute_init_command(Session *session, sys_var_str *init_command_var,
230
void execute_init_command(THD *thd, sys_var_str *init_command_var,
221
231
rw_lock_t *var_mutex)
224
234
ulong save_client_capabilities;
226
session->set_proc_info("Execution of init_command");
236
thd_proc_info(thd, "Execution of init_command");
228
238
We need to lock init_command_var because
229
239
during execution of init_command_var query
230
240
values of init_command_var can't be changed
232
242
rw_rdlock(var_mutex);
233
save_client_capabilities= session->client_capabilities;
234
session->client_capabilities|= CLIENT_MULTI_STATEMENTS;
243
save_client_capabilities= thd->client_capabilities;
244
thd->client_capabilities|= CLIENT_MULTI_STATEMENTS;
236
246
We don't need return result of execution to client side.
237
To forbid this we should set session->net.vio to 0.
247
To forbid this we should set thd->net.vio to 0.
239
save_vio= session->net.vio;
241
dispatch_command(COM_QUERY, session,
249
save_vio= thd->net.vio;
251
dispatch_command(COM_QUERY, thd,
242
252
init_command_var->value,
243
253
init_command_var->value_length);
244
254
rw_unlock(var_mutex);
245
session->client_capabilities= save_client_capabilities;
246
session->net.vio= save_vio;
255
thd->client_capabilities= save_client_capabilities;
256
thd->net.vio= save_vio;
250
260
Ends the current transaction and (maybe) begin the next.
252
@param session Current thread
262
@param thd Current thread
253
263
@param completion Completion type
259
int end_trans(Session *session, enum enum_mysql_completiontype completion)
269
int end_trans(THD *thd, enum enum_mysql_completiontype completion)
261
271
bool do_release= 0;
264
if (session->transaction.xid_state.xa_state != XA_NOTR)
274
if (unlikely(thd->in_sub_stmt))
276
my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
279
if (thd->transaction.xid_state.xa_state != XA_NOTR)
266
281
my_error(ER_XAER_RMFAIL, MYF(0),
267
xa_state_names[session->transaction.xid_state.xa_state]);
282
xa_state_names[thd->transaction.xid_state.xa_state]);
270
285
switch (completion) {
492
507
1 request of thread shutdown, i. e. if command is
493
508
COM_QUIT/COM_SHUTDOWN
495
bool dispatch_command(enum enum_server_command command, Session *session,
496
char* packet, uint32_t packet_length)
510
bool dispatch_command(enum enum_server_command command, THD *thd,
511
char* packet, uint packet_length)
498
NET *net= &session->net;
500
Query_id &query_id= Query_id::get_query_id();
502
session->command=command;
503
session->lex->sql_command= SQLCOM_END; /* to avoid confusing VIEW detectors */
505
pthread_mutex_lock(&LOCK_thread_count);
506
session->query_id= query_id.value();
516
thd->command=command;
518
Commands which always take a long time are logged into
519
the slow log only if opt_log_slow_admin_statements is set.
521
thd->enable_slow_log= true;
522
thd->lex->sql_command= SQLCOM_END; /* to avoid confusing VIEW detectors */
524
VOID(pthread_mutex_lock(&LOCK_thread_count));
525
thd->query_id= global_query_id;
508
527
switch( command ) {
509
528
/* Ignore these statements. */
512
532
/* Increase id and count all other statements. */
514
statistic_increment(session->status_var.questions, &LOCK_status);
534
statistic_increment(thd->status_var.questions, &LOCK_status);
518
538
thread_running++;
519
/* TODO: set session->lex->sql_command to SQLCOM_END here */
520
pthread_mutex_unlock(&LOCK_thread_count);
522
logging_pre_do(session);
524
session->server_status&=
539
/* TODO: set thd->lex->sql_command to SQLCOM_END here */
540
VOID(pthread_mutex_unlock(&LOCK_thread_count));
525
543
~(SERVER_QUERY_NO_INDEX_USED | SERVER_QUERY_NO_GOOD_INDEX_USED);
526
544
switch (command) {
527
545
case COM_INIT_DB:
530
status_var_increment(session->status_var.com_stat[SQLCOM_CHANGE_DB]);
531
session->convert_string(&tmp, system_charset_info,
532
packet, packet_length, session->charset());
533
if (!mysql_change_db(session, &tmp, false))
548
status_var_increment(thd->status_var.com_stat[SQLCOM_CHANGE_DB]);
549
thd->convert_string(&tmp, system_charset_info,
550
packet, packet_length, thd->charset());
551
if (!mysql_change_db(thd, &tmp, false))
553
general_log_write(thd, command, thd->db, thd->db_length);
558
case COM_REGISTER_SLAVE:
560
if (!register_slave(thd, (uchar*)packet, packet_length))
539
564
case COM_CHANGE_USER:
541
status_var_increment(session->status_var.com_other);
566
status_var_increment(thd->status_var.com_other);
542
567
char *user= (char*) packet, *packet_end= packet + packet_length;
543
568
/* Safe because there is always a trailing \0 at the end of the packet */
544
char *passwd= strchr(user, '\0')+1;
547
session->clear_error(); // if errors from rollback
569
char *passwd= strend(user)+1;
572
thd->clear_error(); // if errors from rollback
550
575
Old clients send null-terminated string ('\0' for empty string) for
602
627
/* Convert database name to utf8 */
603
628
db_buff[copy_and_convert(db_buff, sizeof(db_buff)-1,
604
629
system_charset_info, db, db_length,
605
session->charset(), &dummy_errors)]= 0;
630
thd->charset(), &dummy_errors)]= 0;
608
633
/* Save user and privileges */
609
save_db_length= session->db_length;
610
save_db= session->db;
611
save_user_connect= session->user_connect;
634
save_db_length= thd->db_length;
636
save_user_connect= thd->user_connect;
613
if (!(session->security_ctx->user= my_strdup(user, MYF(0))))
638
if (!(thd->security_ctx->user= my_strdup(user, MYF(0))))
615
session->security_ctx->user= save_security_ctx.user;
640
thd->security_ctx->user= save_security_ctx.user;
616
641
my_message(ER_OUT_OF_RESOURCES, ER(ER_OUT_OF_RESOURCES), MYF(0));
620
645
/* Clear variables that are allocated */
621
session->user_connect= 0;
622
res= check_user(session, passwd, passwd_len, db, false);
646
thd->user_connect= 0;
647
thd->security_ctx->priv_user= thd->security_ctx->user;
648
res= check_user(thd, COM_CHANGE_USER, passwd, passwd_len, db, false);
626
if (session->security_ctx->user)
627
free(session->security_ctx->user);
628
*session->security_ctx= save_security_ctx;
629
session->user_connect= save_user_connect;
630
session->db= save_db;
631
session->db_length= save_db_length;
652
x_free(thd->security_ctx->user);
653
*thd->security_ctx= save_security_ctx;
654
thd->user_connect= save_user_connect;
656
thd->db_length= save_db_length;
637
if (save_security_ctx.user)
638
free(save_security_ctx.user);
661
x_free(save_security_ctx.user);
642
session_init_client_charset(session, cs_number);
643
session->update_charset();
665
thd_init_client_charset(thd, cs_number);
666
thd->update_charset();
650
if (alloc_query(session, packet, packet_length))
673
if (alloc_query(thd, packet, packet_length))
651
674
break; // fatal error is set
652
char *packet_end= session->query + session->query_length;
675
char *packet_end= thd->query + thd->query_length;
653
676
const char* end_of_stmt= NULL;
655
mysql_parse(session, session->query, session->query_length, &end_of_stmt);
657
while (!session->killed && (end_of_stmt != NULL) && ! session->is_error())
678
general_log_write(thd, command, thd->query, thd->query_length);
680
mysql_parse(thd, thd->query, thd->query_length, &end_of_stmt);
682
while (!thd->killed && (end_of_stmt != NULL) && ! thd->is_error())
659
684
char *beginning_of_next_stmt= (char*) end_of_stmt;
661
net_end_statement(session);
686
net_end_statement(thd);
663
688
Multiple queries exits, execute them individually
665
close_thread_tables(session);
690
close_thread_tables(thd);
666
691
ulong length= (ulong)(packet_end - beginning_of_next_stmt);
668
log_slow_statement(session);
693
log_slow_statement(thd);
670
695
/* Remove garbage at start of query */
671
while (length > 0 && my_isspace(session->charset(), *beginning_of_next_stmt))
696
while (length > 0 && my_isspace(thd->charset(), *beginning_of_next_stmt))
673
698
beginning_of_next_stmt++;
677
pthread_mutex_lock(&LOCK_thread_count);
678
session->query_length= length;
679
session->query= beginning_of_next_stmt;
702
VOID(pthread_mutex_lock(&LOCK_thread_count));
703
thd->query_length= length;
704
thd->query= beginning_of_next_stmt;
681
706
Count each statement from the client.
683
statistic_increment(session->status_var.questions, &LOCK_status);
684
session->query_id= query_id.next();
685
session->set_time(); /* Reset the query start time. */
686
/* TODO: set session->lex->sql_command to SQLCOM_END here */
687
pthread_mutex_unlock(&LOCK_thread_count);
708
statistic_increment(thd->status_var.questions, &LOCK_status);
709
thd->query_id= next_query_id();
710
thd->set_time(); /* Reset the query start time. */
711
/* TODO: set thd->lex->sql_command to SQLCOM_END here */
712
VOID(pthread_mutex_unlock(&LOCK_thread_count));
689
mysql_parse(session, beginning_of_next_stmt, length, &end_of_stmt);
714
mysql_parse(thd, beginning_of_next_stmt, length, &end_of_stmt);
695
720
char *fields, *packet_end= packet + packet_length, *arg_end;
696
721
/* Locked closure of all tables */
697
TableList table_list;
722
TABLE_LIST table_list;
698
723
LEX_STRING conv_name;
700
725
/* used as fields initializator */
703
status_var_increment(session->status_var.com_stat[SQLCOM_SHOW_FIELDS]);
728
status_var_increment(thd->status_var.com_stat[SQLCOM_SHOW_FIELDS]);
704
729
memset(&table_list, 0, sizeof(table_list));
705
if (session->copy_db_to(&table_list.db, &table_list.db_length))
730
if (thd->copy_db_to(&table_list.db, &table_list.db_length))
708
733
We have name + wildcard in packet, separated by endzero
710
arg_end= strchr(packet, '\0');
711
session->convert_string(&conv_name, system_charset_info,
712
packet, (uint32_t) (arg_end - packet), session->charset());
735
arg_end= strend(packet);
736
thd->convert_string(&conv_name, system_charset_info,
737
packet, (uint) (arg_end - packet), thd->charset());
713
738
table_list.alias= table_list.table_name= conv_name.str;
714
739
packet= arg_end + 1;
716
741
if (!my_strcasecmp(system_charset_info, table_list.db,
717
742
INFORMATION_SCHEMA_NAME.str))
719
ST_SCHEMA_TABLE *schema_table= find_schema_table(session, table_list.alias);
744
ST_SCHEMA_TABLE *schema_table= find_schema_table(thd, table_list.alias);
720
745
if (schema_table)
721
746
table_list.schema_table= schema_table;
724
session->query_length= (uint32_t) (packet_end - packet); // Don't count end \0
725
if (!(session->query=fields= (char*) session->memdup(packet,session->query_length+1)))
749
thd->query_length= (uint) (packet_end - packet); // Don't count end \0
750
if (!(thd->query=fields= (char*) thd->memdup(packet,thd->query_length+1)))
752
general_log_print(thd, command, "%s %s", table_list.table_name, fields);
727
753
if (lower_case_table_names)
728
754
my_casedn_str(files_charset_info, table_list.table_name);
730
756
/* init structures for VIEW processing */
731
table_list.select_lex= &(session->lex->select_lex);
734
mysql_reset_session_for_next_command(session);
737
select_lex.table_list.link_in_list((unsigned char*) &table_list,
738
(unsigned char**) &table_list.next_local);
739
session->lex->add_to_query_tables(&table_list);
757
table_list.select_lex= &(thd->lex->select_lex);
760
mysql_reset_thd_for_next_command(thd);
763
select_lex.table_list.link_in_list((uchar*) &table_list,
764
(uchar**) &table_list.next_local);
765
thd->lex->add_to_query_tables(&table_list);
741
767
/* switch on VIEW optimisation: do not fill temporary tables */
742
session->lex->sql_command= SQLCOM_SHOW_FIELDS;
743
mysqld_list_fields(session,&table_list,fields);
744
session->lex->unit.cleanup();
745
session->cleanup_after_query();
768
thd->lex->sql_command= SQLCOM_SHOW_FIELDS;
769
mysqld_list_fields(thd,&table_list,fields);
770
thd->lex->unit.cleanup();
771
thd->cleanup_after_query();
749
775
/* We don't calculate statistics for this command */
776
general_log_print(thd, command, NullS);
750
777
net->error=0; // Don't give 'abort' message
751
session->main_da.disable_status(); // Don't send anything back
778
thd->main_da.disable_status(); // Don't send anything back
752
779
error=true; // End server
754
781
case COM_BINLOG_DUMP:
758
785
uint32_t slave_server_id;
760
status_var_increment(session->status_var.com_other);
787
status_var_increment(thd->status_var.com_other);
788
thd->enable_slow_log= opt_log_slow_admin_statements;
761
789
/* TODO: The following has to be changed to an 8 byte integer */
762
790
pos = uint4korr(packet);
763
791
flags = uint2korr(packet + 4);
764
session->server_id=0; /* avoid suicide */
792
thd->server_id=0; /* avoid suicide */
765
793
if ((slave_server_id= uint4korr(packet+6))) // mysqlbinlog.server_id==0
766
794
kill_zombie_dump_threads(slave_server_id);
767
session->server_id = slave_server_id;
795
thd->server_id = slave_server_id;
769
mysql_binlog_send(session, session->strdup(packet + 10), (my_off_t) pos, flags);
797
general_log_print(thd, command, "Log: '%s' Pos: %ld", packet+10,
799
mysql_binlog_send(thd, thd->strdup(packet + 10), (my_off_t) pos, flags);
800
unregister_slave(thd,1,1);
770
801
/* fake COM_QUIT -- if we get here, the thread needs to terminate */
774
805
case COM_SHUTDOWN:
776
status_var_increment(session->status_var.com_other);
778
close_thread_tables(session); // Free before kill
807
status_var_increment(thd->status_var.com_other);
809
If the client is < 4.1.3, it is going to send us no argument; then
810
packet_length is 0, packet[0] is the end 0 of the packet. Note that
811
SHUTDOWN_DEFAULT is 0. If client is >= 4.1.3, the shutdown level is in
814
enum drizzle_enum_shutdown_level level=
815
(enum drizzle_enum_shutdown_level) (uchar) packet[0];
816
if (level == SHUTDOWN_DEFAULT)
817
level= SHUTDOWN_WAIT_ALL_BUFFERS; // soon default will be configurable
818
else if (level != SHUTDOWN_WAIT_ALL_BUFFERS)
820
my_error(ER_NOT_SUPPORTED_YET, MYF(0), "this shutdown level");
823
general_log_print(thd, command, NullS);
825
close_thread_tables(thd); // Free before kill
832
STATUS_VAR current_global_status_var;
835
uint64_t queries_per_second1000;
837
uint buff_len= sizeof(buff);
839
general_log_print(thd, command, NullS);
840
status_var_increment(thd->status_var.com_stat[SQLCOM_SHOW_STATUS]);
841
calc_sum_of_all_status(¤t_global_status_var);
842
if (!(uptime= (ulong) (thd->start_time - server_start_time)))
843
queries_per_second1000= 0;
845
queries_per_second1000= thd->query_id * 1000LL / uptime;
847
length= snprintf((char*) buff, buff_len - 1,
848
"Uptime: %lu Threads: %d Questions: %lu "
849
"Slow queries: %lu Opens: %lu Flush tables: %lu "
850
"Open tables: %u Queries per second avg: %u.%u",
852
(int) thread_count, (ulong) thd->query_id,
853
current_global_status_var.long_query_count,
854
current_global_status_var.opened_tables,
856
cached_open_tables(),
857
(uint) (queries_per_second1000 / 1000),
858
(uint) (queries_per_second1000 % 1000));
859
VOID(my_net_write(net, (uchar*) buff, length));
860
VOID(net_flush(net));
861
thd->main_da.disable_status();
784
status_var_increment(session->status_var.com_other);
785
my_ok(session); // Tell client we are alive
865
status_var_increment(thd->status_var.com_other);
866
my_ok(thd); // Tell client we are alive
787
868
case COM_PROCESS_INFO:
788
status_var_increment(session->status_var.com_stat[SQLCOM_SHOW_PROCESSLIST]);
789
mysqld_list_processes(session, NULL, 0);
869
status_var_increment(thd->status_var.com_stat[SQLCOM_SHOW_PROCESSLIST]);
870
general_log_print(thd, command, NullS);
871
mysqld_list_processes(thd, NullS, 0);
791
873
case COM_PROCESS_KILL:
793
status_var_increment(session->status_var.com_stat[SQLCOM_KILL]);
875
status_var_increment(thd->status_var.com_stat[SQLCOM_KILL]);
794
876
ulong id=(ulong) uint4korr(packet);
795
sql_kill(session,id,false);
877
sql_kill(thd,id,false);
798
880
case COM_SET_OPTION:
800
status_var_increment(session->status_var.com_stat[SQLCOM_SET_OPTION]);
801
uint32_t opt_command= uint2korr(packet);
882
status_var_increment(thd->status_var.com_stat[SQLCOM_SET_OPTION]);
883
uint opt_command= uint2korr(packet);
803
885
switch (opt_command) {
804
case (int) DRIZZLE_OPTION_MULTI_STATEMENTS_ON:
805
session->client_capabilities|= CLIENT_MULTI_STATEMENTS;
886
case (int) MYSQL_OPTION_MULTI_STATEMENTS_ON:
887
thd->client_capabilities|= CLIENT_MULTI_STATEMENTS;
808
case (int) DRIZZLE_OPTION_MULTI_STATEMENTS_OFF:
809
session->client_capabilities&= ~CLIENT_MULTI_STATEMENTS;
890
case (int) MYSQL_OPTION_MULTI_STATEMENTS_OFF:
891
thd->client_capabilities&= ~CLIENT_MULTI_STATEMENTS;
813
895
my_message(ER_UNKNOWN_COM_ERROR, ER(ER_UNKNOWN_COM_ERROR), MYF(0));
827
909
/* If commit fails, we should be able to reset the OK status. */
828
session->main_da.can_overwrite_status= true;
829
ha_autocommit_or_rollback(session, session->is_error());
830
session->main_da.can_overwrite_status= false;
910
thd->main_da.can_overwrite_status= true;
911
ha_autocommit_or_rollback(thd, thd->is_error());
912
thd->main_da.can_overwrite_status= false;
832
session->transaction.stmt.reset();
914
thd->transaction.stmt.reset();
835
917
/* report error issued during command execution */
836
if (session->killed_errno())
838
if (! session->main_da.is_set())
839
session->send_kill_message();
841
if (session->killed == Session::KILL_QUERY || session->killed == Session::KILL_BAD_DATA)
843
session->killed= Session::NOT_KILLED;
844
session->mysys_var->abort= 0;
847
net_end_statement(session);
849
session->set_proc_info("closing tables");
918
if (thd->killed_errno())
920
if (! thd->main_da.is_set())
921
thd->send_kill_message();
923
if (thd->killed == THD::KILL_QUERY || thd->killed == THD::KILL_BAD_DATA)
925
thd->killed= THD::NOT_KILLED;
926
thd->mysys_var->abort= 0;
929
net_end_statement(thd);
931
thd->proc_info= "closing tables";
850
932
/* Free tables */
851
close_thread_tables(session);
853
log_slow_statement(session);
855
session->set_proc_info("cleaning up");
856
pthread_mutex_lock(&LOCK_thread_count); // For process list
857
session->set_proc_info(0);
858
session->command=COM_SLEEP;
860
session->query_length=0;
933
close_thread_tables(thd);
935
log_slow_statement(thd);
937
thd_proc_info(thd, "cleaning up");
938
VOID(pthread_mutex_lock(&LOCK_thread_count)); // For process list
939
thd_proc_info(thd, 0);
940
thd->command=COM_SLEEP;
861
943
thread_running--;
862
pthread_mutex_unlock(&LOCK_thread_count);
863
session->packet.shrink(session->variables.net_buffer_length); // Reclaim some memory
864
free_root(session->mem_root,MYF(MY_KEEP_PREALLOC));
944
VOID(pthread_mutex_unlock(&LOCK_thread_count));
945
thd->packet.shrink(thd->variables.net_buffer_length); // Reclaim some memory
946
free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
869
void log_slow_statement(Session *session)
951
void log_slow_statement(THD *thd)
871
logging_post_do(session);
954
The following should never be true with our current code base,
955
but better to keep this here so we don't accidently try to log a
956
statement in a trigger or stored function
958
if (unlikely(thd->in_sub_stmt))
959
return; // Don't set time for sub stmt
962
Do not log administrative statements unless the appropriate option is
963
set; do not log into slow log if reading from backup.
965
if (thd->enable_slow_log && !thd->user_time)
967
thd_proc_info(thd, "logging slow query");
968
uint64_t end_utime_of_query= thd->current_utime();
970
if (((end_utime_of_query - thd->utime_after_lock) >
971
thd->variables.long_query_time ||
972
((thd->server_status &
973
(SERVER_QUERY_NO_INDEX_USED | SERVER_QUERY_NO_GOOD_INDEX_USED)) &&
974
opt_log_queries_not_using_indexes &&
975
!(sql_command_flags[thd->lex->sql_command] & CF_STATUS_COMMAND))) &&
976
thd->examined_row_count >= thd->variables.min_examined_row_limit)
978
thd_proc_info(thd, "logging slow query");
979
thd->status_var.long_query_count++;
980
slow_log_print(thd, thd->query, thd->query_length, end_utime_of_query);
878
Create a TableList object for an INFORMATION_SCHEMA table.
988
Create a TABLE_LIST object for an INFORMATION_SCHEMA table.
880
990
This function is used in the parser to convert a SHOW or DESCRIBE
881
991
table_name command to a SELECT from INFORMATION_SCHEMA.
882
It prepares a SELECT_LEX and a TableList object to represent the
992
It prepares a SELECT_LEX and a TABLE_LIST object to represent the
883
993
given command as a SELECT parse tree.
885
@param session thread handle
995
@param thd thread handle
886
996
@param lex current lex
887
997
@param table_ident table alias if it's used
888
998
@param schema_table_idx the type of the INFORMATION_SCHEMA table to be
974
Read query from packet and store in session->query.
1084
Read query from packet and store in thd->query.
975
1085
Used in COM_QUERY and COM_STMT_PREPARE.
977
Sets the following Session variables:
1087
Sets the following THD variables:
984
true error; In this case session->fatal_error is set
1094
true error; In this case thd->fatal_error is set
987
bool alloc_query(Session *session, const char *packet, uint32_t packet_length)
1097
bool alloc_query(THD *thd, const char *packet, uint packet_length)
989
1099
/* Remove garbage at start and end of query */
990
while (packet_length > 0 && my_isspace(session->charset(), packet[0]))
1100
while (packet_length > 0 && my_isspace(thd->charset(), packet[0]))
993
1103
packet_length--;
995
1105
const char *pos= packet + packet_length; // Point at end null
996
1106
while (packet_length > 0 &&
997
(pos[-1] == ';' || my_isspace(session->charset() ,pos[-1])))
1107
(pos[-1] == ';' || my_isspace(thd->charset() ,pos[-1])))
1000
1110
packet_length--;
1002
1112
/* We must allocate some extra memory for query cache */
1003
session->query_length= 0; // Extra safety: Avoid races
1004
if (!(session->query= (char*) session->memdup_w_gap((unsigned char*) (packet),
1113
thd->query_length= 0; // Extra safety: Avoid races
1114
if (!(thd->query= (char*) thd->memdup_w_gap((uchar*) (packet),
1006
session->db_length+ 1)))
1116
thd->db_length+ 1)))
1008
session->query[packet_length]=0;
1009
session->query_length= packet_length;
1118
thd->query[packet_length]=0;
1119
thd->query_length= packet_length;
1011
1121
/* Reclaim some memory */
1012
session->packet.shrink(session->variables.net_buffer_length);
1013
session->convert_buffer.shrink(session->variables.net_buffer_length);
1122
thd->packet.shrink(thd->variables.net_buffer_length);
1123
thd->convert_buffer.shrink(thd->variables.net_buffer_length);
1018
static void reset_one_shot_variables(Session *session)
1128
static void reset_one_shot_variables(THD *thd)
1020
session->variables.character_set_client=
1130
thd->variables.character_set_client=
1021
1131
global_system_variables.character_set_client;
1022
session->variables.collation_connection=
1132
thd->variables.collation_connection=
1023
1133
global_system_variables.collation_connection;
1024
session->variables.collation_database=
1134
thd->variables.collation_database=
1025
1135
global_system_variables.collation_database;
1026
session->variables.collation_server=
1136
thd->variables.collation_server=
1027
1137
global_system_variables.collation_server;
1028
session->update_charset();
1029
session->variables.time_zone=
1138
thd->update_charset();
1139
thd->variables.time_zone=
1030
1140
global_system_variables.time_zone;
1031
session->variables.lc_time_names= &my_locale_en_US;
1032
session->one_shot_set= 0;
1141
thd->variables.lc_time_names= &my_locale_en_US;
1142
thd->one_shot_set= 0;
1037
Execute command saved in session and lex->sql_command.
1147
Execute command saved in thd and lex->sql_command.
1039
1149
Before every operation that can request a write lock for a table
1040
1150
wait if a global read lock exists. However do not wait if this
1162
1272
When option readonly is set deny operations which change non-temporary
1163
1273
tables. Except for the replication thread and the 'super' users.
1165
if (deny_updates_if_read_only_option(session, all_tables))
1275
if (deny_updates_if_read_only_option(thd, all_tables))
1167
1277
my_error(ER_OPTION_PREVENTS_STATEMENT, MYF(0), "--read-only");
1170
1280
} /* endif unlikely slave */
1171
status_var_increment(session->status_var.com_stat[lex->sql_command]);
1281
status_var_increment(thd->status_var.com_stat[lex->sql_command]);
1173
assert(session->transaction.stmt.modified_non_trans_table == false);
1283
assert(thd->transaction.stmt.modified_non_trans_table == false);
1175
1285
switch (lex->sql_command) {
1176
1286
case SQLCOM_SHOW_STATUS:
1178
system_status_var old_status_var= session->status_var;
1179
session->initial_status_var= &old_status_var;
1180
res= execute_sqlcom_select(session, all_tables);
1288
system_status_var old_status_var= thd->status_var;
1289
thd->initial_status_var= &old_status_var;
1290
res= execute_sqlcom_select(thd, all_tables);
1181
1291
/* Don't log SHOW STATUS commands to slow query log */
1182
session->server_status&= ~(SERVER_QUERY_NO_INDEX_USED |
1292
thd->server_status&= ~(SERVER_QUERY_NO_INDEX_USED |
1183
1293
SERVER_QUERY_NO_GOOD_INDEX_USED);
1185
1295
restore status variables, as we don't want 'show status' to cause
1188
1298
pthread_mutex_lock(&LOCK_status);
1189
add_diff_to_status(&global_status_var, &session->status_var,
1299
add_diff_to_status(&global_status_var, &thd->status_var,
1190
1300
&old_status_var);
1191
session->status_var= old_status_var;
1301
thd->status_var= old_status_var;
1192
1302
pthread_mutex_unlock(&LOCK_status);
1232
1344
value of constant
1234
1346
it->quick_fix_field();
1235
res = purge_master_logs_before_date(session, (ulong)it->val_int());
1347
res = purge_master_logs_before_date(thd, (ulong)it->val_int());
1238
1350
case SQLCOM_SHOW_WARNS:
1240
res= mysqld_show_warnings(session, (uint32_t)
1241
((1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_NOTE) |
1242
(1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_WARN) |
1243
(1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_ERROR)
1352
res= mysqld_show_warnings(thd, (ulong)
1353
((1L << (uint) DRIZZLE_ERROR::WARN_LEVEL_NOTE) |
1354
(1L << (uint) DRIZZLE_ERROR::WARN_LEVEL_WARN) |
1355
(1L << (uint) DRIZZLE_ERROR::WARN_LEVEL_ERROR)
1247
1359
case SQLCOM_SHOW_ERRORS:
1249
res= mysqld_show_warnings(session, (uint32_t)
1250
(1L << (uint32_t) DRIZZLE_ERROR::WARN_LEVEL_ERROR));
1361
res= mysqld_show_warnings(thd, (ulong)
1362
(1L << (uint) DRIZZLE_ERROR::WARN_LEVEL_ERROR));
1365
case SQLCOM_SHOW_SLAVE_HOSTS:
1367
res = show_slave_hosts(thd);
1370
case SQLCOM_SHOW_BINLOG_EVENTS:
1372
res = mysql_show_binlog_events(thd);
1253
1376
case SQLCOM_ASSIGN_TO_KEYCACHE:
1255
1378
assert(first_table == all_tables && first_table != 0);
1256
res= mysql_assign_to_keycache(session, first_table, &lex->ident);
1379
res= mysql_assign_to_keycache(thd, first_table, &lex->ident);
1259
1382
case SQLCOM_CHANGE_MASTER:
1261
1384
pthread_mutex_lock(&LOCK_active_mi);
1262
res = change_master(session,active_mi);
1385
res = change_master(thd,active_mi);
1263
1386
pthread_mutex_unlock(&LOCK_active_mi);
1468
1621
/* Prepare stack copies to be re-execution safe */
1469
1622
HA_CREATE_INFO create_info;
1470
Alter_info alter_info(lex->alter_info, session->mem_root);
1623
Alter_info alter_info(lex->alter_info, thd->mem_root);
1472
if (session->is_fatal_error) /* out of memory creating a copy of alter_info */
1625
if (thd->is_fatal_error) /* out of memory creating a copy of alter_info */
1475
1628
assert(first_table == all_tables && first_table != 0);
1476
if (end_active_trans(session))
1629
if (end_active_trans(thd))
1632
Currently CREATE INDEX or DROP INDEX cause a full table rebuild
1633
and thus classify as slow administrative statements just like
1636
thd->enable_slow_log= opt_log_slow_admin_statements;
1479
1638
memset(&create_info, 0, sizeof(create_info));
1480
1639
create_info.db_type= 0;
1481
1640
create_info.row_type= ROW_TYPE_NOT_USED;
1482
create_info.default_table_charset= session->variables.collation_database;
1641
create_info.default_table_charset= thd->variables.collation_database;
1484
res= mysql_alter_table(session, first_table->db, first_table->table_name,
1643
res= mysql_alter_table(thd, first_table->db, first_table->table_name,
1485
1644
&create_info, first_table, &alter_info,
1486
0, (order_st*) 0, 0);
1489
1648
case SQLCOM_SLAVE_START:
1491
1650
pthread_mutex_lock(&LOCK_active_mi);
1492
start_slave(session,active_mi,1 /* net report*/);
1651
start_slave(thd,active_mi,1 /* net report*/);
1493
1652
pthread_mutex_unlock(&LOCK_active_mi);
1550
1709
/* Don't yet allow changing of symlinks with ALTER TABLE */
1551
1710
if (create_info.data_file_name)
1552
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1711
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1553
1712
"DATA DIRECTORY option ignored");
1554
1713
if (create_info.index_file_name)
1555
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1714
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN, 0,
1556
1715
"INDEX DIRECTORY option ignored");
1557
1716
create_info.data_file_name= create_info.index_file_name= NULL;
1558
1717
/* ALTER TABLE ends previous transaction */
1559
if (end_active_trans(session))
1718
if (end_active_trans(thd))
1562
if (!session->locked_tables &&
1563
!(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
1721
if (!thd->locked_tables &&
1722
!(need_start_waiting= !wait_if_global_read_lock(thd, 0, 1)))
1569
res= mysql_alter_table(session, select_lex->db, lex->name.str,
1728
thd->enable_slow_log= opt_log_slow_admin_statements;
1729
res= mysql_alter_table(thd, select_lex->db, lex->name.str,
1573
1733
select_lex->order_list.elements,
1574
(order_st *) select_lex->order_list.first,
1734
(ORDER *) select_lex->order_list.first,
1578
1738
case SQLCOM_RENAME_TABLE:
1580
1740
assert(first_table == all_tables && first_table != 0);
1582
1742
for (table= first_table; table; table= table->next_local->next_local)
1584
TableList old_list, new_list;
1744
TABLE_LIST old_list, new_list;
1586
1746
we do not need initialize old_list and new_list because we will
1587
1747
come table[0] and table->next[0] there
1599
1759
case SQLCOM_SHOW_BINLOGS:
1601
res = show_binlogs(session);
1761
res = show_binlogs(thd);
1604
1764
case SQLCOM_SHOW_CREATE:
1605
1765
assert(first_table == all_tables && first_table != 0);
1607
res= mysqld_show_create(session, first_table);
1767
res= mysqld_show_create(thd, first_table);
1610
1770
case SQLCOM_CHECKSUM:
1612
1772
assert(first_table == all_tables && first_table != 0);
1613
res = mysql_checksum_table(session, first_table, &lex->check_opt);
1773
res = mysql_checksum_table(thd, first_table, &lex->check_opt);
1616
1776
case SQLCOM_REPAIR:
1618
1778
assert(first_table == all_tables && first_table != 0);
1619
res= mysql_repair_table(session, first_table, &lex->check_opt);
1779
thd->enable_slow_log= opt_log_slow_admin_statements;
1780
res= mysql_repair_table(thd, first_table, &lex->check_opt);
1620
1781
/* ! we write after unlocking the table */
1622
Presumably, REPAIR and binlog writing doesn't require synchronization
1624
write_bin_log(session, true, session->query, session->query_length);
1625
select_lex->table_list.first= (unsigned char*) first_table;
1782
if (!res && !lex->no_write_to_binlog)
1785
Presumably, REPAIR and binlog writing doesn't require synchronization
1787
write_bin_log(thd, true, thd->query, thd->query_length);
1789
select_lex->table_list.first= (uchar*) first_table;
1626
1790
lex->query_tables=all_tables;
1629
1793
case SQLCOM_CHECK:
1631
1795
assert(first_table == all_tables && first_table != 0);
1632
res = mysql_check_table(session, first_table, &lex->check_opt);
1633
select_lex->table_list.first= (unsigned char*) first_table;
1796
thd->enable_slow_log= opt_log_slow_admin_statements;
1797
res = mysql_check_table(thd, first_table, &lex->check_opt);
1798
select_lex->table_list.first= (uchar*) first_table;
1634
1799
lex->query_tables=all_tables;
1637
1802
case SQLCOM_ANALYZE:
1639
1804
assert(first_table == all_tables && first_table != 0);
1640
res= mysql_analyze_table(session, first_table, &lex->check_opt);
1805
thd->enable_slow_log= opt_log_slow_admin_statements;
1806
res= mysql_analyze_table(thd, first_table, &lex->check_opt);
1641
1807
/* ! we write after unlocking the table */
1642
write_bin_log(session, true, session->query, session->query_length);
1643
select_lex->table_list.first= (unsigned char*) first_table;
1808
if (!res && !lex->no_write_to_binlog)
1811
Presumably, ANALYZE and binlog writing doesn't require synchronization
1813
write_bin_log(thd, true, thd->query, thd->query_length);
1815
select_lex->table_list.first= (uchar*) first_table;
1644
1816
lex->query_tables=all_tables;
1648
1820
case SQLCOM_OPTIMIZE:
1650
1822
assert(first_table == all_tables && first_table != 0);
1651
res= mysql_optimize_table(session, first_table, &lex->check_opt);
1823
thd->enable_slow_log= opt_log_slow_admin_statements;
1824
res= (specialflag & (SPECIAL_SAFE_MODE | SPECIAL_NO_NEW_FUNC)) ?
1825
mysql_recreate_table(thd, first_table) :
1826
mysql_optimize_table(thd, first_table, &lex->check_opt);
1652
1827
/* ! we write after unlocking the table */
1653
write_bin_log(session, true, session->query, session->query_length);
1654
select_lex->table_list.first= (unsigned char*) first_table;
1828
if (!res && !lex->no_write_to_binlog)
1831
Presumably, OPTIMIZE and binlog writing doesn't require synchronization
1833
write_bin_log(thd, true, thd->query, thd->query_length);
1835
select_lex->table_list.first= (uchar*) first_table;
1655
1836
lex->query_tables=all_tables;
1658
1839
case SQLCOM_UPDATE:
1659
1840
assert(first_table == all_tables && first_table != 0);
1660
if (update_precheck(session, all_tables))
1841
if (update_precheck(thd, all_tables))
1662
1843
assert(select_lex->offset_limit == 0);
1663
1844
unit->set_limit(select_lex);
1664
res= (up_result= mysql_update(session, all_tables,
1845
res= (up_result= mysql_update(thd, all_tables,
1665
1846
select_lex->item_list,
1666
1847
lex->value_list,
1667
1848
select_lex->where,
1668
1849
select_lex->order_list.elements,
1669
(order_st *) select_lex->order_list.first,
1850
(ORDER *) select_lex->order_list.first,
1670
1851
unit->select_limit_cnt,
1671
1852
lex->duplicates, lex->ignore));
1672
1853
/* mysql_update return 2 if we need to switch to multi-update */
1850
2031
case SQLCOM_DELETE_MULTI:
1852
2033
assert(first_table == all_tables && first_table != 0);
1853
TableList *aux_tables=
1854
(TableList *)session->lex->auxiliary_table_list.first;
2034
TABLE_LIST *aux_tables=
2035
(TABLE_LIST *)thd->lex->auxiliary_table_list.first;
1855
2036
multi_delete *del_result;
1857
if (!session->locked_tables &&
1858
!(need_start_waiting= !wait_if_global_read_lock(session, 0, 1)))
2038
if (!thd->locked_tables &&
2039
!(need_start_waiting= !wait_if_global_read_lock(thd, 0, 1)))
1864
if ((res= multi_delete_precheck(session, all_tables)))
2045
if ((res= multi_delete_precheck(thd, all_tables)))
1867
2048
/* condition will be true on SP re-excuting */
1868
2049
if (select_lex->item_list.elements != 0)
1869
2050
select_lex->item_list.empty();
1870
if (add_item_to_list(session, new Item_null()))
2051
if (add_item_to_list(thd, new Item_null()))
1873
session->set_proc_info("init");
1874
if ((res= open_and_lock_tables(session, all_tables)))
2054
thd_proc_info(thd, "init");
2055
if ((res= open_and_lock_tables(thd, all_tables)))
1877
if ((res= mysql_multi_delete_prepare(session)))
2058
if ((res= mysql_multi_delete_prepare(thd)))
1880
if (!session->is_fatal_error &&
2061
if (!thd->is_fatal_error &&
1881
2062
(del_result= new multi_delete(aux_tables, lex->table_count)))
1883
res= mysql_select(session, &select_lex->ref_pointer_array,
2064
res= mysql_select(thd, &select_lex->ref_pointer_array,
1884
2065
select_lex->get_table_list(),
1885
2066
select_lex->with_wild,
1886
2067
select_lex->item_list,
1887
2068
select_lex->where,
1888
0, (order_st *)NULL, (order_st *)NULL, (Item *)NULL,
1890
select_lex->options | session->options |
2069
0, (ORDER *)NULL, (ORDER *)NULL, (Item *)NULL,
2071
select_lex->options | thd->options |
1891
2072
SELECT_NO_JOIN_CACHE | SELECT_NO_UNLOCK |
1892
2073
OPTION_SETUP_TABLES_DONE,
1893
2074
del_result, unit, select_lex);
1894
res|= session->is_error();
2075
res|= thd->is_error();
1896
2077
del_result->abort();
1897
2078
delete del_result;
2236
if ((!it->fixed && it->fix_fields(lex->session, &it)) || it->check_cols(1))
2425
if ((!it->fixed && it->fix_fields(lex->thd, &it)) || it->check_cols(1))
2238
2427
my_message(ER_SET_CONSTANTS_ONLY, ER(ER_SET_CONSTANTS_ONLY),
2242
sql_kill(session, (ulong)it->val_int(), lex->type & ONLY_KILL_QUERY);
2431
sql_kill(thd, (ulong)it->val_int(), lex->type & ONLY_KILL_QUERY);
2245
2434
case SQLCOM_BEGIN:
2246
if (session->transaction.xid_state.xa_state != XA_NOTR)
2435
if (thd->transaction.xid_state.xa_state != XA_NOTR)
2248
2437
my_error(ER_XAER_RMFAIL, MYF(0),
2249
xa_state_names[session->transaction.xid_state.xa_state]);
2438
xa_state_names[thd->transaction.xid_state.xa_state]);
2253
2442
Breakpoints for backup testing.
2255
if (begin_trans(session))
2444
if (begin_trans(thd))
2259
2448
case SQLCOM_COMMIT:
2260
if (end_trans(session, lex->tx_release ? COMMIT_RELEASE :
2449
if (end_trans(thd, lex->tx_release ? COMMIT_RELEASE :
2261
2450
lex->tx_chain ? COMMIT_AND_CHAIN : COMMIT))
2265
2454
case SQLCOM_ROLLBACK:
2266
if (end_trans(session, lex->tx_release ? ROLLBACK_RELEASE :
2455
if (end_trans(thd, lex->tx_release ? ROLLBACK_RELEASE :
2267
2456
lex->tx_chain ? ROLLBACK_AND_CHAIN : ROLLBACK))
2271
2460
case SQLCOM_RELEASE_SAVEPOINT:
2274
for (sv=session->transaction.savepoints; sv; sv=sv->prev)
2463
for (sv=thd->transaction.savepoints; sv; sv=sv->prev)
2276
2465
if (my_strnncoll(system_charset_info,
2277
(unsigned char *)lex->ident.str, lex->ident.length,
2278
(unsigned char *)sv->name, sv->length) == 0)
2466
(uchar *)lex->ident.str, lex->ident.length,
2467
(uchar *)sv->name, sv->length) == 0)
2283
if (ha_release_savepoint(session, sv))
2472
if (ha_release_savepoint(thd, sv))
2284
2473
res= true; // cannot happen
2287
session->transaction.savepoints=sv->prev;
2476
thd->transaction.savepoints=sv->prev;
2290
2479
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
2293
2482
case SQLCOM_ROLLBACK_TO_SAVEPOINT:
2296
for (sv=session->transaction.savepoints; sv; sv=sv->prev)
2485
for (sv=thd->transaction.savepoints; sv; sv=sv->prev)
2298
2487
if (my_strnncoll(system_charset_info,
2299
(unsigned char *)lex->ident.str, lex->ident.length,
2300
(unsigned char *)sv->name, sv->length) == 0)
2488
(uchar *)lex->ident.str, lex->ident.length,
2489
(uchar *)sv->name, sv->length) == 0)
2305
if (ha_rollback_to_savepoint(session, sv))
2494
if (ha_rollback_to_savepoint(thd, sv))
2306
2495
res= true; // cannot happen
2309
if (((session->options & OPTION_KEEP_LOG) ||
2310
session->transaction.all.modified_non_trans_table) &&
2311
!session->slave_thread)
2312
push_warning(session, DRIZZLE_ERROR::WARN_LEVEL_WARN,
2498
if (((thd->options & OPTION_KEEP_LOG) ||
2499
thd->transaction.all.modified_non_trans_table) &&
2501
push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN,
2313
2502
ER_WARNING_NOT_COMPLETE_ROLLBACK,
2314
2503
ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
2317
session->transaction.savepoints=sv;
2506
thd->transaction.savepoints=sv;
2320
2509
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "SAVEPOINT", lex->ident.str);
2323
2512
case SQLCOM_SAVEPOINT:
2324
if (!(session->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN)) || !opt_using_transactions)
2513
if (!(thd->options & (OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN) ||
2514
thd->in_sub_stmt) || !opt_using_transactions)
2328
2518
SAVEPOINT **sv, *newsv;
2329
for (sv=&session->transaction.savepoints; *sv; sv=&(*sv)->prev)
2519
for (sv=&thd->transaction.savepoints; *sv; sv=&(*sv)->prev)
2331
2521
if (my_strnncoll(system_charset_info,
2332
(unsigned char *)lex->ident.str, lex->ident.length,
2333
(unsigned char *)(*sv)->name, (*sv)->length) == 0)
2522
(uchar *)lex->ident.str, lex->ident.length,
2523
(uchar *)(*sv)->name, (*sv)->length) == 0)
2336
2526
if (*sv) /* old savepoint of the same name exists */
2339
ha_release_savepoint(session, *sv); // it cannot fail
2529
ha_release_savepoint(thd, *sv); // it cannot fail
2340
2530
*sv=(*sv)->prev;
2342
else if ((newsv=(SAVEPOINT *) alloc_root(&session->transaction.mem_root,
2532
else if ((newsv=(SAVEPOINT *) alloc_root(&thd->transaction.mem_root,
2343
2533
savepoint_alloc_size)) == 0)
2345
2535
my_error(ER_OUT_OF_RESOURCES, MYF(0));
2348
newsv->name=strmake_root(&session->transaction.mem_root,
2538
newsv->name=strmake_root(&thd->transaction.mem_root,
2349
2539
lex->ident.str, lex->ident.length);
2350
2540
newsv->length=lex->ident.length;
2535
Reset Session part responsible for command processing state.
2726
Reset THD part responsible for command processing state.
2537
2728
This needs to be called before execution of every statement
2538
2729
(prepared or conventional).
2539
2730
It is not called by substatements of routines.
2542
Make it a method of Session and align its name with the rest of
2733
Make it a method of THD and align its name with the rest of
2543
2734
reset/end/start/init methods.
2545
Call it after we use Session for queries, not before.
2736
Call it after we use THD for queries, not before.
2548
void mysql_reset_session_for_next_command(Session *session)
2739
void mysql_reset_thd_for_next_command(THD *thd)
2550
session->free_list= 0;
2551
session->select_number= 1;
2741
assert(! thd->in_sub_stmt);
2743
thd->select_number= 1;
2553
2745
Those two lines below are theoretically unneeded as
2554
Session::cleanup_after_query() should take care of this already.
2746
THD::cleanup_after_query() should take care of this already.
2556
session->auto_inc_intervals_in_cur_stmt_for_binlog.empty();
2557
session->stmt_depends_on_first_successful_insert_id_in_prev_stmt= 0;
2748
thd->auto_inc_intervals_in_cur_stmt_for_binlog.empty();
2749
thd->stmt_depends_on_first_successful_insert_id_in_prev_stmt= 0;
2559
session->query_start_used= 0;
2560
session->is_fatal_error= session->time_zone_used= 0;
2561
session->server_status&= ~ (SERVER_MORE_RESULTS_EXISTS |
2751
thd->query_start_used= 0;
2752
thd->is_fatal_error= thd->time_zone_used= 0;
2753
thd->server_status&= ~ (SERVER_MORE_RESULTS_EXISTS |
2562
2754
SERVER_QUERY_NO_INDEX_USED |
2563
2755
SERVER_QUERY_NO_GOOD_INDEX_USED);
2754
2946
- first, call query_cache_send_result_to_client,
2755
2947
- second, if caching failed, initialise the lexical and syntactic parser.
2756
2948
The problem is that the query cache depends on a clean initialization
2757
of (among others) lex->safe_to_cache_query and session->server_status,
2949
of (among others) lex->safe_to_cache_query and thd->server_status,
2758
2950
which are reset respectively in
2760
- mysql_reset_session_for_next_command()
2952
- mysql_reset_thd_for_next_command()
2761
2953
So, initializing the lexical analyser *before* using the query cache
2762
2954
is required for the cache to work properly.
2763
2955
FIXME: cleanup the dependencies in the code to simplify this.
2766
mysql_reset_session_for_next_command(session);
2958
mysql_reset_thd_for_next_command(thd);
2769
LEX *lex= session->lex;
2771
Lex_input_stream lip(session, inBuf, length);
2773
bool err= parse_sql(session, &lip);
2963
Lex_input_stream lip(thd, inBuf, length);
2965
bool err= parse_sql(thd, &lip, NULL);
2774
2966
*found_semicolon= lip.found_semicolon;
2779
if (! session->is_error())
2971
if (! thd->is_error())
2782
Binlog logs a string starting from session->query and having length
2783
session->query_length; so we set session->query_length correctly (to not
2974
Binlog logs a string starting from thd->query and having length
2975
thd->query_length; so we set thd->query_length correctly (to not
2784
2976
log several statements in one event, when we executed only first).
2785
2977
We set it to not see the ';' (otherwise it would get into binlog
2786
2978
and Query_log_event::print() would give ';;' output).
4246
extern int DRIZZLEparse(void *session); // from sql_yacc.cc
4501
extern int MYSQLparse(void *thd); // from sql_yacc.cc
4250
This is a wrapper of DRIZZLEparse(). All the code should call parse_sql()
4251
instead of DRIZZLEparse().
4505
This is a wrapper of MYSQLparse(). All the code should call parse_sql()
4506
instead of MYSQLparse().
4253
@param session Thread context.
4508
@param thd Thread context.
4254
4509
@param lip Lexer context.
4510
@param creation_ctx Object creation context.
4256
4512
@return Error status.
4257
4513
@retval false on success.
4258
4514
@retval true on parsing error.
4261
bool parse_sql(Session *session, Lex_input_stream *lip)
4517
bool parse_sql(THD *thd,
4518
Lex_input_stream *lip,
4519
Object_creation_ctx *creation_ctx)
4263
assert(session->m_lip == NULL);
4521
assert(thd->m_lip == NULL);
4523
/* Backup creation context. */
4525
Object_creation_ctx *backup_ctx= NULL;
4528
backup_ctx= creation_ctx->set_n_backup(thd);
4265
4530
/* Set Lex_input_stream. */
4267
session->m_lip= lip;
4269
4534
/* Parse the query. */
4271
bool mysql_parse_status= DRIZZLEparse(session) != 0;
4273
/* Check that if DRIZZLEparse() failed, session->is_error() is set. */
4275
assert(!mysql_parse_status || session->is_error());
4536
bool mysql_parse_status= MYSQLparse(thd) != 0;
4538
/* Check that if MYSQLparse() failed, thd->is_error() is set. */
4540
assert(!mysql_parse_status || thd->is_error());
4277
4542
/* Reset Lex_input_stream. */
4279
session->m_lip= NULL;
4546
/* Restore creation context. */
4549
creation_ctx->restore_env(thd, backup_ctx);
4281
4551
/* That's it. */
4283
return mysql_parse_status || session->is_fatal_error;
4553
return mysql_parse_status || thd->is_fatal_error;