From 987a3fce6fb7823b42631658079e8ec2d0b432e4 Mon Sep 17 00:00:00 2001 From: Henson Choi Date: Sat, 3 Jan 2026 19:51:38 +0900 Subject: [PATCH] parser: Add "|" and "{}" --- src/backend/parser/gram.y | 27 ++++++++++++++++++++++++++- src/backend/parser/scan.l | 4 ++-- 2 files changed, 28 insertions(+), 3 deletions(-) diff --git a/src/backend/parser/gram.y b/src/backend/parser/gram.y index 99c27dc178c..bd7c2820265 100644 --- a/src/backend/parser/gram.y +++ b/src/backend/parser/gram.y @@ -900,7 +900,7 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); %nonassoc IDENT PARTITION RANGE ROWS GROUPS PRECEDING FOLLOWING CUBE ROLLUP SET KEYS OBJECT_P SCALAR VALUE_P WITH WITHOUT PATH AFTER INITIAL SEEK PATTERN_P -%left Op OPERATOR /* multi-character ops and user-defined operators */ +%left Op OPERATOR '|' /* multi-character ops and user-defined operators */ %left '+' '-' %left '*' '/' '%' %left '^' @@ -16871,6 +16871,7 @@ opt_row_pattern_initial_or_seek: row_pattern: row_pattern_term { $$ = list_make1($1); } | row_pattern row_pattern_term { $$ = lappend($1, $2); } + | row_pattern '|' row_pattern_term { $$ = lappend($1, $3); /* TODO: mark as alternation */ } ; row_pattern_term: @@ -16892,6 +16893,27 @@ row_pattern_term: $$ = (Node *) makeSimpleA_Expr(AEXPR_OP, "?", (Node *)makeString($1), NULL, @1); } + /* {m} - exactly m times */ + | ColId '{' Iconst '}' + { + $$ = (Node *) makeSimpleA_Expr(AEXPR_OP, "{m}", (Node *)makeString($1), (Node *)makeInteger($3), @1); + } + /* {m,} - at least m times */ + | ColId '{' Iconst ',' '}' + { + $$ = (Node *) makeSimpleA_Expr(AEXPR_OP, "{m,}", (Node *)makeString($1), (Node *)makeInteger($3), @1); + } + /* {m,n} - between m and n times */ + | ColId '{' Iconst ',' Iconst '}' + { + List *bounds = list_make2(makeInteger($3), makeInteger($5)); + $$ = (Node *) makeSimpleA_Expr(AEXPR_OP, "{m,n}", (Node *)makeString($1), (Node *)bounds, @1); + } + /* {,n} - at most n times (0 to n) */ + | ColId '{' ',' Iconst '}' + { + $$ = (Node *) makeSimpleA_Expr(AEXPR_OP, "{,n}", (Node *)makeString($1), (Node *)makeInteger($4), @1); + } ; row_pattern_definition_list: @@ -16953,12 +16975,15 @@ MathOp: '+' { $$ = "+"; } | LESS_EQUALS { $$ = "<="; } | GREATER_EQUALS { $$ = ">="; } | NOT_EQUALS { $$ = "<>"; } + | '|' { $$ = "|"; } ; qual_Op: Op { $$ = list_make1(makeString($1)); } | OPERATOR '(' any_operator ')' { $$ = $3; } + | '|' + { $$ = list_make1(makeString("|")); } ; qual_all_Op: diff --git a/src/backend/parser/scan.l b/src/backend/parser/scan.l index a67815339b7..c7b984df34c 100644 --- a/src/backend/parser/scan.l +++ b/src/backend/parser/scan.l @@ -363,7 +363,7 @@ not_equals "!=" * If you change either set, adjust the character lists appearing in the * rule for "operator"! */ -self [,()\[\].;\:\+\-\*\/\%\^\<\>\=] +self [,()\[\].;\:\+\-\*\/\%\^\<\>\=\|\{\}] op_chars [\~\!\@\#\^\&\|\`\?\+\-\*\/\%\<\>\=] operator {op_chars}+ @@ -955,7 +955,7 @@ other . * that the "self" rule would have. */ if (nchars == 1 && - strchr(",()[].;:+-*/%^<>=", yytext[0])) + strchr(",()[].;:+-*/%^<>=|{}", yytext[0])) return yytext[0]; /* * Likewise, if what we have left is two chars, and -- 2.50.1 (Apple Git-155)