aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorko1 <ko1@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2007-12-20 08:20:02 +0000
committerko1 <ko1@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2007-12-20 08:20:02 +0000
commit40d8543fbdec5485a638a2cb1008089d106b978d (patch)
treed08f1eed70fa9ac29d79131908abeda5fd89429a
parent1b79b5be82ac6baa5be2c4483ab44143493069d5 (diff)
downloadruby-40d8543fbdec5485a638a2cb1008089d106b978d.tar.gz
* proc.c: support Proc#binding.
* sample/test.rb: add a test. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@14360 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog6
-rw-r--r--proc.c35
-rw-r--r--sample/test.rb10
3 files changed, 51 insertions, 0 deletions
diff --git a/ChangeLog b/ChangeLog
index 7c2600d449..19d679642f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+Thu Dec 20 17:18:38 2007 Koichi Sasada <ko1@atdot.net>
+
+ * proc.c: support Proc#binding.
+
+ * sample/test.rb: add a test.
+
Thu Dec 20 17:15:15 2007 Martin Duerst <duerst@it.aoyama.ac.jp>
* pack.c: Slight change to documentation ('character' ->
diff --git a/proc.c b/proc.c
index e75a90706c..a3dcc0c970 100644
--- a/proc.c
+++ b/proc.c
@@ -1459,6 +1459,40 @@ localjump_reason(VALUE exc)
return rb_iv_get(exc, "@reason");
}
+/*
+ * call-seq:
+ * prc.binding => binding
+ *
+ * Returns the binding associated with <i>prc</i>. Note that
+ * <code>Kernel#eval</code> accepts either a <code>Proc</code> or a
+ * <code>Binding</code> object as its second parameter.
+ *
+ * def fred(param)
+ * proc {}
+ * end
+ *
+ * b = fred(99)
+ * eval("param", b.binding) #=> 99
+ * eval("param", b) #=> 99
+ */
+static VALUE
+proc_binding(VALUE self)
+{
+ rb_proc_t *proc;
+ VALUE bindval = binding_alloc(rb_cBinding);
+ rb_binding_t *bind;
+
+ GetProcPtr(self, proc);
+ GetBindingPtr(bindval, bind);
+
+ if (TYPE(proc->block.iseq) == T_NODE) {
+ rb_raise(rb_eArgError, "Can't create Binding from C level Proc");
+ }
+
+ bind->env = proc->envval;
+ bind->cref_stack = proc->special_cref_stack;
+ return bindval;
+}
/*
* <code>Proc</code> objects are blocks of code that have been bound to
@@ -1497,6 +1531,7 @@ Init_Proc(void)
rb_define_method(rb_cProc, "hash", proc_hash, 0);
rb_define_method(rb_cProc, "to_s", proc_to_s, 0);
rb_define_method(rb_cProc, "lambda?", proc_lambda_p, 0);
+ rb_define_method(rb_cProc, "binding", proc_binding, 0);
/* Exceptions */
rb_eLocalJumpError = rb_define_class("LocalJumpError", rb_eStandardError);
diff --git a/sample/test.rb b/sample/test.rb
index 4cbddabfbf..a9940039cd 100644
--- a/sample/test.rb
+++ b/sample/test.rb
@@ -2178,6 +2178,15 @@ end
test_ok(File.expand_path(".", "//") == "//")
test_ok(File.expand_path("sub", "//") == "//sub")
+# test_check "Proc#binding"
+ObjectSpace.each_object(Proc){|o|
+ begin
+ b = o.binding
+ eval 'self', b
+ rescue ArgumentError
+ end
+}
+
test_check "gc"
begin
1.upto(10000) {
@@ -2209,6 +2218,7 @@ test_ok true # reach here or dumps core
ObjectSpace.each_object{|o|
o.class.name
}
+
test_ok true # reach here or dumps core
if $failed > 0