summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJeremy Evans <code@jeremyevans.net>2020-10-28 15:17:49 -0700
committerJeremy Evans <code@jeremyevans.net>2020-10-29 08:08:42 -0700
commitc0aeb98aa903334f06758d39c772cb22440d8a4e (patch)
tree95f414628d555fad347afbeaa339f8e3d21b3ef2
parent07c03bc30984a496558d9e830bc4fb2f8cfb1854 (diff)
Make ENV.replace handle multiple environ entries with the same key
While it is expected that all environment keys are unique, that is not enforced. It is possible by manipulating environ directly you can call a process with an environment with duplicate keys. If ENV.replace was passed a hash with a key where environ had a duplicate for that key, ENV.replace would end up deleting the key from environ. The fix in this case is to not assume that the environment key list has unique keys, and continue processing the entire key list in keylist_delete. Fixes [Bug #17254]
Notes
Notes: Merged: https://github.com/ruby/ruby/pull/3716
-rw-r--r--hash.c5
1 files changed, 4 insertions, 1 deletions
diff --git a/hash.c b/hash.c
index a8d6978f45..e0f8773b64 100644
--- a/hash.c
+++ b/hash.c
@@ -6448,13 +6448,16 @@ keylist_delete(VALUE keys, VALUE key)
long keylen, elen;
const char *keyptr, *eptr;
RSTRING_GETMEM(key, keyptr, keylen);
+ /* Don't stop at first key, as it is possible to have
+ multiple environment values with the same key.
+ */
for (long i=0; i<RARRAY_LEN(keys); i++) {
VALUE e = RARRAY_AREF(keys, i);
RSTRING_GETMEM(e, eptr, elen);
if (elen != keylen) continue;
if (!ENVNMATCH(keyptr, eptr, elen)) continue;
rb_ary_delete_at(keys, i);
- return;
+ i--;
}
}