void * pic_realloc(pic_state *pic, void *ptr, size_t size) { ptr = pic->allocf(pic->userdata, ptr, size); if (ptr == NULL && size > 0) { pic_panic(pic, "memory exhausted"); } return ptr; }
struct pic_proc * pic_pop_handler(pic_state *pic) { if (pic->xp == pic->xpbase) { pic_panic(pic, "no exception handler registered"); } return *--pic->xp; }
pic_value pic_raise_continuable(pic_state *pic, pic_value err) { pic_value stack, exc = pic_ref(pic, "picrin.base", "current-exception-handlers"); stack = pic_call(pic, exc, 0); if (pic_nil_p(pic, stack)) { pic_panic(pic, "no exception handler"); } return pic_dynamic_bind(pic, exc, pic_cdr(pic, stack), pic_lambda(pic, raise_continuable, 2, pic_car(pic, stack), err)); }
void * pic_calloc(pic_state *pic, size_t count, size_t size) { void *ptr; size *= count; ptr = pic->allocf(pic->userdata, NULL, size); if (ptr == NULL && size > 0) { pic_panic(pic, "memory exhausted"); } memset(ptr, 0, size); return ptr; }
void pic_raise(pic_state *pic, pic_value err) { pic_value stack, exc = pic_ref(pic, "picrin.base", "current-exception-handlers"); stack = pic_call(pic, exc, 0); if (pic_nil_p(pic, stack)) { pic_panic(pic, "no exception handler"); } pic_dynamic_bind(pic, exc, pic_cdr(pic, stack), pic_lambda(pic, raise, 2, pic_car(pic, stack), err)); PIC_UNREACHABLE(); }
pic_value pic_raise_continuable(pic_state *pic, pic_value err) { struct pic_proc *handler; pic_value v; if (pic->xp == pic->xpbase) { pic_panic(pic, "no exception handler registered"); } handler = *--pic->xp; pic_gc_protect(pic, pic_obj_value(handler)); v = pic_apply1(pic, handler, err); *pic->xp++ = handler; return v; }
struct object * pic_obj_alloc_unsafe(pic_state *pic, int type) { struct object *obj; if (pic->heap->pages == NULL) { heap_morecore(pic); } #if GC_STRESS pic_gc(pic); #endif obj = obj_alloc(pic, type); if (obj == NULL) { pic_gc(pic); obj = obj_alloc(pic, type); if (obj == NULL) pic_panic(pic, "GC memory exhausted"); } return obj; }