Ruby 2.1.5p273(2014-11-13revision48405)

- Main Page
- Modules
- Data Structures
- Files

- File List
- Globals

hash.c
Go to the documentation of this file.
1 /**********************************************************************
2
3 hash.c -
4
5 $Author: nagachika $
6 created at: Mon Nov 22 18:51:18 JST 1993
7
8 Copyright (C) 1993-2007 Yukihiro Matsumoto
9 Copyright (C) 2000 Network Applied Communication Laboratory, Inc.
10 Copyright (C) 2000 Information-technology Promotion Agency, Japan
11
12 **********************************************************************/
13
14 #include "ruby/ruby.h"
15 #include "ruby/st.h"
16 #include "ruby/util.h"
17 #include "ruby/encoding.h"
18 #include "internal.h"
19 #include <errno.h>
20 #include "probes.h"
21
22 #ifdef __APPLE__
23 # ifdef HAVE_CRT_EXTERNS_H
24 # include <crt_externs.h>
25 # else
26 # include "missing/crt_externs.h"
27 # endif
28 #endif
29
30 #define HAS_EXTRA_STATES(hash, klass) ( \
31 ((klass = has_extra_methods(rb_obj_class(hash))) != 0) || \
32 FL_TEST((hash), FL_EXIVAR|FL_TAINT|HASH_PROC_DEFAULT) || \
33 !NIL_P(RHASH_IFNONE(hash)))
34 #define HASH_REJECT_COPY_EXTRA_STATES 1
35
36 static VALUE
37 has_extra_methods(VALUE klass)
38 {
39 const VALUE base = rb_cHash;
40 VALUE c = klass;
41 while (c != base) {
42 st_table *mtbl = RCLASS_M_TBL(c);
43 if (mtbl && mtbl->num_entries) return klass;
44 c = RCLASS_SUPER(c);
45 }
46 return 0;
47 }
48
49 static VALUE rb_hash_s_try_convert(VALUE, VALUE);
50
51 /*
52 * Hash WB strategy:
53 * 1. Check mutate st_* functions
54 * * st_insert()
55 * * st_insert2()
56 * * st_update()
57 * * st_add_direct()
58 * 2. Insert WBs
59 */
60
61 VALUE
62 rb_hash_freeze(VALUE hash)
63 {
64 return rb_obj_freeze(hash);
65 }
66
67 VALUE rb_cHash;
68
69 static VALUE envtbl;
70 static ID id_hash, id_yield, id_default, id_flatten_bang;
71
72 VALUE
73 rb_hash_set_ifnone(VALUE hash, VALUE ifnone)
74 {
75 RB_OBJ_WRITE(hash, (&RHASH(hash)->ifnone), ifnone);
76 return hash;
77 }
78
79 static int
80 rb_any_cmp(VALUE a, VALUE b)
81 {
82 if (a == b) return 0;
83 if (FIXNUM_P(a) && FIXNUM_P(b)) {
84 return a != b;
85 }
86 if (RB_TYPE_P(a, T_STRING) && RBASIC(a)->klass == rb_cString &&
87 RB_TYPE_P(b, T_STRING) && RBASIC(b)->klass == rb_cString) {
88 return rb_str_hash_cmp(a, b);
89 }
90 if (a == Qundef || b == Qundef) return -1;
91 if (SYMBOL_P(a) && SYMBOL_P(b)) {
92 return a != b;
93 }
94
95 return !rb_eql(a, b);
96 }
97
98 static VALUE
99 hash_recursive(VALUE obj, VALUE arg, int recurse)
100 {
101 if (recurse) return INT2FIX(0);
102 return rb_funcallv(obj, id_hash, 0, 0);
103 }
104
105 VALUE
106 rb_hash(VALUE obj)
107 {
108 VALUE hval = rb_exec_recursive_outer(hash_recursive, obj, 0);
109
110 while (!FIXNUM_P(hval)) {
111 if (RB_TYPE_P(hval, T_BIGNUM)) {
112 int sign;
113 unsigned long ul;
114 sign = rb_integer_pack(hval, &ul, 1, sizeof(ul), 0,
115 INTEGER_PACK_NATIVE_BYTE_ORDER);
116 ul &= (1UL << (sizeof(long)*CHAR_BIT-1)) - 1;
117 if (sign < 0)
118 return LONG2FIX(-(long)ul);
119 return LONG2FIX((long)ul);
120 }
121 hval = rb_to_int(hval);
122 }
123 return hval;
124 }
125
126 long rb_objid_hash(st_index_t index);
127
128 static st_index_t
129 rb_any_hash(VALUE a)
130 {
131 VALUE hval;
132 st_index_t hnum;
133
134 if (SPECIAL_CONST_P(a)) {
135 if (a == Qundef) return 0;
136 hnum = rb_objid_hash((st_index_t)a);
137 }
138 else if (BUILTIN_TYPE(a) == T_STRING) {
139 hnum = rb_str_hash(a);
140 }
141 else {
142 hval = rb_hash(a);
143 hnum = FIX2LONG(hval);
144 }
145 hnum <<= 1;
146 return (st_index_t)RSHIFT(hnum, 1);
147 }
148
149 long
150 rb_objid_hash(st_index_t index)
151 {
152 st_index_t hnum = rb_hash_start(index);
153 hnum = rb_hash_uint(hnum, (st_index_t)rb_any_hash);
154 hnum = rb_hash_end(hnum);
155 return hnum;
156 }
157
158 static const struct st_hash_type objhash = {
159 rb_any_cmp,
160 rb_any_hash,
161 };
162
163 extern const struct st_hash_type st_hashtype_num;
164 #define identhash st_hashtype_num
165
166 typedef int st_foreach_func(st_data_t, st_data_t, st_data_t);
167
168 struct foreach_safe_arg {
169 st_table *tbl;
170 st_foreach_func *func;
171 st_data_t arg;
172 };
173
174 static int
175 foreach_safe_i(st_data_t key, st_data_t value, st_data_t args, int error)
176 {
177 int status;
178 struct foreach_safe_arg *arg = (void *)args;
179
180 if (error) return ST_STOP;
181 status = (*arg->func)(key, value, arg->arg);
182 if (status == ST_CONTINUE) {
183 return ST_CHECK;
184 }
185 return status;
186 }
187
188 void
189 st_foreach_safe(st_table *table, int (*func)(ANYARGS), st_data_t a)
190 {
191 struct foreach_safe_arg arg;
192
193 arg.tbl = table;
194 arg.func = (st_foreach_func *)func;
195 arg.arg = a;
196 if (st_foreach_check(table, foreach_safe_i, (st_data_t)&arg, 0)) {
197 rb_raise(rb_eRuntimeError, "hash modified during iteration");
198 }
199 }
200
201 typedef int rb_foreach_func(VALUE, VALUE, VALUE);
202
203 struct hash_foreach_arg {
204 VALUE hash;
205 rb_foreach_func *func;
206 VALUE arg;
207 };
208
209 static int
210 hash_foreach_iter(st_data_t key, st_data_t value, st_data_t argp, int error)
211 {
212 struct hash_foreach_arg *arg = (struct hash_foreach_arg *)argp;
213 int status;
214 st_table *tbl;
215
216 if (error) return ST_STOP;
217 tbl = RHASH(arg->hash)->ntbl;
218 status = (*arg->func)((VALUE)key, (VALUE)value, arg->arg);
219 if (RHASH(arg->hash)->ntbl != tbl) {
220 rb_raise(rb_eRuntimeError, "rehash occurred during iteration");
221 }
222 switch (status) {
223 case ST_DELETE:
224 FL_SET(arg->hash, HASH_DELETED);
225 return ST_DELETE;
226 case ST_CONTINUE:
227 break;
228 case ST_STOP:
229 return ST_STOP;
230 }
231 return ST_CHECK;
232 }
233
234 static VALUE
235 hash_foreach_ensure_rollback(VALUE hash)
236 {
237 RHASH_ITER_LEV(hash)++;
238 return 0;
239 }
240
241 static VALUE
242 hash_foreach_ensure(VALUE hash)
243 {
244 if (--RHASH_ITER_LEV(hash) == 0) {
245 if (FL_TEST(hash, HASH_DELETED)) {
246 st_cleanup_safe(RHASH(hash)->ntbl, (st_data_t)Qundef);
247 FL_UNSET(hash, HASH_DELETED);
248 }
249 }
250 return 0;
251 }
252
253 static VALUE
254 hash_foreach_call(VALUE arg)
255 {
256 VALUE hash = ((struct hash_foreach_arg *)arg)->hash;
257 if (st_foreach_check(RHASH(hash)->ntbl, hash_foreach_iter, (st_data_t)arg, (st_data_t)Qundef)) {
258 rb_raise(rb_eRuntimeError, "hash modified during iteration");
259 }
260 return Qnil;
261 }
262
263 void
264 rb_hash_foreach(VALUE hash, int (*func)(ANYARGS), VALUE farg)
265 {
266 struct hash_foreach_arg arg;
267
268 if (!RHASH(hash)->ntbl)
269 return;
270 RHASH_ITER_LEV(hash)++;
271 arg.hash = hash;
272 arg.func = (rb_foreach_func *)func;
273 arg.arg = farg;
274 rb_ensure(hash_foreach_call, (VALUE)&arg, hash_foreach_ensure, hash);
275 }
276
277 static VALUE
278 hash_alloc(VALUE klass)
279 {
280 NEWOBJ_OF(hash, struct RHash, klass, T_HASH | (RGENGC_WB_PROTECTED_HASH ? FL_WB_PROTECTED : 0));
281
282 RHASH_SET_IFNONE((VALUE)hash, Qnil);
283
284 return (VALUE)hash;
285 }
286
287 static VALUE
288 empty_hash_alloc(VALUE klass)
289 {
290 if (RUBY_DTRACE_HASH_CREATE_ENABLED()) {
291 RUBY_DTRACE_HASH_CREATE(0, rb_sourcefile(), rb_sourceline());
292 }
293
294 return hash_alloc(klass);
295 }
296
297 VALUE
298 rb_hash_new(void)
299 {
300 return hash_alloc(rb_cHash);
301 }
302
303 static VALUE
304 rb_hash_dup_empty(VALUE hash)
305 {
306 NEWOBJ_OF(ret, struct RHash,
307 rb_obj_class(hash),
308 (RBASIC(hash)->flags)&(T_MASK|FL_EXIVAR|FL_TAINT));
309 if (FL_TEST((hash), FL_EXIVAR))
310 rb_copy_generic_ivar((VALUE)(ret),(VALUE)(hash));
311
312 if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
313 FL_SET(ret, HASH_PROC_DEFAULT);
314 }
315 RHASH_SET_IFNONE(ret, RHASH_IFNONE(hash));
316 return (VALUE)ret;
317 }
318
319 VALUE
320 rb_hash_dup(VALUE hash)
321 {
322 VALUE ret = rb_hash_dup_empty(hash);
323 if (!RHASH_EMPTY_P(hash))
324 RHASH(ret)->ntbl = st_copy(RHASH(hash)->ntbl);
325 return ret;
326 }
327
328 static void
329 rb_hash_modify_check(VALUE hash)
330 {
331 rb_check_frozen(hash);
332 }
333
334 static struct st_table *
335 hash_tbl(VALUE hash)
336 {
337 if (!RHASH(hash)->ntbl) {
338 RHASH(hash)->ntbl = st_init_table(&objhash);
339 }
340 return RHASH(hash)->ntbl;
341 }
342
343 struct st_table *
344 rb_hash_tbl(VALUE hash)
345 {
346 OBJ_WB_UNPROTECT(hash);
347 return hash_tbl(hash);
348 }
349
350 struct st_table *
351 rb_hash_tbl_raw(VALUE hash)
352 {
353 return hash_tbl(hash);
354 }
355
356 static void
357 rb_hash_modify(VALUE hash)
358 {
359 rb_hash_modify_check(hash);
360 hash_tbl(hash);
361 }
362
363 NORETURN(static void no_new_key(void));
364 static void
365 no_new_key(void)
366 {
367 rb_raise(rb_eRuntimeError, "can't add a new key into hash during iteration");
368 }
369
370 struct update_callback_arg {
371 VALUE hash;
372 st_data_t arg;
373 };
374
375 #define NOINSERT_UPDATE_CALLBACK(func) \
376 static int \
377 func##_noinsert(st_data_t *key, st_data_t *val, st_data_t arg, int existing) \
378 { \
379 if (!existing) no_new_key(); \
380 return func(key, val, (struct update_arg *)arg, existing); \
381 } \
382 \
383 static int \
384 func##_insert(st_data_t *key, st_data_t *val, st_data_t arg, int existing) \
385 { \
386 return func(key, val, (struct update_arg *)arg, existing); \
387 }
388
389 struct update_arg {
390 st_data_t arg;
391 VALUE hash;
392 VALUE new_key;
393 VALUE old_key;
394 VALUE new_value;
395 VALUE old_value;
396 };
397
398 static int
399 tbl_update(VALUE hash, VALUE key, int (*func)(st_data_t *key, st_data_t *val, st_data_t arg, int existing), st_data_t optional_arg)
400 {
401 struct update_arg arg;
402 int result;
403
404 arg.arg = optional_arg;
405 arg.hash = hash;
406 arg.new_key = 0;
407 arg.old_key = Qundef;
408 arg.new_value = 0;
409 arg.old_value = Qundef;
410
411 result = st_update(RHASH(hash)->ntbl, (st_data_t)key, func, (st_data_t)&arg);
412
413 /* write barrier */
414 if (arg.new_key) RB_OBJ_WRITTEN(hash, arg.old_key, arg.new_key);
415 if (arg.new_value) RB_OBJ_WRITTEN(hash, arg.old_value, arg.new_value);
416
417 return result;
418 }
419
420 #define UPDATE_CALLBACK(iter_lev, func) ((iter_lev) > 0 ? func##_noinsert : func##_insert)
421
422 #define RHASH_UPDATE_ITER(h, iter_lev, key, func, a) do { \
423 tbl_update((h), (key), UPDATE_CALLBACK((iter_lev), func), (st_data_t)(a)); \
424 } while (0)
425
426 #define RHASH_UPDATE(hash, key, func, arg) \
427 RHASH_UPDATE_ITER(hash, RHASH_ITER_LEV(hash), key, func, arg)
428
429 static void
430 default_proc_arity_check(VALUE proc)
431 {
432 int n = rb_proc_arity(proc);
433
434 if (rb_proc_lambda_p(proc) && n != 2 && (n >= 0 || n < -3)) {
435 if (n < 0) n = -n-1;
436 rb_raise(rb_eTypeError, "default_proc takes two arguments (2 for %d)", n);
437 }
438 }
439
440 /*
441 * call-seq:
442 * Hash.new -> new_hash
443 * Hash.new(obj) -> new_hash
444 * Hash.new {|hash, key| block } -> new_hash
445 *
446 * Returns a new, empty hash. If this hash is subsequently accessed by
447 * a key that doesn't correspond to a hash entry, the value returned
448 * depends on the style of <code>new</code> used to create the hash. In
449 * the first form, the access returns <code>nil</code>. If
450 * <i>obj</i> is specified, this single object will be used for
451 * all <em>default values</em>. If a block is specified, it will be
452 * called with the hash object and the key, and should return the
453 * default value. It is the block's responsibility to store the value
454 * in the hash if required.
455 *
456 * h = Hash.new("Go Fish")
457 * h["a"] = 100
458 * h["b"] = 200
459 * h["a"] #=> 100
460 * h["c"] #=> "Go Fish"
461 * # The following alters the single default object
462 * h["c"].upcase! #=> "GO FISH"
463 * h["d"] #=> "GO FISH"
464 * h.keys #=> ["a", "b"]
465 *
466 * # While this creates a new default object each time
467 * h = Hash.new { |hash, key| hash[key] = "Go Fish: #{key}" }
468 * h["c"] #=> "Go Fish: c"
469 * h["c"].upcase! #=> "GO FISH: C"
470 * h["d"] #=> "Go Fish: d"
471 * h.keys #=> ["c", "d"]
472 *
473 */
474
475 static VALUE
476 rb_hash_initialize(int argc, VALUE *argv, VALUE hash)
477 {
478 VALUE ifnone;
479
480 rb_hash_modify(hash);
481 if (rb_block_given_p()) {
482 rb_check_arity(argc, 0, 0);
483 ifnone = rb_block_proc();
484 default_proc_arity_check(ifnone);
485 RHASH_SET_IFNONE(hash, ifnone);
486 FL_SET(hash, HASH_PROC_DEFAULT);
487 }
488 else {
489 rb_scan_args(argc, argv, "01", &ifnone);
490 RHASH_SET_IFNONE(hash, ifnone);
491 }
492
493 return hash;
494 }
495
496 /*
497 * call-seq:
498 * Hash[ key, value, ... ] -> new_hash
499 * Hash[ [ [key, value], ... ] ] -> new_hash
500 * Hash[ object ] -> new_hash
501 *
502 * Creates a new hash populated with the given objects.
503 *
504 * Similar to the literal <code>{ _key_ => _value_, ... }</code>. In the first
505 * form, keys and values occur in pairs, so there must be an even number of
506 * arguments.
507 *
508 * The second and third form take a single argument which is either an array
509 * of key-value pairs or an object convertible to a hash.
510 *
511 * Hash["a", 100, "b", 200] #=> {"a"=>100, "b"=>200}
512 * Hash[ [ ["a", 100], ["b", 200] ] ] #=> {"a"=>100, "b"=>200}
513 * Hash["a" => 100, "b" => 200] #=> {"a"=>100, "b"=>200}
514 */
515
516 static VALUE
517 rb_hash_s_create(int argc, VALUE *argv, VALUE klass)
518 {
519 VALUE hash, tmp;
520 int i;
521
522 if (argc == 1) {
523 tmp = rb_hash_s_try_convert(Qnil, argv[0]);
524 if (!NIL_P(tmp)) {
525 hash = hash_alloc(klass);
526 if (RHASH(tmp)->ntbl) {
527 RHASH(hash)->ntbl = st_copy(RHASH(tmp)->ntbl);
528 }
529 return hash;
530 }
531
532 tmp = rb_check_array_type(argv[0]);
533 if (!NIL_P(tmp)) {
534 long i;
535
536 hash = hash_alloc(klass);
537 for (i = 0; i < RARRAY_LEN(tmp); ++i) {
538 VALUE e = RARRAY_AREF(tmp, i);
539 VALUE v = rb_check_array_type(e);
540 VALUE key, val = Qnil;
541
542 if (NIL_P(v)) {
543 #if 0 /* refix in the next release */
544 rb_raise(rb_eArgError, "wrong element type %s at %ld (expected array)",
545 rb_builtin_class_name(e), i);
546
547 #else
548 rb_warn("wrong element type %s at %ld (expected array)",
549 rb_builtin_class_name(e), i);
550 rb_warn("ignoring wrong elements is deprecated, remove them explicitly");
551 rb_warn("this causes ArgumentError in the next release");
552 continue;
553 #endif
554 }
555 switch (RARRAY_LEN(v)) {
556 default:
557 rb_raise(rb_eArgError, "invalid number of elements (%ld for 1..2)",
558 RARRAY_LEN(v));
559 case 2:
560 val = RARRAY_AREF(v, 1);
561 case 1:
562 key = RARRAY_AREF(v, 0);
563 rb_hash_aset(hash, key, val);
564 }
565 }
566 return hash;
567 }
568 }
569 if (argc % 2 != 0) {
570 rb_raise(rb_eArgError, "odd number of arguments for Hash");
571 }
572
573 hash = hash_alloc(klass);
574 for (i=0; i<argc; i+=2) {
575 rb_hash_aset(hash, argv[i], argv[i + 1]);
576 }
577
578 return hash;
579 }
580
581 static VALUE
582 to_hash(VALUE hash)
583 {
584 return rb_convert_type(hash, T_HASH, "Hash", "to_hash");
585 }
586
587 VALUE
588 rb_check_hash_type(VALUE hash)
589 {
590 return rb_check_convert_type(hash, T_HASH, "Hash", "to_hash");
591 }
592
593 /*
594 * call-seq:
595 * Hash.try_convert(obj) -> hash or nil
596 *
597 * Try to convert <i>obj</i> into a hash, using to_hash method.
598 * Returns converted hash or nil if <i>obj</i> cannot be converted
599 * for any reason.
600 *
601 * Hash.try_convert({1=>2}) # => {1=>2}
602 * Hash.try_convert("1=>2") # => nil
603 */
604 static VALUE
605 rb_hash_s_try_convert(VALUE dummy, VALUE hash)
606 {
607 return rb_check_hash_type(hash);
608 }
609
610 struct rehash_arg {
611 VALUE hash;
612 st_table *tbl;
613 };
614
615 static int
616 rb_hash_rehash_i(VALUE key, VALUE value, VALUE arg)
617 {
618 st_table *tbl = (st_table *)arg;
619
620 st_insert(tbl, (st_data_t)key, (st_data_t)value);
621 return ST_CONTINUE;
622 }
623
624 /*
625 * call-seq:
626 * hsh.rehash -> hsh
627 *
628 * Rebuilds the hash based on the current hash values for each key. If
629 * values of key objects have changed since they were inserted, this
630 * method will reindex <i>hsh</i>. If <code>Hash#rehash</code> is
631 * called while an iterator is traversing the hash, an
632 * <code>RuntimeError</code> will be raised in the iterator.
633 *
634 * a = [ "a", "b" ]
635 * c = [ "c", "d" ]
636 * h = { a => 100, c => 300 }
637 * h[a] #=> 100
638 * a[0] = "z"
639 * h[a] #=> nil
640 * h.rehash #=> {["z", "b"]=>100, ["c", "d"]=>300}
641 * h[a] #=> 100
642 */
643
644 static VALUE
645 rb_hash_rehash(VALUE hash)
646 {
647 VALUE tmp;
648 st_table *tbl;
649
650 if (RHASH_ITER_LEV(hash) > 0) {
651 rb_raise(rb_eRuntimeError, "rehash during iteration");
652 }
653 rb_hash_modify_check(hash);
654 if (!RHASH(hash)->ntbl)
655 return hash;
656 tmp = hash_alloc(0);
657 tbl = st_init_table_with_size(RHASH(hash)->ntbl->type, RHASH(hash)->ntbl->num_entries);
658 RHASH(tmp)->ntbl = tbl;
659
660 rb_hash_foreach(hash, rb_hash_rehash_i, (VALUE)tbl);
661 st_free_table(RHASH(hash)->ntbl);
662 RHASH(hash)->ntbl = tbl;
663 RHASH(tmp)->ntbl = 0;
664
665 return hash;
666 }
667
668 static VALUE
669 hash_default_value(VALUE hash, VALUE key)
670 {
671 if (rb_method_basic_definition_p(CLASS_OF(hash), id_default)) {
672 VALUE ifnone = RHASH_IFNONE(hash);
673 if (!FL_TEST(hash, HASH_PROC_DEFAULT)) return ifnone;
674 if (key == Qundef) return Qnil;
675 return rb_funcall(ifnone, id_yield, 2, hash, key);
676 }
677 else {
678 return rb_funcall(hash, id_default, 1, key);
679 }
680 }
681
682 /*
683 * call-seq:
684 * hsh[key] -> value
685 *
686 * Element Reference---Retrieves the <i>value</i> object corresponding
687 * to the <i>key</i> object. If not found, returns the default value (see
688 * <code>Hash::new</code> for details).
689 *
690 * h = { "a" => 100, "b" => 200 }
691 * h["a"] #=> 100
692 * h["c"] #=> nil
693 *
694 */
695
696 VALUE
697 rb_hash_aref(VALUE hash, VALUE key)
698 {
699 st_data_t val;
700
701 if (!RHASH(hash)->ntbl || !st_lookup(RHASH(hash)->ntbl, key, &val)) {
702 return hash_default_value(hash, key);
703 }
704 return (VALUE)val;
705 }
706
707 VALUE
708 rb_hash_lookup2(VALUE hash, VALUE key, VALUE def)
709 {
710 st_data_t val;
711
712 if (!RHASH(hash)->ntbl || !st_lookup(RHASH(hash)->ntbl, key, &val)) {
713 return def; /* without Hash#default */
714 }
715 return (VALUE)val;
716 }
717
718 VALUE
719 rb_hash_lookup(VALUE hash, VALUE key)
720 {
721 return rb_hash_lookup2(hash, key, Qnil);
722 }
723
724 /*
725 * call-seq:
726 * hsh.fetch(key [, default] ) -> obj
727 * hsh.fetch(key) {| key | block } -> obj
728 *
729 * Returns a value from the hash for the given key. If the key can't be
730 * found, there are several options: With no other arguments, it will
731 * raise an <code>KeyError</code> exception; if <i>default</i> is
732 * given, then that will be returned; if the optional code block is
733 * specified, then that will be run and its result returned.
734 *
735 * h = { "a" => 100, "b" => 200 }
736 * h.fetch("a") #=> 100
737 * h.fetch("z", "go fish") #=> "go fish"
738 * h.fetch("z") { |el| "go fish, #{el}"} #=> "go fish, z"
739 *
740 * The following example shows that an exception is raised if the key
741 * is not found and a default value is not supplied.
742 *
743 * h = { "a" => 100, "b" => 200 }
744 * h.fetch("z")
745 *
746 * <em>produces:</em>
747 *
748 * prog.rb:2:in `fetch': key not found (KeyError)
749 * from prog.rb:2
750 *
751 */
752
753 static VALUE
754 rb_hash_fetch_m(int argc, VALUE *argv, VALUE hash)
755 {
756 VALUE key, if_none;
757 st_data_t val;
758 long block_given;
759
760 rb_scan_args(argc, argv, "11", &key, &if_none);
761
762 block_given = rb_block_given_p();
763 if (block_given && argc == 2) {
764 rb_warn("block supersedes default value argument");
765 }
766 if (!RHASH(hash)->ntbl || !st_lookup(RHASH(hash)->ntbl, key, &val)) {
767 if (block_given) return rb_yield(key);
768 if (argc == 1) {
769 volatile VALUE desc = rb_protect(rb_inspect, key, 0);
770 if (NIL_P(desc)) {
771 desc = rb_any_to_s(key);
772 }
773 desc = rb_str_ellipsize(desc, 65);
774 rb_raise(rb_eKeyError, "key not found: %"PRIsVALUE, desc);
775 }
776 return if_none;
777 }
778 return (VALUE)val;
779 }
780
781 VALUE
782 rb_hash_fetch(VALUE hash, VALUE key)
783 {
784 return rb_hash_fetch_m(1, &key, hash);
785 }
786
787 /*
788 * call-seq:
789 * hsh.default(key=nil) -> obj
790 *
791 * Returns the default value, the value that would be returned by
792 * <i>hsh</i>[<i>key</i>] if <i>key</i> did not exist in <i>hsh</i>.
793 * See also <code>Hash::new</code> and <code>Hash#default=</code>.
794 *
795 * h = Hash.new #=> {}
796 * h.default #=> nil
797 * h.default(2) #=> nil
798 *
799 * h = Hash.new("cat") #=> {}
800 * h.default #=> "cat"
801 * h.default(2) #=> "cat"
802 *
803 * h = Hash.new {|h,k| h[k] = k.to_i*10} #=> {}
804 * h.default #=> nil
805 * h.default(2) #=> 20
806 */
807
808 static VALUE
809 rb_hash_default(int argc, VALUE *argv, VALUE hash)
810 {
811 VALUE key, ifnone;
812
813 rb_scan_args(argc, argv, "01", &key);
814 ifnone = RHASH_IFNONE(hash);
815 if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
816 if (argc == 0) return Qnil;
817 return rb_funcall(ifnone, id_yield, 2, hash, key);
818 }
819 return ifnone;
820 }
821
822 /*
823 * call-seq:
824 * hsh.default = obj -> obj
825 *
826 * Sets the default value, the value returned for a key that does not
827 * exist in the hash. It is not possible to set the default to a
828 * <code>Proc</code> that will be executed on each key lookup.
829 *
830 * h = { "a" => 100, "b" => 200 }
831 * h.default = "Go fish"
832 * h["a"] #=> 100
833 * h["z"] #=> "Go fish"
834 * # This doesn't do what you might hope...
835 * h.default = proc do |hash, key|
836 * hash[key] = key + key
837 * end
838 * h[2] #=> #<Proc:0x401b3948@-:6>
839 * h["cat"] #=> #<Proc:0x401b3948@-:6>
840 */
841
842 static VALUE
843 rb_hash_set_default(VALUE hash, VALUE ifnone)
844 {
845 rb_hash_modify_check(hash);
846 RHASH_SET_IFNONE(hash, ifnone);
847 FL_UNSET(hash, HASH_PROC_DEFAULT);
848 return ifnone;
849 }
850
851 /*
852 * call-seq:
853 * hsh.default_proc -> anObject
854 *
855 * If <code>Hash::new</code> was invoked with a block, return that
856 * block, otherwise return <code>nil</code>.
857 *
858 * h = Hash.new {|h,k| h[k] = k*k } #=> {}
859 * p = h.default_proc #=> #<Proc:0x401b3d08@-:1>
860 * a = [] #=> []
861 * p.call(a, 2)
862 * a #=> [nil, nil, 4]
863 */
864
865
866 static VALUE
867 rb_hash_default_proc(VALUE hash)
868 {
869 if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
870 return RHASH_IFNONE(hash);
871 }
872 return Qnil;
873 }
874
875 /*
876 * call-seq:
877 * hsh.default_proc = proc_obj or nil
878 *
879 * Sets the default proc to be executed on each failed key lookup.
880 *
881 * h.default_proc = proc do |hash, key|
882 * hash[key] = key + key
883 * end
884 * h[2] #=> 4
885 * h["cat"] #=> "catcat"
886 */
887
888 static VALUE
889 rb_hash_set_default_proc(VALUE hash, VALUE proc)
890 {
891 VALUE b;
892
893 rb_hash_modify_check(hash);
894 if (NIL_P(proc)) {
895 FL_UNSET(hash, HASH_PROC_DEFAULT);
896 RHASH_SET_IFNONE(hash, proc);
897 return proc;
898 }
899 b = rb_check_convert_type(proc, T_DATA, "Proc", "to_proc");
900 if (NIL_P(b) || !rb_obj_is_proc(b)) {
901 rb_raise(rb_eTypeError,
902 "wrong default_proc type %s (expected Proc)",
903 rb_obj_classname(proc));
904 }
905 proc = b;
906 default_proc_arity_check(proc);
907 RHASH_SET_IFNONE(hash, proc);
908 FL_SET(hash, HASH_PROC_DEFAULT);
909 return proc;
910 }
911
912 static int
913 key_i(VALUE key, VALUE value, VALUE arg)
914 {
915 VALUE *args = (VALUE *)arg;
916
917 if (rb_equal(value, args[0])) {
918 args[1] = key;
919 return ST_STOP;
920 }
921 return ST_CONTINUE;
922 }
923
924 /*
925 * call-seq:
926 * hsh.key(value) -> key
927 *
928 * Returns the key of an occurrence of a given value. If the value is
929 * not found, returns <code>nil</code>.
930 *
931 * h = { "a" => 100, "b" => 200, "c" => 300, "d" => 300 }
932 * h.key(200) #=> "b"
933 * h.key(300) #=> "c"
934 * h.key(999) #=> nil
935 *
936 */
937
938 static VALUE
939 rb_hash_key(VALUE hash, VALUE value)
940 {
941 VALUE args[2];
942
943 args[0] = value;
944 args[1] = Qnil;
945
946 rb_hash_foreach(hash, key_i, (VALUE)args);
947
948 return args[1];
949 }
950
951 /* :nodoc: */
952 static VALUE
953 rb_hash_index(VALUE hash, VALUE value)
954 {
955 rb_warn("Hash#index is deprecated; use Hash#key");
956 return rb_hash_key(hash, value);
957 }
958
959 static VALUE
960 rb_hash_delete_key(VALUE hash, VALUE key)
961 {
962 st_data_t ktmp = (st_data_t)key, val;
963
964 if (!RHASH(hash)->ntbl)
965 return Qundef;
966 if (RHASH_ITER_LEV(hash) > 0) {
967 if (st_delete_safe(RHASH(hash)->ntbl, &ktmp, &val, (st_data_t)Qundef)) {
968 FL_SET(hash, HASH_DELETED);
969 return (VALUE)val;
970 }
971 }
972 else if (st_delete(RHASH(hash)->ntbl, &ktmp, &val))
973 return (VALUE)val;
974 return Qundef;
975 }
976
977 /*
978 * call-seq:
979 * hsh.delete(key) -> value
980 * hsh.delete(key) {| key | block } -> value
981 *
982 * Deletes the key-value pair and returns the value from <i>hsh</i> whose
983 * key is equal to <i>key</i>. If the key is not found, returns the
984 * <em>default value</em>. If the optional code block is given and the
985 * key is not found, pass in the key and return the result of
986 * <i>block</i>.
987 *
988 * h = { "a" => 100, "b" => 200 }
989 * h.delete("a") #=> 100
990 * h.delete("z") #=> nil
991 * h.delete("z") { |el| "#{el} not found" } #=> "z not found"
992 *
993 */
994
995 VALUE
996 rb_hash_delete(VALUE hash, VALUE key)
997 {
998 VALUE val;
999
1000 rb_hash_modify_check(hash);
1001 val = rb_hash_delete_key(hash, key);
1002 if (val != Qundef) return val;
1003 if (rb_block_given_p()) {
1004 return rb_yield(key);
1005 }
1006 return Qnil;
1007 }
1008
1009 struct shift_var {
1010 VALUE key;
1011 VALUE val;
1012 };
1013
1014 static int
1015 shift_i_safe(VALUE key, VALUE value, VALUE arg)
1016 {
1017 struct shift_var *var = (struct shift_var *)arg;
1018
1019 var->key = key;
1020 var->val = value;
1021 return ST_STOP;
1022 }
1023
1024 /*
1025 * call-seq:
1026 * hsh.shift -> anArray or obj
1027 *
1028 * Removes a key-value pair from <i>hsh</i> and returns it as the
1029 * two-item array <code>[</code> <i>key, value</i> <code>]</code>, or
1030 * the hash's default value if the hash is empty.
1031 *
1032 * h = { 1 => "a", 2 => "b", 3 => "c" }
1033 * h.shift #=> [1, "a"]
1034 * h #=> {2=>"b", 3=>"c"}
1035 */
1036
1037 static VALUE
1038 rb_hash_shift(VALUE hash)
1039 {
1040 struct shift_var var;
1041
1042 rb_hash_modify_check(hash);
1043 if (RHASH(hash)->ntbl) {
1044 var.key = Qundef;
1045 if (RHASH_ITER_LEV(hash) == 0) {
1046 if (st_shift(RHASH(hash)->ntbl, &var.key, &var.val)) {
1047 return rb_assoc_new(var.key, var.val);
1048 }
1049 }
1050 else {
1051 rb_hash_foreach(hash, shift_i_safe, (VALUE)&var);
1052 if (var.key != Qundef) {
1053 rb_hash_delete_key(hash, var.key);
1054 return rb_assoc_new(var.key, var.val);
1055 }
1056 }
1057 }
1058 return hash_default_value(hash, Qnil);
1059 }
1060
1061 static int
1062 delete_if_i(VALUE key, VALUE value, VALUE hash)
1063 {
1064 if (RTEST(rb_yield_values(2, key, value))) {
1065 return ST_DELETE;
1066 }
1067 return ST_CONTINUE;
1068 }
1069
1070 static VALUE rb_hash_size(VALUE hash);
1071
1072 static VALUE
1073 hash_enum_size(VALUE hash, VALUE args, VALUE eobj)
1074 {
1075 return rb_hash_size(hash);
1076 }
1077
1078 /*
1079 * call-seq:
1080 * hsh.delete_if {| key, value | block } -> hsh
1081 * hsh.delete_if -> an_enumerator
1082 *
1083 * Deletes every key-value pair from <i>hsh</i> for which <i>block</i>
1084 * evaluates to <code>true</code>.
1085 *
1086 * If no block is given, an enumerator is returned instead.
1087 *
1088 * h = { "a" => 100, "b" => 200, "c" => 300 }
1089 * h.delete_if {|key, value| key >= "b" } #=> {"a"=>100}
1090 *
1091 */
1092
1093 VALUE
1094 rb_hash_delete_if(VALUE hash)
1095 {
1096 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1097 rb_hash_modify_check(hash);
1098 if (RHASH(hash)->ntbl)
1099 rb_hash_foreach(hash, delete_if_i, hash);
1100 return hash;
1101 }
1102
1103 /*
1104 * call-seq:
1105 * hsh.reject! {| key, value | block } -> hsh or nil
1106 * hsh.reject! -> an_enumerator
1107 *
1108 * Equivalent to <code>Hash#delete_if</code>, but returns
1109 * <code>nil</code> if no changes were made.
1110 */
1111
1112 VALUE
1113 rb_hash_reject_bang(VALUE hash)
1114 {
1115 st_index_t n;
1116
1117 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1118 rb_hash_modify(hash);
1119 n = RHASH_SIZE(hash);
1120 if (!n) return Qnil;
1121 rb_hash_foreach(hash, delete_if_i, hash);
1122 if (n == RHASH(hash)->ntbl->num_entries) return Qnil;
1123 return hash;
1124 }
1125
1126 static int
1127 reject_i(VALUE key, VALUE value, VALUE result)
1128 {
1129 if (!RTEST(rb_yield_values(2, key, value))) {
1130 rb_hash_aset(result, key, value);
1131 }
1132 return ST_CONTINUE;
1133 }
1134
1135 /*
1136 * call-seq:
1137 * hsh.reject {|key, value| block} -> a_hash
1138 * hsh.reject -> an_enumerator
1139 *
1140 * Returns a new hash consisting of entries for which the block returns false.
1141 *
1142 * If no block is given, an enumerator is returned instead.
1143 *
1144 * h = { "a" => 100, "b" => 200, "c" => 300 }
1145 * h.reject {|k,v| k < "b"} #=> {"b" => 200, "c" => 300}
1146 * h.reject {|k,v| v > 100} #=> {"a" => 100}
1147 */
1148
1149 VALUE
1150 rb_hash_reject(VALUE hash)
1151 {
1152 VALUE result;
1153
1154 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1155 if (RTEST(ruby_verbose)) {
1156 VALUE klass;
1157 if (HAS_EXTRA_STATES(hash, klass)) {
1158 #if HASH_REJECT_COPY_EXTRA_STATES
1159 rb_warn("copying extra states: %+"PRIsVALUE, hash);
1160 rb_warn("following states will not be copied in the future version:");
1161 if (klass) {
1162 rb_warn(" subclass: %+"PRIsVALUE, klass);
1163 }
1164 if (FL_TEST(hash, FL_EXIVAR)) {
1165 rb_warn(" instance variables: %+"PRIsVALUE,
1166 rb_obj_instance_variables(hash));
1167 }
1168 if (FL_TEST(hash, FL_TAINT)) {
1169 rb_warn(" taintedness");
1170 }
1171 if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
1172 rb_warn(" default proc: %+"PRIsVALUE, RHASH_IFNONE(hash));
1173 }
1174 else if (!NIL_P(RHASH_IFNONE(hash)))
1175 rb_warn(" default value: %+"PRIsVALUE, RHASH_IFNONE(hash));
1176 #else
1177 rb_warn("extra states are no longer copied: %+"PRIsVALUE, hash);
1178 #endif
1179 }
1180 }
1181 #if HASH_REJECT_COPY_EXTRA_STATES
1182 result = rb_hash_dup_empty(hash);
1183 #else
1184 result = rb_hash_new();
1185 #endif
1186 if (!RHASH_EMPTY_P(hash)) {
1187 rb_hash_foreach(hash, reject_i, result);
1188 }
1189 return result;
1190 }
1191
1192 /*
1193 * call-seq:
1194 * hsh.values_at(key, ...) -> array
1195 *
1196 * Return an array containing the values associated with the given keys.
1197 * Also see <code>Hash.select</code>.
1198 *
1199 * h = { "cat" => "feline", "dog" => "canine", "cow" => "bovine" }
1200 * h.values_at("cow", "cat") #=> ["bovine", "feline"]
1201 */
1202
1203 VALUE
1204 rb_hash_values_at(int argc, VALUE *argv, VALUE hash)
1205 {
1206 VALUE result = rb_ary_new2(argc);
1207 long i;
1208
1209 for (i=0; i<argc; i++) {
1210 rb_ary_push(result, rb_hash_aref(hash, argv[i]));
1211 }
1212 return result;
1213 }
1214
1215 static int
1216 select_i(VALUE key, VALUE value, VALUE result)
1217 {
1218 if (RTEST(rb_yield_values(2, key, value))) {
1219 rb_hash_aset(result, key, value);
1220 }
1221 return ST_CONTINUE;
1222 }
1223
1224 /*
1225 * call-seq:
1226 * hsh.select {|key, value| block} -> a_hash
1227 * hsh.select -> an_enumerator
1228 *
1229 * Returns a new hash consisting of entries for which the block returns true.
1230 *
1231 * If no block is given, an enumerator is returned instead.
1232 *
1233 * h = { "a" => 100, "b" => 200, "c" => 300 }
1234 * h.select {|k,v| k > "a"} #=> {"b" => 200, "c" => 300}
1235 * h.select {|k,v| v < 200} #=> {"a" => 100}
1236 */
1237
1238 VALUE
1239 rb_hash_select(VALUE hash)
1240 {
1241 VALUE result;
1242
1243 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1244 result = rb_hash_new();
1245 if (!RHASH_EMPTY_P(hash)) {
1246 rb_hash_foreach(hash, select_i, result);
1247 }
1248 return result;
1249 }
1250
1251 static int
1252 keep_if_i(VALUE key, VALUE value, VALUE hash)
1253 {
1254 if (!RTEST(rb_yield_values(2, key, value))) {
1255 return ST_DELETE;
1256 }
1257 return ST_CONTINUE;
1258 }
1259
1260 /*
1261 * call-seq:
1262 * hsh.select! {| key, value | block } -> hsh or nil
1263 * hsh.select! -> an_enumerator
1264 *
1265 * Equivalent to <code>Hash#keep_if</code>, but returns
1266 * <code>nil</code> if no changes were made.
1267 */
1268
1269 VALUE
1270 rb_hash_select_bang(VALUE hash)
1271 {
1272 st_index_t n;
1273
1274 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1275 rb_hash_modify_check(hash);
1276 if (!RHASH(hash)->ntbl)
1277 return Qnil;
1278 n = RHASH(hash)->ntbl->num_entries;
1279 rb_hash_foreach(hash, keep_if_i, hash);
1280 if (n == RHASH(hash)->ntbl->num_entries) return Qnil;
1281 return hash;
1282 }
1283
1284 /*
1285 * call-seq:
1286 * hsh.keep_if {| key, value | block } -> hsh
1287 * hsh.keep_if -> an_enumerator
1288 *
1289 * Deletes every key-value pair from <i>hsh</i> for which <i>block</i>
1290 * evaluates to false.
1291 *
1292 * If no block is given, an enumerator is returned instead.
1293 *
1294 */
1295
1296 VALUE
1297 rb_hash_keep_if(VALUE hash)
1298 {
1299 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1300 rb_hash_modify_check(hash);
1301 if (RHASH(hash)->ntbl)
1302 rb_hash_foreach(hash, keep_if_i, hash);
1303 return hash;
1304 }
1305
1306 static int
1307 clear_i(VALUE key, VALUE value, VALUE dummy)
1308 {
1309 return ST_DELETE;
1310 }
1311
1312 /*
1313 * call-seq:
1314 * hsh.clear -> hsh
1315 *
1316 * Removes all key-value pairs from <i>hsh</i>.
1317 *
1318 * h = { "a" => 100, "b" => 200 } #=> {"a"=>100, "b"=>200}
1319 * h.clear #=> {}
1320 *
1321 */
1322
1323 VALUE
1324 rb_hash_clear(VALUE hash)
1325 {
1326 rb_hash_modify_check(hash);
1327 if (!RHASH(hash)->ntbl)
1328 return hash;
1329 if (RHASH(hash)->ntbl->num_entries > 0) {
1330 if (RHASH_ITER_LEV(hash) > 0)
1331 rb_hash_foreach(hash, clear_i, 0);
1332 else
1333 st_clear(RHASH(hash)->ntbl);
1334 }
1335
1336 return hash;
1337 }
1338
1339 static int
1340 hash_aset(st_data_t *key, st_data_t *val, struct update_arg *arg, int existing)
1341 {
1342 if (existing) {
1343 arg->new_value = arg->arg;
1344 arg->old_value = *val;
1345 }
1346 else {
1347 arg->new_key = *key;
1348 arg->new_value = arg->arg;
1349 }
1350 *val = arg->arg;
1351 return ST_CONTINUE;
1352 }
1353
1354 static int
1355 hash_aset_str(st_data_t *key, st_data_t *val, struct update_arg *arg, int existing)
1356 {
1357 if (!existing) {
1358 *key = rb_str_new_frozen(*key);
1359 }
1360 return hash_aset(key, val, arg, existing);
1361 }
1362
1363 NOINSERT_UPDATE_CALLBACK(hash_aset);
1364 NOINSERT_UPDATE_CALLBACK(hash_aset_str);
1365
1366 /*
1367 * call-seq:
1368 * hsh[key] = value -> value
1369 * hsh.store(key, value) -> value
1370 *
1371 * == Element Assignment
1372 *
1373 * Associates the value given by +value+ with the key given by +key+.
1374 *
1375 * h = { "a" => 100, "b" => 200 }
1376 * h["a"] = 9
1377 * h["c"] = 4
1378 * h #=> {"a"=>9, "b"=>200, "c"=>4}
1379 * h.store("d", 42) #=> {"a"=>9, "b"=>200, "c"=>4, "d"=>42}
1380 *
1381 * +key+ should not have its value changed while it is in use as a key (an
1382 * <tt>unfrozen String</tt> passed as a key will be duplicated and frozen).
1383 *
1384 * a = "a"
1385 * b = "b".freeze
1386 * h = { a => 100, b => 200 }
1387 * h.key(100).equal? a #=> false
1388 * h.key(200).equal? b #=> true
1389 *
1390 */
1391
1392 VALUE
1393 rb_hash_aset(VALUE hash, VALUE key, VALUE val)
1394 {
1395 int iter_lev = RHASH_ITER_LEV(hash);
1396 st_table *tbl = RHASH(hash)->ntbl;
1397
1398 rb_hash_modify(hash);
1399 if (!tbl) {
1400 if (iter_lev > 0) no_new_key();
1401 tbl = hash_tbl(hash);
1402 }
1403 if (tbl->type == &identhash || rb_obj_class(key) != rb_cString) {
1404 RHASH_UPDATE_ITER(hash, iter_lev, key, hash_aset, val);
1405 }
1406 else {
1407 RHASH_UPDATE_ITER(hash, iter_lev, key, hash_aset_str, val);
1408 }
1409 return val;
1410 }
1411
1412 static int
1413 replace_i(VALUE key, VALUE val, VALUE hash)
1414 {
1415 rb_hash_aset(hash, key, val);
1416
1417 return ST_CONTINUE;
1418 }
1419
1420 /* :nodoc: */
1421 static VALUE
1422 rb_hash_initialize_copy(VALUE hash, VALUE hash2)
1423 {
1424 st_table *ntbl;
1425
1426 rb_hash_modify_check(hash);
1427 hash2 = to_hash(hash2);
1428
1429 Check_Type(hash2, T_HASH);
1430
1431 if (hash == hash2) return hash;
1432
1433 ntbl = RHASH(hash)->ntbl;
1434 if (RHASH(hash2)->ntbl) {
1435 if (ntbl) st_free_table(ntbl);
1436 RHASH(hash)->ntbl = st_copy(RHASH(hash2)->ntbl);
1437 if (RHASH(hash)->ntbl->num_entries)
1438 rb_hash_rehash(hash);
1439 }
1440 else if (ntbl) {
1441 st_clear(ntbl);
1442 }
1443
1444 if (FL_TEST(hash2, HASH_PROC_DEFAULT)) {
1445 FL_SET(hash, HASH_PROC_DEFAULT);
1446 }
1447 else {
1448 FL_UNSET(hash, HASH_PROC_DEFAULT);
1449 }
1450 RHASH_SET_IFNONE(hash, RHASH_IFNONE(hash2));
1451
1452 return hash;
1453 }
1454
1455 /*
1456 * call-seq:
1457 * hsh.replace(other_hash) -> hsh
1458 *
1459 * Replaces the contents of <i>hsh</i> with the contents of
1460 * <i>other_hash</i>.
1461 *
1462 * h = { "a" => 100, "b" => 200 }
1463 * h.replace({ "c" => 300, "d" => 400 }) #=> {"c"=>300, "d"=>400}
1464 *
1465 */
1466
1467 static VALUE
1468 rb_hash_replace(VALUE hash, VALUE hash2)
1469 {
1470 st_table *table2;
1471
1472 rb_hash_modify_check(hash);
1473 if (hash == hash2) return hash;
1474 hash2 = to_hash(hash2);
1475
1476 RHASH_SET_IFNONE(hash, RHASH_IFNONE(hash2));
1477 if (FL_TEST(hash2, HASH_PROC_DEFAULT))
1478 FL_SET(hash, HASH_PROC_DEFAULT);
1479 else
1480 FL_UNSET(hash, HASH_PROC_DEFAULT);
1481
1482 table2 = RHASH(hash2)->ntbl;
1483
1484 rb_hash_clear(hash);
1485 if (table2) hash_tbl(hash)->type = table2->type;
1486 rb_hash_foreach(hash2, replace_i, hash);
1487
1488 return hash;
1489 }
1490
1491 /*
1492 * call-seq:
1493 * hsh.length -> fixnum
1494 * hsh.size -> fixnum
1495 *
1496 * Returns the number of key-value pairs in the hash.
1497 *
1498 * h = { "d" => 100, "a" => 200, "v" => 300, "e" => 400 }
1499 * h.length #=> 4
1500 * h.delete("a") #=> 200
1501 * h.length #=> 3
1502 */
1503
1504 static VALUE
1505 rb_hash_size(VALUE hash)
1506 {
1507 return INT2FIX(RHASH_SIZE(hash));
1508 }
1509
1510
1511 /*
1512 * call-seq:
1513 * hsh.empty? -> true or false
1514 *
1515 * Returns <code>true</code> if <i>hsh</i> contains no key-value pairs.
1516 *
1517 * {}.empty? #=> true
1518 *
1519 */
1520
1521 static VALUE
1522 rb_hash_empty_p(VALUE hash)
1523 {
1524 return RHASH_EMPTY_P(hash) ? Qtrue : Qfalse;
1525 }
1526
1527 static int
1528 each_value_i(VALUE key, VALUE value)
1529 {
1530 rb_yield(value);
1531 return ST_CONTINUE;
1532 }
1533
1534 /*
1535 * call-seq:
1536 * hsh.each_value {| value | block } -> hsh
1537 * hsh.each_value -> an_enumerator
1538 *
1539 * Calls <i>block</i> once for each key in <i>hsh</i>, passing the
1540 * value as a parameter.
1541 *
1542 * If no block is given, an enumerator is returned instead.
1543 *
1544 * h = { "a" => 100, "b" => 200 }
1545 * h.each_value {|value| puts value }
1546 *
1547 * <em>produces:</em>
1548 *
1549 * 100
1550 * 200
1551 */
1552
1553 static VALUE
1554 rb_hash_each_value(VALUE hash)
1555 {
1556 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1557 rb_hash_foreach(hash, each_value_i, 0);
1558 return hash;
1559 }
1560
1561 static int
1562 each_key_i(VALUE key, VALUE value)
1563 {
1564 rb_yield(key);
1565 return ST_CONTINUE;
1566 }
1567
1568 /*
1569 * call-seq:
1570 * hsh.each_key {| key | block } -> hsh
1571 * hsh.each_key -> an_enumerator
1572 *
1573 * Calls <i>block</i> once for each key in <i>hsh</i>, passing the key
1574 * as a parameter.
1575 *
1576 * If no block is given, an enumerator is returned instead.
1577 *
1578 * h = { "a" => 100, "b" => 200 }
1579 * h.each_key {|key| puts key }
1580 *
1581 * <em>produces:</em>
1582 *
1583 * a
1584 * b
1585 */
1586 static VALUE
1587 rb_hash_each_key(VALUE hash)
1588 {
1589 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1590 rb_hash_foreach(hash, each_key_i, 0);
1591 return hash;
1592 }
1593
1594 static int
1595 each_pair_i(VALUE key, VALUE value)
1596 {
1597 rb_yield(rb_assoc_new(key, value));
1598 return ST_CONTINUE;
1599 }
1600
1601 static int
1602 each_pair_i_fast(VALUE key, VALUE value)
1603 {
1604 rb_yield_values(2, key, value);
1605 return ST_CONTINUE;
1606 }
1607
1608 /*
1609 * call-seq:
1610 * hsh.each {| key, value | block } -> hsh
1611 * hsh.each_pair {| key, value | block } -> hsh
1612 * hsh.each -> an_enumerator
1613 * hsh.each_pair -> an_enumerator
1614 *
1615 * Calls <i>block</i> once for each key in <i>hsh</i>, passing the key-value
1616 * pair as parameters.
1617 *
1618 * If no block is given, an enumerator is returned instead.
1619 *
1620 * h = { "a" => 100, "b" => 200 }
1621 * h.each {|key, value| puts "#{key} is #{value}" }
1622 *
1623 * <em>produces:</em>
1624 *
1625 * a is 100
1626 * b is 200
1627 *
1628 */
1629
1630 static VALUE
1631 rb_hash_each_pair(VALUE hash)
1632 {
1633 RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
1634 if (rb_block_arity() > 1)
1635 rb_hash_foreach(hash, each_pair_i_fast, 0);
1636 else
1637 rb_hash_foreach(hash, each_pair_i, 0);
1638 return hash;
1639 }
1640
1641 static int
1642 to_a_i(VALUE key, VALUE value, VALUE ary)
1643 {
1644 rb_ary_push(ary, rb_assoc_new(key, value));
1645 return ST_CONTINUE;
1646 }
1647
1648 /*
1649 * call-seq:
1650 * hsh.to_a -> array
1651 *
1652 * Converts <i>hsh</i> to a nested array of <code>[</code> <i>key,
1653 * value</i> <code>]</code> arrays.
1654 *
1655 * h = { "c" => 300, "a" => 100, "d" => 400, "c" => 300 }
1656 * h.to_a #=> [["c", 300], ["a", 100], ["d", 400]]
1657 */
1658
1659 static VALUE
1660 rb_hash_to_a(VALUE hash)
1661 {
1662 VALUE ary;
1663
1664 ary = rb_ary_new_capa(RHASH_SIZE(hash));
1665 rb_hash_foreach(hash, to_a_i, ary);
1666 OBJ_INFECT(ary, hash);
1667
1668 return ary;
1669 }
1670
1671 static int
1672 inspect_i(VALUE key, VALUE value, VALUE str)
1673 {
1674 VALUE str2;
1675
1676 str2 = rb_inspect(key);
1677 if (RSTRING_LEN(str) > 1) {
1678 rb_str_buf_cat_ascii(str, ", ");
1679 }
1680 else {
1681 rb_enc_copy(str, str2);
1682 }
1683 rb_str_buf_append(str, str2);
1684 OBJ_INFECT(str, str2);
1685 rb_str_buf_cat_ascii(str, "=>");
1686 str2 = rb_inspect(value);
1687 rb_str_buf_append(str, str2);
1688 OBJ_INFECT(str, str2);
1689
1690 return ST_CONTINUE;
1691 }
1692
1693 static VALUE
1694 inspect_hash(VALUE hash, VALUE dummy, int recur)
1695 {
1696 VALUE str;
1697
1698 if (recur) return rb_usascii_str_new2("{...}");
1699 str = rb_str_buf_new2("{");
1700 rb_hash_foreach(hash, inspect_i, str);
1701 rb_str_buf_cat2(str, "}");
1702 OBJ_INFECT(str, hash);
1703
1704 return str;
1705 }
1706
1707 /*
1708 * call-seq:
1709 * hsh.to_s -> string
1710 * hsh.inspect -> string
1711 *
1712 * Return the contents of this hash as a string.
1713 *
1714 * h = { "c" => 300, "a" => 100, "d" => 400, "c" => 300 }
1715 * h.to_s #=> "{\"c\"=>300, \"a\"=>100, \"d\"=>400}"
1716 */
1717
1718 static VALUE
1719 rb_hash_inspect(VALUE hash)
1720 {
1721 if (RHASH_EMPTY_P(hash))
1722 return rb_usascii_str_new2("{}");
1723 return rb_exec_recursive(inspect_hash, hash, 0);
1724 }
1725
1726 /*
1727 * call-seq:
1728 * hsh.to_hash => hsh
1729 *
1730 * Returns +self+.
1731 */
1732
1733 static VALUE
1734 rb_hash_to_hash(VALUE hash)
1735 {
1736 return hash;
1737 }
1738
1739 /*
1740 * call-seq:
1741 * hsh.to_h -> hsh or new_hash
1742 *
1743 * Returns +self+. If called on a subclass of Hash, converts
1744 * the receiver to a Hash object.
1745 */
1746
1747 static VALUE
1748 rb_hash_to_h(VALUE hash)
1749 {
1750 if (rb_obj_class(hash) != rb_cHash) {
1751 VALUE ret = rb_hash_new();
1752 if (!RHASH_EMPTY_P(hash))
1753 RHASH(ret)->ntbl = st_copy(RHASH(hash)->ntbl);
1754 if (FL_TEST(hash, HASH_PROC_DEFAULT)) {
1755 FL_SET(ret, HASH_PROC_DEFAULT);
1756 }
1757 RHASH_SET_IFNONE(ret, RHASH_IFNONE(hash));
1758 return ret;
1759 }
1760 return hash;
1761 }
1762
1763 static int
1764 keys_i(VALUE key, VALUE value, VALUE ary)
1765 {
1766 rb_ary_push(ary, key);
1767 return ST_CONTINUE;
1768 }
1769
1770 /*
1771 * call-seq:
1772 * hsh.keys -> array
1773 *
1774 * Returns a new array populated with the keys from this hash. See also
1775 * <code>Hash#values</code>.
1776 *
1777 * h = { "a" => 100, "b" => 200, "c" => 300, "d" => 400 }
1778 * h.keys #=> ["a", "b", "c", "d"]
1779 *
1780 */
1781
1782 VALUE
1783 rb_hash_keys(VALUE hash)
1784 {
1785 VALUE keys;
1786 st_index_t size = RHASH_SIZE(hash);
1787
1788 keys = rb_ary_new_capa(size);
1789 if (size == 0) return keys;
1790
1791 if (ST_DATA_COMPATIBLE_P(VALUE)) {
1792 st_table *table = RHASH(hash)->ntbl;
1793
1794 if (OBJ_PROMOTED(keys)) rb_gc_writebarrier_remember_promoted(keys);
1795 RARRAY_PTR_USE(keys, ptr, {
1796 size = st_keys_check(table, ptr, size, Qundef);
1797 });
1798 rb_ary_set_len(keys, size);
1799 }
1800 else {
1801 rb_hash_foreach(hash, keys_i, keys);
1802 }
1803
1804 return keys;
1805 }
1806
1807 static int
1808 values_i(VALUE key, VALUE value, VALUE ary)
1809 {
1810 rb_ary_push(ary, value);
1811 return ST_CONTINUE;
1812 }
1813
1814 /*
1815 * call-seq:
1816 * hsh.values -> array
1817 *
1818 * Returns a new array populated with the values from <i>hsh</i>. See
1819 * also <code>Hash#keys</code>.
1820 *
1821 * h = { "a" => 100, "b" => 200, "c" => 300 }
1822 * h.values #=> [100, 200, 300]
1823 *
1824 */
1825
1826 VALUE
1827 rb_hash_values(VALUE hash)
1828 {
1829 VALUE values;
1830 st_index_t size = RHASH_SIZE(hash);
1831
1832 values = rb_ary_new_capa(size);
1833 if (size == 0) return values;
1834
1835 if (ST_DATA_COMPATIBLE_P(VALUE)) {
1836 st_table *table = RHASH(hash)->ntbl;
1837
1838 if (OBJ_PROMOTED(values)) rb_gc_writebarrier_remember_promoted(values);
1839 RARRAY_PTR_USE(values, ptr, {
1840 size = st_values_check(table, ptr, size, Qundef);
1841 });
1842 rb_ary_set_len(values, size);
1843 }
1844 else {
1845 rb_hash_foreach(hash, values_i, values);
1846 }
1847
1848 return values;
1849 }
1850
1851 /*
1852 * call-seq:
1853 * hsh.has_key?(key) -> true or false
1854 * hsh.include?(key) -> true or false
1855 * hsh.key?(key) -> true or false
1856 * hsh.member?(key) -> true or false
1857 *
1858 * Returns <code>true</code> if the given key is present in <i>hsh</i>.
1859 *
1860 * h = { "a" => 100, "b" => 200 }
1861 * h.has_key?("a") #=> true
1862 * h.has_key?("z") #=> false
1863 *
1864 */
1865
1866 static VALUE
1867 rb_hash_has_key(VALUE hash, VALUE key)
1868 {
1869 if (!RHASH(hash)->ntbl)
1870 return Qfalse;
1871 if (st_lookup(RHASH(hash)->ntbl, key, 0)) {
1872 return Qtrue;
1873 }
1874 return Qfalse;
1875 }
1876
1877 static int
1878 rb_hash_search_value(VALUE key, VALUE value, VALUE arg)
1879 {
1880 VALUE *data = (VALUE *)arg;
1881
1882 if (rb_equal(value, data[1])) {
1883 data[0] = Qtrue;
1884 return ST_STOP;
1885 }
1886 return ST_CONTINUE;
1887 }
1888
1889 /*
1890 * call-seq:
1891 * hsh.has_value?(value) -> true or false
1892 * hsh.value?(value) -> true or false
1893 *
1894 * Returns <code>true</code> if the given value is present for some key
1895 * in <i>hsh</i>.
1896 *
1897 * h = { "a" => 100, "b" => 200 }
1898 * h.has_value?(100) #=> true
1899 * h.has_value?(999) #=> false
1900 */
1901
1902 static VALUE
1903 rb_hash_has_value(VALUE hash, VALUE val)
1904 {
1905 VALUE data[2];
1906
1907 data[0] = Qfalse;
1908 data[1] = val;
1909 rb_hash_foreach(hash, rb_hash_search_value, (VALUE)data);
1910 return data[0];
1911 }
1912
1913 struct equal_data {
1914 VALUE result;
1915 st_table *tbl;
1916 int eql;
1917 };
1918
1919 static int
1920 eql_i(VALUE key, VALUE val1, VALUE arg)
1921 {
1922 struct equal_data *data = (struct equal_data *)arg;
1923 st_data_t val2;
1924
1925 if (!st_lookup(data->tbl, key, &val2)) {
1926 data->result = Qfalse;
1927 return ST_STOP;
1928 }
1929 if (!(data->eql ? rb_eql(val1, (VALUE)val2) : (int)rb_equal(val1, (VALUE)val2))) {
1930 data->result = Qfalse;
1931 return ST_STOP;
1932 }
1933 return ST_CONTINUE;
1934 }
1935
1936 static VALUE
1937 recursive_eql(VALUE hash, VALUE dt, int recur)
1938 {
1939 struct equal_data *data;
1940
1941 if (recur) return Qtrue; /* Subtle! */
1942 data = (struct equal_data*)dt;
1943 data->result = Qtrue;
1944 rb_hash_foreach(hash, eql_i, dt);
1945
1946 return data->result;
1947 }
1948
1949 static VALUE
1950 hash_equal(VALUE hash1, VALUE hash2, int eql)
1951 {
1952 struct equal_data data;
1953
1954 if (hash1 == hash2) return Qtrue;
1955 if (!RB_TYPE_P(hash2, T_HASH)) {
1956 if (!rb_respond_to(hash2, rb_intern("to_hash"))) {
1957 return Qfalse;
1958 }
1959 if (eql)
1960 return rb_eql(hash2, hash1);
1961 else
1962 return rb_equal(hash2, hash1);
1963 }
1964 if (RHASH_SIZE(hash1) != RHASH_SIZE(hash2))
1965 return Qfalse;
1966 if (!RHASH(hash1)->ntbl || !RHASH(hash2)->ntbl)
1967 return Qtrue;
1968 if (RHASH(hash1)->ntbl->type != RHASH(hash2)->ntbl->type)
1969 return Qfalse;
1970 #if 0
1971 if (!(rb_equal(RHASH_IFNONE(hash1), RHASH_IFNONE(hash2)) &&
1972 FL_TEST(hash1, HASH_PROC_DEFAULT) == FL_TEST(hash2, HASH_PROC_DEFAULT)))
1973 return Qfalse;
1974 #endif
1975
1976 data.tbl = RHASH(hash2)->ntbl;
1977 data.eql = eql;
1978 return rb_exec_recursive_paired(recursive_eql, hash1, hash2, (VALUE)&data);
1979 }
1980
1981 /*
1982 * call-seq:
1983 * hsh == other_hash -> true or false
1984 *
1985 * Equality---Two hashes are equal if they each contain the same number
1986 * of keys and if each key-value pair is equal to (according to
1987 * <code>Object#==</code>) the corresponding elements in the other
1988 * hash.
1989 *
1990 * h1 = { "a" => 1, "c" => 2 }
1991 * h2 = { 7 => 35, "c" => 2, "a" => 1 }
1992 * h3 = { "a" => 1, "c" => 2, 7 => 35 }
1993 * h4 = { "a" => 1, "d" => 2, "f" => 35 }
1994 * h1 == h2 #=> false
1995 * h2 == h3 #=> true
1996 * h3 == h4 #=> false
1997 *
1998 */
1999
2000 static VALUE
2001 rb_hash_equal(VALUE hash1, VALUE hash2)
2002 {
2003 return hash_equal(hash1, hash2, FALSE);
2004 }
2005
2006 /*
2007 * call-seq:
2008 * hash.eql?(other) -> true or false
2009 *
2010 * Returns <code>true</code> if <i>hash</i> and <i>other</i> are
2011 * both hashes with the same content.
2012 */
2013
2014 static VALUE
2015 rb_hash_eql(VALUE hash1, VALUE hash2)
2016 {
2017 return hash_equal(hash1, hash2, TRUE);
2018 }
2019
2020 static int
2021 hash_i(VALUE key, VALUE val, VALUE arg)
2022 {
2023 st_index_t *hval = (st_index_t *)arg;
2024 st_index_t hdata[2];
2025
2026 hdata[0] = rb_hash(key);
2027 hdata[1] = rb_hash(val);
2028 *hval ^= st_hash(hdata, sizeof(hdata), 0);
2029 return ST_CONTINUE;
2030 }
2031
2032 /*
2033 * call-seq:
2034 * hsh.hash -> fixnum
2035 *
2036 * Compute a hash-code for this hash. Two hashes with the same content
2037 * will have the same hash code (and will compare using <code>eql?</code>).
2038 */
2039
2040 static VALUE
2041 rb_hash_hash(VALUE hash)
2042 {
2043 st_index_t size = RHASH_SIZE(hash);
2044 st_index_t hval = rb_hash_start(size);
2045 hval = rb_hash_uint(hval, (st_index_t)rb_hash_hash);
2046 if (size) {
2047 rb_hash_foreach(hash, hash_i, (VALUE)&hval);
2048 }
2049 hval = rb_hash_end(hval);
2050 return INT2FIX(hval);
2051 }
2052
2053 static int
2054 rb_hash_invert_i(VALUE key, VALUE value, VALUE hash)
2055 {
2056 rb_hash_aset(hash, value, key);
2057 return ST_CONTINUE;
2058 }
2059
2060 /*
2061 * call-seq:
2062 * hsh.invert -> new_hash
2063 *
2064 * Returns a new hash created by using <i>hsh</i>'s values as keys, and
2065 * the keys as values.
2066 *
2067 * h = { "n" => 100, "m" => 100, "y" => 300, "d" => 200, "a" => 0 }
2068 * h.invert #=> {0=>"a", 100=>"m", 200=>"d", 300=>"y"}
2069 *
2070 */
2071
2072 static VALUE
2073 rb_hash_invert(VALUE hash)
2074 {
2075 VALUE h = rb_hash_new();
2076
2077 rb_hash_foreach(hash, rb_hash_invert_i, h);
2078 return h;
2079 }
2080
2081 static int
2082 rb_hash_update_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
2083 {
2084 if (existing) {
2085 arg->old_value = *value;
2086 arg->new_value = arg->arg;
2087 }
2088 else {
2089 arg->new_key = *key;
2090 arg->new_value = arg->arg;
2091 }
2092 *value = arg->arg;
2093 return ST_CONTINUE;
2094 }
2095
2096 NOINSERT_UPDATE_CALLBACK(rb_hash_update_callback);
2097
2098 static int
2099 rb_hash_update_i(VALUE key, VALUE value, VALUE hash)
2100 {
2101 RHASH_UPDATE(hash, key, rb_hash_update_callback, value);
2102 return ST_CONTINUE;
2103 }
2104
2105 static int
2106 rb_hash_update_block_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
2107 {
2108 VALUE newvalue = (VALUE)arg->arg;
2109
2110 if (existing) {
2111 newvalue = rb_yield_values(3, (VALUE)*key, (VALUE)*value, newvalue);
2112 arg->old_value = *value;
2113 arg->new_value = newvalue;
2114 }
2115 else {
2116 arg->new_key = *key;
2117 arg->new_value = newvalue;
2118 }
2119 *value = newvalue;
2120 return ST_CONTINUE;
2121 }
2122
2123 NOINSERT_UPDATE_CALLBACK(rb_hash_update_block_callback);
2124
2125 static int
2126 rb_hash_update_block_i(VALUE key, VALUE value, VALUE hash)
2127 {
2128 RHASH_UPDATE(hash, key, rb_hash_update_block_callback, value);
2129 return ST_CONTINUE;
2130 }
2131
2132 /*
2133 * call-seq:
2134 * hsh.merge!(other_hash) -> hsh
2135 * hsh.update(other_hash) -> hsh
2136 * hsh.merge!(other_hash){|key, oldval, newval| block} -> hsh
2137 * hsh.update(other_hash){|key, oldval, newval| block} -> hsh
2138 *
2139 * Adds the contents of _other_hash_ to _hsh_. If no block is specified,
2140 * entries with duplicate keys are overwritten with the values from
2141 * _other_hash_, otherwise the value of each duplicate key is determined by
2142 * calling the block with the key, its value in _hsh_ and its value in
2143 * _other_hash_.
2144 *
2145 * h1 = { "a" => 100, "b" => 200 }
2146 * h2 = { "b" => 254, "c" => 300 }
2147 * h1.merge!(h2) #=> {"a"=>100, "b"=>254, "c"=>300}
2148 *
2149 * h1 = { "a" => 100, "b" => 200 }
2150 * h2 = { "b" => 254, "c" => 300 }
2151 * h1.merge!(h2) { |key, v1, v2| v1 }
2152 * #=> {"a"=>100, "b"=>200, "c"=>300}
2153 */
2154
2155 static VALUE
2156 rb_hash_update(VALUE hash1, VALUE hash2)
2157 {
2158 rb_hash_modify(hash1);
2159 hash2 = to_hash(hash2);
2160 if (rb_block_given_p()) {
2161 rb_hash_foreach(hash2, rb_hash_update_block_i, hash1);
2162 }
2163 else {
2164 rb_hash_foreach(hash2, rb_hash_update_i, hash1);
2165 }
2166 return hash1;
2167 }
2168
2169 struct update_func_arg {
2170 VALUE hash;
2171 VALUE value;
2172 rb_hash_update_func *func;
2173 };
2174
2175 static int
2176 rb_hash_update_func_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
2177 {
2178 struct update_func_arg *uf_arg = (struct update_func_arg *)arg->arg;
2179 VALUE newvalue = uf_arg->value;
2180
2181 if (existing) {
2182 newvalue = (*uf_arg->func)((VALUE)*key, (VALUE)*value, newvalue);
2183 arg->old_value = *value;
2184 arg->new_value = newvalue;
2185 }
2186 else {
2187 arg->new_key = *key;
2188 arg->new_value = newvalue;
2189 }
2190 *value = newvalue;
2191 return ST_CONTINUE;
2192 }
2193
2194 NOINSERT_UPDATE_CALLBACK(rb_hash_update_func_callback);
2195
2196 static int
2197 rb_hash_update_func_i(VALUE key, VALUE value, VALUE arg0)
2198 {
2199 struct update_func_arg *arg = (struct update_func_arg *)arg0;
2200 VALUE hash = arg->hash;
2201
2202 arg->value = value;
2203 RHASH_UPDATE(hash, key, rb_hash_update_func_callback, (VALUE)arg);
2204 return ST_CONTINUE;
2205 }
2206
2207 VALUE
2208 rb_hash_update_by(VALUE hash1, VALUE hash2, rb_hash_update_func *func)
2209 {
2210 rb_hash_modify(hash1);
2211 hash2 = to_hash(hash2);
2212 if (func) {
2213 struct update_func_arg arg;
2214 arg.hash = hash1;
2215 arg.func = func;
2216 rb_hash_foreach(hash2, rb_hash_update_func_i, (VALUE)&arg);
2217 }
2218 else {
2219 rb_hash_foreach(hash2, rb_hash_update_i, hash1);
2220 }
2221 return hash1;
2222 }
2223
2224 /*
2225 * call-seq:
2226 * hsh.merge(other_hash) -> new_hash
2227 * hsh.merge(other_hash){|key, oldval, newval| block} -> new_hash
2228 *
2229 * Returns a new hash containing the contents of <i>other_hash</i> and
2230 * the contents of <i>hsh</i>. If no block is specified, the value for
2231 * entries with duplicate keys will be that of <i>other_hash</i>. Otherwise
2232 * the value for each duplicate key is determined by calling the block
2233 * with the key, its value in <i>hsh</i> and its value in <i>other_hash</i>.
2234 *
2235 * h1 = { "a" => 100, "b" => 200 }
2236 * h2 = { "b" => 254, "c" => 300 }
2237 * h1.merge(h2) #=> {"a"=>100, "b"=>254, "c"=>300}
2238 * h1.merge(h2){|key, oldval, newval| newval - oldval}
2239 * #=> {"a"=>100, "b"=>54, "c"=>300}
2240 * h1 #=> {"a"=>100, "b"=>200}
2241 *
2242 */
2243
2244 static VALUE
2245 rb_hash_merge(VALUE hash1, VALUE hash2)
2246 {
2247 return rb_hash_update(rb_obj_dup(hash1), hash2);
2248 }
2249
2250 static int
2251 assoc_cmp(VALUE a, VALUE b)
2252 {
2253 return !RTEST(rb_equal(a, b));
2254 }
2255
2256 static VALUE
2257 lookup2_call(VALUE arg)
2258 {
2259 VALUE *args = (VALUE *)arg;
2260 return rb_hash_lookup2(args[0], args[1], Qundef);
2261 }
2262
2263 struct reset_hash_type_arg {
2264 VALUE hash;
2265 const struct st_hash_type *orighash;
2266 };
2267
2268 static VALUE
2269 reset_hash_type(VALUE arg)
2270 {
2271 struct reset_hash_type_arg *p = (struct reset_hash_type_arg *)arg;
2272 RHASH(p->hash)->ntbl->type = p->orighash;
2273 return Qundef;
2274 }
2275
2276 static int
2277 assoc_i(VALUE key, VALUE val, VALUE arg)
2278 {
2279 VALUE *args = (VALUE *)arg;
2280
2281 if (RTEST(rb_equal(args[0], key))) {
2282 args[1] = rb_assoc_new(key, val);
2283 return ST_STOP;
2284 }
2285 return ST_CONTINUE;
2286 }
2287
2288 /*
2289 * call-seq:
2290 * hash.assoc(obj) -> an_array or nil
2291 *
2292 * Searches through the hash comparing _obj_ with the key using <code>==</code>.
2293 * Returns the key-value pair (two elements array) or +nil+
2294 * if no match is found. See <code>Array#assoc</code>.
2295 *
2296 * h = {"colors" => ["red", "blue", "green"],
2297 * "letters" => ["a", "b", "c" ]}
2298 * h.assoc("letters") #=> ["letters", ["a", "b", "c"]]
2299 * h.assoc("foo") #=> nil
2300 */
2301
2302 VALUE
2303 rb_hash_assoc(VALUE hash, VALUE key)
2304 {
2305 st_table *table;
2306 const struct st_hash_type *orighash;
2307 VALUE args[2];
2308
2309 if (RHASH_EMPTY_P(hash)) return Qnil;
2310 table = RHASH(hash)->ntbl;
2311 orighash = table->type;
2312
2313 if (orighash != &identhash) {
2314 VALUE value;
2315 struct reset_hash_type_arg ensure_arg;
2316 struct st_hash_type assochash;
2317
2318 assochash.compare = assoc_cmp;
2319 assochash.hash = orighash->hash;
2320 table->type = &assochash;
2321 args[0] = hash;
2322 args[1] = key;
2323 ensure_arg.hash = hash;
2324 ensure_arg.orighash = orighash;
2325 value = rb_ensure(lookup2_call, (VALUE)&args, reset_hash_type, (VALUE)&ensure_arg);
2326 if (value != Qundef) return rb_assoc_new(key, value);
2327 }
2328
2329 args[0] = key;
2330 args[1] = Qnil;
2331 rb_hash_foreach(hash, assoc_i, (VALUE)args);
2332 return args[1];
2333 }
2334
2335 static int
2336 rassoc_i(VALUE key, VALUE val, VALUE arg)
2337 {
2338 VALUE *args = (VALUE *)arg;
2339
2340 if (RTEST(rb_equal(args[0], val))) {
2341 args[1] = rb_assoc_new(key, val);
2342 return ST_STOP;
2343 }
2344 return ST_CONTINUE;
2345 }
2346
2347 /*
2348 * call-seq:
2349 * hash.rassoc(obj) -> an_array or nil
2350 *
2351 * Searches through the hash comparing _obj_ with the value using <code>==</code>.
2352 * Returns the first key-value pair (two-element array) that matches. See
2353 * also <code>Array#rassoc</code>.
2354 *
2355 * a = {1=> "one", 2 => "two", 3 => "three", "ii" => "two"}
2356 * a.rassoc("two") #=> [2, "two"]
2357 * a.rassoc("four") #=> nil
2358 */
2359
2360 VALUE
2361 rb_hash_rassoc(VALUE hash, VALUE obj)
2362 {
2363 VALUE args[2];
2364
2365 args[0] = obj;
2366 args[1] = Qnil;
2367 rb_hash_foreach(hash, rassoc_i, (VALUE)args);
2368 return args[1];
2369 }
2370
2371 static int
2372 flatten_i(VALUE key, VALUE val, VALUE ary)
2373 {
2374 VALUE pair[2];
2375
2376 pair[0] = key;
2377 pair[1] = val;
2378 rb_ary_cat(ary, pair, 2);
2379
2380 return ST_CONTINUE;
2381 }
2382
2383 /*
2384 * call-seq:
2385 * hash.flatten -> an_array
2386 * hash.flatten(level) -> an_array
2387 *
2388 * Returns a new array that is a one-dimensional flattening of this
2389 * hash. That is, for every key or value that is an array, extract
2390 * its elements into the new array. Unlike Array#flatten, this
2391 * method does not flatten recursively by default. The optional
2392 * <i>level</i> argument determines the level of recursion to flatten.
2393 *
2394 * a = {1=> "one", 2 => [2,"two"], 3 => "three"}
2395 * a.flatten # => [1, "one", 2, [2, "two"], 3, "three"]
2396 * a.flatten(2) # => [1, "one", 2, 2, "two", 3, "three"]
2397 */
2398
2399 static VALUE
2400 rb_hash_flatten(int argc, VALUE *argv, VALUE hash)
2401 {
2402 VALUE ary;
2403
2404 if (argc) {
2405 int level = NUM2INT(*argv);
2406 if (level == 0) return rb_hash_to_a(hash);
2407
2408 ary = rb_ary_new_capa(RHASH_SIZE(hash) * 2);
2409 rb_hash_foreach(hash, flatten_i, ary);
2410 if (level - 1 > 0) {
2411 *argv = INT2FIX(level - 1);
2412 rb_funcall2(ary, id_flatten_bang, argc, argv);
2413 }
2414 else if (level < 0) {
2415 rb_funcall2(ary, id_flatten_bang, 0, 0);
2416 }
2417 }
2418 else {
2419 ary = rb_ary_new_capa(RHASH_SIZE(hash) * 2);
2420 rb_hash_foreach(hash, flatten_i, ary);
2421 }
2422
2423 return ary;
2424 }
2425
2426 static VALUE rb_hash_compare_by_id_p(VALUE hash);
2427
2428 /*
2429 * call-seq:
2430 * hsh.compare_by_identity -> hsh
2431 *
2432 * Makes <i>hsh</i> compare its keys by their identity, i.e. it
2433 * will consider exact same objects as same keys.
2434 *
2435 * h1 = { "a" => 100, "b" => 200, :c => "c" }
2436 * h1["a"] #=> 100
2437 * h1.compare_by_identity
2438 * h1.compare_by_identity? #=> true
2439 * h1["a"] #=> nil # different objects.
2440 * h1[:c] #=> "c" # same symbols are all same.
2441 *
2442 */
2443
2444 static VALUE
2445 rb_hash_compare_by_id(VALUE hash)
2446 {
2447 if (rb_hash_compare_by_id_p(hash)) return hash;
2448 rb_hash_modify(hash);
2449 RHASH(hash)->ntbl->type = &identhash;
2450 rb_hash_rehash(hash);
2451 return hash;
2452 }
2453
2454 /*
2455 * call-seq:
2456 * hsh.compare_by_identity? -> true or false
2457 *
2458 * Returns <code>true</code> if <i>hsh</i> will compare its keys by
2459 * their identity. Also see <code>Hash#compare_by_identity</code>.
2460 *
2461 */
2462
2463 static VALUE
2464 rb_hash_compare_by_id_p(VALUE hash)
2465 {
2466 if (!RHASH(hash)->ntbl)
2467 return Qfalse;
2468 if (RHASH(hash)->ntbl->type == &identhash) {
2469 return Qtrue;
2470 }
2471 return Qfalse;
2472 }
2473
2474 static int path_tainted = -1;
2475
2476 static char **origenviron;
2477 #ifdef _WIN32
2478 #define GET_ENVIRON(e) ((e) = rb_w32_get_environ())
2479 #define FREE_ENVIRON(e) rb_w32_free_environ(e)
2480 static char **my_environ;
2481 #undef environ
2482 #define environ my_environ
2483 #undef getenv
2484 static inline char *
2485 w32_getenv(const char *name)
2486 {
2487 static int binary = -1;
2488 static int locale = -1;
2489 if (binary < 0) {
2490 binary = rb_ascii8bit_encindex();
2491 locale = rb_locale_encindex();
2492 }
2493 return locale == binary ? rb_w32_getenv(name) : rb_w32_ugetenv(name);
2494 }
2495 #define getenv(n) w32_getenv(n)
2496 #elif defined(__APPLE__)
2497 #undef environ
2498 #define environ (*_NSGetEnviron())
2499 #define GET_ENVIRON(e) (e)
2500 #define FREE_ENVIRON(e)
2501 #else
2502 extern char **environ;
2503 #define GET_ENVIRON(e) (e)
2504 #define FREE_ENVIRON(e)
2505 #endif
2506 #ifdef ENV_IGNORECASE
2507 #define ENVMATCH(s1, s2) (STRCASECMP((s1), (s2)) == 0)
2508 #define ENVNMATCH(s1, s2, n) (STRNCASECMP((s1), (s2), (n)) == 0)
2509 #else
2510 #define ENVMATCH(n1, n2) (strcmp((n1), (n2)) == 0)
2511 #define ENVNMATCH(s1, s2, n) (memcmp((s1), (s2), (n)) == 0)
2512 #endif
2513
2514 static VALUE
2515 env_str_new(const char *ptr, long len)
2516 {
2517 #ifdef _WIN32
2518 VALUE str = rb_str_conv_enc(rb_str_new(ptr, len), rb_utf8_encoding(), rb_locale_encoding());
2519 #else
2520 VALUE str = rb_locale_str_new(ptr, len);
2521 #endif
2522
2523 rb_obj_freeze(str);
2524 return str;
2525 }
2526
2527 static VALUE
2528 env_str_new2(const char *ptr)
2529 {
2530 if (!ptr) return Qnil;
2531 return env_str_new(ptr, strlen(ptr));
2532 }
2533
2534 static VALUE
2535 env_delete(VALUE obj, VALUE name)
2536 {
2537 char *nam, *val;
2538
2539 SafeStringValue(name);
2540 nam = RSTRING_PTR(name);
2541 if (memchr(nam, '\0', RSTRING_LEN(name))) {
2542 rb_raise(rb_eArgError, "bad environment variable name");
2543 }
2544 val = getenv(nam);
2545 if (val) {
2546 VALUE value = env_str_new2(val);
2547
2548 ruby_setenv(nam, 0);
2549 if (ENVMATCH(nam, PATH_ENV)) {
2550 path_tainted = 0;
2551 }
2552 return value;
2553 }
2554 return Qnil;
2555 }
2556
2557 /*
2558 * call-seq:
2559 * ENV.delete(name) -> value
2560 * ENV.delete(name) { |name| } -> value
2561 *
2562 * Deletes the environment variable with +name+ and returns the value of the
2563 * variable. If a block is given it will be called when the named environment
2564 * does not exist.
2565 */
2566 static VALUE
2567 env_delete_m(VALUE obj, VALUE name)
2568 {
2569 VALUE val;
2570
2571 val = env_delete(obj, name);
2572 if (NIL_P(val) && rb_block_given_p()) rb_yield(name);
2573 return val;
2574 }
2575
2576 static int env_path_tainted(const char *);
2577
2578 /*
2579 * call-seq:
2580 * ENV[name] -> value
2581 *
2582 * Retrieves the +value+ for environment variable +name+ as a String. Returns
2583 * +nil+ if the named variable does not exist.
2584 */
2585 static VALUE
2586 rb_f_getenv(VALUE obj, VALUE name)
2587 {
2588 char *nam, *env;
2589
2590 SafeStringValue(name);
2591 nam = RSTRING_PTR(name);
2592 if (memchr(nam, '\0', RSTRING_LEN(name))) {
2593 rb_raise(rb_eArgError, "bad environment variable name");
2594 }
2595 env = getenv(nam);
2596 if (env) {
2597 if (ENVMATCH(nam, PATH_ENV) && !env_path_tainted(env)) {
2598 #ifdef _WIN32
2599 VALUE str = rb_str_conv_enc(rb_str_new(env, strlen(env)), rb_utf8_encoding(), rb_filesystem_encoding());
2600 #else
2601 VALUE str = rb_filesystem_str_new_cstr(env);
2602 #endif
2603
2604 rb_obj_freeze(str);
2605 return str;
2606 }
2607 return env_str_new2(env);
2608 }
2609 return Qnil;
2610 }
2611
2612 /*
2613 * :yield: missing_name
2614 * call-seq:
2615 * ENV.fetch(name) -> value
2616 * ENV.fetch(name, default) -> value
2617 * ENV.fetch(name) { |missing_name| ... } -> value
2618 *
2619 * Retrieves the environment variable +name+.
2620 *
2621 * If the given name does not exist and neither +default+ nor a block a
2622 * provided an IndexError is raised. If a block is given it is called with
2623 * the missing name to provide a value. If a default value is given it will
2624 * be returned when no block is given.
2625 */
2626 static VALUE
2627 env_fetch(int argc, VALUE *argv)
2628 {
2629 VALUE key, if_none;
2630 long block_given;
2631 char *nam, *env;
2632
2633 rb_scan_args(argc, argv, "11", &key, &if_none);
2634 block_given = rb_block_given_p();
2635 if (block_given && argc == 2) {
2636 rb_warn("block supersedes default value argument");
2637 }
2638 SafeStringValue(key);
2639 nam = RSTRING_PTR(key);
2640 if (memchr(nam, '\0', RSTRING_LEN(key))) {
2641 rb_raise(rb_eArgError, "bad environment variable name");
2642 }
2643 env = getenv(nam);
2644 if (!env) {
2645 if (block_given) return rb_yield(key);
2646 if (argc == 1) {
2647 rb_raise(rb_eKeyError, "key not found: \"%"PRIsVALUE"\"", key);
2648 }
2649 return if_none;
2650 }
2651 if (ENVMATCH(nam, PATH_ENV) && !env_path_tainted(env))
2652 #ifdef _WIN32
2653 return rb_str_conv_enc(rb_str_new(env, strlen(env)), rb_utf8_encoding(), rb_filesystem_encoding());
2654 #else
2655 return rb_filesystem_str_new_cstr(env);
2656 #endif
2657 return env_str_new2(env);
2658 }
2659
2660 static void
2661 path_tainted_p(const char *path)
2662 {
2663 path_tainted = rb_path_check(path)?0:1;
2664 }
2665
2666 static int
2667 env_path_tainted(const char *path)
2668 {
2669 if (path_tainted < 0) {
2670 path_tainted_p(path);
2671 }
2672 return path_tainted;
2673 }
2674
2675 int
2676 rb_env_path_tainted(void)
2677 {
2678 if (path_tainted < 0) {
2679 path_tainted_p(getenv(PATH_ENV));
2680 }
2681 return path_tainted;
2682 }
2683
2684 #if defined(_WIN32) || (defined(HAVE_SETENV) && defined(HAVE_UNSETENV))
2685 #elif defined __sun
2686 static int
2687 in_origenv(const char *str)
2688 {
2689 char **env;
2690 for (env = origenviron; *env; ++env) {
2691 if (*env == str) return 1;
2692 }
2693 return 0;
2694 }
2695 #else
2696 static int
2697 envix(const char *nam)
2698 {
2699 register int i, len = strlen(nam);
2700 char **env;
2701
2702 env = GET_ENVIRON(environ);
2703 for (i = 0; env[i]; i++) {
2704 if (ENVNMATCH(env[i],nam,len) && env[i][len] == '=')
2705 break; /* memcmp must come first to avoid */
2706 } /* potential SEGV's */
2707 FREE_ENVIRON(environ);
2708 return i;
2709 }
2710 #endif
2711
2712 #if defined(_WIN32)
2713 static size_t
2714 getenvsize(const char* p)
2715 {
2716 const char* porg = p;
2717 while (*p++) p += strlen(p) + 1;
2718 return p - porg + 1;
2719 }
2720 static size_t
2721 getenvblocksize()
2722 {
2723 return (rb_w32_osver() >= 5) ? 32767 : 5120;
2724 }
2725 #endif
2726
2727 #if !defined(HAVE_SETENV) || !defined(HAVE_UNSETENV)
2728 NORETURN(static void invalid_envname(const char *name));
2729
2730 static void
2731 invalid_envname(const char *name)
2732 {
2733 rb_syserr_fail_str(EINVAL, rb_sprintf("ruby_setenv(%s)", name));
2734 }
2735
2736 static const char *
2737 check_envname(const char *name)
2738 {
2739 if (strchr(name, '=')) {
2740 invalid_envname(name);
2741 }
2742 return name;
2743 }
2744 #endif
2745
2746 void
2747 ruby_setenv(const char *name, const char *value)
2748 {
2749 #if defined(_WIN32)
2750 VALUE buf;
2751 int failed = 0;
2752 check_envname(name);
2753 if (value) {
2754 char* p = GetEnvironmentStringsA();
2755 size_t n;
2756 if (!p) goto fail; /* never happen */
2757 n = strlen(name) + 2 + strlen(value) + getenvsize(p);
2758 FreeEnvironmentStringsA(p);
2759 if (n >= getenvblocksize()) {
2760 goto fail; /* 2 for '=' & '\0' */
2761 }
2762 buf = rb_sprintf("%s=%s", name, value);
2763 }
2764 else {
2765 buf = rb_sprintf("%s=", name);
2766 }
2767 failed = putenv(RSTRING_PTR(buf));
2768 /* even if putenv() failed, clean up and try to delete the
2769 * variable from the system area. */
2770 rb_str_resize(buf, 0);
2771 if (!value || !*value) {
2772 /* putenv() doesn't handle empty value */
2773 if (!SetEnvironmentVariable(name, value) &&
2774 GetLastError() != ERROR_ENVVAR_NOT_FOUND) goto fail;
2775 }
2776 if (failed) {
2777 fail:
2778 invalid_envname(name);
2779 }
2780 #elif defined(HAVE_SETENV) && defined(HAVE_UNSETENV)
2781 #undef setenv
2782 #undef unsetenv
2783 if (value) {
2784 if (setenv(name, value, 1))
2785 rb_sys_fail_str(rb_sprintf("setenv(%s)", name));
2786 }
2787 else {
2788 #ifdef VOID_UNSETENV
2789 unsetenv(name);
2790 #else
2791 if (unsetenv(name))
2792 rb_sys_fail_str(rb_sprintf("unsetenv(%s)", name));
2793 #endif
2794 }
2795 #elif defined __sun
2796 size_t len;
2797 char **env_ptr, *str;
2798
2799 len = strlen(name);
2800 for (env_ptr = GET_ENVIRON(environ); (str = *env_ptr) != 0; ++env_ptr) {
2801 if (!strncmp(str, name, len) && str[len] == '=') {
2802 if (!in_origenv(str)) free(str);
2803 while ((env_ptr[0] = env_ptr[1]) != 0) env_ptr++;
2804 break;
2805 }
2806 }
2807 if (value) {
2808 str = malloc(len += strlen(value) + 2);
2809 snprintf(str, len, "%s=%s", name, value);
2810 if (putenv(str))
2811 rb_sys_fail_str(rb_sprintf("putenv(%s)", name));
2812 }
2813 #else /* WIN32 */
2814 size_t len;
2815 int i;
2816
2817 i=envix(name); /* where does it go? */
2818
2819 if (environ == origenviron) { /* need we copy environment? */
2820 int j;
2821 int max;
2822 char **tmpenv;
2823
2824 for (max = i; environ[max]; max++) ;
2825 tmpenv = ALLOC_N(char*, max+2);
2826 for (j=0; j<max; j++) /* copy environment */
2827 tmpenv[j] = ruby_strdup(environ[j]);
2828 tmpenv[max] = 0;
2829 environ = tmpenv; /* tell exec where it is now */
2830 }
2831 if (environ[i]) {
2832 char **envp = origenviron;
2833 while (*envp && *envp != environ[i]) envp++;
2834 if (!*envp)
2835 xfree(environ[i]);
2836 if (!value) {
2837 while (environ[i]) {
2838 environ[i] = environ[i+1];
2839 i++;
2840 }
2841 return;
2842 }
2843 }
2844 else { /* does not exist yet */
2845 if (!value) return;
2846 REALLOC_N(environ, char*, i+2); /* just expand it a bit */
2847 environ[i+1] = 0; /* make sure it's null terminated */
2848 }
2849 len = strlen(name) + strlen(value) + 2;
2850 environ[i] = ALLOC_N(char, len);
2851 snprintf(environ[i],len,"%s=%s",name,value); /* all that work just for this */
2852 #endif /* WIN32 */
2853 }
2854
2855 void
2856 ruby_unsetenv(const char *name)
2857 {
2858 ruby_setenv(name, 0);
2859 }
2860
2861 /*
2862 * call-seq:
2863 * ENV[name] = value
2864 * ENV.store(name, value) -> value
2865 *
2866 * Sets the environment variable +name+ to +value+. If the value given is
2867 * +nil+ the environment variable is deleted.
2868 *
2869 */
2870 static VALUE
2871 env_aset(VALUE obj, VALUE nm, VALUE val)
2872 {
2873 char *name, *value;
2874
2875 if (NIL_P(val)) {
2876 env_delete(obj, nm);
2877 return Qnil;
2878 }
2879 SafeStringValue(nm);
2880 SafeStringValue(val);
2881 name = RSTRING_PTR(nm);
2882 value = RSTRING_PTR(val);
2883 if (memchr(name, '\0', RSTRING_LEN(nm)))
2884 rb_raise(rb_eArgError, "bad environment variable name");
2885 if (memchr(value, '\0', RSTRING_LEN(val)))
2886 rb_raise(rb_eArgError, "bad environment variable value");
2887
2888 ruby_setenv(name, value);
2889 if (ENVMATCH(name, PATH_ENV)) {
2890 if (OBJ_TAINTED(val)) {
2891 /* already tainted, no check */
2892 path_tainted = 1;
2893 return val;
2894 }
2895 else {
2896 path_tainted_p(value);
2897 }
2898 }
2899 return val;
2900 }
2901
2902 /*
2903 * call-seq:
2904 * ENV.keys -> Array
2905 *
2906 * Returns every environment variable name in an Array
2907 */
2908 static VALUE
2909 env_keys(void)
2910 {
2911 char **env;
2912 VALUE ary;
2913
2914 ary = rb_ary_new();
2915 env = GET_ENVIRON(environ);
2916 while (*env) {
2917 char *s = strchr(*env, '=');
2918 if (s) {
2919 rb_ary_push(ary, env_str_new(*env, s-*env));
2920 }
2921 env++;
2922 }
2923 FREE_ENVIRON(environ);
2924 return ary;
2925 }
2926
2927 static VALUE
2928 rb_env_size(VALUE ehash, VALUE args, VALUE eobj)
2929 {
2930 char **env;
2931 long cnt = 0;
2932
2933 env = GET_ENVIRON(environ);
2934 for (; *env ; ++env) {
2935 if (strchr(*env, '=')) {
2936 cnt++;
2937 }
2938 }
2939 FREE_ENVIRON(environ);
2940 return LONG2FIX(cnt);
2941 }
2942
2943 /*
2944 * call-seq:
2945 * ENV.each_key { |name| } -> Hash
2946 * ENV.each_key -> Enumerator
2947 *
2948 * Yields each environment variable name.
2949 *
2950 * An Enumerator is returned if no block is given.
2951 */
2952 static VALUE
2953 env_each_key(VALUE ehash)
2954 {
2955 VALUE keys;
2956 long i;
2957
2958 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
2959 keys = env_keys();
2960 for (i=0; i<RARRAY_LEN(keys); i++) {
2961 rb_yield(RARRAY_AREF(keys, i));
2962 }
2963 return ehash;
2964 }
2965
2966 /*
2967 * call-seq:
2968 * ENV.values -> Array
2969 *
2970 * Returns every environment variable value as an Array
2971 */
2972 static VALUE
2973 env_values(void)
2974 {
2975 VALUE ary;
2976 char **env;
2977
2978 ary = rb_ary_new();
2979 env = GET_ENVIRON(environ);
2980 while (*env) {
2981 char *s = strchr(*env, '=');
2982 if (s) {
2983 rb_ary_push(ary, env_str_new2(s+1));
2984 }
2985 env++;
2986 }
2987 FREE_ENVIRON(environ);
2988 return ary;
2989 }
2990
2991 /*
2992 * call-seq:
2993 * ENV.each_value { |value| } -> Hash
2994 * ENV.each_value -> Enumerator
2995 *
2996 * Yields each environment variable +value+.
2997 *
2998 * An Enumerator is returned if no block was given.
2999 */
3000 static VALUE
3001 env_each_value(VALUE ehash)
3002 {
3003 VALUE values;
3004 long i;
3005
3006 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3007 values = env_values();
3008 for (i=0; i<RARRAY_LEN(values); i++) {
3009 rb_yield(RARRAY_AREF(values, i));
3010 }
3011 return ehash;
3012 }
3013
3014 /*
3015 * call-seq:
3016 * ENV.each { |name, value| } -> Hash
3017 * ENV.each -> Enumerator
3018 * ENV.each_pair { |name, value| } -> Hash
3019 * ENV.each_pair -> Enumerator
3020 *
3021 * Yields each environment variable +name+ and +value+.
3022 *
3023 * If no block is given an Enumerator is returned.
3024 */
3025 static VALUE
3026 env_each_pair(VALUE ehash)
3027 {
3028 char **env;
3029 VALUE ary;
3030 long i;
3031
3032 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3033
3034 ary = rb_ary_new();
3035 env = GET_ENVIRON(environ);
3036 while (*env) {
3037 char *s = strchr(*env, '=');
3038 if (s) {
3039 rb_ary_push(ary, env_str_new(*env, s-*env));
3040 rb_ary_push(ary, env_str_new2(s+1));
3041 }
3042 env++;
3043 }
3044 FREE_ENVIRON(environ);
3045
3046 if (rb_block_arity() > 1) {
3047 for (i=0; i<RARRAY_LEN(ary); i+=2) {
3048 rb_yield_values(2, RARRAY_AREF(ary, i), RARRAY_AREF(ary, i+1));
3049 }
3050 }
3051 else {
3052 for (i=0; i<RARRAY_LEN(ary); i+=2) {
3053 rb_yield(rb_assoc_new(RARRAY_AREF(ary, i), RARRAY_AREF(ary, i+1)));
3054 }
3055 }
3056 return ehash;
3057 }
3058
3059 /*
3060 * call-seq:
3061 * ENV.reject! { |name, value| } -> ENV or nil
3062 * ENV.reject! -> Enumerator
3063 *
3064 * Equivalent to ENV#delete_if but returns +nil+ if no changes were made.
3065 *
3066 * Returns an Enumerator if no block was given.
3067 */
3068 static VALUE
3069 env_reject_bang(VALUE ehash)
3070 {
3071 volatile VALUE keys;
3072 long i;
3073 int del = 0;
3074
3075 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3076 keys = env_keys();
3077 RBASIC_CLEAR_CLASS(keys);
3078 for (i=0; i<RARRAY_LEN(keys); i++) {
3079 VALUE val = rb_f_getenv(Qnil, RARRAY_AREF(keys, i));
3080 if (!NIL_P(val)) {
3081 if (RTEST(rb_yield_values(2, RARRAY_AREF(keys, i), val))) {
3082 FL_UNSET(RARRAY_AREF(keys, i), FL_TAINT);
3083 env_delete(Qnil, RARRAY_AREF(keys, i));
3084 del++;
3085 }
3086 }
3087 }
3088 if (del == 0) return Qnil;
3089 return envtbl;
3090 }
3091
3092 /*
3093 * call-seq:
3094 * ENV.delete_if { |name, value| } -> Hash
3095 * ENV.delete_if -> Enumerator
3096 *
3097 * Deletes every environment variable for which the block evaluates to +true+.
3098 *
3099 * If no block is given an enumerator is returned instead.
3100 */
3101 static VALUE
3102 env_delete_if(VALUE ehash)
3103 {
3104 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3105 env_reject_bang(ehash);
3106 return envtbl;
3107 }
3108
3109 /*
3110 * call-seq:
3111 * ENV.values_at(name, ...) -> Array
3112 *
3113 * Returns an array containing the environment variable values associated with
3114 * the given names. See also ENV.select.
3115 */
3116 static VALUE
3117 env_values_at(int argc, VALUE *argv)
3118 {
3119 VALUE result;
3120 long i;
3121
3122 result = rb_ary_new();
3123 for (i=0; i<argc; i++) {
3124 rb_ary_push(result, rb_f_getenv(Qnil, argv[i]));
3125 }
3126 return result;
3127 }
3128
3129 /*
3130 * call-seq:
3131 * ENV.select { |name, value| } -> Hash
3132 * ENV.select -> Enumerator
3133 *
3134 * Returns a copy of the environment for entries where the block returns true.
3135 *
3136 * Returns an Enumerator if no block was given.
3137 */
3138 static VALUE
3139 env_select(VALUE ehash)
3140 {
3141 VALUE result;
3142 VALUE keys;
3143 long i;
3144
3145 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3146 result = rb_hash_new();
3147 keys = env_keys();
3148 for (i = 0; i < RARRAY_LEN(keys); ++i) {
3149 VALUE key = RARRAY_AREF(keys, i);
3150 VALUE val = rb_f_getenv(Qnil, key);
3151 if (!NIL_P(val)) {
3152 if (RTEST(rb_yield_values(2, key, val))) {
3153 rb_hash_aset(result, key, val);
3154 }
3155 }
3156 }
3157
3158 return result;
3159 }
3160
3161 /*
3162 * call-seq:
3163 * ENV.select! { |name, value| } -> ENV or nil
3164 * ENV.select! -> Enumerator
3165 *
3166 * Equivalent to ENV#keep_if but returns +nil+ if no changes were made.
3167 */
3168 static VALUE
3169 env_select_bang(VALUE ehash)
3170 {
3171 volatile VALUE keys;
3172 long i;
3173 int del = 0;
3174
3175 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3176 keys = env_keys();
3177 RBASIC_CLEAR_CLASS(keys);
3178 for (i=0; i<RARRAY_LEN(keys); i++) {
3179 VALUE val = rb_f_getenv(Qnil, RARRAY_AREF(keys, i));
3180 if (!NIL_P(val)) {
3181 if (!RTEST(rb_yield_values(2, RARRAY_AREF(keys, i), val))) {
3182 FL_UNSET(RARRAY_AREF(keys, i), FL_TAINT);
3183 env_delete(Qnil, RARRAY_AREF(keys, i));
3184 del++;
3185 }
3186 }
3187 }
3188 if (del == 0) return Qnil;
3189 return envtbl;
3190 }
3191
3192 /*
3193 * call-seq:
3194 * ENV.keep_if { |name, value| } -> Hash
3195 * ENV.keep_if -> Enumerator
3196 *
3197 * Deletes every environment variable where the block evaluates to +false+.
3198 *
3199 * Returns an enumerator if no block was given.
3200 */
3201 static VALUE
3202 env_keep_if(VALUE ehash)
3203 {
3204 RETURN_SIZED_ENUMERATOR(ehash, 0, 0, rb_env_size);
3205 env_select_bang(ehash);
3206 return envtbl;
3207 }
3208
3209 /*
3210 * call-seq:
3211 * ENV.clear
3212 *
3213 * Removes every environment variable.
3214 */
3215 VALUE
3216 rb_env_clear(void)
3217 {
3218 volatile VALUE keys;
3219 long i;
3220
3221 keys = env_keys();
3222 for (i=0; i<RARRAY_LEN(keys); i++) {
3223 VALUE val = rb_f_getenv(Qnil, RARRAY_AREF(keys, i));
3224 if (!NIL_P(val)) {
3225 env_delete(Qnil, RARRAY_AREF(keys, i));
3226 }
3227 }
3228 return envtbl;
3229 }
3230
3231 /*
3232 * call-seq:
3233 * ENV.to_s -> "ENV"
3234 *
3235 * Returns "ENV"
3236 */
3237 static VALUE
3238 env_to_s(void)
3239 {
3240 return rb_usascii_str_new2("ENV");
3241 }
3242
3243 /*
3244 * call-seq:
3245 * ENV.inspect -> string
3246 *
3247 * Returns the contents of the environment as a String.
3248 */
3249 static VALUE
3250 env_inspect(void)
3251 {
3252 char **env;
3253 VALUE str, i;
3254
3255 str = rb_str_buf_new2("{");
3256 env = GET_ENVIRON(environ);
3257 while (*env) {
3258 char *s = strchr(*env, '=');
3259
3260 if (env != environ) {
3261 rb_str_buf_cat2(str, ", ");
3262 }
3263 if (s) {
3264 rb_str_buf_cat2(str, "\"");
3265 rb_str_buf_cat(str, *env, s-*env);
3266 rb_str_buf_cat2(str, "\"=>");
3267 i = rb_inspect(rb_str_new2(s+1));
3268 rb_str_buf_append(str, i);
3269 }
3270 env++;
3271 }
3272 FREE_ENVIRON(environ);
3273 rb_str_buf_cat2(str, "}");
3274 OBJ_TAINT(str);
3275
3276 return str;
3277 }
3278
3279 /*
3280 * call-seq:
3281 * ENV.to_a -> Array
3282 *
3283 * Converts the environment variables into an array of names and value arrays.
3284 *
3285 * ENV.to_a # => [["TERM", "xterm-color"], ["SHELL", "/bin/bash"], ...]
3286 *
3287 */
3288 static VALUE
3289 env_to_a(void)
3290 {
3291 char **env;
3292 VALUE ary;
3293
3294 ary = rb_ary_new();
3295 env = GET_ENVIRON(environ);
3296 while (*env) {
3297 char *s = strchr(*env, '=');
3298 if (s) {
3299 rb_ary_push(ary, rb_assoc_new(env_str_new(*env, s-*env),
3300 env_str_new2(s+1)));
3301 }
3302 env++;
3303 }
3304 FREE_ENVIRON(environ);
3305 return ary;
3306 }
3307
3308 /*
3309 * call-seq:
3310 * ENV.rehash
3311 *
3312 * Re-hashing the environment variables does nothing. It is provided for
3313 * compatibility with Hash.
3314 */
3315 static VALUE
3316 env_none(void)
3317 {
3318 return Qnil;
3319 }
3320
3321 /*
3322 * call-seq:
3323 * ENV.length
3324 * ENV.size
3325 *
3326 * Returns the number of environment variables.
3327 */
3328 static VALUE
3329 env_size(void)
3330 {
3331 int i;
3332 char **env;
3333
3334 env = GET_ENVIRON(environ);
3335 for (i=0; env[i]; i++)
3336 ;
3337 FREE_ENVIRON(environ);
3338 return INT2FIX(i);
3339 }
3340
3341 /*
3342 * call-seq:
3343 * ENV.empty? -> true or false
3344 *
3345 * Returns true when there are no environment variables
3346 */
3347 static VALUE
3348 env_empty_p(void)
3349 {
3350 char **env;
3351
3352 env = GET_ENVIRON(environ);
3353 if (env[0] == 0) {
3354 FREE_ENVIRON(environ);
3355 return Qtrue;
3356 }
3357 FREE_ENVIRON(environ);
3358 return Qfalse;
3359 }
3360
3361 /*
3362 * call-seq:
3363 * ENV.key?(name) -> true or false
3364 * ENV.include?(name) -> true or false
3365 * ENV.has_key?(name) -> true or false
3366 * ENV.member?(name) -> true or false
3367 *
3368 * Returns +true+ if there is an environment variable with the given +name+.
3369 */
3370 static VALUE
3371 env_has_key(VALUE env, VALUE key)
3372 {
3373 char *s;
3374
3375 SafeStringValue(key);
3376 s = RSTRING_PTR(key);
3377 if (memchr(s, '\0', RSTRING_LEN(key)))
3378 rb_raise(rb_eArgError, "bad environment variable name");
3379 if (getenv(s)) return Qtrue;
3380 return Qfalse;
3381 }
3382
3383 /*
3384 * call-seq:
3385 * ENV.assoc(name) -> Array or nil
3386 *
3387 * Returns an Array of the name and value of the environment variable with
3388 * +name+ or +nil+ if the name cannot be found.
3389 */
3390 static VALUE
3391 env_assoc(VALUE env, VALUE key)
3392 {
3393 char *s, *e;
3394
3395 SafeStringValue(key);
3396 s = RSTRING_PTR(key);
3397 if (memchr(s, '\0', RSTRING_LEN(key)))
3398 rb_raise(rb_eArgError, "bad environment variable name");
3399 e = getenv(s);
3400 if (e) return rb_assoc_new(key, rb_tainted_str_new2(e));
3401 return Qnil;
3402 }
3403
3404 /*
3405 * call-seq:
3406 * ENV.value?(value) -> true or false
3407 * ENV.has_value?(value) -> true or false
3408 *
3409 * Returns +true+ if there is an environment variable with the given +value+.
3410 */
3411 static VALUE
3412 env_has_value(VALUE dmy, VALUE obj)
3413 {
3414 char **env;
3415
3416 obj = rb_check_string_type(obj);
3417 if (NIL_P(obj)) return Qnil;
3418 rb_check_safe_obj(obj);
3419 env = GET_ENVIRON(environ);
3420 while (*env) {
3421 char *s = strchr(*env, '=');
3422 if (s++) {
3423 long len = strlen(s);
3424 if (RSTRING_LEN(obj) == len && strncmp(s, RSTRING_PTR(obj), len) == 0) {
3425 FREE_ENVIRON(environ);
3426 return Qtrue;
3427 }
3428 }
3429 env++;
3430 }
3431 FREE_ENVIRON(environ);
3432 return Qfalse;
3433 }
3434
3435 /*
3436 * call-seq:
3437 * ENV.rassoc(value)
3438 *
3439 * Returns an Array of the name and value of the environment variable with
3440 * +value+ or +nil+ if the value cannot be found.
3441 */
3442 static VALUE
3443 env_rassoc(VALUE dmy, VALUE obj)
3444 {
3445 char **env;
3446
3447 obj = rb_check_string_type(obj);
3448 if (NIL_P(obj)) return Qnil;
3449 rb_check_safe_obj(obj);
3450 env = GET_ENVIRON(environ);
3451 while (*env) {
3452 char *s = strchr(*env, '=');
3453 if (s++) {
3454 long len = strlen(s);
3455 if (RSTRING_LEN(obj) == len && strncmp(s, RSTRING_PTR(obj), len) == 0) {
3456 VALUE result = rb_assoc_new(rb_tainted_str_new(*env, s-*env-1), obj);
3457 FREE_ENVIRON(environ);
3458 return result;
3459 }
3460 }
3461 env++;
3462 }
3463 FREE_ENVIRON(environ);
3464 return Qnil;
3465 }
3466
3467 /*
3468 * call-seq:
3469 * ENV.key(value) -> name
3470 *
3471 * Returns the name of the environment variable with +value+. If the value is
3472 * not found +nil+ is returned.
3473 */
3474 static VALUE
3475 env_key(VALUE dmy, VALUE value)
3476 {
3477 char **env;
3478 VALUE str;
3479
3480 SafeStringValue(value);
3481 env = GET_ENVIRON(environ);
3482 while (*env) {
3483 char *s = strchr(*env, '=');
3484 if (s++) {
3485 long len = strlen(s);
3486 if (RSTRING_LEN(value) == len && strncmp(s, RSTRING_PTR(value), len) == 0) {
3487 str = env_str_new(*env, s-*env-1);
3488 FREE_ENVIRON(environ);
3489 return str;
3490 }
3491 }
3492 env++;
3493 }
3494 FREE_ENVIRON(environ);
3495 return Qnil;
3496 }
3497
3498 /*
3499 * call-seq:
3500 * ENV.index(value) -> key
3501 *
3502 * Deprecated method that is equivalent to ENV.key
3503 */
3504 static VALUE
3505 env_index(VALUE dmy, VALUE value)
3506 {
3507 rb_warn("ENV.index is deprecated; use ENV.key");
3508 return env_key(dmy, value);
3509 }
3510
3511 /*
3512 * call-seq:
3513 * ENV.to_hash -> hash
3514 * ENV.to_h -> hash
3515 *
3516 * Creates a hash with a copy of the environment variables.
3517 *
3518 */
3519 static VALUE
3520 env_to_hash(void)
3521 {
3522 char **env;
3523 VALUE hash;
3524
3525 hash = rb_hash_new();
3526 env = GET_ENVIRON(environ);
3527 while (*env) {
3528 char *s = strchr(*env, '=');
3529 if (s) {
3530 rb_hash_aset(hash, env_str_new(*env, s-*env),
3531 env_str_new2(s+1));
3532 }
3533 env++;
3534 }
3535 FREE_ENVIRON(environ);
3536 return hash;
3537 }
3538
3539 /*
3540 * call-seq:
3541 * ENV.reject { |name, value| } -> Hash
3542 * ENV.reject -> Enumerator
3543 *
3544 * Same as ENV#delete_if, but works on (and returns) a copy of the
3545 * environment.
3546 */
3547 static VALUE
3548 env_reject(void)
3549 {
3550 return rb_hash_delete_if(env_to_hash());
3551 }
3552
3553 /*
3554 * call-seq:
3555 * ENV.shift -> Array or nil
3556 *
3557 * Removes an environment variable name-value pair from ENV and returns it as
3558 * an Array. Returns +nil+ if when the environment is empty.
3559 */
3560 static VALUE
3561 env_shift(void)
3562 {
3563 char **env;
3564 VALUE result = Qnil;
3565
3566 env = GET_ENVIRON(environ);
3567 if (*env) {
3568 char *s = strchr(*env, '=');
3569 if (s) {
3570 VALUE key = env_str_new(*env, s-*env);
3571 VALUE val = env_str_new2(getenv(RSTRING_PTR(key)));
3572 env_delete(Qnil, key);
3573 result = rb_assoc_new(key, val);
3574 }
3575 }
3576 FREE_ENVIRON(environ);
3577 return result;
3578 }
3579
3580 /*
3581 * call-seq:
3582 * ENV.invert -> Hash
3583 *
3584 * Returns a new hash created by using environment variable names as values
3585 * and values as names.
3586 */
3587 static VALUE
3588 env_invert(void)
3589 {
3590 return rb_hash_invert(env_to_hash());
3591 }
3592
3593 static int
3594 env_replace_i(VALUE key, VALUE val, VALUE keys)
3595 {
3596 env_aset(Qnil, key, val);
3597 if (rb_ary_includes(keys, key)) {
3598 rb_ary_delete(keys, key);
3599 }
3600 return ST_CONTINUE;
3601 }
3602
3603 /*
3604 * call-seq:
3605 * ENV.replace(hash) -> env
3606 *
3607 * Replaces the contents of the environment variables with the contents of
3608 * +hash+.
3609 */
3610 static VALUE
3611 env_replace(VALUE env, VALUE hash)
3612 {
3613 volatile VALUE keys;
3614 long i;
3615
3616 keys = env_keys();
3617 if (env == hash) return env;
3618 hash = to_hash(hash);
3619 rb_hash_foreach(hash, env_replace_i, keys);
3620
3621 for (i=0; i<RARRAY_LEN(keys); i++) {
3622 env_delete(env, RARRAY_AREF(keys, i));
3623 }
3624 return env;
3625 }
3626
3627 static int
3628 env_update_i(VALUE key, VALUE val)
3629 {
3630 if (rb_block_given_p()) {
3631 val = rb_yield_values(3, key, rb_f_getenv(Qnil, key), val);
3632 }
3633 env_aset(Qnil, key, val);
3634 return ST_CONTINUE;
3635 }
3636
3637 /*
3638 * call-seq:
3639 * ENV.update(hash) -> Hash
3640 * ENV.update(hash) { |name, old_value, new_value| } -> Hash
3641 *
3642 * Adds the contents of +hash+ to the environment variables. If no block is
3643 * specified entries with duplicate keys are overwritten, otherwise the value
3644 * of each duplicate name is determined by calling the block with the key, its
3645 * value from the environment and its value from the hash.
3646 */
3647 static VALUE
3648 env_update(VALUE env, VALUE hash)
3649 {
3650 if (env == hash) return env;
3651 hash = to_hash(hash);
3652 rb_hash_foreach(hash, env_update_i, 0);
3653 return env;
3654 }
3655
3656 /*
3657 * A Hash is a dictionary-like collection of unique keys and their values.
3658 * Also called associative arrays, they are similar to Arrays, but where an
3659 * Array uses integers as its index, a Hash allows you to use any object
3660 * type.
3661 *
3662 * Hashes enumerate their values in the order that the corresponding keys
3663 * were inserted.
3664 *
3665 * A Hash can be easily created by using its implicit form:
3666 *
3667 * grades = { "Jane Doe" => 10, "Jim Doe" => 6 }
3668 *
3669 * Hashes allow an alternate syntax form when your keys are always symbols.
3670 * Instead of
3671 *
3672 * options = { :font_size => 10, :font_family => "Arial" }
3673 *
3674 * You could write it as:
3675 *
3676 * options = { font_size: 10, font_family: "Arial" }
3677 *
3678 * Each named key is a symbol you can access in hash:
3679 *
3680 * options[:font_size] # => 10
3681 *
3682 * A Hash can also be created through its ::new method:
3683 *
3684 * grades = Hash.new
3685 * grades["Dorothy Doe"] = 9
3686 *
3687 * Hashes have a <em>default value</em> that is returned when accessing
3688 * keys that do not exist in the hash. If no default is set +nil+ is used.
3689 * You can set the default value by sending it as an argument to Hash.new:
3690 *
3691 * grades = Hash.new(0)
3692 *
3693 * Or by using the #default= method:
3694 *
3695 * grades = {"Timmy Doe" => 8}
3696 * grades.default = 0
3697 *
3698 * Accessing a value in a Hash requires using its key:
3699 *
3700 * puts grades["Jane Doe"] # => 0
3701 *
3702 * === Common Uses
3703 *
3704 * Hashes are an easy way to represent data structures, such as
3705 *
3706 * books = {}
3707 * books[:matz] = "The Ruby Language"
3708 * books[:black] = "The Well-Grounded Rubyist"
3709 *
3710 * Hashes are also commonly used as a way to have named parameters in
3711 * functions. Note that no brackets are used below. If a hash is the last
3712 * argument on a method call, no braces are needed, thus creating a really
3713 * clean interface:
3714 *
3715 * Person.create(name: "John Doe", age: 27)
3716 *
3717 * def self.create(params)
3718 * @name = params[:name]
3719 * @age = params[:age]
3720 * end
3721 *
3722 * === Hash Keys
3723 *
3724 * Two objects refer to the same hash key when their <code>hash</code> value
3725 * is identical and the two objects are <code>eql?</code> to each other.
3726 *
3727 * A user-defined class may be used as a hash key if the <code>hash</code>
3728 * and <code>eql?</code> methods are overridden to provide meaningful
3729 * behavior. By default, separate instances refer to separate hash keys.
3730 *
3731 * A typical implementation of <code>hash</code> is based on the
3732 * object's data while <code>eql?</code> is usually aliased to the overridden
3733 * <code>==</code> method:
3734 *
3735 * class Book
3736 * attr_reader :author, :title
3737 *
3738 * def initialize(author, title)
3739 * @author = author
3740 * @title = title
3741 * end
3742 *
3743 * def ==(other)
3744 * self.class === other and
3745 * other.author == @author and
3746 * other.title == @title
3747 * end
3748 *
3749 * alias eql? ==
3750 *
3751 * def hash
3752 * @author.hash ^ @title.hash # XOR
3753 * end
3754 * end
3755 *
3756 * book1 = Book.new 'matz', 'Ruby in a Nutshell'
3757 * book2 = Book.new 'matz', 'Ruby in a Nutshell'
3758 *
3759 * reviews = {}
3760 *
3761 * reviews[book1] = 'Great reference!'
3762 * reviews[book2] = 'Nice and compact!'
3763 *
3764 * reviews.length #=> 1
3765 *
3766 * See also Object#hash and Object#eql?
3767 */
3768
3769 void
3770 Init_Hash(void)
3771 {
3772 #undef rb_intern
3773 #define rb_intern(str) rb_intern_const(str)
3774
3775 id_hash = rb_intern("hash");
3776 id_yield = rb_intern("yield");
3777 id_default = rb_intern("default");
3778 id_flatten_bang = rb_intern("flatten!");
3779
3780 rb_cHash = rb_define_class("Hash", rb_cObject);
3781
3782 rb_include_module(rb_cHash, rb_mEnumerable);
3783
3784 rb_define_alloc_func(rb_cHash, empty_hash_alloc);
3785 rb_define_singleton_method(rb_cHash, "[]", rb_hash_s_create, -1);
3786 rb_define_singleton_method(rb_cHash, "try_convert", rb_hash_s_try_convert, 1);
3787 rb_define_method(rb_cHash,"initialize", rb_hash_initialize, -1);
3788 rb_define_method(rb_cHash,"initialize_copy", rb_hash_initialize_copy, 1);
3789 rb_define_method(rb_cHash,"rehash", rb_hash_rehash, 0);
3790
3791 rb_define_method(rb_cHash,"to_hash", rb_hash_to_hash, 0);
3792 rb_define_method(rb_cHash,"to_h", rb_hash_to_h, 0);
3793 rb_define_method(rb_cHash,"to_a", rb_hash_to_a, 0);
3794 rb_define_method(rb_cHash,"inspect", rb_hash_inspect, 0);
3795 rb_define_alias(rb_cHash, "to_s", "inspect");
3796
3797 rb_define_method(rb_cHash,"==", rb_hash_equal, 1);
3798 rb_define_method(rb_cHash,"[]", rb_hash_aref, 1);
3799 rb_define_method(rb_cHash,"hash", rb_hash_hash, 0);
3800 rb_define_method(rb_cHash,"eql?", rb_hash_eql, 1);
3801 rb_define_method(rb_cHash,"fetch", rb_hash_fetch_m, -1);
3802 rb_define_method(rb_cHash,"[]=", rb_hash_aset, 2);
3803 rb_define_method(rb_cHash,"store", rb_hash_aset, 2);
3804 rb_define_method(rb_cHash,"default", rb_hash_default, -1);
3805 rb_define_method(rb_cHash,"default=", rb_hash_set_default, 1);
3806 rb_define_method(rb_cHash,"default_proc", rb_hash_default_proc, 0);
3807 rb_define_method(rb_cHash,"default_proc=", rb_hash_set_default_proc, 1);
3808 rb_define_method(rb_cHash,"key", rb_hash_key, 1);
3809 rb_define_method(rb_cHash,"index", rb_hash_index, 1);
3810 rb_define_method(rb_cHash,"size", rb_hash_size, 0);
3811 rb_define_method(rb_cHash,"length", rb_hash_size, 0);
3812 rb_define_method(rb_cHash,"empty?", rb_hash_empty_p, 0);
3813
3814 rb_define_method(rb_cHash,"each_value", rb_hash_each_value, 0);
3815 rb_define_method(rb_cHash,"each_key", rb_hash_each_key, 0);
3816 rb_define_method(rb_cHash,"each_pair", rb_hash_each_pair, 0);
3817 rb_define_method(rb_cHash,"each", rb_hash_each_pair, 0);
3818
3819 rb_define_method(rb_cHash,"keys", rb_hash_keys, 0);
3820 rb_define_method(rb_cHash,"values", rb_hash_values, 0);
3821 rb_define_method(rb_cHash,"values_at", rb_hash_values_at, -1);
3822
3823 rb_define_method(rb_cHash,"shift", rb_hash_shift, 0);
3824 rb_define_method(rb_cHash,"delete", rb_hash_delete, 1);
3825 rb_define_method(rb_cHash,"delete_if", rb_hash_delete_if, 0);
3826 rb_define_method(rb_cHash,"keep_if", rb_hash_keep_if, 0);
3827 rb_define_method(rb_cHash,"select", rb_hash_select, 0);
3828 rb_define_method(rb_cHash,"select!", rb_hash_select_bang, 0);
3829 rb_define_method(rb_cHash,"reject", rb_hash_reject, 0);
3830 rb_define_method(rb_cHash,"reject!", rb_hash_reject_bang, 0);
3831 rb_define_method(rb_cHash,"clear", rb_hash_clear, 0);
3832 rb_define_method(rb_cHash,"invert", rb_hash_invert, 0);
3833 rb_define_method(rb_cHash,"update", rb_hash_update, 1);
3834 rb_define_method(rb_cHash,"replace", rb_hash_replace, 1);
3835 rb_define_method(rb_cHash,"merge!", rb_hash_update, 1);
3836 rb_define_method(rb_cHash,"merge", rb_hash_merge, 1);
3837 rb_define_method(rb_cHash, "assoc", rb_hash_assoc, 1);
3838 rb_define_method(rb_cHash, "rassoc", rb_hash_rassoc, 1);
3839 rb_define_method(rb_cHash, "flatten", rb_hash_flatten, -1);
3840
3841 rb_define_method(rb_cHash,"include?", rb_hash_has_key, 1);
3842 rb_define_method(rb_cHash,"member?", rb_hash_has_key, 1);
3843 rb_define_method(rb_cHash,"has_key?", rb_hash_has_key, 1);
3844 rb_define_method(rb_cHash,"has_value?", rb_hash_has_value, 1);
3845 rb_define_method(rb_cHash,"key?", rb_hash_has_key, 1);
3846 rb_define_method(rb_cHash,"value?", rb_hash_has_value, 1);
3847
3848 rb_define_method(rb_cHash,"compare_by_identity", rb_hash_compare_by_id, 0);
3849 rb_define_method(rb_cHash,"compare_by_identity?", rb_hash_compare_by_id_p, 0);
3850
3851 /* Document-class: ENV
3852 *
3853 * ENV is a hash-like accessor for environment variables.
3854 */
3855
3856 /*
3857 * Hack to get RDoc to regard ENV as a class:
3858 * envtbl = rb_define_class("ENV", rb_cObject);
3859 */
3860 origenviron = environ;
3861 envtbl = rb_obj_alloc(rb_cObject);
3862 rb_extend_object(envtbl, rb_mEnumerable);
3863
3864 rb_define_singleton_method(envtbl,"[]", rb_f_getenv, 1);
3865 rb_define_singleton_method(envtbl,"fetch", env_fetch, -1);
3866 rb_define_singleton_method(envtbl,"[]=", env_aset, 2);
3867 rb_define_singleton_method(envtbl,"store", env_aset, 2);
3868 rb_define_singleton_method(envtbl,"each", env_each_pair, 0);
3869 rb_define_singleton_method(envtbl,"each_pair", env_each_pair, 0);
3870 rb_define_singleton_method(envtbl,"each_key", env_each_key, 0);
3871 rb_define_singleton_method(envtbl,"each_value", env_each_value, 0);
3872 rb_define_singleton_method(envtbl,"delete", env_delete_m, 1);
3873 rb_define_singleton_method(envtbl,"delete_if", env_delete_if, 0);
3874 rb_define_singleton_method(envtbl,"keep_if", env_keep_if, 0);
3875 rb_define_singleton_method(envtbl,"clear", rb_env_clear, 0);
3876 rb_define_singleton_method(envtbl,"reject", env_reject, 0);
3877 rb_define_singleton_method(envtbl,"reject!", env_reject_bang, 0);
3878 rb_define_singleton_method(envtbl,"select", env_select, 0);
3879 rb_define_singleton_method(envtbl,"select!", env_select_bang, 0);
3880 rb_define_singleton_method(envtbl,"shift", env_shift, 0);
3881 rb_define_singleton_method(envtbl,"invert", env_invert, 0);
3882 rb_define_singleton_method(envtbl,"replace", env_replace, 1);
3883 rb_define_singleton_method(envtbl,"update", env_update, 1);
3884 rb_define_singleton_method(envtbl,"inspect", env_inspect, 0);
3885 rb_define_singleton_method(envtbl,"rehash", env_none, 0);
3886 rb_define_singleton_method(envtbl,"to_a", env_to_a, 0);
3887 rb_define_singleton_method(envtbl,"to_s", env_to_s, 0);
3888 rb_define_singleton_method(envtbl,"key", env_key, 1);
3889 rb_define_singleton_method(envtbl,"index", env_index, 1);
3890 rb_define_singleton_method(envtbl,"size", env_size, 0);
3891 rb_define_singleton_method(envtbl,"length", env_size, 0);
3892 rb_define_singleton_method(envtbl,"empty?", env_empty_p, 0);
3893 rb_define_singleton_method(envtbl,"keys", env_keys, 0);
3894 rb_define_singleton_method(envtbl,"values", env_values, 0);
3895 rb_define_singleton_method(envtbl,"values_at", env_values_at, -1);
3896 rb_define_singleton_method(envtbl,"include?", env_has_key, 1);
3897 rb_define_singleton_method(envtbl,"member?", env_has_key, 1);
3898 rb_define_singleton_method(envtbl,"has_key?", env_has_key, 1);
3899 rb_define_singleton_method(envtbl,"has_value?", env_has_value, 1);
3900 rb_define_singleton_method(envtbl,"key?", env_has_key, 1);
3901 rb_define_singleton_method(envtbl,"value?", env_has_value, 1);
3902 rb_define_singleton_method(envtbl,"to_hash", env_to_hash, 0);
3903 rb_define_singleton_method(envtbl,"to_h", env_to_hash, 0);
3904 rb_define_singleton_method(envtbl,"assoc", env_assoc, 1);
3905 rb_define_singleton_method(envtbl,"rassoc", env_rassoc, 1);
3906
3907 /*
3908 * ENV is a Hash-like accessor for environment variables.
3909 *
3910 * See ENV (the class) for more details.
3911 */
3912 rb_define_global_const("ENV", envtbl);
3913
3914 /* for callcc */
3915 ruby_register_rollback_func_for_ensure(hash_foreach_ensure, hash_foreach_ensure_rollback);
3916 }
rb_cString
RUBY_EXTERN VALUE rb_cString
Definition: ruby.h:1583
rb_define_global_const
void rb_define_global_const(const char *, VALUE)
Definition: variable.c:2236
RBASIC_CLEAR_CLASS
#define RBASIC_CLEAR_CLASS(obj)
Definition: internal.h:607
RHASH_UPDATE
#define RHASH_UPDATE(hash, key, func, arg)
Definition: hash.c:426
empty_hash_alloc
static VALUE empty_hash_alloc(VALUE klass)
Definition: hash.c:288
rb_builtin_class_name
const char * rb_builtin_class_name(VALUE x)
Definition: error.c:451
rb_hash
VALUE rb_hash(VALUE obj)
Definition: hash.c:106
hash_foreach_call
static VALUE hash_foreach_call(VALUE arg)
Definition: hash.c:254
rb_hash_invert_i
static int rb_hash_invert_i(VALUE key, VALUE value, VALUE hash)
Definition: hash.c:2054
ST_DELETE
Definition: st.h:100
each_pair_i
static int each_pair_i(VALUE key, VALUE value)
Definition: hash.c:1595
rb_integer_pack
int rb_integer_pack(VALUE val, void *words, size_t numwords, size_t wordsize, size_t nails, int flags)
Definition: bignum.c:3531
FL_EXIVAR
#define FL_EXIVAR
Definition: ruby.h:1139
reset_hash_type_arg::orighash
const struct st_hash_type * orighash
Definition: hash.c:2265
foreach_safe_arg::func
st_foreach_func * func
Definition: hash.c:170
RARRAY_LEN
#define RARRAY_LEN(a)
Definition: ruby.h:878
env_each_value
static VALUE env_each_value(VALUE ehash)
Definition: hash.c:3001
rb_ary_new_capa
VALUE rb_ary_new_capa(long capa)
Definition: array.c:489
rb_w32_ugetenv
char * rb_w32_ugetenv(const char *)
Definition: win32.c:4660
FALSE
#define FALSE
Definition: nkf.h:174
rb_enc_copy
void rb_enc_copy(VALUE obj1, VALUE obj2)
Definition: encoding.c:916
rb_hash_each_value
static VALUE rb_hash_each_value(VALUE hash)
Definition: hash.c:1554
update_callback_arg::arg
st_data_t arg
Definition: hash.c:372
env_delete_m
static VALUE env_delete_m(VALUE obj, VALUE name)
Definition: hash.c:2567
strlen
size_t strlen(const char *)
rb_hash_has_value
static VALUE rb_hash_has_value(VALUE hash, VALUE val)
Definition: hash.c:1903
path_tainted
static int path_tainted
Definition: hash.c:2474
st_table
Definition: st.h:69
invalid_envname
static void invalid_envname(const char *name)
Definition: hash.c:2731
FREE_ENVIRON
#define FREE_ENVIRON(e)
Definition: hash.c:2504
ST_STOP
Definition: st.h:100
path_tainted_p
static void path_tainted_p(const char *path)
Definition: hash.c:2661
replace_i
static int replace_i(VALUE key, VALUE val, VALUE hash)
Definition: hash.c:1413
id_yield
static ID id_yield
Definition: hash.c:70
rb_hash_dup
VALUE rb_hash_dup(VALUE hash)
Definition: hash.c:320
rb_hash_s_try_convert
static VALUE rb_hash_s_try_convert(VALUE, VALUE)
Definition: hash.c:605
envix
static int envix(const char *nam)
Definition: hash.c:2697
rb_yield_values
VALUE rb_yield_values(int n,...)
Definition: vm_eval.c:953
NUM2INT
#define NUM2INT(x)
Definition: ruby.h:630
RB_OBJ_WRITTEN
#define RB_OBJ_WRITTEN(a, oldv, b)
Definition: ruby.h:1214
max
static int max(int a, int b)
Definition: strftime.c:141
id_hash
static ID id_hash
Definition: hash.c:70
keep_if_i
static int keep_if_i(VALUE key, VALUE value, VALUE hash)
Definition: hash.c:1252
no_new_key
static void no_new_key(void)
Definition: hash.c:365
rb_define_singleton_method
void rb_define_singleton_method(VALUE obj, const char *name, VALUE(*func)(ANYARGS), int argc)
Defines a singleton method for obj.
Definition: class.c:1655
foreach_safe_arg
Definition: hash.c:168
rb_exec_recursive_outer
VALUE rb_exec_recursive_outer(VALUE(*)(VALUE, VALUE, int), VALUE, VALUE)
Definition: thread.c:5005
env_update_i
static int env_update_i(VALUE key, VALUE val)
Definition: hash.c:3628
rb_eKeyError
VALUE rb_eKeyError
Definition: error.c:551
ruby.h
rb_hash_size
static VALUE rb_hash_size(VALUE hash)
Definition: hash.c:1505
rb_hash_empty_p
static VALUE rb_hash_empty_p(VALUE hash)
Definition: hash.c:1522
RHASH_ITER_LEV
#define RHASH_ITER_LEV(h)
Definition: ruby.h:928
env_invert
static VALUE env_invert(void)
Definition: hash.c:3588
hash_aset_str
static int hash_aset_str(st_data_t *key, st_data_t *val, struct update_arg *arg, int existing)
Definition: hash.c:1355
rb_usascii_str_new2
#define rb_usascii_str_new2
Definition: intern.h:846
FL_TAINT
#define FL_TAINT
Definition: ruby.h:1137
CLASS_OF
#define CLASS_OF(v)
Definition: ruby.h:440
rb_hash_default
static VALUE rb_hash_default(int argc, VALUE *argv, VALUE hash)
Definition: hash.c:809
ENVMATCH
#define ENVMATCH(n1, n2)
Definition: hash.c:2510
rehash_arg
Definition: hash.c:610
Qtrue
#define Qtrue
Definition: ruby.h:426
st_insert
int st_insert(st_table *, st_data_t, st_data_t)
rb_hash_update_block_i
static int rb_hash_update_block_i(VALUE key, VALUE value, VALUE hash)
Definition: hash.c:2126
rb_hash_modify
static void rb_hash_modify(VALUE hash)
Definition: hash.c:357
rb_cHash
VALUE rb_cHash
Definition: hash.c:67
env_str_new2
static VALUE env_str_new2(const char *ptr)
Definition: hash.c:2528
rehash_arg::tbl
st_table * tbl
Definition: hash.c:612
rb_hash_end
st_index_t rb_hash_end(st_index_t)
foreach_safe_i
static int foreach_safe_i(st_data_t key, st_data_t value, st_data_t args, int error)
Definition: hash.c:175
rb_hash_select_bang
VALUE rb_hash_select_bang(VALUE hash)
Definition: hash.c:1270
keys_i
static int keys_i(VALUE key, VALUE value, VALUE ary)
Definition: hash.c:1764
id_flatten_bang
static ID id_flatten_bang
Definition: hash.c:70
env_to_s
static VALUE env_to_s(void)
Definition: hash.c:3238
rb_env_path_tainted
int rb_env_path_tainted(void)
Definition: hash.c:2676
probes.h
ST_CONTINUE
Definition: st.h:100
reset_hash_type_arg
Definition: hash.c:2263
env_keys
static VALUE env_keys(void)
Definition: hash.c:2909
shift_var::val
VALUE val
Definition: hash.c:1011
rb_eTypeError
VALUE rb_eTypeError
Definition: error.c:548
env_delete_if
static VALUE env_delete_if(VALUE ehash)
Definition: hash.c:3102
equal_data::tbl
st_table * tbl
Definition: hash.c:1915
st_hash_type::compare
int(* compare)(ANYARGS)
Definition: st.h:56
rb_check_arity
#define rb_check_arity
Definition: intern.h:296
env_shift
static VALUE env_shift(void)
Definition: hash.c:3561
rb_ary_push
VALUE rb_ary_push(VALUE ary, VALUE item)
Definition: array.c:896
update_arg::new_value
VALUE new_value
Definition: hash.c:394
eql_i
static int eql_i(VALUE key, VALUE val1, VALUE arg)
Definition: hash.c:1920
rb_str_buf_new2
VALUE rb_str_buf_new2(const char *)
st_free_table
void st_free_table(st_table *)
Definition: st.c:334
env_each_pair
static VALUE env_each_pair(VALUE ehash)
Definition: hash.c:3026
rb_env_size
static VALUE rb_env_size(VALUE ehash, VALUE args, VALUE eobj)
Definition: hash.c:2928
rb_hash_tbl_raw
struct st_table * rb_hash_tbl_raw(VALUE hash)
Definition: hash.c:351
OBJ_PROMOTED
#define OBJ_PROMOTED(x)
Definition: ruby.h:1189
id_default
static ID id_default
Definition: hash.c:70
rb_hash_update_by
VALUE rb_hash_update_by(VALUE hash1, VALUE hash2, rb_hash_update_func *func)
Definition: hash.c:2208
rb_funcall
VALUE rb_funcall(VALUE, ID, int,...)
Calls a method.
Definition: vm_eval.c:775
rb_hash_tbl
struct st_table * rb_hash_tbl(VALUE hash)
Definition: hash.c:344
INTEGER_PACK_NATIVE_BYTE_ORDER
#define INTEGER_PACK_NATIVE_BYTE_ORDER
Definition: intern.h:146
rb_protect
VALUE rb_protect(VALUE(*proc)(VALUE), VALUE data, int *state)
Definition: eval.c:807
assoc_i
static int assoc_i(VALUE key, VALUE val, VALUE arg)
Definition: hash.c:2277
rb_to_int
VALUE rb_to_int(VALUE)
Definition: object.c:2679
Check_Type
#define Check_Type(v, t)
Definition: ruby.h:532
rb_raise
void rb_raise(VALUE exc, const char *fmt,...)
Definition: error.c:1857
rb_hash_shift
static VALUE rb_hash_shift(VALUE hash)
Definition: hash.c:1038
update_func_arg
Definition: hash.c:2169
inspect_hash
static VALUE inspect_hash(VALUE hash, VALUE dummy, int recur)
Definition: hash.c:1694
rb_convert_type
VALUE rb_convert_type(VALUE, int, const char *, const char *)
Definition: object.c:2616
rb_exec_recursive
VALUE rb_exec_recursive(VALUE(*)(VALUE, VALUE, int), VALUE, VALUE)
Definition: thread.c:4982
rb_define_alloc_func
void rb_define_alloc_func(VALUE, rb_alloc_func_t)
rb_hash_equal
static VALUE rb_hash_equal(VALUE hash1, VALUE hash2)
Definition: hash.c:2001
T_HASH
#define T_HASH
Definition: ruby.h:485
rb_str_hash
st_index_t rb_str_hash(VALUE)
Definition: string.c:2422
ENVNMATCH
#define ENVNMATCH(s1, s2, n)
Definition: hash.c:2511
rb_include_module
void rb_include_module(VALUE klass, VALUE module)
Definition: class.c:827
env_path_tainted
static int env_path_tainted(const char *)
Definition: hash.c:2667
rb_hash_lookup
VALUE rb_hash_lookup(VALUE hash, VALUE key)
Definition: hash.c:719
values_i
static int values_i(VALUE key, VALUE value, VALUE ary)
Definition: hash.c:1808
st_index_t
st_data_t st_index_t
Definition: st.h:48
st_update
int st_update(st_table *table, st_data_t key, st_update_callback_func *func, st_data_t arg)
Definition: st.c:867
env_keep_if
static VALUE env_keep_if(VALUE ehash)
Definition: hash.c:3202
rb_hash_update_i
static int rb_hash_update_i(VALUE key, VALUE value, VALUE hash)
Definition: hash.c:2099
rb_hash_fetch
VALUE rb_hash_fetch(VALUE hash, VALUE key)
Definition: hash.c:782
rb_hash_each_key
static VALUE rb_hash_each_key(VALUE hash)
Definition: hash.c:1587
FIXNUM_P
#define FIXNUM_P(f)
Definition: ruby.h:347
rb_utf8_encoding
rb_encoding * rb_utf8_encoding(void)
Definition: encoding.c:1242
rb_hash_search_value
static int rb_hash_search_value(VALUE key, VALUE value, VALUE arg)
Definition: hash.c:1878
environ
char ** environ
Definition: missing-pips.c:6
rb_str_buf_append
VALUE rb_str_buf_append(VALUE, VALUE)
Definition: string.c:2282
rb_hash_replace
static VALUE rb_hash_replace(VALUE hash, VALUE hash2)
Definition: hash.c:1468
update_arg::old_key
VALUE old_key
Definition: hash.c:393
equal_data::result
VALUE result
Definition: hash.c:1914
rb_intern
#define rb_intern(str)
NOINSERT_UPDATE_CALLBACK
#define NOINSERT_UPDATE_CALLBACK(func)
Definition: hash.c:375
OBJ_TAINTED
#define OBJ_TAINTED(x)
Definition: ruby.h:1176
RHASH_IFNONE
#define RHASH_IFNONE(h)
Definition: ruby.h:929
rb_obj_classname
const char * rb_obj_classname(VALUE)
Definition: variable.c:406
rb_hash_fetch_m
static VALUE rb_hash_fetch_m(int argc, VALUE *argv, VALUE hash)
Definition: hash.c:754
rb_ary_new2
#define rb_ary_new2
Definition: intern.h:90
envtbl
static VALUE envtbl
Definition: hash.c:69
env_rassoc
static VALUE env_rassoc(VALUE dmy, VALUE obj)
Definition: hash.c:3443
rb_hash_update_func_i
static int rb_hash_update_func_i(VALUE key, VALUE value, VALUE arg0)
Definition: hash.c:2197
update_arg
Definition: hash.c:389
env_each_key
static VALUE env_each_key(VALUE ehash)
Definition: hash.c:2953
RHASH_SET_IFNONE
#define RHASH_SET_IFNONE(h, ifnone)
Definition: ruby.h:932
rb_hash_keys
VALUE rb_hash_keys(VALUE hash)
Definition: hash.c:1783
rb_str_buf_cat
VALUE rb_str_buf_cat(VALUE, const char *, long)
Definition: string.c:2124
st_data_t
RUBY_SYMBOL_EXPORT_BEGIN typedef unsigned long st_data_t
Definition: st.h:20
NEWOBJ_OF
#define NEWOBJ_OF(obj, type, klass, flags)
Definition: ruby.h:694
check_envname
static const char * check_envname(const char *name)
Definition: hash.c:2737
rb_hash_foreach
void rb_hash_foreach(VALUE hash, int(*func)(ANYARGS), VALUE farg)
Definition: hash.c:264
rb_obj_dup
VALUE rb_obj_dup(VALUE)
Definition: object.c:406
HAS_EXTRA_STATES
#define HAS_EXTRA_STATES(hash, klass)
Definition: hash.c:30
RB_TYPE_P
#define RB_TYPE_P(obj, type)
Definition: ruby.h:1664
st_hashtype_num
const struct st_hash_type st_hashtype_num
RHASH
#define RHASH(obj)
Definition: ruby.h:1124
fail
#define fail()
Definition: date_strptime.c:118
st_hash_type
Definition: st.h:55
st_lookup
int st_lookup(st_table *, st_data_t, st_data_t *)
rb_hash_rehash_i
static int rb_hash_rehash_i(VALUE key, VALUE value, VALUE arg)
Definition: hash.c:616
env_key
static VALUE env_key(VALUE dmy, VALUE value)
Definition: hash.c:3475
FL_TEST
#define FL_TEST(x, f)
Definition: ruby.h:1169
Init_Hash
void Init_Hash(void)
Definition: hash.c:3770
ALLOC_N
#define ALLOC_N(type, n)
Definition: ruby.h:1333
rb_block_given_p
int rb_block_given_p(void)
Definition: eval.c:712
rb_hash_aset
VALUE rb_hash_aset(VALUE hash, VALUE key, VALUE val)
Definition: hash.c:1393
env_assoc
static VALUE env_assoc(VALUE env, VALUE key)
Definition: hash.c:3391
rb_hash_set_default_proc
static VALUE rb_hash_set_default_proc(VALUE hash, VALUE proc)
Definition: hash.c:889
rb_ary_cat
VALUE rb_ary_cat(VALUE ary, const VALUE *ptr, long len)
Definition: array.c:907
rb_hash_reject_bang
VALUE rb_hash_reject_bang(VALUE hash)
Definition: hash.c:1113
val
#define val
rb_cObject
RUBY_EXTERN VALUE rb_cObject
Definition: ruby.h:1553
rb_eRuntimeError
VALUE rb_eRuntimeError
Definition: error.c:547
rb_exec_recursive_paired
VALUE rb_exec_recursive_paired(VALUE(*)(VALUE, VALUE, int), VALUE, VALUE, VALUE)
Definition: thread.c:4993
env_select_bang
static VALUE env_select_bang(VALUE ehash)
Definition: hash.c:3169
assoc_cmp
static int assoc_cmp(VALUE a, VALUE b)
Definition: hash.c:2251
rb_hash_initialize_copy
static VALUE rb_hash_initialize_copy(VALUE hash, VALUE hash2)
Definition: hash.c:1422
ruby_strdup
char * ruby_strdup(const char *)
Definition: util.c:457
hash_i
static int hash_i(VALUE key, VALUE val, VALUE arg)
Definition: hash.c:2021
rb_ary_new
VALUE rb_ary_new(void)
Definition: array.c:495
rb_str_buf_cat2
VALUE rb_str_buf_cat2(VALUE, const char *)
Definition: string.c:2134
OBJ_WB_UNPROTECT
#define OBJ_WB_UNPROTECT(x)
Definition: ruby.h:1191
rb_objid_hash
long rb_objid_hash(st_index_t index)
Definition: hash.c:150
each_value_i
static int each_value_i(VALUE key, VALUE value)
Definition: hash.c:1528
rb_hash_set_ifnone
VALUE rb_hash_set_ifnone(VALUE hash, VALUE ifnone)
Definition: hash.c:73
snprintf
#define snprintf
Definition: subst.h:6
w32_getenv
static char * w32_getenv(const char *name, UINT cp)
Definition: win32.c:4622
rb_locale_str_new
VALUE rb_locale_str_new(const char *, long)
Definition: string.c:719
update_callback_arg::hash
VALUE hash
Definition: hash.c:371
NIL_P
#define NIL_P(v)
Definition: ruby.h:438
rb_define_class
VALUE rb_define_class(const char *name, VALUE super)
Defines a top-level class.
Definition: class.c:630
rb_hash_eql
static VALUE rb_hash_eql(VALUE hash1, VALUE hash2)
Definition: hash.c:2015
env_delete
static VALUE env_delete(VALUE obj, VALUE name)
Definition: hash.c:2535
st_delete
int st_delete(st_table *, st_data_t *, st_data_t *)
rb_sys_fail_str
void rb_sys_fail_str(VALUE mesg)
Definition: error.c:1982
cnt
rb_atomic_t cnt[RUBY_NSIG]
Definition: signal.c:496
rb_hash_update_func
VALUE rb_hash_update_func(VALUE newkey, VALUE oldkey, VALUE value)
Definition: intern.h:508
update_func_arg::value
VALUE value
Definition: hash.c:2171
rb_foreach_func
int rb_foreach_func(VALUE, VALUE, VALUE)
Definition: hash.c:201
rb_str_conv_enc
VALUE rb_str_conv_enc(VALUE str, rb_encoding *from, rb_encoding *to)
Definition: string.c:680
argc
int argc
Definition: ruby.c:131
rb_hash_to_h
static VALUE rb_hash_to_h(VALUE hash)
Definition: hash.c:1748
env_reject
static VALUE env_reject(void)
Definition: hash.c:3548
Qfalse
#define Qfalse
Definition: ruby.h:425
rb_hash_each_pair
static VALUE rb_hash_each_pair(VALUE hash)
Definition: hash.c:1631
rb_sourcefile
#define rb_sourcefile()
Definition: tcltklib.c:98
rb_locale_encindex
int rb_locale_encindex(void)
Definition: encoding.c:1272
equal_data::eql
int eql
Definition: hash.c:1916
objhash
static const struct st_hash_type objhash
Definition: hash.c:158
T_BIGNUM
#define T_BIGNUM
Definition: ruby.h:487
if
if((ID)(DISPID) nameid!=nameid)
Definition: win32ole.c:770
rb_any_cmp
static int rb_any_cmp(VALUE a, VALUE b)
Definition: hash.c:80
rb_hash_reject
VALUE rb_hash_reject(VALUE hash)
Definition: hash.c:1150
rb_str_new2
#define rb_str_new2
Definition: intern.h:840
rb_obj_alloc
VALUE rb_obj_alloc(VALUE)
Definition: object.c:1801
update_arg::new_key
VALUE new_key
Definition: hash.c:392
reset_hash_type
static VALUE reset_hash_type(VALUE arg)
Definition: hash.c:2269
hash_foreach_arg
Definition: hash.c:203
HASH_PROC_DEFAULT
#define HASH_PROC_DEFAULT
Definition: internal.h:482
identhash
#define identhash
Definition: hash.c:164
encoding.h
reject_i
static int reject_i(VALUE key, VALUE value, VALUE result)
Definition: hash.c:1127
rb_hash_to_hash
static VALUE rb_hash_to_hash(VALUE hash)
Definition: hash.c:1734
hash_foreach_arg::hash
VALUE hash
Definition: hash.c:204
GET_ENVIRON
#define GET_ENVIRON(e)
Definition: hash.c:2503
env_replace
static VALUE env_replace(VALUE env, VALUE hash)
Definition: hash.c:3611
rb_str_resize
VALUE rb_str_resize(VALUE, long)
Definition: string.c:2025
rb_hash_set_default
static VALUE rb_hash_set_default(VALUE hash, VALUE ifnone)
Definition: hash.c:843
reset_hash_type_arg::hash
VALUE hash
Definition: hash.c:2264
rb_str_hash_cmp
int rb_str_hash_cmp(VALUE, VALUE)
Definition: string.c:2432
st_foreach_safe
void st_foreach_safe(st_table *table, int(*func)(ANYARGS), st_data_t a)
Definition: hash.c:189
rb_hash_modify_check
static void rb_hash_modify_check(VALUE hash)
Definition: hash.c:329
rb_define_alias
void rb_define_alias(VALUE klass, const char *name1, const char *name2)
Defines an alias of a method.
Definition: class.c:1697
rb_hash_s_create
static VALUE rb_hash_s_create(int argc, VALUE *argv, VALUE klass)
Definition: hash.c:517
origenviron
static char ** origenviron
Definition: hash.c:2476
select_i
static int select_i(VALUE key, VALUE value, VALUE result)
Definition: hash.c:1216
RSTRING_LEN
#define RSTRING_LEN(str)
Definition: ruby.h:841
rb_hash_index
static VALUE rb_hash_index(VALUE hash, VALUE value)
Definition: hash.c:953
rb_yield
VALUE rb_yield(VALUE)
Definition: vm_eval.c:942
env_index
static VALUE env_index(VALUE dmy, VALUE value)
Definition: hash.c:3505
rb_hash_dup_empty
static VALUE rb_hash_dup_empty(VALUE hash)
Definition: hash.c:304
RCLASS_M_TBL
#define RCLASS_M_TBL(c)
Definition: internal.h:295
rb_f_getenv
static VALUE rb_f_getenv(VALUE obj, VALUE name)
Definition: hash.c:2586
REALLOC_N
#define REALLOC_N(var, type, n)
Definition: ruby.h:1335
func
SSL_METHOD *(* func)(void)
Definition: ossl_ssl.c:113
util.h
TRUE
#define TRUE
Definition: nkf.h:175
T_DATA
#define T_DATA
Definition: ruby.h:492
hash_foreach_ensure
static VALUE hash_foreach_ensure(VALUE hash)
Definition: hash.c:242
rb_obj_is_proc
VALUE rb_obj_is_proc(VALUE)
Definition: proc.c:94
env_inspect
static VALUE env_inspect(void)
Definition: hash.c:3250
rb_mEnumerable
VALUE rb_mEnumerable
Definition: enum.c:20
rb_sprintf
VALUE rb_sprintf(const char *format,...)
Definition: sprintf.c:1250
rb_hash_update
static VALUE rb_hash_update(VALUE hash1, VALUE hash2)
Definition: hash.c:2156
rb_hash_delete
VALUE rb_hash_delete(VALUE hash, VALUE key)
Definition: hash.c:996
rb_hash_key
static VALUE rb_hash_key(VALUE hash, VALUE value)
Definition: hash.c:939
rb_eql
int rb_eql(VALUE, VALUE)
Definition: object.c:100
RARRAY_PTR_USE
#define RARRAY_PTR_USE(ary, ptr_name, expr)
Definition: ruby.h:894
rb_ary_delete
VALUE rb_ary_delete(VALUE ary, VALUE item)
Definition: array.c:2898
malloc
#define malloc
Definition: ripper.c:96
env_has_key
static VALUE env_has_key(VALUE env, VALUE key)
Definition: hash.c:3371
update_arg::old_value
VALUE old_value
Definition: hash.c:395
rb_hash_values
VALUE rb_hash_values(VALUE hash)
Definition: hash.c:1827
rb_hash_new
VALUE rb_hash_new(void)
Definition: hash.c:298
unsetenv
#define unsetenv(name, val)
Definition: util.h:63
rb_scan_args
int rb_scan_args(int argc, const VALUE *argv, const char *fmt,...)
Definition: class.c:1728
each_pair_i_fast
static int each_pair_i_fast(VALUE key, VALUE value)
Definition: hash.c:1602
rb_check_hash_type
VALUE rb_check_hash_type(VALUE hash)
Definition: hash.c:588
buf
unsigned char buf[MIME_BUF_SIZE]
Definition: nkf.c:4308
rb_assoc_new
VALUE rb_assoc_new(VALUE car, VALUE cdr)
Definition: array.c:616
PRIsVALUE
#define PRIsVALUE
Definition: ruby.h:137
internal.h
ID
unsigned long ID
Definition: ruby.h:89
PATH_ENV
#define PATH_ENV
Definition: defines.h:280
rb_block_arity
int rb_block_arity(void)
Definition: proc.c:860
RHASH_SIZE
#define RHASH_SIZE(h)
Definition: ruby.h:930
Qnil
#define Qnil
Definition: ruby.h:427
rb_hash_compare_by_id_p
static VALUE rb_hash_compare_by_id_p(VALUE hash)
Definition: hash.c:2464
BUILTIN_TYPE
#define BUILTIN_TYPE(x)
Definition: ruby.h:502
rb_hash_update_block_callback
static int rb_hash_update_block_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
Definition: hash.c:2106
OBJ_TAINT
#define OBJ_TAINT(x)
Definition: ruby.h:1177
VALUE
unsigned long VALUE
Definition: ruby.h:88
rb_locale_encoding
rb_encoding * rb_locale_encoding(void)
Definition: encoding.c:1294
lookup2_call
static VALUE lookup2_call(VALUE arg)
Definition: hash.c:2257
rb_funcall2
#define rb_funcall2
Definition: ruby.h:1456
result
static VALUE result
Definition: nkf.c:40
rb_w32_getenv
char * rb_w32_getenv(const char *)
Definition: win32.c:4667
rb_hash_clear
VALUE rb_hash_clear(VALUE hash)
Definition: hash.c:1324
env_values
static VALUE env_values(void)
Definition: hash.c:2973
RETURN_SIZED_ENUMERATOR
#define RETURN_SIZED_ENUMERATOR(obj, argc, argv, size_fn)
Definition: intern.h:237
clear_i
static int clear_i(VALUE key, VALUE value, VALUE dummy)
Definition: hash.c:1307
RBASIC
#define RBASIC(obj)
Definition: ruby.h:1116
rb_hash_keep_if
VALUE rb_hash_keep_if(VALUE hash)
Definition: hash.c:1297
hash_alloc
static VALUE hash_alloc(VALUE klass)
Definition: hash.c:278
strchr
char * strchr(char *, char)
rb_extend_object
void rb_extend_object(VALUE obj, VALUE module)
Definition: eval.c:1305
setenv
#define setenv(name, val)
Definition: util.h:62
env_aset
static VALUE env_aset(VALUE obj, VALUE nm, VALUE val)
Definition: hash.c:2871
env_to_a
static VALUE env_to_a(void)
Definition: hash.c:3289
st_values_check
st_index_t st_values_check(st_table *table, st_data_t *values, st_index_t size, st_data_t never)
Definition: st.c:1177
hash_equal
static VALUE hash_equal(VALUE hash1, VALUE hash2, int eql)
Definition: hash.c:1950
rb_hash_flatten
static VALUE rb_hash_flatten(int argc, VALUE *argv, VALUE hash)
Definition: hash.c:2400
rb_ensure
VALUE rb_ensure(VALUE(*b_proc)(ANYARGS), VALUE data1, VALUE(*e_proc)(ANYARGS), VALUE data2)
Definition: eval.c:839
rb_str_ellipsize
VALUE rb_str_ellipsize(VALUE, long)
Shortens str and adds three dots, an ellipsis, if it is longer than len characters.
Definition: string.c:7969
rb_proc_lambda_p
VALUE rb_proc_lambda_p(VALUE)
Definition: proc.c:234
rb_tainted_str_new2
#define rb_tainted_str_new2
Definition: intern.h:844
each_key_i
static int each_key_i(VALUE key, VALUE value)
Definition: hash.c:1562
hash_foreach_arg::func
rb_foreach_func * func
Definition: hash.c:205
shift_var
Definition: hash.c:1009
shift_var::key
VALUE key
Definition: hash.c:1010
ruby_unsetenv
void ruby_unsetenv(const char *name)
Definition: hash.c:2856
env_select
static VALUE env_select(VALUE ehash)
Definition: hash.c:3139
CHAR_BIT
#define CHAR_BIT
Definition: ruby.h:198
rb_hash_freeze
VALUE rb_hash_freeze(VALUE hash)
Definition: hash.c:62
FL_UNSET
#define FL_UNSET(x, f)
Definition: ruby.h:1173
RUBY_DTRACE_HASH_CREATE_ENABLED
#define RUBY_DTRACE_HASH_CREATE_ENABLED()
Definition: probes.h:45
update_callback_arg
Definition: hash.c:370
NORETURN
NORETURN(static void no_new_key(void))
rb_respond_to
int rb_respond_to(VALUE, ID)
Definition: vm_method.c:1639
st_hash
st_index_t st_hash(const void *ptr, size_t len, st_index_t h)
Definition: st.c:1429
env_none
static VALUE env_none(void)
Definition: hash.c:3316
env_size
static VALUE env_size(void)
Definition: hash.c:3329
delete_if_i
static int delete_if_i(VALUE key, VALUE value, VALUE hash)
Definition: hash.c:1062
has_extra_methods
static VALUE has_extra_methods(VALUE klass)
Definition: hash.c:37
getenv
#define getenv(name)
Definition: win32.c:66
recur
#define recur(fmt)
Definition: date_strptime.c:147
RSTRING_PTR
#define RSTRING_PTR(str)
Definition: ruby.h:845
update_arg::arg
st_data_t arg
Definition: hash.c:390
st_init_table_with_size
st_table * st_init_table_with_size(const struct st_hash_type *, st_index_t)
Definition: st.c:229
rb_equal
VALUE rb_equal(VALUE, VALUE)
Definition: object.c:89
inspect_i
static int inspect_i(VALUE key, VALUE value, VALUE str)
Definition: hash.c:1672
rb_hash_compare_by_id
static VALUE rb_hash_compare_by_id(VALUE hash)
Definition: hash.c:2445
size
int size
Definition: encoding.c:49
rb_funcallv
VALUE rb_funcallv(VALUE, ID, int, const VALUE *)
Calls a method.
Definition: vm_eval.c:806
equal_data
Definition: hash.c:1913
rb_hash_lookup2
VALUE rb_hash_lookup2(VALUE hash, VALUE key, VALUE def)
Definition: hash.c:708
to_hash
static VALUE to_hash(VALUE hash)
Definition: hash.c:582
INT2FIX
#define INT2FIX(i)
Definition: ruby.h:231
st_shift
int st_shift(st_table *, st_data_t *, st_data_t *)
RCLASS_SUPER
#define RCLASS_SUPER(c)
Definition: classext.h:16
rb_sourceline
int rb_sourceline(void)
Definition: vm.c:1001
hash_enum_size
static VALUE hash_enum_size(VALUE hash, VALUE args, VALUE eobj)
Definition: hash.c:1073
RARRAY_AREF
#define RARRAY_AREF(a, i)
Definition: ruby.h:901
rb_path_check
int rb_path_check(const char *path)
Definition: file.c:5360
rb_check_convert_type
VALUE rb_check_convert_type(VALUE, int, const char *, const char *)
Definition: object.c:2631
tbl_update
static int tbl_update(VALUE hash, VALUE key, int(*func)(st_data_t *key, st_data_t *val, st_data_t arg, int existing), st_data_t optional_arg)
Definition: hash.c:399
rb_block_proc
VALUE rb_block_proc(void)
Definition: proc.c:620
flatten_i
static int flatten_i(VALUE key, VALUE val, VALUE ary)
Definition: hash.c:2372
foreach_safe_arg::arg
st_data_t arg
Definition: hash.c:171
rb_str_buf_cat_ascii
VALUE rb_str_buf_cat_ascii(VALUE, const char *)
Definition: string.c:2258
ANYARGS
#define ANYARGS
Definition: defines.h:98
env_to_hash
static VALUE env_to_hash(void)
Definition: hash.c:3520
rb_hash_has_key
static VALUE rb_hash_has_key(VALUE hash, VALUE key)
Definition: hash.c:1867
rb_check_array_type
VALUE rb_check_array_type(VALUE ary)
Definition: array.c:628
rb_hash_aref
VALUE rb_hash_aref(VALUE hash, VALUE key)
Definition: hash.c:697
RHASH_UPDATE_ITER
#define RHASH_UPDATE_ITER(h, iter_lev, key, func, a)
Definition: hash.c:422
hash_foreach_iter
static int hash_foreach_iter(st_data_t key, st_data_t value, st_data_t argp, int error)
Definition: hash.c:210
rb_syserr_fail_str
void rb_syserr_fail_str(int e, VALUE mesg)
Definition: error.c:1970
hash_default_value
static VALUE hash_default_value(VALUE hash, VALUE key)
Definition: hash.c:669
FL_WB_PROTECTED
#define FL_WB_PROTECTED
Definition: ruby.h:1134
env_values_at
static VALUE env_values_at(int argc, VALUE *argv)
Definition: hash.c:3117
rb_check_string_type
VALUE rb_check_string_type(VALUE)
Definition: string.c:1679
key
uint8_t key[16]
Definition: random.c:1250
rb_any_to_s
VALUE rb_any_to_s(VALUE)
Definition: object.c:452
rb_ary_includes
VALUE rb_ary_includes(VALUE ary, VALUE item)
Definition: array.c:3818
shift_i_safe
static int shift_i_safe(VALUE key, VALUE value, VALUE arg)
Definition: hash.c:1015
rb_any_hash
static st_index_t rb_any_hash(VALUE a)
Definition: hash.c:129
LONG2FIX
#define LONG2FIX(i)
Definition: ruby.h:232
rb_gc_writebarrier_remember_promoted
void rb_gc_writebarrier_remember_promoted(VALUE obj)
Definition: gc.c:4782
RTEST
#define RTEST(v)
Definition: ruby.h:437
T_STRING
#define T_STRING
Definition: ruby.h:482
OBJ_INFECT
#define OBJ_INFECT(x, s)
Definition: ruby.h:1180
rb_check_safe_obj
void rb_check_safe_obj(VALUE)
Definition: safe.c:122
st_foreach_check
int st_foreach_check(st_table *, int(*)(ANYARGS), st_data_t, st_data_t)
Definition: st.c:942
rb_hash_uint
st_index_t rb_hash_uint(st_index_t, st_index_t)
rb_hash_invert
static VALUE rb_hash_invert(VALUE hash)
Definition: hash.c:2073
rb_filesystem_encoding
rb_encoding * rb_filesystem_encoding(void)
Definition: encoding.c:1309
rb_method_basic_definition_p
int rb_method_basic_definition_p(VALUE, ID)
Definition: vm_method.c:1573
rb_w32_osver
DWORD rb_w32_osver(void)
Definition: win32.c:296
rb_hash_hash
static VALUE rb_hash_hash(VALUE hash)
Definition: hash.c:2041
recursive_eql
static VALUE recursive_eql(VALUE hash, VALUE dt, int recur)
Definition: hash.c:1937
st_table::type
const struct st_hash_type * type
Definition: st.h:70
st.h
hash
static unsigned int hash(const char *str, unsigned int len)
Definition: lex.c:56
ST_CHECK
Definition: st.h:100
rassoc_i
static int rassoc_i(VALUE key, VALUE val, VALUE arg)
Definition: hash.c:2336
SafeStringValue
#define SafeStringValue(v)
Definition: ruby.h:545
rb_filesystem_str_new_cstr
VALUE rb_filesystem_str_new_cstr(const char *)
Definition: string.c:737
foreach_safe_arg::tbl
st_table * tbl
Definition: hash.c:169
st_keys_check
st_index_t st_keys_check(st_table *table, st_data_t *keys, st_index_t size, st_data_t never)
Definition: st.c:1136
rehash_arg::hash
VALUE hash
Definition: hash.c:611
rb_hash_merge
static VALUE rb_hash_merge(VALUE hash1, VALUE hash2)
Definition: hash.c:2245
name
const char * name
Definition: nkf.c:208
FL_SET
#define FL_SET(x, f)
Definition: ruby.h:1172
st_cleanup_safe
void st_cleanup_safe(st_table *, st_data_t)
Definition: st.c:830
st_hash_type::hash
st_index_t(* hash)(ANYARGS)
Definition: st.h:57
rb_hash_values_at
VALUE rb_hash_values_at(int argc, VALUE *argv, VALUE hash)
Definition: hash.c:1204
hash_aset
static int hash_aset(st_data_t *key, st_data_t *val, struct update_arg *arg, int existing)
Definition: hash.c:1340
rb_str_new_frozen
VALUE rb_str_new_frozen(VALUE)
Definition: string.c:833
HASH_DELETED
#define HASH_DELETED
Definition: internal.h:481
rb_inspect
VALUE rb_inspect(VALUE)
Definition: object.c:470
st_copy
st_table * st_copy(st_table *)
Definition: st.c:663
hash_foreach_arg::arg
VALUE arg
Definition: hash.c:206
key_i
static int key_i(VALUE key, VALUE value, VALUE arg)
Definition: hash.c:913
ST_DATA_COMPATIBLE_P
#define ST_DATA_COMPATIBLE_P(type)
Definition: st.h:66
rb_hash_rehash
static VALUE rb_hash_rehash(VALUE hash)
Definition: hash.c:645
st_foreach_func
int st_foreach_func(st_data_t, st_data_t, st_data_t)
Definition: hash.c:166
rb_env_clear
VALUE rb_env_clear(void)
Definition: hash.c:3216
env_replace_i
static int env_replace_i(VALUE key, VALUE val, VALUE keys)
Definition: hash.c:3594
st_clear
void st_clear(st_table *)
Definition: st.c:308
update_func_arg::func
rb_hash_update_func * func
Definition: hash.c:2172
rb_hash_delete_if
VALUE rb_hash_delete_if(VALUE hash)
Definition: hash.c:1094
RHash
Definition: ruby.h:920
rb_check_frozen
#define rb_check_frozen(obj)
Definition: intern.h:277
ruby_register_rollback_func_for_ensure
void ruby_register_rollback_func_for_ensure(VALUE(*ensure_func)(ANYARGS), VALUE(*rollback_func)(ANYARGS))
Definition: cont.c:947
rb_proc_arity
int rb_proc_arity(VALUE)
Definition: proc.c:851
env_empty_p
static VALUE env_empty_p(void)
Definition: hash.c:3348
st_init_table
st_table * st_init_table(const struct st_hash_type *)
Definition: st.c:266
rb_hash_assoc
VALUE rb_hash_assoc(VALUE hash, VALUE key)
Definition: hash.c:2303
to_a_i
static int to_a_i(VALUE key, VALUE value, VALUE ary)
Definition: hash.c:1642
rb_obj_freeze
VALUE rb_obj_freeze(VALUE)
Definition: object.c:1076
rb_copy_generic_ivar
void rb_copy_generic_ivar(VALUE, VALUE)
Definition: variable.c:1049
SPECIAL_CONST_P
#define SPECIAL_CONST_P(x)
Definition: ruby.h:1165
xfree
void void xfree(void *)
rb_tainted_str_new
VALUE rb_tainted_str_new(const char *, long)
Definition: string.c:589
RHASH_EMPTY_P
#define RHASH_EMPTY_P(h)
Definition: ruby.h:931
hash_recursive
static VALUE hash_recursive(VALUE obj, VALUE arg, int recurse)
Definition: hash.c:99
SYMBOL_P
#define SYMBOL_P(x)
Definition: ruby.h:354
hash_foreach_ensure_rollback
static VALUE hash_foreach_ensure_rollback(VALUE hash)
Definition: hash.c:235
env
#define env
env_reject_bang
static VALUE env_reject_bang(VALUE ehash)
Definition: hash.c:3069
env_fetch
static VALUE env_fetch(int argc, VALUE *argv)
Definition: hash.c:2627
FIX2LONG
#define FIX2LONG(x)
Definition: ruby.h:345
Qundef
#define Qundef
Definition: ruby.h:428
rb_hash_select
VALUE rb_hash_select(VALUE hash)
Definition: hash.c:1239
env_has_value
static VALUE env_has_value(VALUE dmy, VALUE obj)
Definition: hash.c:3412
env_update
static VALUE env_update(VALUE env, VALUE hash)
Definition: hash.c:3648
st_delete_safe
int st_delete_safe(st_table *, st_data_t *, st_data_t *, st_data_t)
RGENGC_WB_PROTECTED_HASH
#define RGENGC_WB_PROTECTED_HASH
Definition: ruby.h:714
st_table::num_entries
st_index_t num_entries
Definition: st.h:85
rb_hash_delete_key
static VALUE rb_hash_delete_key(VALUE hash, VALUE key)
Definition: hash.c:960
rb_define_method
void rb_define_method(VALUE klass, const char *name, VALUE(*func)(ANYARGS), int argc)
Definition: class.c:1488
ruby_verbose
#define ruby_verbose
Definition: ruby.h:1475
rb_ascii8bit_encindex
#define rb_ascii8bit_encindex()
Definition: internal.h:402
ruby_setenv
void ruby_setenv(const char *name, const char *value)
Definition: hash.c:2747
rb_warn
void rb_warn(const char *fmt,...)
Definition: error.c:223
free
free(psz)
rb_obj_instance_variables
#define rb_obj_instance_variables(object)
Definition: generator.h:21
rb_eArgError
VALUE rb_eArgError
Definition: error.c:549
default_proc_arity_check
static void default_proc_arity_check(VALUE proc)
Definition: hash.c:430
update_arg::hash
VALUE hash
Definition: hash.c:391
hash_tbl
static struct st_table * hash_tbl(VALUE hash)
Definition: hash.c:335
T_MASK
#define T_MASK
Definition: md5.c:131
rb_hash_start
st_index_t rb_hash_start(st_index_t)
Definition: random.c:1296
rb_hash_update_callback
static int rb_hash_update_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
Definition: hash.c:2082
RB_OBJ_WRITE
#define RB_OBJ_WRITE(a, slot, b)
Definition: ruby.h:1213
crt_externs.h
rb_hash_rassoc
VALUE rb_hash_rassoc(VALUE hash, VALUE obj)
Definition: hash.c:2361
rb_hash_to_a
static VALUE rb_hash_to_a(VALUE hash)
Definition: hash.c:1660
argv
char ** argv
Definition: ruby.c:132
rb_hash_initialize
static VALUE rb_hash_initialize(int argc, VALUE *argv, VALUE hash)
Definition: hash.c:476
rb_hash_update_func_callback
static int rb_hash_update_func_callback(st_data_t *key, st_data_t *value, struct update_arg *arg, int existing)
Definition: hash.c:2176
env_str_new
static VALUE env_str_new(const char *ptr, long len)
Definition: hash.c:2515
rb_hash_default_proc
static VALUE rb_hash_default_proc(VALUE hash)
Definition: hash.c:867
RUBY_DTRACE_HASH_CREATE
#define RUBY_DTRACE_HASH_CREATE(arg0, arg1, arg2)
Definition: probes.h:46
rb_hash_inspect
static VALUE rb_hash_inspect(VALUE hash)
Definition: hash.c:1719
update_func_arg::hash
VALUE hash
Definition: hash.c:2170
rb_ary_set_len
void rb_ary_set_len(VALUE ary, long len)
Definition: array.c:1592
rb_str_new
VALUE rb_str_new(const char *, long)
Definition: string.c:534
rb_obj_class
VALUE rb_obj_class(VALUE)
Definition: object.c:226