summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorwyhaines <wyhaines@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2010-06-08 11:45:41 +0000
committerwyhaines <wyhaines@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2010-06-08 11:45:41 +0000
commit38c8d6df29fac3d1e1e12706fcbe07b9428ce8a4 (patch)
tree7eaa488718b0bb5eae16257eb231f52f3d2492b3
parent70271340af90bdfedd52854b45704cb488946d92 (diff)
downloadruby-38c8d6df29fac3d1e1e12706fcbe07b9428ce8a4.tar.gz
eval.c: Backport #2202 [ruby-core:26074]; backport of r25359, which modifies rb_clear_cache_for_undef to clear entries for inherited methods.
test/ruby/test_object.rb: Backport #2202 [ruby-core:26074]; Added this file, from r25359, which tests a number of behaviors of Object, including this change. This version differs from the one in r25359 because there are several tests which currently fail on 1.8.6 because those capabilities are not implemented. Those tests are commented out. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_1_8_6@28229 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog5
-rw-r--r--eval.c3
-rw-r--r--test/ruby/test_object.rb350
-rw-r--r--version.h2
4 files changed, 358 insertions, 2 deletions
diff --git a/ChangeLog b/ChangeLog
index 0b67d24005..28d68ad8af 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+Tue Jun 9 20:40:00 2010 Kirk Haines <khaines@ruby-lang.org>
+
+ * eval.c: Backport #2202 [ruby-core:26074]; backport of r25359, which modifies rb_clear_cache_for_undef to clear entries for inherited methods.
+ * test/ruby/test_object.rb: Backport #2202 [ruby-core:26074]; Added this file, from r25359, which tests a number of behaviors of Object, including this change. This version differs from the one in r25359 because there are several tests which currently fail on 1.8.6 because those capabilities are not implemented. Those tests are commented out.
+
Tue Jun 9 3:20:00 2010 Kirk Haines <khaines@ruby-lang.org>
* lib/net/http.rb: Backport #1284 [ruby-core:22874]; Change Net:HTTP to use a block size of 16k instead of 1k when streaming or chunking POST bodies.
diff --git a/eval.c b/eval.c
index 7aa45867f9..4b6e5c3440 100644
--- a/eval.c
+++ b/eval.c
@@ -372,7 +372,8 @@ rb_clear_cache_for_undef(klass, id)
ent = cache; end = ent + CACHE_SIZE;
while (ent < end) {
if (ent->mid == id &&
- RCLASS(ent->origin)->m_tbl == RCLASS(klass)->m_tbl) {
+ (ent->klass == klass ||
+ RCLASS(ent->origin)->m_tbl == RCLASS(klass)->m_tbl)) {
ent->mid = 0;
}
ent++;
diff --git a/test/ruby/test_object.rb b/test/ruby/test_object.rb
new file mode 100644
index 0000000000..76bfc64f22
--- /dev/null
+++ b/test/ruby/test_object.rb
@@ -0,0 +1,350 @@
+require 'test/unit'
+require File.expand_path('../envutil', __FILE__)
+
+class TestObject < Test::Unit::TestCase
+ def setup
+ @verbose = $VERBOSE
+ $VERBOSE = nil
+ end
+
+ def teardown
+ $VERBOSE = @verbose
+ end
+
+ def test_dup
+ assert_raise(TypeError) { 1.dup }
+ assert_raise(TypeError) { true.dup }
+ assert_raise(TypeError) { nil.dup }
+
+ assert_raise(TypeError) do
+ Object.new.instance_eval { initialize_copy(1) }
+ end
+ end
+
+ def test_instance_of
+ assert_raise(TypeError) { 1.instance_of?(1) }
+ end
+
+ def test_kind_of
+ assert_raise(TypeError) { 1.kind_of?(1) }
+ end
+
+ def test_taint_frozen_obj
+ o = Object.new
+ o.freeze
+ assert_raise(TypeError) { o.taint }
+
+ o = Object.new
+ o.taint
+ o.freeze
+ assert_raise(TypeError) { o.untaint }
+ end
+
+ def test_freeze_under_safe_4
+ o = Object.new
+ assert_raise(SecurityError) do
+ Thread.new do
+ $SAFE = 4
+ o.freeze
+ end.join
+ end
+ end
+
+ def test_nil_to_f
+ assert_equal(0.0, nil.to_f)
+ end
+
+ def test_true_and
+ assert_equal(true, true & true)
+ assert_equal(true, true & 1)
+ assert_equal(false, true & false)
+ assert_equal(false, true & nil)
+ end
+
+ def test_true_or
+ assert_equal(true, true | true)
+ assert_equal(true, true | 1)
+ assert_equal(true, true | false)
+ assert_equal(true, true | nil)
+ end
+
+ def test_true_xor
+ assert_equal(false, true ^ true)
+ assert_equal(false, true ^ 1)
+ assert_equal(true, true ^ false)
+ assert_equal(true, true ^ nil)
+ end
+
+ def test_false_and
+ assert_equal(false, false & true)
+ assert_equal(false, false & 1)
+ assert_equal(false, false & false)
+ assert_equal(false, false & nil)
+ end
+
+ def test_false_or
+ assert_equal(true, false | true)
+ assert_equal(true, false | 1)
+ assert_equal(false, false | false)
+ assert_equal(false, false | nil)
+ end
+
+ def test_false_xor
+ assert_equal(true, false ^ true)
+ assert_equal(true, false ^ 1)
+ assert_equal(false, false ^ false)
+ assert_equal(false, false ^ nil)
+ end
+
+ def test_methods
+ o = Object.new
+ a1 = o.methods
+ a2 = o.methods(false)
+
+ def o.foo; end
+
+ assert_equal(["foo"], o.methods(true) - a1)
+ assert_equal(["foo"], o.methods(false) - a2)
+ end
+
+ def test_methods2
+ c0 = Class.new
+ c1 = Class.new(c0)
+ c1.module_eval do
+ public ; def foo; end
+ protected; def bar; end
+ private ; def baz; end
+ end
+ c2 = Class.new(c1)
+ c2.module_eval do
+ public ; def foo2; end
+ protected; def bar2; end
+ private ; def baz2; end
+ end
+
+ o0 = c0.new
+ o2 = c2.new
+
+ assert_equal(["baz", "baz2"], (o2.private_methods - o0.private_methods).sort)
+ assert_equal(["baz2"], (o2.private_methods(false) - o0.private_methods(false)).sort)
+
+ assert_equal(["bar", "bar2"], (o2.protected_methods - o0.protected_methods).sort)
+ assert_equal(["bar2"], (o2.protected_methods(false) - o0.protected_methods(false)).sort)
+
+ assert_equal(["foo", "foo2"], (o2.public_methods - o0.public_methods).sort)
+ assert_equal(["foo2"], (o2.public_methods(false) - o0.public_methods(false)).sort)
+ end
+
+ def test_instance_variable_get
+ o = Object.new
+ o.instance_eval { @foo = :foo }
+ assert_equal(:foo, o.instance_variable_get(:@foo))
+ assert_equal(nil, o.instance_variable_get(:@bar))
+ assert_raise(NameError) { o.instance_variable_get(:foo) }
+ end
+
+ def test_instance_variable_set
+ o = Object.new
+ o.instance_variable_set(:@foo, :foo)
+ assert_equal(:foo, o.instance_eval { @foo })
+ assert_raise(NameError) { o.instance_variable_set(:foo, 1) }
+ end
+
+ def test_instance_variable_defined
+ o = Object.new
+ o.instance_eval { @foo = :foo }
+ assert_equal(true, o.instance_variable_defined?(:@foo))
+ assert_equal(false, o.instance_variable_defined?(:@bar))
+ assert_raise(NameError) { o.instance_variable_defined?(:foo) }
+ end
+
+ def test_remove_instance_variable
+ o = Object.new
+ o.instance_eval { @foo = :foo }
+ o.instance_eval { remove_instance_variable(:@foo) }
+ assert_equal(false, o.instance_variable_defined?(:@foo))
+ end
+
+ def test_convert_type
+ o = Object.new
+ def o.to_s; 1; end
+ assert_raise(TypeError) { String(o) }
+ end
+
+ def test_check_convert_type
+ o = Object.new
+ def o.to_a; 1; end
+ assert_raise(TypeError) { Array(o) }
+ end
+
+ def test_to_integer
+ o = Object.new
+ def o.to_i; nil; end
+ assert_raise(TypeError) { Integer(o) }
+ end
+
+ class MyInteger
+ def initialize(n); @num = n; end
+ def to_int; @num; end
+ def <=>(n); @num <=> n.to_int; end
+ def <=(n); @num <= n.to_int; end
+ def +(n); MyInteger.new(@num + n.to_int); end
+ end
+
+# def test_check_to_integer
+# o1 = MyInteger.new(1)
+# o9 = MyInteger.new(9)
+# n = 0
+# Range.new(o1, o9).step(2) {|x| n += x.to_int }
+# assert_equal(1+3+5+7+9, n)
+# end
+
+ def test_add_method_under_safe4
+ o = Object.new
+ assert_raise(SecurityError) do
+ Thread.new do
+ $SAFE = 4
+ def o.foo
+ end
+ end.join
+ end
+ end
+
+ def test_remove_method
+ assert_raise(SecurityError) do
+ Thread.new do
+ $SAFE = 4
+ Object.instance_eval { remove_method(:foo) }
+ end.join
+ end
+
+ assert_raise(SecurityError) do
+ Thread.new do
+ $SAFE = 4
+ Class.instance_eval { remove_method(:foo) }
+ end.join
+ end
+
+ c = Class.new
+ c.freeze
+ assert_raise(TypeError) do
+ c.instance_eval { remove_method(:foo) }
+ end
+
+ c = Class.new do
+ def meth1; "meth" end
+ end
+ d = Class.new(c) do
+ alias meth2 meth1
+ end
+ o1 = c.new
+ assert_respond_to(o1, :meth1)
+ assert_equal("meth", o1.meth1)
+ o2 = d.new
+ assert_respond_to(o2, :meth1)
+ assert_equal("meth", o2.meth1)
+ assert_respond_to(o2, :meth2)
+ assert_equal("meth", o2.meth2)
+ d.class_eval do
+ remove_method :meth2
+ end
+ bug2202 = '[ruby-core:26074]'
+ assert_raise(NoMethodError, bug2202) {o2.meth2}
+ end
+
+ def test_method_missing
+ assert_raise(ArgumentError) do
+ 1.instance_eval { method_missing }
+ end
+
+ c = Class.new
+ c.class_eval do
+ protected
+ def foo; end
+ end
+ assert_raise(NoMethodError) do
+ c.new.foo
+ end
+
+ assert_raise(NoMethodError) do
+ 1.instance_eval { method_missing(:method_missing) }
+ end
+
+ c.class_eval do
+ undef_method(:method_missing)
+ end
+
+ assert_raise(ArgumentError) do
+ c.new.method_missing
+ end
+ end
+
+ def test_send_with_no_arguments
+ assert_raise(ArgumentError) { 1.send }
+ end
+
+ def test_specific_eval_with_wrong_arguments
+ assert_raise(ArgumentError) do
+ 1.instance_eval("foo") { foo }
+ end
+
+ assert_raise(ArgumentError) do
+ 1.instance_eval
+ end
+
+ assert_raise(ArgumentError) do
+ 1.instance_eval("", 1, 1, 1)
+ end
+ end
+
+# def test_instance_exec
+# x = 1.instance_exec(42) {|a| self + a }
+# assert_equal(43, x)
+#
+# x = "foo".instance_exec("bar") {|a| self + a }
+# assert_equal("foobar", x)
+# end
+
+ def test_extend
+ assert_raise(ArgumentError) do
+ 1.extend
+ end
+ end
+
+ def test_to_s
+ x = Object.new
+ x.taint
+ s = x.to_s
+ assert_equal(true, s.tainted?)
+ end
+
+# def test_exec_recursive
+# Thread.current[:__recursive_key__] = nil
+# a = [[]]
+# a.inspect
+#
+# assert_nothing_raised do
+# proc do
+# $SAFE = 4
+# begin
+# a.hash
+# rescue ArgumentError
+# end
+# end.call
+# end
+#
+# proc do
+# o = Object.new
+# def o.to_ary(x); end
+# def o.==(x); $SAFE = 4; false; end
+# a = [[o]]
+# b = []
+# b << b
+#
+# assert_nothing_raised do
+# b == a
+# end
+# end.call
+# end
+end
+
diff --git a/version.h b/version.h
index 3592c6a41f..e055dbaa68 100644
--- a/version.h
+++ b/version.h
@@ -2,7 +2,7 @@
#define RUBY_RELEASE_DATE "2010-06-08"
#define RUBY_VERSION_CODE 186
#define RUBY_RELEASE_CODE 20100608
-#define RUBY_PATCHLEVEL 405
+#define RUBY_PATCHLEVEL 406
#define RUBY_VERSION_MAJOR 1
#define RUBY_VERSION_MINOR 8