Commit 04659677 authored by andrey@lmy004's avatar andrey@lmy004

WL#3337 (Events new infrasctructure)

Second cut of separating parsing phase from execution phase
Separate Event_timed from parsing phase and introducing Event_parse_data.
parent e5936fce
...@@ -1778,3 +1778,8 @@ vio/viotest-sslconnect.cpp ...@@ -1778,3 +1778,8 @@ vio/viotest-sslconnect.cpp
vio/viotest.cpp vio/viotest.cpp
zlib/*.ds? zlib/*.ds?
zlib/*.vcproj zlib/*.vcproj
libmysql/viosocket.o.6WmSJk
libmysqld/event_data_objects.cc
libmysqld/event_db_repository.cc
libmysqld/event_queue.cc
server-tools/instance-manager/net_serv.cc
...@@ -22,6 +22,95 @@ ...@@ -22,6 +22,95 @@
#include "sp_head.h" #include "sp_head.h"
Event_parse_data *
Event_parse_data::new_instance(THD *thd)
{
return new (thd->mem_root) Event_parse_data;
}
Event_parse_data::Event_parse_data()
{
item_execute_at= item_expression= item_starts= item_ends= NULL;
}
/*
Set body of the event - what should be executed.
SYNOPSIS
Event_timed::init_body()
thd THD
NOTE
The body is extracted by copying all data between the
start of the body set by another method and the current pointer in Lex.
Some questionable removal of characters is done in here, and that part
should be refactored when the parser is smarter.
*/
void
Event_parse_data::init_body(THD *thd)
{
DBUG_ENTER("Event_parse_data::init_body");
DBUG_PRINT("info", ("body=[%s] body_begin=0x%ld end=0x%ld", body_begin,
body_begin, thd->lex->ptr));
body.length= thd->lex->ptr - body_begin;
const uchar *body_end= body_begin + body.length - 1;
/* Trim nuls or close-comments ('*'+'/') or spaces at the end */
while (body_begin < body_end)
{
if ((*body_end == '\0') ||
(my_isspace(thd->variables.character_set_client, *body_end)))
{ /* consume NULs and meaningless whitespace */
--body.length;
--body_end;
continue;
}
/*
consume closing comments
This is arguably wrong, but it's the best we have until the parser is
changed to be smarter. FIXME PARSER
See also the sp_head code, where something like this is done also.
One idea is to keep in the lexer structure the count of the number of
open-comments we've entered, and scan left-to-right looking for a
closing comment IFF the count is greater than zero.
Another idea is to remove the closing comment-characters wholly in the
parser, since that's where it "removes" the opening characters.
*/
if ((*(body_end - 1) == '*') && (*body_end == '/'))
{
DBUG_PRINT("info", ("consumend one '*" "/' comment in the query '%s'",
body_begin));
body.length-= 2;
body_end-= 2;
continue;
}
break; /* none were found, so we have excised all we can. */
}
/* the first is always whitespace which I cannot skip in the parser */
while (my_isspace(thd->variables.character_set_client, *body_begin))
{
++body_begin;
--body.length;
}
body.str= thd->strmake((char *)body_begin, body.length);
DBUG_VOID_RETURN;
}
/* /*
Constructor Constructor
......
...@@ -259,19 +259,16 @@ class Event_parse_data : public Sql_alloc ...@@ -259,19 +259,16 @@ class Event_parse_data : public Sql_alloc
my_bool ends_null; my_bool ends_null;
my_bool execute_at_null; my_bool execute_at_null;
sp_name *identifier;
Item* item_expression; Item* item_expression;
Item* item_interval;
longlong expression; longlong expression;
interval_type interval; interval_type interval;
// ulonglong created;
// ulonglong modified;
static Event_parse_data * static Event_parse_data *
new_instance(THD *thd); new_instance(THD *thd);
Event_parse_data() {} Event_parse_data();
~Event_parse_data() {} ~Event_parse_data();
int int
init_definer(THD *thd); init_definer(THD *thd);
......
...@@ -904,8 +904,8 @@ db_find_event(THD *thd, sp_name *name, Event_timed **ett, TABLE *tbl, ...@@ -904,8 +904,8 @@ db_find_event(THD *thd, sp_name *name, Event_timed **ett, TABLE *tbl,
*/ */
int int
Events::create_event(THD *thd, Event_timed *et, uint create_options, Events::create_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected) uint create_options, uint *rows_affected)
{ {
int ret; int ret;
...@@ -948,8 +948,8 @@ Events::create_event(THD *thd, Event_timed *et, uint create_options, ...@@ -948,8 +948,8 @@ Events::create_event(THD *thd, Event_timed *et, uint create_options,
*/ */
int int
Events::update_event(THD *thd, Event_timed *et, sp_name *new_name, Events::update_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected) sp_name *new_name, uint *rows_affected)
{ {
int ret; int ret;
...@@ -1054,8 +1054,8 @@ int db_drop_event(THD *thd, Event_timed *et, bool drop_if_exists, ...@@ -1054,8 +1054,8 @@ int db_drop_event(THD *thd, Event_timed *et, bool drop_if_exists,
*/ */
int int
Events::drop_event(THD *thd, Event_timed *et, bool drop_if_exists, Events::drop_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected) bool drop_if_exists, uint *rows_affected)
{ {
int ret; int ret;
...@@ -1091,7 +1091,7 @@ Events::show_create_event(THD *thd, sp_name *spn) ...@@ -1091,7 +1091,7 @@ Events::show_create_event(THD *thd, sp_name *spn)
Event_timed *et= NULL; Event_timed *et= NULL;
Open_tables_state backup; Open_tables_state backup;
DBUG_ENTER("evex_update_event"); DBUG_ENTER("Events::show_create_event");
DBUG_PRINT("enter", ("name: %*s", spn->m_name.length, spn->m_name.str)); DBUG_PRINT("enter", ("name: %*s", spn->m_name.length, spn->m_name.str));
thd->reset_n_backup_open_tables_state(&backup); thd->reset_n_backup_open_tables_state(&backup);
......
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
class Event_timed; class Event_timed;
class Event_parse_data;
class Events class Events
{ {
...@@ -47,16 +48,16 @@ class Events ...@@ -47,16 +48,16 @@ class Events
}; };
static int static int
create_event(THD *thd, Event_timed *et, uint create_options, create_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected); uint create_options, uint *rows_affected);
static int static int
update_event(THD *thd, Event_timed *et, sp_name *new_name, update_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected); sp_name *new_name, uint *rows_affected);
static int static int
drop_event(THD *thd, Event_timed *et, bool drop_if_exists, drop_event(THD *thd, Event_timed *et, Event_parse_data *parse_data,
uint *rows_affected); bool drop_if_exists, uint *rows_affected);
static int static int
open_event_table(THD *thd, enum thr_lock_type lock_type, TABLE **table); open_event_table(THD *thd, enum thr_lock_type lock_type, TABLE **table);
......
...@@ -5839,6 +5839,3 @@ ER_CANT_ACTIVATE_LOG ...@@ -5839,6 +5839,3 @@ ER_CANT_ACTIVATE_LOG
eng "Cannot activate '%-.64s' log." eng "Cannot activate '%-.64s' log."
ER_RBR_NOT_AVAILABLE ER_RBR_NOT_AVAILABLE
eng "The server was not built with row-based replication" eng "The server was not built with row-based replication"
ER_EVENT_RECURSIVITY_FORBIDDEN
eng "Recursivity of EVENT DDL statements is forbidden when body is present"
...@@ -28,6 +28,7 @@ class sp_pcontext; ...@@ -28,6 +28,7 @@ class sp_pcontext;
class st_alter_tablespace; class st_alter_tablespace;
class partition_info; class partition_info;
class Event_timed; class Event_timed;
class Event_parse_data;
#ifdef MYSQL_SERVER #ifdef MYSQL_SERVER
/* /*
...@@ -1017,6 +1018,7 @@ typedef struct st_lex : public Query_tables_list ...@@ -1017,6 +1018,7 @@ typedef struct st_lex : public Query_tables_list
st_sp_chistics sp_chistics; st_sp_chistics sp_chistics;
Event_timed *et; Event_timed *et;
Event_parse_data *event_parse_data;
bool et_compile_phase; bool et_compile_phase;
bool only_view; /* used for SHOW CREATE TABLE/VIEW */ bool only_view; /* used for SHOW CREATE TABLE/VIEW */
......
...@@ -3848,17 +3848,17 @@ mysql_execute_command(THD *thd) ...@@ -3848,17 +3848,17 @@ mysql_execute_command(THD *thd)
switch (lex->sql_command) { switch (lex->sql_command) {
case SQLCOM_CREATE_EVENT: case SQLCOM_CREATE_EVENT:
res= Events::create_event(thd, lex->et, res= Events::create_event(thd, lex->et, lex->event_parse_data,
(uint) lex->create_info.options, (uint) lex->create_info.options,
&rows_affected); &rows_affected);
break; break;
case SQLCOM_ALTER_EVENT: case SQLCOM_ALTER_EVENT:
res= Events::update_event(thd, lex->et, lex->spname, res= Events::update_event(thd, lex->et, lex->event_parse_data,
&rows_affected); lex->spname, &rows_affected);
break; break;
case SQLCOM_DROP_EVENT: case SQLCOM_DROP_EVENT:
res= Events::drop_event(thd, lex->et, lex->drop_if_exists, res= Events::drop_event(thd, lex->et, lex->event_parse_data,
&rows_affected); lex->drop_if_exists, &rows_affected);
default:; default:;
} }
DBUG_PRINT("info", ("CREATE/ALTER/DROP returned error code=%d af_rows=%d", DBUG_PRINT("info", ("CREATE/ALTER/DROP returned error code=%d af_rows=%d",
...@@ -3880,7 +3880,6 @@ mysql_execute_command(THD *thd) ...@@ -3880,7 +3880,6 @@ mysql_execute_command(THD *thd)
case SQLCOM_SHOW_CREATE_EVENT: case SQLCOM_SHOW_CREATE_EVENT:
{ {
DBUG_ASSERT(lex->spname); DBUG_ASSERT(lex->spname);
DBUG_ASSERT(lex->et);
if (! lex->spname->m_db.str) if (! lex->spname->m_db.str)
{ {
my_message(ER_NO_DB_ERROR, ER(ER_NO_DB_ERROR), MYF(0)); my_message(ER_NO_DB_ERROR, ER(ER_NO_DB_ERROR), MYF(0));
......
...@@ -1280,6 +1280,8 @@ create: ...@@ -1280,6 +1280,8 @@ create:
if (!(lex->et= new(YYTHD->mem_root) Event_timed())) // implicitly calls Event_timed::init() if (!(lex->et= new(YYTHD->mem_root) Event_timed())) // implicitly calls Event_timed::init()
YYABORT; YYABORT;
if (!(lex->event_parse_data= Event_parse_data::new_instance(YYTHD)))
YYABORT;
/* /*
We have to turn of CLIENT_MULTI_QUERIES while parsing a We have to turn of CLIENT_MULTI_QUERIES while parsing a
...@@ -1289,6 +1291,9 @@ create: ...@@ -1289,6 +1291,9 @@ create:
$<ulong_num>$= YYTHD->client_capabilities & CLIENT_MULTI_QUERIES; $<ulong_num>$= YYTHD->client_capabilities & CLIENT_MULTI_QUERIES;
YYTHD->client_capabilities &= (~CLIENT_MULTI_QUERIES); YYTHD->client_capabilities &= (~CLIENT_MULTI_QUERIES);
lex->event_parse_data->identifier= $4;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
lex->et->init_name(YYTHD, $4); lex->et->init_name(YYTHD, $4);
...@@ -1344,6 +1349,8 @@ create: ...@@ -1344,6 +1349,8 @@ create:
ev_schedule_time: EVERY_SYM expr interval ev_schedule_time: EVERY_SYM expr interval
{ {
Lex->event_parse_data->item_expression= $2;
Lex->event_parse_data->interval= $3;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
...@@ -1365,6 +1372,7 @@ ev_schedule_time: EVERY_SYM expr interval ...@@ -1365,6 +1372,7 @@ ev_schedule_time: EVERY_SYM expr interval
ev_ends ev_ends
| AT_SYM expr | AT_SYM expr
{ {
Lex->event_parse_data->item_execute_at= $2;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
...@@ -1395,6 +1403,7 @@ ev_schedule_time: EVERY_SYM expr interval ...@@ -1395,6 +1403,7 @@ ev_schedule_time: EVERY_SYM expr interval
opt_ev_status: /* empty */ { $$= 0; } opt_ev_status: /* empty */ { $$= 0; }
| ENABLE_SYM | ENABLE_SYM
{ {
Lex->event_parse_data->status= Event_parse_data::ENABLED;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
lex->et->status= Event_timed::ENABLED; lex->et->status= Event_timed::ENABLED;
...@@ -1402,6 +1411,7 @@ opt_ev_status: /* empty */ { $$= 0; } ...@@ -1402,6 +1411,7 @@ opt_ev_status: /* empty */ { $$= 0; }
} }
| DISABLE_SYM | DISABLE_SYM
{ {
Lex->event_parse_data->status= Event_parse_data::DISABLED;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
...@@ -1412,10 +1422,12 @@ opt_ev_status: /* empty */ { $$= 0; } ...@@ -1412,10 +1422,12 @@ opt_ev_status: /* empty */ { $$= 0; }
ev_starts: /* empty */ ev_starts: /* empty */
{ {
Lex->event_parse_data->item_starts= new Item_func_now_local();
Lex->et->init_starts(YYTHD, new Item_func_now_local()); Lex->et->init_starts(YYTHD, new Item_func_now_local());
} }
| STARTS_SYM expr | STARTS_SYM expr
{ {
Lex->event_parse_data->item_starts= $2;
LEX *lex= Lex; LEX *lex= Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
...@@ -1443,6 +1455,7 @@ ev_starts: /* empty */ ...@@ -1443,6 +1455,7 @@ ev_starts: /* empty */
ev_ends: /* empty */ ev_ends: /* empty */
| ENDS_SYM expr | ENDS_SYM expr
{ {
Lex->event_parse_data->item_ends= $2;
LEX *lex= Lex; LEX *lex= Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
...@@ -1467,6 +1480,8 @@ opt_ev_on_completion: /* empty */ { $$= 0; } ...@@ -1467,6 +1480,8 @@ opt_ev_on_completion: /* empty */ { $$= 0; }
ev_on_completion: ev_on_completion:
ON COMPLETION_SYM PRESERVE_SYM ON COMPLETION_SYM PRESERVE_SYM
{ {
Lex->event_parse_data->on_completion=
Event_parse_data::ON_COMPLETION_PRESERVE;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
lex->et->on_completion= Event_timed::ON_COMPLETION_PRESERVE; lex->et->on_completion= Event_timed::ON_COMPLETION_PRESERVE;
...@@ -1474,6 +1489,8 @@ ev_on_completion: ...@@ -1474,6 +1489,8 @@ ev_on_completion:
} }
| ON COMPLETION_SYM NOT_SYM PRESERVE_SYM | ON COMPLETION_SYM NOT_SYM PRESERVE_SYM
{ {
Lex->event_parse_data->on_completion=
Event_parse_data::ON_COMPLETION_DROP;
LEX *lex=Lex; LEX *lex=Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
lex->et->on_completion= Event_timed::ON_COMPLETION_DROP; lex->et->on_completion= Event_timed::ON_COMPLETION_DROP;
...@@ -1484,6 +1501,7 @@ ev_on_completion: ...@@ -1484,6 +1501,7 @@ ev_on_completion:
opt_ev_comment: /* empty */ { $$= 0; } opt_ev_comment: /* empty */ { $$= 0; }
| COMMENT_SYM TEXT_STRING_sys | COMMENT_SYM TEXT_STRING_sys
{ {
Lex->comment= Lex->event_parse_data->comment= $2;
LEX *lex= Lex; LEX *lex= Lex;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
...@@ -1518,6 +1536,8 @@ ev_sql_stmt: ...@@ -1518,6 +1536,8 @@ ev_sql_stmt:
lex->sphead->m_body_begin= lex->ptr; lex->sphead->m_body_begin= lex->ptr;
} }
Lex->event_parse_data->body_begin= lex->ptr;
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
lex->et->body_begin= lex->ptr; lex->et->body_begin= lex->ptr;
...@@ -1538,6 +1558,7 @@ ev_sql_stmt: ...@@ -1538,6 +1558,7 @@ ev_sql_stmt:
lex->et->sphead= lex->sphead; lex->et->sphead= lex->sphead;
lex->sphead= NULL; lex->sphead= NULL;
} }
Lex->event_parse_data->init_body(YYTHD);
if (!lex->et_compile_phase) if (!lex->et_compile_phase)
{ {
lex->et->init_body(YYTHD); lex->et->init_body(YYTHD);
...@@ -4728,6 +4749,10 @@ alter: ...@@ -4728,6 +4749,10 @@ alter:
} }
lex->spname= 0;//defensive programming lex->spname= 0;//defensive programming
if (!(Lex->event_parse_data= Event_parse_data::new_instance(YYTHD)))
YYABORT;
Lex->event_parse_data->identifier= $3;
if (!(et= new (YYTHD->mem_root) Event_timed()))// implicitly calls Event_timed::init() if (!(et= new (YYTHD->mem_root) Event_timed()))// implicitly calls Event_timed::init()
YYABORT; YYABORT;
lex->et = et; lex->et = et;
...@@ -4739,9 +4764,9 @@ alter: ...@@ -4739,9 +4764,9 @@ alter:
} }
/* /*
We have to turn of CLIENT_MULTI_QUERIES while parsing a We have to turn of CLIENT_MULTI_QUERIES while parsing a
stored procedure, otherwise yylex will chop it into pieces stored procedure, otherwise yylex will chop it into pieces
at each ';'. at each ';'.
*/ */
$<ulong_num>$= YYTHD->client_capabilities & CLIENT_MULTI_QUERIES; $<ulong_num>$= YYTHD->client_capabilities & CLIENT_MULTI_QUERIES;
YYTHD->client_capabilities &= ~CLIENT_MULTI_QUERIES; YYTHD->client_capabilities &= ~CLIENT_MULTI_QUERIES;
...@@ -7661,6 +7686,10 @@ drop: ...@@ -7661,6 +7686,10 @@ drop:
} }
| DROP EVENT_SYM if_exists sp_name | DROP EVENT_SYM if_exists sp_name
{ {
if (!(Lex->event_parse_data= Event_parse_data::new_instance(YYTHD)))
YYABORT;
Lex->event_parse_data->identifier= $4;
LEX *lex=Lex; LEX *lex=Lex;
if (lex->et) if (lex->et)
...@@ -8430,12 +8459,8 @@ show_param: ...@@ -8430,12 +8459,8 @@ show_param:
} }
| CREATE EVENT_SYM sp_name | CREATE EVENT_SYM sp_name
{ {
Lex->sql_command = SQLCOM_SHOW_CREATE_EVENT;
Lex->spname= $3; Lex->spname= $3;
Lex->et= new (YYTHD->mem_root) Event_timed(); Lex->sql_command = SQLCOM_SHOW_CREATE_EVENT;
if (!Lex->et)
YYABORT;
Lex->et->init_definer(YYTHD);
} }
; ;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment