Skip to content

Commit

Permalink
[Ruby 3.0] Add support for find pattern
Browse files Browse the repository at this point in the history
  • Loading branch information
vinistock committed Jul 14, 2021
1 parent 9b353db commit e592de9
Show file tree
Hide file tree
Showing 5 changed files with 65 additions and 20 deletions.
20 changes: 20 additions & 0 deletions parser/Builder.cc
Expand Up @@ -779,6 +779,20 @@ class Builder::Impl {
return make_unique<False>(tokLoc(tok));
}

unique_ptr<Node> find_pattern(const token *lbrack_t, sorbet::parser::NodeVec elements, const token *rbrack_t) {
auto loc = collectionLoc(elements);

if (lbrack_t != nullptr) {
loc = tokLoc(lbrack_t).join(loc);
}

if (rbrack_t != nullptr) {
loc = loc.join(tokLoc(rbrack_t));
}

return make_unique<FindPattern>(loc, std::move(elements));
}

unique_ptr<Node> fileLiteral(const token *tok) {
return make_unique<FileLiteral>(tokLoc(tok));
}
Expand Down Expand Up @@ -1846,6 +1860,11 @@ ForeignPtr false_(SelfPtr builder, const token *tok) {
return build->toForeign(build->false_(tok));
}

ForeignPtr find_pattern(SelfPtr builder, const token *lbrack_t, const node_list *elements, const token *rbrack_t) {
auto build = cast_builder(builder);
return build->toForeign(build->find_pattern(lbrack_t, build->convertNodeList(elements), rbrack_t));
}

ForeignPtr fileLiteral(SelfPtr builder, const token *tok) {
auto build = cast_builder(builder);
return build->toForeign(build->fileLiteral(tok));
Expand Down Expand Up @@ -2387,6 +2406,7 @@ struct ruby_parser::builder Builder::interface = {
defSingleton,
encodingLiteral,
false_,
find_pattern,
fileLiteral,
float_,
floatComplex,
Expand Down
6 changes: 6 additions & 0 deletions parser/tools/generate_ast.cc
Expand Up @@ -268,6 +268,12 @@ NodeDef nodes[] = {
"false",
vector<FieldDef>(),
},
// Find pattern
{
"FindPattern",
"find_pattern",
vector<FieldDef>({{"elements", FieldType::NodeVec}}),
},
// __FILE__
{
"FileLiteral",
Expand Down
56 changes: 37 additions & 19 deletions third_party/parser/cc/grammars/typedruby.ypp
Expand Up @@ -239,6 +239,7 @@ using namespace std::string_literals;
p_kw
p_kw_label
p_primitive
p_rest
p_top_expr_body
p_var_ref
p_value
Expand Down Expand Up @@ -308,6 +309,7 @@ using namespace std::string_literals;
p_args_head
p_args_post
p_args_tail
p_find
p_kwarg
p_kwargs
p_kwnorest
Expand Down Expand Up @@ -2426,6 +2428,10 @@ opt_block_args_tail:
list->concat($3);
$$ = driver.build.array_pattern(self, nullptr, list, nullptr);
}
| p_find
{
$$ = driver.build.find_pattern(self, nullptr, $1, nullptr);
}
| p_args_tail
{
$$ = driver.build.array_pattern(self, nullptr, $1, nullptr);
Expand Down Expand Up @@ -2462,6 +2468,12 @@ opt_block_args_tail:
auto pattern = driver.build.array_pattern(self, nullptr, $3, nullptr);
$$ = driver.build.const_pattern(self, $1, $2, pattern, $4);
}
| p_const p_lparen p_find rparen
{
driver.pattern_hash_keys.pop();
auto pattern = driver.build.find_pattern(self, nullptr, $3, nullptr);
$$ = driver.build.const_pattern(self, $1, $2, pattern, $4);
}
| p_const p_lparen p_kwargs rparen
{
driver.pattern_hash_keys.pop();
Expand All @@ -2480,6 +2492,12 @@ opt_block_args_tail:
auto pattern = driver.build.array_pattern(self, nullptr, $3, nullptr);
$$ = driver.build.const_pattern(self, $1, $2, pattern, $4);
}
| p_const p_lbracket p_find rbracket
{
driver.pattern_hash_keys.pop();
auto pattern = driver.build.find_pattern(self, nullptr, $3, nullptr);
$$ = driver.build.const_pattern(self, $1, $2, pattern, $4);
}
| p_const p_lbracket p_kwargs rbracket
{
driver.pattern_hash_keys.pop();
Expand All @@ -2492,14 +2510,13 @@ opt_block_args_tail:
auto pattern = driver.build.array_pattern(self, $2, list, nullptr);
$$ = driver.build.const_pattern(self, $1, $2, pattern, $3);
}
| tLBRACK
| tLBRACK p_args rbracket
{
driver.pattern_hash_keys.push();
$$ = driver.build.array_pattern(self, $1, $2, $3);
}
p_args rbracket
| tLBRACK p_find rbracket
{
driver.pattern_hash_keys.pop();
$$ = driver.build.array_pattern(self, $1, $3, $4);
$$ = driver.build.find_pattern(self, $1, $2, $3);
}
| tLBRACK rbracket
{
Expand Down Expand Up @@ -2587,27 +2604,28 @@ opt_block_args_tail:
$$ = $1;
$$->emplace_back(last_item);
}
p_args_tail: tSTAR tIDENTIFIER
p_args_tail: p_rest
{
auto match_rest = driver.build.match_rest(self, $1, $2);
$$ = driver.alloc.node_list(match_rest);
$$ = driver.alloc.node_list($1);
}
| tSTAR tIDENTIFIER tCOMMA p_args_post
| p_rest tCOMMA p_args_post
{
auto match_rest = driver.build.match_rest(self, $1, $2);
$$ = driver.alloc.node_list(match_rest);
$$->concat($4);
$$ = driver.alloc.node_list($1);
$$->concat($3);
}
| tSTAR
p_find: p_rest tCOMMA p_args_post tCOMMA p_rest
{
auto match_rest = driver.build.match_rest(self, $1, nullptr);
$$ = driver.alloc.node_list(match_rest);
$$ = driver.alloc.node_list($1);
$$->concat($3);
$$->emplace_back($5);
}
| tSTAR tCOMMA p_args_post
p_rest: tSTAR tIDENTIFIER
{
auto match_rest = driver.build.match_rest(self, $1, nullptr);
$$ = driver.alloc.node_list(match_rest);
$$->concat($3);
$$ = driver.build.match_rest(self, $1, $2);
}
| tSTAR
{
$$ = driver.build.match_rest(self, $1, nullptr);
}
p_args_post: p_arg
{
Expand Down
2 changes: 1 addition & 1 deletion third_party/parser/cc/lexer.rl
Expand Up @@ -2683,7 +2683,7 @@ void lexer::set_state_expr_value() {
'*' | '=>'
=> {
emit_table(PUNCTUATION);
fgoto expr_value;
fnext expr_value; fbreak;
};

# When '|', '~', '!', '=>' are used as operators
Expand Down
1 change: 1 addition & 0 deletions third_party/parser/include/ruby_parser/builder.hh
Expand Up @@ -56,6 +56,7 @@ struct builder {
ForeignPtr(*defSingleton)(SelfPtr builder, ForeignPtr defHead, ForeignPtr args, ForeignPtr body, const token* end);
ForeignPtr(*encodingLiteral)(SelfPtr builder, const token* tok);
ForeignPtr(*false_)(SelfPtr builder, const token* tok);
ForeignPtr(*find_pattern)(SelfPtr builder, const token* lbrack_t, const node_list* elements, const token* rbrack_t);
ForeignPtr(*fileLiteral)(SelfPtr builder, const token* tok);
ForeignPtr(*float_)(SelfPtr builder, const token* tok);
ForeignPtr(*floatComplex)(SelfPtr builder, const token* tok);
Expand Down

0 comments on commit e592de9

Please sign in to comment.