From 76fc1ce0a774aab411b4e9f4462c236852624764 Mon Sep 17 00:00:00 2001 From: mame Date: Mon, 11 Mar 2019 12:48:33 +0000 Subject: The combination of non-Symbol keys and Symbol keys is now allowed again Revert r64358. [Bug #15658] git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@67217 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- class.c | 44 ++++++++++---------------------------------- 1 file changed, 10 insertions(+), 34 deletions(-) (limited to 'class.c') diff --git a/class.c b/class.c index 051632e08c..4b4237018f 100644 --- a/class.c +++ b/class.c @@ -1824,57 +1824,33 @@ unknown_keyword_error(VALUE hash, const ID *table, int keywords) rb_keyword_error("unknown", rb_hash_keys(hash)); } -struct extract_keywords { - VALUE kwdhash, nonsymkey; -}; static int separate_symbol(st_data_t key, st_data_t value, st_data_t arg) { - struct extract_keywords *argp = (struct extract_keywords *)arg; - VALUE k = (VALUE)key, v = (VALUE)value; - - if (argp->kwdhash) { - if (UNLIKELY(!SYMBOL_P(k))) { - argp->nonsymkey = k; - return ST_STOP; - } - } - else if (SYMBOL_P(k)) { - if (UNLIKELY(argp->nonsymkey != Qundef)) { - argp->kwdhash = Qnil; - return ST_STOP; - } - argp->kwdhash = rb_hash_new(); - } - else { - if (argp->nonsymkey == Qundef) - argp->nonsymkey = k; - return ST_CONTINUE; - } - rb_hash_aset(argp->kwdhash, k, v); + VALUE *kwdhash = (VALUE *)arg; + if (!SYMBOL_P(key)) kwdhash++; + if (!*kwdhash) *kwdhash = rb_hash_new(); + rb_hash_aset(*kwdhash, (VALUE)key, (VALUE)value); return ST_CONTINUE; } VALUE rb_extract_keywords(VALUE *orighash) { - struct extract_keywords arg = {0, Qundef}; + VALUE parthash[2] = {0, 0}; VALUE hash = *orighash; if (RHASH_EMPTY_P(hash)) { *orighash = 0; return hash; } - rb_hash_foreach(hash, separate_symbol, (st_data_t)&arg); - if (arg.kwdhash) { - if (arg.nonsymkey != Qundef) { - rb_raise(rb_eArgError, "non-symbol key in keyword arguments: %+"PRIsVALUE, - arg.nonsymkey); - } - *orighash = 0; + rb_hash_foreach(hash, separate_symbol, (st_data_t)&parthash); + *orighash = parthash[1]; + if (parthash[1] && RBASIC_CLASS(hash) != rb_cHash) { + RBASIC_SET_CLASS(parthash[1], RBASIC_CLASS(hash)); } - return arg.kwdhash; + return parthash[0]; } int -- cgit v1.2.3