diff --git a/eval.c b/eval.c index 5fe00e1..22a0a60 100644 --- a/eval.c +++ b/eval.c @@ -347,6 +347,20 @@ rb_mod_s_constants(int argc, VALUE *argv, VALUE mod) return rb_const_list(data); } +/* + * call-seq: + * Module.current -> Module + * + * Returns "current class". + */ + +VALUE rb_vm_cref_cls(void); +static VALUE +rb_mod_current(void) +{ + return rb_vm_cref_cls(); +} + void rb_frozen_class_p(VALUE klass) { @@ -1144,6 +1158,8 @@ Init_eval(void) rb_define_singleton_method(rb_cModule, "nesting", rb_mod_nesting, 0); rb_define_singleton_method(rb_cModule, "constants", rb_mod_s_constants, -1); + rb_define_singleton_method(rb_cModule, "current", rb_mod_current, 0); + rb_define_singleton_method(rb_vm_top_self(), "include", top_include, -1); rb_define_method(rb_mKernel, "extend", rb_obj_extend, -1); diff --git a/test/ruby/test_module.rb b/test/ruby/test_module.rb index ce6e8a6..b6277dc 100644 --- a/test/ruby/test_module.rb +++ b/test/ruby/test_module.rb @@ -1000,4 +1000,28 @@ class TestModule < Test::Unit::TestCase INPUT assert_in_out_err([], src, %w(Object :ok), []) end + + class ModuleCurrentTestModule1 + CURRENT = Module.current + + def self.foo + Module.current + end + + def foo + Module.current + end + end + + def test_module_current + assert_equal(TestModule, Module.current) + assert_equal(ModuleCurrentTestModule1, ModuleCurrentTestModule1::CURRENT) + assert_equal(ModuleCurrentTestModule1, ModuleCurrentTestModule1.foo) + module_current_test = ModuleCurrentTestModule1.new + assert_equal(ModuleCurrentTestModule1, module_current_test.foo) + foo = ModuleCurrentTestModule1.module_eval{Module.current} + assert_equal(ModuleCurrentTestModule1, foo) + foo = ModuleCurrentTestModule1.instance_eval{Module.current} + assert_equal("#", foo.to_s) + end end diff --git a/vm.c b/vm.c index d0c2592..03f15e7 100644 --- a/vm.c +++ b/vm.c @@ -827,6 +827,12 @@ rb_vm_cref(void) return vm_get_cref(cfp->iseq, cfp->lfp, cfp->dfp); } +VALUE +rb_vm_cref_cls(void) +{ + return rb_vm_cref()->nd_clss; +} + #if 0 void debug_cref(NODE *cref)