summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEarlopain <14981592+Earlopain@users.noreply.github.com>2025-10-27 11:24:45 +0100
committergit <svn-admin@ruby-lang.org>2025-10-30 13:05:51 +0000
commit99382f7461db80497b69df84ac52fab6710ba160 (patch)
tree8818bb2379fe557e13f6fdc304febdf875f31602
parentd5fbff50c7ff880ae71b8a8ae9aad976c69bea73 (diff)
[ruby/prism] Unescape unary method calls
Followup to https://github.com/ruby/prism/pull/2213 Before: ```sh $ ruby -ve "puts 42.~@" ruby 3.4.6 (2025-09-16 revision https://github.com/ruby/prism/commit/dbd83256b1) +PRISM [x86_64-linux] -e:1:in '<main>': undefined method '~@' for an instance of Integer (NoMethodError) Did you mean? ~ ``` After (matches parse.y): ```sh $ ./miniruby -ve "puts 42.~@" ruby 3.5.0dev (2025-10-16T03:40:45Z master https://github.com/ruby/prism/commit/1d95d75c3f) +PRISM [x86_64-linux] -43 ``` https://github.com/ruby/prism/commit/a755bf228f
-rw-r--r--prism/prism.c10
-rw-r--r--test/prism/fixtures/unary_method_calls.txt2
-rw-r--r--test/prism/ruby/parser_test.rb3
-rw-r--r--test/prism/ruby/ruby_parser_test.rb1
4 files changed, 14 insertions, 2 deletions
diff --git a/prism/prism.c b/prism/prism.c
index 95e7d09050..a92de163f5 100644
--- a/prism/prism.c
+++ b/prism/prism.c
@@ -2721,6 +2721,8 @@ pm_call_node_binary_create(pm_parser_t *parser, pm_node_t *receiver, pm_token_t
return node;
}
+static const uint8_t * parse_operator_symbol_name(const pm_token_t *);
+
/**
* Allocate and initialize a new CallNode node from a call expression.
*/
@@ -2749,7 +2751,11 @@ pm_call_node_call_create(pm_parser_t *parser, pm_node_t *receiver, pm_token_t *o
pm_node_flag_set((pm_node_t *)node, PM_CALL_NODE_FLAGS_SAFE_NAVIGATION);
}
- node->name = pm_parser_constant_id_token(parser, message);
+ /**
+ * If the final character is `@` as is the case for `foo.~@`,
+ * we should ignore the @ in the same way we do for symbols.
+ */
+ node->name = pm_parser_constant_id_location(parser, message->start, parse_operator_symbol_name(message));
return node;
}
@@ -19702,7 +19708,7 @@ parse_expression_prefix(pm_parser_t *parser, pm_binding_power_t binding_power, b
pm_parser_scope_pop(parser);
/**
- * If the final character is @. As is the case when defining
+ * If the final character is `@` as is the case when defining
* methods to override the unary operators, we should ignore
* the @ in the same way we do for symbols.
*/
diff --git a/test/prism/fixtures/unary_method_calls.txt b/test/prism/fixtures/unary_method_calls.txt
new file mode 100644
index 0000000000..dda85e4bdb
--- /dev/null
+++ b/test/prism/fixtures/unary_method_calls.txt
@@ -0,0 +1,2 @@
+42.~@
+42.!@
diff --git a/test/prism/ruby/parser_test.rb b/test/prism/ruby/parser_test.rb
index 016fda91f0..3104369d3e 100644
--- a/test/prism/ruby/parser_test.rb
+++ b/test/prism/ruby/parser_test.rb
@@ -109,6 +109,9 @@ module Prism
# Regex with \c escape
"unescaping.txt",
"seattlerb/regexp_esc_C_slash.txt",
+
+ # https://github.com/whitequark/parser/issues/1084
+ "unary_method_calls.txt",
]
# These files are failing to translate their lexer output into the lexer
diff --git a/test/prism/ruby/ruby_parser_test.rb b/test/prism/ruby/ruby_parser_test.rb
index 7640ddaf1c..42a888be82 100644
--- a/test/prism/ruby/ruby_parser_test.rb
+++ b/test/prism/ruby/ruby_parser_test.rb
@@ -57,6 +57,7 @@ module Prism
"spanning_heredoc.txt",
"symbols.txt",
"tilde_heredocs.txt",
+ "unary_method_calls.txt",
"unparser/corpus/literal/literal.txt",
"while.txt",
"whitequark/cond_eflipflop.txt",