summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog8
-rw-r--r--hash.c13
-rw-r--r--include/ruby/intern.h1
-rw-r--r--process.c4
-rw-r--r--test/ruby/test_process.rb15
5 files changed, 41 insertions, 0 deletions
diff --git a/ChangeLog b/ChangeLog
index d081251f5c..52be7c1e55 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+Sat Apr 26 21:30:40 2008 Tanaka Akira <akr@fsij.org>
+
+ * include/ruby/intern.h (rb_hash_dup): declared.
+
+ * hash.c (rb_hash_dup): new function.
+
+ * process.c (rb_spawn_internal): don't modify option hash.
+
Sat Apr 26 18:36:31 2008 Nobuyoshi Nakada <nobu@ruby-lang.org>
* io.c, signal.c, thread.c, thread_win32.c, include/ruby/intern.h:
diff --git a/hash.c b/hash.c
index 006b5f85d8..89c470f9e4 100644
--- a/hash.c
+++ b/hash.c
@@ -228,6 +228,19 @@ rb_hash_new(void)
return hash_alloc(rb_cHash);
}
+VALUE
+rb_hash_dup(VALUE hash)
+{
+ VALUE ret = hash_alloc(RBASIC(hash)->klass);
+ if (!RHASH_EMPTY_P(hash))
+ RHASH(ret)->ntbl = st_copy(RHASH(hash)->ntbl);
+ if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
+ FL_SET(ret, HASH_PROC_DEFAULT);
+ }
+ RHASH(ret)->ifnone = RHASH(hash)->ifnone;
+ return ret;
+}
+
static void
rb_hash_modify_check(VALUE hash)
{
diff --git a/include/ruby/intern.h b/include/ruby/intern.h
index 5272079df7..4df92419b4 100644
--- a/include/ruby/intern.h
+++ b/include/ruby/intern.h
@@ -344,6 +344,7 @@ void st_foreach_safe(struct st_table *, int (*)(ANYARGS), st_data_t);
void rb_hash_foreach(VALUE, int (*)(ANYARGS), VALUE);
VALUE rb_hash(VALUE);
VALUE rb_hash_new(void);
+VALUE rb_hash_dup(VALUE);
VALUE rb_hash_freeze(VALUE);
VALUE rb_hash_aref(VALUE, VALUE);
VALUE rb_hash_lookup(VALUE, VALUE);
diff --git a/process.c b/process.c
index cb0ab4f4ac..6a1b84fa5e 100644
--- a/process.c
+++ b/process.c
@@ -2560,6 +2560,10 @@ rb_spawn_internal(int argc, VALUE *argv, int default_close_others)
opthash = rb_hash_new();
RBASIC(opthash)->klass = 0;
}
+ if (RBASIC(opthash)->klass) {
+ opthash = rb_hash_dup(opthash);
+ RBASIC(opthash)->klass = 0;
+ }
if (!st_lookup(RHASH_TBL(opthash), close_others, 0))
rb_hash_aset(opthash, close_others, Qtrue);
}
diff --git a/test/ruby/test_process.rb b/test/ruby/test_process.rb
index e68f1070e6..36cc5d14a7 100644
--- a/test/ruby/test_process.rb
+++ b/test/ruby/test_process.rb
@@ -500,6 +500,21 @@ class TestProcess < Test::Unit::TestCase
}
end
+ def test_execopts_modification
+ h = {}
+ Process.wait spawn(EnvUtil.rubybin, '-e', '', h)
+ assert_equal({}, h)
+
+ h = {}
+ system(EnvUtil.rubybin, '-e', '', h)
+ assert_equal({}, h)
+
+ h = {}
+ io = IO.popen([EnvUtil.rubybin, '-e', '', h])
+ io.close
+ assert_equal({}, h)
+ end
+
def test_system
str = "echo fofo"
assert_nil(system([str, str]))