diff options
Diffstat (limited to 'sql/sql_yacc.yy')
-rw-r--r-- | sql/sql_yacc.yy | 58 |
1 files changed, 51 insertions, 7 deletions
diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index b3632c339c4..f073d4173ad 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -1911,7 +1911,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); opt_field_or_var_spec fields_or_vars opt_load_data_set_spec view_list_opt view_list view_select trigger_tail sp_tail sf_tail event_tail - udf_tail create_function_tail + udf_tail create_function_tail create_aggregate_function_tail install uninstall partition_entry binlog_base64_event normal_key_options normal_key_opts all_key_opt spatial_key_options fulltext_key_options normal_key_opt @@ -2638,8 +2638,16 @@ create: event_tail { } | create_or_replace definer FUNCTION_SYM - { Lex->create_info.set($1); } - sf_tail + { + Lex->create_info.set($1); + } + sf_tail_not_aggregate + { } + | create_or_replace definer AGGREGATE_SYM FUNCTION_SYM + { + Lex->create_info.set($1); + } + sf_tail_aggregate { } | create_or_replace no_definer FUNCTION_SYM { Lex->create_info.set($1); } @@ -2648,9 +2656,8 @@ create: | create_or_replace no_definer AGGREGATE_SYM FUNCTION_SYM { Lex->create_info.set($1); - Lex->udf.type= UDFTYPE_AGGREGATE; } - udf_tail + create_aggregate_function_tail { } | create_or_replace USER_SYM opt_if_not_exists clear_privileges grant_list opt_require_clause opt_resource_options @@ -2677,11 +2684,36 @@ create: { } ; +sf_tail_not_aggregate: + sf_tail + { + if (Lex->sphead->m_flags & sp_head::HAS_AGGREGATE_INSTR) + { + my_yyabort_error((ER_NOT_AGGREGATE_FUNCTION, MYF(0), "")); + } + Lex->sphead->set_chistics_agg_type(NOT_AGGREGATE); + } + +sf_tail_aggregate: + sf_tail + { + if (!(Lex->sphead->m_flags & sp_head::HAS_AGGREGATE_INSTR)) + { + my_yyabort_error((ER_INVALID_AGGREGATE_FUNCTION, MYF(0), "")); + } + Lex->sphead->set_chistics_agg_type(GROUP_AGGREGATE); + } + create_function_tail: - sf_tail { } + sf_tail_not_aggregate { } | udf_tail { Lex->udf.type= UDFTYPE_FUNCTION; } ; +create_aggregate_function_tail: + sf_tail_aggregate + { } + | udf_tail { Lex->udf.type= UDFTYPE_AGGREGATE; } + ; opt_sequence: /* empty */ { } | sequence_defs @@ -4011,7 +4043,19 @@ sp_proc_stmt_fetch_head: ; sp_proc_stmt_fetch: - sp_proc_stmt_fetch_head sp_fetch_list { } + sp_proc_stmt_fetch_head sp_fetch_list { } + | FETCH_SYM GROUP_SYM NEXT_SYM ROW_SYM + { + LEX *lex= Lex; + sp_head *sp= lex->sphead; + lex->sphead->m_flags|= sp_head::HAS_AGGREGATE_INSTR; + sp_instr_agg_cfetch *i= + new (thd->mem_root) sp_instr_agg_cfetch(sp->instructions(), + lex->spcont); + if (i == NULL || + sp->add_instr(i)) + MYSQL_YYABORT; + } ; sp_proc_stmt_close: |