Skip to content

Commit 883e7e6

Browse files
committed
[GR-18163] Fix arity of rb_define_method()-defined methods and add specs (#2662)
PullRequest: truffleruby/3367
2 parents 7dae01e + 1ecc773 commit 883e7e6

File tree

7 files changed

+47
-79
lines changed

7 files changed

+47
-79
lines changed

spec/ruby/optional/capi/class_spec.rb

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -196,16 +196,6 @@
196196
end
197197
end
198198

199-
describe "rb_define_method" do
200-
it "defines a method taking variable arguments as a C array if the argument count is -1" do
201-
@s.rb_method_varargs_1(1, 3, 7, 4).should == [1, 3, 7, 4]
202-
end
203-
204-
it "defines a method taking variable arguments as a Ruby array if the argument count is -2" do
205-
@s.rb_method_varargs_2(1, 3, 7, 4).should == [1, 3, 7, 4]
206-
end
207-
end
208-
209199
describe "rb_class2name" do
210200
it "returns the class name" do
211201
@s.rb_class2name(CApiClassSpecs).should == "CApiClassSpecs"

spec/ruby/optional/capi/ext/class_spec.c

Lines changed: 0 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -142,19 +142,6 @@ static VALUE class_spec_include_module(VALUE self, VALUE klass, VALUE module) {
142142
return klass;
143143
}
144144

145-
static VALUE class_spec_method_var_args_1(int argc, VALUE *argv, VALUE self) {
146-
VALUE ary = rb_ary_new();
147-
int i;
148-
for (i = 0; i < argc; i++) {
149-
rb_ary_push(ary, argv[i]);
150-
}
151-
return ary;
152-
}
153-
154-
static VALUE class_spec_method_var_args_2(VALUE self, VALUE argv) {
155-
return argv;
156-
}
157-
158145
void Init_class_spec(void) {
159146
VALUE cls = rb_define_class("CApiClassSpecs", rb_cObject);
160147
rb_define_method(cls, "define_call_super_method", class_spec_define_call_super_method, 2);
@@ -185,8 +172,6 @@ void Init_class_spec(void) {
185172
rb_define_method(cls, "rb_define_class_id_under", class_spec_rb_define_class_id_under, 3);
186173
rb_define_method(cls, "rb_define_class_variable", class_spec_define_class_variable, 3);
187174
rb_define_method(cls, "rb_include_module", class_spec_include_module, 2);
188-
rb_define_method(cls, "rb_method_varargs_1", class_spec_method_var_args_1, -1);
189-
rb_define_method(cls, "rb_method_varargs_2", class_spec_method_var_args_2, -2);
190175
}
191176

192177
#ifdef __cplusplus

spec/ruby/optional/capi/ext/module_spec.c

Lines changed: 23 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -9,18 +9,6 @@ static VALUE module_specs_test_method(VALUE self) {
99
return ID2SYM(rb_intern("test_method"));
1010
}
1111

12-
static VALUE module_specs_test_method_2required(VALUE self, VALUE arg1, VALUE arg2) {
13-
return ID2SYM(rb_intern("test_method_2required"));
14-
}
15-
16-
static VALUE module_specs_test_method_c_array(int argc, VALUE *argv, VALUE self) {
17-
return ID2SYM(rb_intern("test_method_c_array"));
18-
}
19-
20-
static VALUE module_specs_test_method_ruby_array(VALUE self, VALUE args) {
21-
return ID2SYM(rb_intern("test_method_ruby_array"));
22-
}
23-
2412
static VALUE module_specs_const_defined(VALUE self, VALUE klass, VALUE id) {
2513
return rb_const_defined(klass, SYM2ID(id)) ? Qtrue : Qfalse;
2614
}
@@ -88,19 +76,25 @@ static VALUE module_specs_rb_define_method(VALUE self, VALUE cls, VALUE str_name
8876
return Qnil;
8977
}
9078

91-
static VALUE module_specs_rb_define_method_2required(VALUE self, VALUE cls, VALUE str_name) {
92-
rb_define_method(cls, RSTRING_PTR(str_name), module_specs_test_method_2required, 2);
93-
return Qnil;
79+
static VALUE module_specs_method_var_args_1(int argc, VALUE *argv, VALUE self) {
80+
VALUE ary = rb_ary_new();
81+
int i;
82+
for (i = 0; i < argc; i++) {
83+
rb_ary_push(ary, argv[i]);
84+
}
85+
return ary;
9486
}
9587

96-
static VALUE module_specs_rb_define_method_c_array(VALUE self, VALUE cls, VALUE str_name) {
97-
rb_define_method(cls, RSTRING_PTR(str_name), module_specs_test_method_c_array, -1);
98-
return Qnil;
88+
static VALUE module_specs_method_var_args_2(VALUE self, VALUE argv) {
89+
return argv;
9990
}
10091

101-
static VALUE module_specs_rb_define_method_ruby_array(VALUE self, VALUE cls, VALUE str_name) {
102-
rb_define_method(cls, RSTRING_PTR(str_name), module_specs_test_method_ruby_array, -2);
103-
return Qnil;
92+
static VALUE module_specs_rb_define_method_1required(VALUE self, VALUE arg1) {
93+
return arg1;
94+
}
95+
96+
static VALUE module_specs_rb_define_method_2required(VALUE self, VALUE arg1, VALUE arg2) {
97+
return arg2;
10498
}
10599

106100
static VALUE module_specs_rb_define_module_function(VALUE self, VALUE cls, VALUE str_name) {
@@ -155,25 +149,21 @@ void Init_module_spec(void) {
155149
rb_define_method(cls, "rb_define_module_under", module_specs_rb_define_module_under, 2);
156150
rb_define_method(cls, "rb_define_const", module_specs_define_const, 3);
157151
rb_define_method(cls, "rb_define_global_const", module_specs_define_global_const, 2);
158-
rb_define_method(cls, "rb_define_global_function",
159-
module_specs_rb_define_global_function, 1);
152+
rb_define_method(cls, "rb_define_global_function", module_specs_rb_define_global_function, 1);
160153

161154
rb_define_method(cls, "rb_define_method", module_specs_rb_define_method, 2);
155+
rb_define_method(cls, "rb_define_method_varargs_1", module_specs_method_var_args_1, -1);
156+
rb_define_method(cls, "rb_define_method_varargs_2", module_specs_method_var_args_2, -2);
157+
rb_define_method(cls, "rb_define_method_1required", module_specs_rb_define_method_1required, 1);
162158
rb_define_method(cls, "rb_define_method_2required", module_specs_rb_define_method_2required, 2);
163-
rb_define_method(cls, "rb_define_method_c_array", module_specs_rb_define_method_c_array, 2);
164-
rb_define_method(cls, "rb_define_method_ruby_array", module_specs_rb_define_method_ruby_array, 2);
165159

166-
rb_define_method(cls, "rb_define_module_function",
167-
module_specs_rb_define_module_function, 2);
160+
rb_define_method(cls, "rb_define_module_function", module_specs_rb_define_module_function, 2);
168161

169-
rb_define_method(cls, "rb_define_private_method",
170-
module_specs_rb_define_private_method, 2);
162+
rb_define_method(cls, "rb_define_private_method", module_specs_rb_define_private_method, 2);
171163

172-
rb_define_method(cls, "rb_define_protected_method",
173-
module_specs_rb_define_protected_method, 2);
164+
rb_define_method(cls, "rb_define_protected_method", module_specs_rb_define_protected_method, 2);
174165

175-
rb_define_method(cls, "rb_define_singleton_method",
176-
module_specs_rb_define_singleton_method, 2);
166+
rb_define_method(cls, "rb_define_singleton_method", module_specs_rb_define_singleton_method, 2);
177167

178168
rb_define_method(cls, "rb_undef_method", module_specs_rb_undef_method, 2);
179169
rb_define_method(cls, "rb_undef", module_specs_rb_undef, 2);

spec/ruby/optional/capi/module_spec.rb

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -252,22 +252,30 @@ def method_to_be_aliased
252252
cls.new.method(:test_method).arity.should == 0
253253
end
254254

255+
it "returns the correct arity when argc of the method in class is 1" do
256+
@m.rb_define_method_1required(42).should == 42
257+
@m.method(:rb_define_method_1required).arity.should == 1
258+
end
259+
260+
it "returns the correct arity when argc of the method in class is 2" do
261+
@m.rb_define_method_2required(1, 2).should == 2
262+
@m.method(:rb_define_method_2required).arity.should == 2
263+
end
264+
265+
it "defines a method taking variable arguments as a C array if the argument count is -1" do
266+
@m.rb_define_method_varargs_1(1, 3, 7, 4).should == [1, 3, 7, 4]
267+
end
268+
255269
it "returns the correct arity when argc of the method in class is -1" do
256-
cls = Class.new
257-
@m.rb_define_method_c_array(cls, "test_method_c_array")
258-
cls.new.method(:test_method_c_array).arity.should == -1
270+
@m.method(:rb_define_method_varargs_1).arity.should == -1
259271
end
260272

261-
it "returns the correct arity when argc of the method in class is -2" do
262-
cls = Class.new
263-
@m.rb_define_method_ruby_array(cls, "test_method_ruby_array")
264-
cls.new.method(:test_method_ruby_array).arity.should == -1
273+
it "defines a method taking variable arguments as a Ruby array if the argument count is -2" do
274+
@m.rb_define_method_varargs_2(1, 3, 7, 4).should == [1, 3, 7, 4]
265275
end
266276

267-
it "returns the correct arity when argc of the method in class is 2" do
268-
cls = Class.new
269-
@m.rb_define_method_2required(cls, "test_method_2required")
270-
cls.new.method(:test_method_2required).arity.should == 2
277+
it "returns the correct arity when argc of the method in class is -2" do
278+
@m.method(:rb_define_method_varargs_2).arity.should == -1
271279
end
272280

273281
it "defines a method on a module" do

spec/tags/optional/capi/module_tags.txt

Lines changed: 0 additions & 6 deletions
This file was deleted.

src/main/java/org/truffleruby/core/module/ModuleNodes.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1334,7 +1334,7 @@ private RubySymbol defineMethod(RubyModule module, String name, RubyProc proc,
13341334
MaterializedFrame callerFrame) {
13351335
final RootCallTarget callTargetForLambda = proc.callTargets.getCallTargetForLambda();
13361336
final RubyLambdaRootNode rootNode = RubyLambdaRootNode.of(callTargetForLambda);
1337-
final SharedMethodInfo info = proc.getSharedMethodInfo().forDefineMethod(module, name);
1337+
final SharedMethodInfo info = proc.getSharedMethodInfo().forDefineMethod(module, name, proc);
13381338
final RubyNode body = rootNode.copyBody();
13391339
final RubyNode newBody = new CallMethodWithLambdaBody(isSingleContext() ? proc : null,
13401340
callTargetForLambda, body);

src/main/java/org/truffleruby/language/methods/SharedMethodInfo.java

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
import org.truffleruby.RubyLanguage;
1313
import org.truffleruby.core.klass.RubyClass;
1414
import org.truffleruby.core.module.RubyModule;
15+
import org.truffleruby.core.proc.RubyProc;
1516
import org.truffleruby.language.LexicalScope;
1617
import org.truffleruby.language.RubyDynamicObject;
1718
import org.truffleruby.language.RubyGuards;
@@ -60,16 +61,16 @@ public SharedMethodInfo(
6061
this.argumentDescriptors = argumentDescriptors;
6162
}
6263

63-
public SharedMethodInfo forDefineMethod(RubyModule declaringModule, String methodName) {
64+
public SharedMethodInfo forDefineMethod(RubyModule declaringModule, String methodName, RubyProc proc) {
6465
return new SharedMethodInfo(
6566
sourceSection,
6667
staticLexicalScope,
67-
arity,
68+
proc.arity,
6869
methodName,
6970
0, // no longer a block
7071
moduleAndMethodName(declaringModule, methodName),
7172
null,
72-
argumentDescriptors);
73+
proc.argumentDescriptors);
7374
}
7475

7576
public SharedMethodInfo convertMethodMissingToMethod(RubyModule declaringModule, String methodName) {

0 commit comments

Comments
 (0)