summaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
authorYukihiro "Matz" Matsumoto <[email protected]>2016-02-05 10:08:28 +0900
committerYukihiro "Matz" Matsumoto <[email protected]>2016-02-05 10:08:28 +0900
commit3c73c315f4dff4dbcacdfda75d42fd92d4ba711d (patch)
tree48cd15a59f9b3c26e0e48deb4468812315d91a40 /src
parent25e4ec3f377275c7be49c9fab0b1cac46621085d (diff)
downloadmruby-3c73c315f4dff4dbcacdfda75d42fd92d4ba711d.tar.gz
mruby-3c73c315f4dff4dbcacdfda75d42fd92d4ba711d.zip
Hash: check flags before accessing ifnone; ref #980
Diffstat (limited to 'src')
-rw-r--r--src/hash.c45
1 files changed, 33 insertions, 12 deletions
diff --git a/src/hash.c b/src/hash.c
index 7712cd467..5dbc6fb83 100644
--- a/src/hash.c
+++ b/src/hash.c
@@ -172,10 +172,13 @@ mrb_hash_get(mrb_state *mrb, mrb_value hash, mrb_value key)
}
/* not found */
- if (MRB_RHASH_PROCDEFAULT_P(hash)) {
- return mrb_funcall(mrb, RHASH_PROCDEFAULT(hash), "call", 2, hash, key);
+ if (MRB_RHASH_DEFAULT_P(hash)) {
+ if (MRB_RHASH_PROCDEFAULT_P(hash)) {
+ return mrb_funcall(mrb, RHASH_PROCDEFAULT(hash), "call", 2, hash, key);
+ }
+ return RHASH_IFNONE(hash);
}
- return RHASH_IFNONE(hash);
+ return mrb_nil_value();
}
MRB_API mrb_value
@@ -323,7 +326,10 @@ mrb_hash_init(mrb_state *mrb, mrb_value hash)
RHASH(hash)->flags |= MRB_HASH_PROC_DEFAULT;
ifnone = block;
}
- mrb_iv_set(mrb, hash, mrb_intern_lit(mrb, "ifnone"), ifnone);
+ if (!mrb_nil_p(ifnone)) {
+ RHASH(hash)->flags |= MRB_HASH_DEFAULT;
+ mrb_iv_set(mrb, hash, mrb_intern_lit(mrb, "ifnone"), ifnone);
+ }
return hash;
}
@@ -417,8 +423,13 @@ mrb_hash_set_default(mrb_state *mrb, mrb_value hash)
mrb_get_args(mrb, "o", &ifnone);
mrb_hash_modify(mrb, hash);
mrb_iv_set(mrb, hash, mrb_intern_lit(mrb, "ifnone"), ifnone);
- RHASH(hash)->flags &= ~(MRB_HASH_PROC_DEFAULT);
-
+ RHASH(hash)->flags &= ~MRB_HASH_PROC_DEFAULT;
+ if (!mrb_nil_p(ifnone)) {
+ RHASH(hash)->flags |= MRB_HASH_DEFAULT;
+ }
+ else {
+ RHASH(hash)->flags &= ~MRB_HASH_DEFAULT;
+ }
return ifnone;
}
@@ -468,7 +479,14 @@ mrb_hash_set_default_proc(mrb_state *mrb, mrb_value hash)
mrb_get_args(mrb, "o", &ifnone);
mrb_hash_modify(mrb, hash);
mrb_iv_set(mrb, hash, mrb_intern_lit(mrb, "ifnone"), ifnone);
- RHASH(hash)->flags |= MRB_HASH_PROC_DEFAULT;
+ if (!mrb_nil_p(ifnone)) {
+ RHASH(hash)->flags |= MRB_HASH_PROC_DEFAULT;
+ RHASH(hash)->flags |= MRB_HASH_DEFAULT;
+ }
+ else {
+ RHASH(hash)->flags &= ~MRB_HASH_DEFAULT;
+ RHASH(hash)->flags &= ~MRB_HASH_PROC_DEFAULT;
+ }
return ifnone;
}
@@ -561,12 +579,15 @@ mrb_hash_shift(mrb_state *mrb, mrb_value hash)
}
}
- if (MRB_RHASH_PROCDEFAULT_P(hash)) {
- return mrb_funcall(mrb, RHASH_PROCDEFAULT(hash), "call", 2, hash, mrb_nil_value());
- }
- else {
- return RHASH_IFNONE(hash);
+ if (MRB_RHASH_DEFAULT_P(hash)) {
+ if (MRB_RHASH_PROCDEFAULT_P(hash)) {
+ return mrb_funcall(mrb, RHASH_PROCDEFAULT(hash), "call", 2, hash, mrb_nil_value());
+ }
+ else {
+ return RHASH_IFNONE(hash);
+ }
}
+ return mrb_nil_value();
}
/* 15.2.13.4.4 */