use khash for registers
This commit is contained in:
		
							parent
							
								
									0fb87449fc
								
							
						
					
					
						commit
						11ed51b236
					
				|  | @ -622,16 +622,20 @@ gc_mark_phase(pic_state *pic) | ||||||
|   do { |   do { | ||||||
|     struct pic_object *key; |     struct pic_object *key; | ||||||
|     pic_value val; |     pic_value val; | ||||||
|     xh_entry *it; |     khiter_t it; | ||||||
|  |     khash_t(reg) *h; | ||||||
|     struct pic_reg *reg; |     struct pic_reg *reg; | ||||||
| 
 | 
 | ||||||
|     j = 0; |     j = 0; | ||||||
|     reg = pic->regs; |     reg = pic->regs; | ||||||
| 
 | 
 | ||||||
|     while (reg != NULL) { |     while (reg != NULL) { | ||||||
|       for (it = xh_begin(®->hash); it != NULL; it = xh_next(it)) { |       h = ®->hash; | ||||||
|         key = xh_key(it, struct pic_object *); |       for (it = kh_begin(h); it != kh_end(h); ++it) { | ||||||
|         val = xh_val(it, pic_value); |         if (! kh_exist(h, it)) | ||||||
|  |           continue; | ||||||
|  |         key = kh_key(h, it); | ||||||
|  |         val = kh_val(h, it); | ||||||
|         if (gc_obj_is_marked(key) && gc_value_need_mark(val)) { |         if (gc_obj_is_marked(key) && gc_value_need_mark(val)) { | ||||||
|           gc_mark(pic, val); |           gc_mark(pic, val); | ||||||
|           ++j; |           ++j; | ||||||
|  | @ -718,7 +722,7 @@ gc_finalize_object(pic_state *pic, struct pic_object *obj) | ||||||
|   } |   } | ||||||
|   case PIC_TT_REG: { |   case PIC_TT_REG: { | ||||||
|     struct pic_reg *reg = (struct pic_reg *)obj; |     struct pic_reg *reg = (struct pic_reg *)obj; | ||||||
|     xh_destroy(®->hash); |     kh_destroy(reg, ®->hash); | ||||||
|     break; |     break; | ||||||
|   } |   } | ||||||
|   case PIC_TT_CP: { |   case PIC_TT_CP: { | ||||||
|  | @ -813,14 +817,17 @@ static void | ||||||
| gc_sweep_phase(pic_state *pic) | gc_sweep_phase(pic_state *pic) | ||||||
| { | { | ||||||
|   struct heap_page *page = pic->heap->pages; |   struct heap_page *page = pic->heap->pages; | ||||||
|   xh_entry *it, *next; |   khiter_t it; | ||||||
|  |   khash_t(reg) *h; | ||||||
| 
 | 
 | ||||||
|   /* registries */ |   /* registries */ | ||||||
|   while (pic->regs != NULL) { |   while (pic->regs != NULL) { | ||||||
|     for (it = xh_begin(&pic->regs->hash); it != NULL; it = next) { |     h = &pic->regs->hash; | ||||||
|       next = xh_next(it); |     for (it = kh_begin(h); it != kh_end(h); ++it) { | ||||||
|       if (! gc_obj_is_marked(xh_key(it, struct pic_object *))) { |       if (! kh_exist(h, it)) | ||||||
|         xh_del_ptr(&pic->regs->hash, xh_key(it, struct pic_object *)); |         continue; | ||||||
|  |       if (! gc_obj_is_marked(kh_key(h, it))) { | ||||||
|  |         kh_del(reg, h, it); | ||||||
|       } |       } | ||||||
|     } |     } | ||||||
|     pic->regs = pic->regs->prev; |     pic->regs = pic->regs->prev; | ||||||
|  |  | ||||||
|  | @ -9,9 +9,11 @@ | ||||||
| extern "C" { | extern "C" { | ||||||
| #endif | #endif | ||||||
| 
 | 
 | ||||||
|  | KHASH_DECLARE(reg, void *, pic_value) | ||||||
|  | 
 | ||||||
| struct pic_reg { | struct pic_reg { | ||||||
|   PIC_OBJECT_HEADER |   PIC_OBJECT_HEADER | ||||||
|   xhash hash; |   khash_t(reg) hash; | ||||||
|   struct pic_reg *prev;         /* for GC */ |   struct pic_reg *prev;         /* for GC */ | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -4,6 +4,8 @@ | ||||||
| 
 | 
 | ||||||
| #include "picrin.h" | #include "picrin.h" | ||||||
| 
 | 
 | ||||||
|  | KHASH_DEFINE(reg, void *, pic_value, kh_ptr_hash_func, kh_ptr_hash_equal) | ||||||
|  | 
 | ||||||
| struct pic_reg * | struct pic_reg * | ||||||
| pic_make_reg(pic_state *pic) | pic_make_reg(pic_state *pic) | ||||||
| { | { | ||||||
|  | @ -11,7 +13,7 @@ pic_make_reg(pic_state *pic) | ||||||
| 
 | 
 | ||||||
|   reg = (struct pic_reg *)pic_obj_alloc(pic, sizeof(struct pic_reg), PIC_TT_REG); |   reg = (struct pic_reg *)pic_obj_alloc(pic, sizeof(struct pic_reg), PIC_TT_REG); | ||||||
|   reg->prev = NULL; |   reg->prev = NULL; | ||||||
|   xh_init_ptr(®->hash, sizeof(pic_value)); |   kh_init(reg, ®->hash); | ||||||
| 
 | 
 | ||||||
|   return reg; |   return reg; | ||||||
| } | } | ||||||
|  | @ -19,35 +21,44 @@ pic_make_reg(pic_state *pic) | ||||||
| pic_value | pic_value | ||||||
| pic_reg_ref(pic_state *pic, struct pic_reg *reg, void *key) | pic_reg_ref(pic_state *pic, struct pic_reg *reg, void *key) | ||||||
| { | { | ||||||
|   xh_entry *e; |   khash_t(reg) *h = ®->hash; | ||||||
|  |   khiter_t it; | ||||||
| 
 | 
 | ||||||
|   e = xh_get_ptr(®->hash, key); |   it = kh_get(reg, h, key); | ||||||
|   if (! e) { |   if (it == kh_end(h)) { | ||||||
|     pic_errorf(pic, "element not found for a key: ~s", pic_obj_value(key)); |     pic_errorf(pic, "element not found for a key: ~s", pic_obj_value(key)); | ||||||
|   } |   } | ||||||
|   return xh_val(e, pic_value); |   return kh_val(h, it); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void | void | ||||||
| pic_reg_set(pic_state PIC_UNUSED(*pic), struct pic_reg *reg, void *key, pic_value val) | pic_reg_set(pic_state PIC_UNUSED(*pic), struct pic_reg *reg, void *key, pic_value val) | ||||||
| { | { | ||||||
|   xh_put_ptr(®->hash, key, &val); |   khash_t(reg) *h = ®->hash; | ||||||
|  |   int ret; | ||||||
|  |   khiter_t it; | ||||||
|  | 
 | ||||||
|  |   it = kh_put(reg, h, key, &ret); | ||||||
|  |   kh_val(h, it) = val; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| bool | bool | ||||||
| pic_reg_has(pic_state PIC_UNUSED(*pic), struct pic_reg *reg, void *key) | pic_reg_has(pic_state PIC_UNUSED(*pic), struct pic_reg *reg, void *key) | ||||||
| { | { | ||||||
|   return xh_get_ptr(®->hash, key) != NULL; |   return kh_get(reg, ®->hash, key) != kh_end(®->hash); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void | void | ||||||
| pic_reg_del(pic_state *pic, struct pic_reg *reg, void *key) | pic_reg_del(pic_state *pic, struct pic_reg *reg, void *key) | ||||||
| { | { | ||||||
|   if (xh_get_ptr(®->hash, key) == NULL) { |   khash_t(reg) *h = ®->hash; | ||||||
|  |   khiter_t it; | ||||||
|  | 
 | ||||||
|  |   it = kh_get(reg, h, key); | ||||||
|  |   if (it == kh_end(h)) { | ||||||
|     pic_errorf(pic, "no slot named ~s found in register", pic_obj_value(key)); |     pic_errorf(pic, "no slot named ~s found in register", pic_obj_value(key)); | ||||||
|   } |   } | ||||||
| 
 |   kh_del(reg, h, it); | ||||||
|   xh_del_ptr(®->hash, key); |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
		Loading…
	
		Reference in New Issue
	
	 Yuichi Nishiwaki
						Yuichi Nishiwaki