summaryrefslogtreecommitdiff
path: root/sql/sql_yacc_ora.yy
diff options
context:
space:
mode:
Diffstat (limited to 'sql/sql_yacc_ora.yy')
-rw-r--r--sql/sql_yacc_ora.yy335
1 files changed, 217 insertions, 118 deletions
diff --git a/sql/sql_yacc_ora.yy b/sql/sql_yacc_ora.yy
index b5387a86fc2..719a6e39e2a 100644
--- a/sql/sql_yacc_ora.yy
+++ b/sql/sql_yacc_ora.yy
@@ -295,10 +295,10 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
%parse-param { THD *thd }
%lex-param { THD *thd }
/*
- Currently there are 49 shift/reduce conflicts.
+ Currently there are 48 shift/reduce conflicts.
We should not introduce new conflicts any more.
*/
-%expect 49
+%expect 48
/*
Comments for TOKENS.
@@ -320,6 +320,8 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
*/
+%token <lex_str> '@'
+
/*
Reserved keywords and operators
*/
@@ -352,7 +354,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
%token CASE_SYM /* SQL-2003-R */
%token CAST_SYM /* SQL-2003-R */
%token CHANGE
-%token CHAR_SYM /* SQL-2003-R */
+%token <kwd> CHAR_SYM /* SQL-2003-R */
%token CHECK_SYM /* SQL-2003-R */
%token COLLATE_SYM /* SQL-2003-R */
%token CONDITION_SYM /* SQL-2003-R, SQL-2008-R */
@@ -381,7 +383,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
%token DECIMAL_SYM /* SQL-2003-R */
%token DECLARE_MARIADB_SYM /* SQL-2003-R */
%token DECLARE_ORACLE_SYM /* Oracle-R */
-%token DEFAULT /* SQL-2003-R */
+%token <kwd> DEFAULT /* SQL-2003-R */
%token DELETE_DOMAIN_ID_SYM
%token DELETE_SYM /* SQL-2003-R */
%token DENSE_RANK_SYM
@@ -1228,7 +1230,6 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
ident
label_ident
sp_decl_ident
- ident_set_usual_case
ident_or_empty
ident_table_alias
ident_sysvar_name
@@ -1247,6 +1248,8 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
IDENT_QUOTED
IDENT_cli
ident_cli
+ ident_cli_set_usual_case
+ ident_cli_directly_assignable
%type <kwd>
keyword_data_type
@@ -1264,6 +1267,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
keyword_table_alias
keyword_verb_clause
keyword_directly_assignable
+ charset
%type <table>
table_ident table_ident_nodb references xid
@@ -1557,7 +1561,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, size_t *yystacksize);
table_to_table_list table_to_table opt_table_list opt_as
handler_rkey_function handler_read_or_scan
single_multi table_wild_list table_wild_one opt_wild
- opt_and charset
+ opt_and
select_var_list select_var_list_init help
opt_extended_describe shutdown
opt_format_json
@@ -4046,16 +4050,18 @@ sp_proc_stmt_if:
sp_statement:
statement
- | ident_directly_assignable
+ | ident_cli_directly_assignable
{
// Direct procedure call (without the CALL keyword)
- if (unlikely(Lex->call_statement_start(thd, &$1)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->call_statement_start(thd, &tmp)))
MYSQL_YYABORT;
}
opt_sp_cparam_list
- | ident_directly_assignable '.' ident
+ | ident_cli_directly_assignable '.' ident
{
- if (unlikely(Lex->call_statement_start(thd, &$1, &$3)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->call_statement_start(thd, &tmp, &$3)))
MYSQL_YYABORT;
}
opt_sp_cparam_list
@@ -7385,8 +7391,8 @@ sp_param_type_with_opt_collate:
;
charset:
- CHAR_SYM SET {}
- | CHARSET {}
+ CHAR_SYM SET { $$= $1; }
+ | CHARSET { $$= $1; }
;
charset_name:
@@ -15672,13 +15678,9 @@ ident_table_alias:
}
;
-ident_set_usual_case:
- IDENT_sys
- | keyword_set_usual_case
- {
- if (unlikely($$.copy_keyword(thd, &$1)))
- MYSQL_YYABORT;
- }
+ident_cli_set_usual_case:
+ IDENT_cli { $$= $1; }
+ | keyword_set_usual_case { $$= $1; }
;
ident_sysvar_name:
@@ -15715,6 +15717,12 @@ ident_directly_assignable:
;
+ident_cli_directly_assignable:
+ IDENT_cli
+ | keyword_directly_assignable { $$= $1; }
+ ;
+
+
label_ident:
IDENT_sys
| keyword_label
@@ -16424,63 +16432,79 @@ set:
if (lex->main_select_push())
MYSQL_YYABORT;
lex->set_stmt_init();
- lex->var_list.empty();
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
}
- start_option_value_list
+ set_param
{
Lex->pop_select(); //main select
if (Lex->check_main_unit_semantics())
MYSQL_YYABORT;
}
- | SET STATEMENT_SYM
+ ;
+
+set_param:
+ option_value_no_option_type
+ | option_value_no_option_type ',' option_value_list
+ | TRANSACTION_SYM
{
- if (Lex->main_select_push())
+ Lex->option_type= OPT_DEFAULT;
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ transaction_characteristics
+ {
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
- Lex->set_stmt_init();
}
- set_stmt_option_value_following_option_type_list
+ | option_type
+ {
+ Lex->option_type= $1;
+ }
+ start_option_value_list_following_option_type
+ | STATEMENT_SYM
+ set_stmt_option_list
{
LEX *lex= Lex;
if (unlikely(lex->table_or_sp_used()))
my_yyabort_error((ER_SUBQUERIES_NOT_SUPPORTED, MYF(0), "SET STATEMENT"));
lex->stmt_var_list= lex->var_list;
lex->var_list.empty();
- Lex->pop_select(); //main select
if (Lex->check_main_unit_semantics())
MYSQL_YYABORT;
}
FOR_SYM verb_clause
- {}
;
set_assign:
- ident_directly_assignable SET_VAR
+ ident_cli_directly_assignable SET_VAR
{
LEX *lex=Lex;
lex->set_stmt_init();
- lex->var_list.empty();
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
}
set_expr_or_default
{
- if (unlikely(Lex->set_variable(&$1, $4)) ||
- unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_variable(&tmp, $4)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY,
+ false)))
MYSQL_YYABORT;
}
- | ident_directly_assignable '.' ident SET_VAR
+ | ident_cli_directly_assignable '.' ident SET_VAR
{
LEX *lex=Lex;
lex->set_stmt_init();
- lex->var_list.empty();
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
}
set_expr_or_default
{
LEX *lex= Lex;
DBUG_ASSERT(lex->var_list.is_empty());
- if (unlikely(lex->set_variable(&$1, &$3, $6)) ||
- unlikely(lex->sphead->restore_lex(thd)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(lex->set_variable(&tmp, &$3, $6)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY,
+ false)))
MYSQL_YYABORT;
}
| COLON_ORACLE_SYM ident '.' ident SET_VAR
@@ -16492,93 +16516,49 @@ set_assign:
MYSQL_YYABORT;
}
lex->set_stmt_init();
- lex->var_list.empty();
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
}
set_expr_or_default
{
LEX_CSTRING tmp= { $2.str, $2.length };
if (unlikely(Lex->set_trigger_field(&tmp, &$4, $7)) ||
- unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY,
+ false)))
MYSQL_YYABORT;
}
;
-set_stmt_option_value_following_option_type_list:
+set_stmt_option_list:
/*
Only system variables can be used here. If this condition is changed
please check careful code under lex->option_type == OPT_STATEMENT
condition on wrong type casts.
*/
- option_value_following_option_type
- | set_stmt_option_value_following_option_type_list ',' option_value_following_option_type
+ set_stmt_option
+ | set_stmt_option_list ',' set_stmt_option
;
-/* Start of option value list */
-start_option_value_list:
- option_value_no_option_type
- {
- if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
- MYSQL_YYABORT;
- }
- option_value_list_continued
- | TRANSACTION_SYM
- {
- Lex->option_type= OPT_DEFAULT;
- }
- transaction_characteristics
- {
- if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
- MYSQL_YYABORT;
- }
- | option_type
- {
- Lex->option_type= $1;
- }
- start_option_value_list_following_option_type
- ;
-
-
/* Start of option value list, option_type was given */
start_option_value_list_following_option_type:
option_value_following_option_type
+ | option_value_following_option_type ',' option_value_list
+ | TRANSACTION_SYM
{
- if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ if (sp_create_assignment_lex(thd, $1.pos()))
MYSQL_YYABORT;
}
- option_value_list_continued
- | TRANSACTION_SYM transaction_characteristics
+ transaction_characteristics
{
if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
;
-/* Remainder of the option value list after first option value. */
-option_value_list_continued:
- /* empty */
- | ',' option_value_list
- ;
-
/* Repeating list of option values after first option value. */
option_value_list:
- {
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
- }
option_value
- {
- if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
- MYSQL_YYABORT;
- }
- | option_value_list ','
- {
- sp_create_assignment_lex(thd, yychar == YYEMPTY);
- }
- option_value
- {
- if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
- MYSQL_YYABORT;
- }
+ | option_value_list ',' option_value
;
/* Wrapper around option values following the first option value in the stmt. */
@@ -16611,16 +16591,21 @@ opt_var_ident_type:
| SESSION_SYM '.' { $$=OPT_SESSION; }
;
-/* Option values with preceding option_type. */
-option_value_following_option_type:
- ident equal set_expr_or_default
+/*
+ SET STATEMENT options do not need their own LEX or Query_arena.
+ Let's put them to the main ones.
+*/
+set_stmt_option:
+ ident_cli equal set_expr_or_default
{
- if (unlikely(Lex->set_system_variable(Lex->option_type, &$1, $3)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_system_variable(Lex->option_type, &tmp, $3)))
MYSQL_YYABORT;
}
- | ident '.' ident equal set_expr_or_default
+ | ident_cli '.' ident equal set_expr_or_default
{
- if (unlikely(Lex->set_system_variable(thd, Lex->option_type, &$1, &$3, $5)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_system_variable(thd, Lex->option_type, &tmp, &$3, $5)))
MYSQL_YYABORT;
}
| DEFAULT '.' ident equal set_expr_or_default
@@ -16630,45 +16615,132 @@ option_value_following_option_type:
}
;
+
+/* Option values with preceding option_type. */
+option_value_following_option_type:
+ ident_cli equal
+ {
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_system_variable(Lex->option_type, &tmp, $4)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | ident_cli '.' ident equal
+ {
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_system_variable(thd, Lex->option_type, &tmp, &$3, $6)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | DEFAULT '.' ident equal
+ {
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ if (unlikely(Lex->set_default_system_variable(Lex->option_type, &$3, $6)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ ;
+
/* Option values without preceding option_type. */
option_value_no_option_type:
- ident_set_usual_case equal set_expr_or_default
+ ident_cli_set_usual_case equal
{
- if (unlikely(Lex->set_variable(&$1, $3)))
+ if (sp_create_assignment_lex(thd, $1.pos()))
MYSQL_YYABORT;
}
- | ident '.' ident equal set_expr_or_default
+ set_expr_or_default
{
- if (unlikely(Lex->set_variable(&$1, &$3, $5)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_variable(&tmp, $4)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
- | DEFAULT '.' ident equal set_expr_or_default
+ | ident_cli_set_usual_case '.' ident equal
{
- if (unlikely(Lex->set_default_system_variable(Lex->option_type, &$3, $5)))
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_variable(&tmp, &$3, $6)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | DEFAULT '.' ident equal
+ {
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ if (unlikely(Lex->set_default_system_variable(Lex->option_type, &$3, $6)))
+ MYSQL_YYABORT;
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
- | '@' ident_or_text equal expr
+ | '@' ident_or_text equal
{
- if (unlikely(Lex->set_user_variable(thd, &$2, $4)))
+ if (sp_create_assignment_lex(thd, $1.str))
MYSQL_YYABORT;
}
- | '@' '@' opt_var_ident_type ident_sysvar_name equal set_expr_or_default
+ expr
+ {
+ if (unlikely(Lex->set_user_variable(thd, &$2, $5)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | '@' '@' opt_var_ident_type ident_sysvar_name equal
+ {
+ if (sp_create_assignment_lex(thd, $1.str))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ if (unlikely(Lex->set_system_variable($3, &$4, $7)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | '@' '@' opt_var_ident_type ident_sysvar_name '.' ident equal
{
- if (unlikely(Lex->set_system_variable($3, &$4, $6)))
+ if (sp_create_assignment_lex(thd, $1.str))
MYSQL_YYABORT;
}
- | '@' '@' opt_var_ident_type ident_sysvar_name '.' ident equal set_expr_or_default
+ set_expr_or_default
{
- if (unlikely(Lex->set_system_variable(thd, $3, &$4, &$6, $8)))
+ if (unlikely(Lex->set_system_variable(thd, $3, &$4, &$6, $9)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
- | '@' '@' opt_var_ident_type DEFAULT '.' ident equal set_expr_or_default
+ | '@' '@' opt_var_ident_type DEFAULT '.' ident equal
{
- if (unlikely(Lex->set_default_system_variable($3, &$6, $8)))
+ if (sp_create_assignment_lex(thd, $1.str))
+ MYSQL_YYABORT;
+ }
+ set_expr_or_default
+ {
+ if (unlikely(Lex->set_default_system_variable($3, &$6, $9)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
| charset old_or_new_charset_name_or_default
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex= thd->lex;
CHARSET_INFO *cs2;
cs2= $2 ? $2: global_system_variables.character_set_client;
@@ -16680,6 +16752,8 @@ option_value_no_option_type:
if (unlikely(var == NULL))
MYSQL_YYABORT;
lex->var_list.push_back(var, thd->mem_root);
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
}
| NAMES_SYM equal expr
{
@@ -16694,6 +16768,8 @@ option_value_no_option_type:
}
| NAMES_SYM charset_name_or_default opt_collate
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex= Lex;
CHARSET_INFO *cs2;
CHARSET_INFO *cs3;
@@ -16708,11 +16784,14 @@ option_value_no_option_type:
set_var_collation_client *var;
var= new (thd->mem_root) set_var_collation_client(cs3, cs3, cs3);
if (unlikely(var == NULL) ||
- unlikely(lex->var_list.push_back(var, thd->mem_root)))
+ unlikely(lex->var_list.push_back(var, thd->mem_root)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
| DEFAULT ROLE_SYM grant_role
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex = Lex;
LEX_USER *user;
if (unlikely(!(user=(LEX_USER *) thd->calloc(sizeof(LEX_USER)))))
@@ -16728,9 +16807,13 @@ option_value_no_option_type:
thd->lex->autocommit= TRUE;
if (lex->sphead)
lex->sphead->m_flags|= sp_head::HAS_SET_AUTOCOMMIT_STMT;
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
}
| DEFAULT ROLE_SYM grant_role FOR_SYM user
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex = Lex;
set_var_default_role *var= (new (thd->mem_root)
set_var_default_role($5, $3->user));
@@ -16740,22 +16823,36 @@ option_value_no_option_type:
thd->lex->autocommit= TRUE;
if (lex->sphead)
lex->sphead->m_flags|= sp_head::HAS_SET_AUTOCOMMIT_STMT;
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
}
| ROLE_SYM ident_or_text
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex = Lex;
set_var_role *var= new (thd->mem_root) set_var_role($2);
if (unlikely(var == NULL) ||
- unlikely(lex->var_list.push_back(var, thd->mem_root)))
+ unlikely(lex->var_list.push_back(var, thd->mem_root)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
+ }
+ | ROLE_SYM equal
+ {
+ if (sp_create_assignment_lex(thd, $1.pos()))
MYSQL_YYABORT;
}
- | ROLE_SYM equal set_expr_or_default
+ set_expr_or_default
{
- if (unlikely(Lex->set_variable(&$1, $3)))
+ Lex_ident_sys tmp(thd, &$1);
+ if (unlikely(Lex->set_variable(&tmp, $4)) ||
+ unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
MYSQL_YYABORT;
}
| PASSWORD_SYM opt_for_user text_or_password
{
+ if (sp_create_assignment_lex(thd, $1.pos()))
+ MYSQL_YYABORT;
LEX *lex = Lex;
set_var_password *var= (new (thd->mem_root)
set_var_password(lex->definer));
@@ -16765,6 +16862,8 @@ option_value_no_option_type:
lex->autocommit= TRUE;
if (lex->sphead)
lex->sphead->m_flags|= sp_head::HAS_SET_AUTOCOMMIT_STMT;
+ if (unlikely(sp_create_assignment_instr(thd, yychar == YYEMPTY)))
+ MYSQL_YYABORT;
}
;