Watson1978
3/18/2011 - 1:08 PM

MacRuby : The defined? keyword when called with a method name having a module as receiver returns nil if the method is private/protected.

MacRuby : The defined? keyword when called with a method name having a module as receiver returns nil if the method is private/protected.

require 'test/unit/assertions.rb'
include Test::Unit::Assertions

module AAA
  class BBB
    private
    def m_private; end

    protected
    def m_protected; end
  end
end

class Object
    private
    def m_private; end

    protected
    def m_protected; end
end

assert_nil( defined?(AAA::BBB.new.m_private) )
assert_nil( defined?(Object.m_private)       )

assert_nil( defined?(AAA::BBB.new.m_protected) )
assert_nil( defined?(Object.m_protected)       )
assert_equal("method", defined?(puts))

puts :ok
diff --git a/vm.cpp b/vm.cpp
index aa2fac1..9bfb8f3 100644
--- a/vm.cpp
+++ b/vm.cpp
@@ -1637,7 +1637,22 @@ rb_vm_defined(VALUE self, int type, VALUE what, VALUE what2)
                }

                if (ok) {
-                   str = type == DEFINED_SUPER ? "super" : "method";
+                   if (type == DEFINED_SUPER) {
+                       str = "super";
+                   }
+                   else {
+                       rb_vm_method_node_t *node = NULL;
+                       str = "method";
+                       if (rb_vm_lookup_method2((Class)klass, (ID)what, NULL, NULL, &node)) {
+                           if(node != NULL) {
+                               int flags = node->flags;
+                               if (!(flags & VM_METHOD_FBODY) &&
+                                   ((flags & VM_METHOD_PRIVATE) || (flags & VM_METHOD_PROTECTED))) {
+                                   str = NULL;
+                               }
+                           }
+                       }
+                   }
                }
            }
            break;