mirror of
https://github.com/mruby/mruby
synced 2026-06-08 16:11:16 +00:00
allow irep to be GCed
This commit is contained in:
@@ -37,7 +37,7 @@ typedef struct mrb_irep {
|
||||
uint16_t *lines;
|
||||
struct mrb_irep_debug_info* debug_info;
|
||||
|
||||
size_t ilen, plen, slen, rlen;
|
||||
size_t ilen, plen, slen, rlen, refcnt;
|
||||
} mrb_irep;
|
||||
|
||||
#define MRB_ISEQ_NO_FREE 1
|
||||
@@ -45,6 +45,8 @@ typedef struct mrb_irep {
|
||||
mrb_irep *mrb_add_irep(mrb_state *mrb);
|
||||
mrb_value mrb_load_irep(mrb_state*, const uint8_t*);
|
||||
void mrb_irep_free(mrb_state*, struct mrb_irep*);
|
||||
void mrb_irep_incref(mrb_state*, struct mrb_irep*);
|
||||
void mrb_irep_decref(mrb_state*, struct mrb_irep*);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
} /* extern "C" { */
|
||||
|
||||
@@ -640,6 +640,16 @@ obj_free(mrb_state *mrb, struct RBasic *obj)
|
||||
mrb_gc_free_str(mrb, (struct RString*)obj);
|
||||
break;
|
||||
|
||||
case MRB_TT_PROC:
|
||||
{
|
||||
struct RProc *p = (struct RProc*)obj;
|
||||
|
||||
if (!MRB_PROC_CFUNC_P(p) && p->body.irep) {
|
||||
mrb_irep_decref(mrb, p->body.irep);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case MRB_TT_RANGE:
|
||||
mrb_free(mrb, ((struct RRange*)obj)->edges);
|
||||
break;
|
||||
|
||||
+5
-1
@@ -22,6 +22,7 @@ mrb_proc_new(mrb_state *mrb, mrb_irep *irep)
|
||||
p->target_class = (mrb->c->ci) ? mrb->c->ci->target_class : 0;
|
||||
p->body.irep = irep;
|
||||
p->env = 0;
|
||||
mrb_irep_incref(mrb, irep);
|
||||
|
||||
return p;
|
||||
}
|
||||
@@ -80,6 +81,9 @@ mrb_proc_copy(struct RProc *a, struct RProc *b)
|
||||
{
|
||||
a->flags = b->flags;
|
||||
a->body = b->body;
|
||||
if (!MRB_PROC_CFUNC_P(a)) {
|
||||
a->body.irep->refcnt++;
|
||||
};
|
||||
a->target_class = b->target_class;
|
||||
a->env = b->env;
|
||||
}
|
||||
@@ -181,7 +185,7 @@ void
|
||||
mrb_init_proc(mrb_state *mrb)
|
||||
{
|
||||
struct RProc *m;
|
||||
mrb_irep *call_irep = (mrb_irep *)mrb_alloca(mrb, sizeof(mrb_irep));
|
||||
mrb_irep *call_irep = (mrb_irep *)mrb_malloc(mrb, sizeof(mrb_irep));
|
||||
static const mrb_irep mrb_irep_zero = { 0 };
|
||||
|
||||
if (call_irep == NULL)
|
||||
|
||||
+19
@@ -106,6 +106,21 @@ mrb_open(void)
|
||||
void mrb_free_symtbl(mrb_state *mrb);
|
||||
void mrb_free_heap(mrb_state *mrb);
|
||||
|
||||
void
|
||||
mrb_irep_incref(mrb_state *mrb, mrb_irep *irep)
|
||||
{
|
||||
irep->refcnt++;
|
||||
}
|
||||
|
||||
void
|
||||
mrb_irep_decref(mrb_state *mrb, mrb_irep *irep)
|
||||
{
|
||||
irep->refcnt--;
|
||||
if (irep->refcnt == 0) {
|
||||
mrb_irep_free(mrb, irep);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
mrb_irep_free(mrb_state *mrb, mrb_irep *irep)
|
||||
{
|
||||
@@ -119,6 +134,9 @@ mrb_irep_free(mrb_state *mrb, mrb_irep *irep)
|
||||
}
|
||||
mrb_free(mrb, irep->pool);
|
||||
mrb_free(mrb, irep->syms);
|
||||
for (i=0; i<irep->rlen; i++) {
|
||||
mrb_irep_decref(mrb, irep->reps[i]);
|
||||
}
|
||||
mrb_free(mrb, irep->reps);
|
||||
mrb_free(mrb, (void *)irep->filename);
|
||||
mrb_free(mrb, irep->lines);
|
||||
@@ -163,6 +181,7 @@ mrb_add_irep(mrb_state *mrb)
|
||||
|
||||
irep = (mrb_irep *)mrb_malloc(mrb, sizeof(mrb_irep));
|
||||
*irep = mrb_irep_zero;
|
||||
irep->refcnt = 1;
|
||||
|
||||
return irep;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user