diff options
author | Timothy Flynn <trflynn89@pm.me> | 2021-06-01 08:34:51 -0400 |
---|---|---|
committer | Ali Mohammad Pur <Ali.mpfard@gmail.com> | 2021-06-01 23:48:21 +0430 |
commit | ab79599a5ef01ea4015731e01c0348b6b7de0024 (patch) | |
tree | 207b217d897b9cea35eb3c0bcb6b53ef30bf4be8 | |
parent | 5b86a8bad171f2fc3aa60e6f753547e3d50ea690 (diff) | |
download | serenity-ab79599a5ef01ea4015731e01c0348b6b7de0024.zip |
LibSQL: Return an error for empty common table expression lists
SQL::CommonTableExpressionList is required to be non-empty. Return an
error if zero common table expressions were parsed.
Fixes #7627
-rw-r--r-- | Tests/LibSQL/TestSqlStatementParser.cpp | 2 | ||||
-rw-r--r-- | Userland/Libraries/LibSQL/Parser.cpp | 10 | ||||
-rw-r--r-- | Userland/Libraries/LibSQL/Parser.h | 2 |
3 files changed, 12 insertions, 2 deletions
diff --git a/Tests/LibSQL/TestSqlStatementParser.cpp b/Tests/LibSQL/TestSqlStatementParser.cpp index 0126a85e4e..64fbe3fb3e 100644 --- a/Tests/LibSQL/TestSqlStatementParser.cpp +++ b/Tests/LibSQL/TestSqlStatementParser.cpp @@ -682,6 +682,8 @@ TEST_CASE(select) TEST_CASE(common_table_expression) { + EXPECT(parse("WITH").is_error()); + EXPECT(parse("WITH;").is_error()); EXPECT(parse("WITH DELETE FROM table;").is_error()); EXPECT(parse("WITH table DELETE FROM table;").is_error()); EXPECT(parse("WITH table AS DELETE FROM table;").is_error()); diff --git a/Userland/Libraries/LibSQL/Parser.cpp b/Userland/Libraries/LibSQL/Parser.cpp index 3e71e1e83f..b12ed59717 100644 --- a/Userland/Libraries/LibSQL/Parser.cpp +++ b/Userland/Libraries/LibSQL/Parser.cpp @@ -23,6 +23,9 @@ NonnullRefPtr<Statement> Parser::next_statement() if (match(TokenType::With)) { auto common_table_expression_list = parse_common_table_expression_list(); + if (!common_table_expression_list) + return create_ast_node<ErrorStatement>(); + return terminate_statement(parse_statement_with_expression_list(move(common_table_expression_list))); } @@ -331,7 +334,7 @@ NonnullRefPtr<Select> Parser::parse_select_statement(RefPtr<CommonTableExpressio return create_ast_node<Select>(move(common_table_expression_list), select_all, move(result_column_list), move(table_or_subquery_list), move(where_clause), move(group_by_clause), move(ordering_term_list), move(limit_clause)); } -NonnullRefPtr<CommonTableExpressionList> Parser::parse_common_table_expression_list() +RefPtr<CommonTableExpressionList> Parser::parse_common_table_expression_list() { consume(TokenType::With); bool recursive = consume_if(TokenType::Recursive); @@ -339,6 +342,11 @@ NonnullRefPtr<CommonTableExpressionList> Parser::parse_common_table_expression_l NonnullRefPtrVector<CommonTableExpression> common_table_expression; parse_comma_separated_list(false, [&]() { common_table_expression.append(parse_common_table_expression()); }); + if (common_table_expression.is_empty()) { + expected("Common table expression list"); + return {}; + } + return create_ast_node<CommonTableExpressionList>(recursive, move(common_table_expression)); } diff --git a/Userland/Libraries/LibSQL/Parser.h b/Userland/Libraries/LibSQL/Parser.h index 4d1c888e37..74595a3b7e 100644 --- a/Userland/Libraries/LibSQL/Parser.h +++ b/Userland/Libraries/LibSQL/Parser.h @@ -59,7 +59,7 @@ private: NonnullRefPtr<Update> parse_update_statement(RefPtr<CommonTableExpressionList>); NonnullRefPtr<Delete> parse_delete_statement(RefPtr<CommonTableExpressionList>); NonnullRefPtr<Select> parse_select_statement(RefPtr<CommonTableExpressionList>); - NonnullRefPtr<CommonTableExpressionList> parse_common_table_expression_list(); + RefPtr<CommonTableExpressionList> parse_common_table_expression_list(); NonnullRefPtr<Expression> parse_primary_expression(); NonnullRefPtr<Expression> parse_secondary_expression(NonnullRefPtr<Expression> primary); |