summaryrefslogtreecommitdiffhomepage
path: root/include
diff options
context:
space:
mode:
authorYukihiro "Matz" Matsumoto <[email protected]>2020-11-10 21:56:42 +0900
committerGitHub <[email protected]>2020-11-10 21:56:42 +0900
commit6a5e97b448e82fe55348ab1a7e96b70b2c45f6c1 (patch)
tree89abbf8aaa8a4997648686b3d455db7e2373f206 /include
parentcc20c5ca3a5da0561be8644b7513d947badb1c56 (diff)
parentf2d8db39be487fcd710c5c5844ae47d3a6920e70 (diff)
downloadmruby-6a5e97b448e82fe55348ab1a7e96b70b2c45f6c1.tar.gz
mruby-6a5e97b448e82fe55348ab1a7e96b70b2c45f6c1.zip
Merge pull request #5121 from shuujii/reduce-memory-usage-of-Hash-object
Reduce memory usage of Hash object
Diffstat (limited to 'include')
-rw-r--r--include/mruby/hash.h47
1 files changed, 34 insertions, 13 deletions
diff --git a/include/mruby/hash.h b/include/mruby/hash.h
index 7dab4a85c..c2af3b976 100644
--- a/include/mruby/hash.h
+++ b/include/mruby/hash.h
@@ -14,10 +14,22 @@
*/
MRB_BEGIN_DECL
+/* offset of `iv` must be 3 words */
struct RHash {
MRB_OBJECT_HEADER;
+#ifdef MRB_64BIT
+ uint32_t size;
struct iv_tbl *iv;
- struct htable *ht;
+ uint32_t ea_capa;
+ uint32_t ea_n_used;
+#else
+ struct iv_tbl *iv;
+ uint32_t size;
+#endif
+ union {
+ struct hash_entry *ea;
+ struct hash_table *ht;
+ };
};
#define mrb_hash_ptr(v) ((struct RHash*)(mrb_ptr(v)))
@@ -179,8 +191,9 @@ MRB_API mrb_value mrb_hash_clear(mrb_state *mrb, mrb_value hash);
MRB_API mrb_int mrb_hash_size(mrb_state *mrb, mrb_value hash);
/*
- * Copies the hash.
- *
+ * Copies the hash. This function does NOT copy the instance variables
+ * (except for the default value). Use mrb_obj_dup() to copy the instance
+ * variables as well.
*
* @param mrb The mruby state reference.
* @param hash The target hash.
@@ -198,16 +211,24 @@ MRB_API mrb_value mrb_hash_dup(mrb_state *mrb, mrb_value hash);
*/
MRB_API void mrb_hash_merge(mrb_state *mrb, mrb_value hash1, mrb_value hash2);
-/* RHASH_TBL allocates st_table if not available. */
-#define RHASH(obj) ((struct RHash*)(mrb_ptr(obj)))
-#define RHASH_TBL(h) (RHASH(h)->ht)
-#define RHASH_IFNONE(h) mrb_iv_get(mrb, (h), MRB_SYM(ifnone))
-#define RHASH_PROCDEFAULT(h) RHASH_IFNONE(h)
-
-#define MRB_HASH_DEFAULT 1
-#define MRB_HASH_PROC_DEFAULT 2
-#define MRB_RHASH_DEFAULT_P(h) (RHASH(h)->flags & MRB_HASH_DEFAULT)
-#define MRB_RHASH_PROCDEFAULT_P(h) (RHASH(h)->flags & MRB_HASH_PROC_DEFAULT)
+#define RHASH(hash) ((struct RHash*)(mrb_ptr(hash)))
+#define RHASH_IFNONE(hash) mrb_iv_get(mrb, (hash), MRB_SYM(ifnone))
+#define RHASH_PROCDEFAULT(hash) RHASH_IFNONE(hash)
+
+#define MRB_HASH_IB_BIT_BIT 5
+#define MRB_HASH_AR_EA_CAPA_BIT 5
+#define MRB_HASH_IB_BIT_SHIFT 0
+#define MRB_HASH_AR_EA_CAPA_SHIFT 0
+#define MRB_HASH_AR_EA_N_USED_SHIFT MRB_HASH_AR_EA_CAPA_BIT
+#define MRB_HASH_SIZE_FLAGS_SHIFT (MRB_HASH_AR_EA_CAPA_BIT * 2)
+#define MRB_HASH_IB_BIT_MASK ((1 << MRB_HASH_IB_BIT_BIT) - 1)
+#define MRB_HASH_AR_EA_CAPA_MASK ((1 << MRB_HASH_AR_EA_CAPA_BIT) - 1)
+#define MRB_HASH_AR_EA_N_USED_MASK (MRB_HASH_AR_EA_CAPA_MASK << MRB_HASH_AR_EA_N_USED_SHIFT)
+#define MRB_HASH_DEFAULT (1 << (MRB_HASH_SIZE_FLAGS_SHIFT + 0))
+#define MRB_HASH_PROC_DEFAULT (1 << (MRB_HASH_SIZE_FLAGS_SHIFT + 1))
+#define MRB_HASH_HT (1 << (MRB_HASH_SIZE_FLAGS_SHIFT + 2))
+#define MRB_RHASH_DEFAULT_P(hash) (RHASH(hash)->flags & MRB_HASH_DEFAULT)
+#define MRB_RHASH_PROCDEFAULT_P(hash) (RHASH(hash)->flags & MRB_HASH_PROC_DEFAULT)
/* GC functions */
void mrb_gc_mark_hash(mrb_state*, struct RHash*);