void potion_test_allocated(CuTest *T) { struct PNMemory *M = P->mem; void *prev = NULL; void *scanptr = (void *)((char *)M->birth_lo + PN_ALIGN(sizeof(struct PNMemory), 8)); while ((PN)scanptr < (PN)M->birth_cur) { if (((struct PNFwd *)scanptr)->fwd != POTION_FWD && ((struct PNFwd *)scanptr)->fwd != POTION_COPIED) { if (((struct PNObject *)scanptr)->vt > PN_TUSER) { vPN(Object) o = (struct PNObject *)scanptr; fprintf(stderr, "error: scanning heap from %p to %p\n", M->birth_lo, M->birth_cur); fprintf(stderr, "%p in %s region\n", scanptr, IS_GC_PROTECTED(scanptr) ? "protected" : IN_BIRTH_REGION(scanptr) ? "birth" : IN_OLDER_REGION(scanptr) ? "older" : "gc"); fprintf(stderr, "%p { uniq:0x%08x vt:0x%08x ivars[0]:0x%08lx type:0x%x}\n", scanptr, o->uniq, o->vt, o->ivars[0], potion_type((PN)scanptr)); fprintf(stderr, "prev %p: size=%d, type:0x%x (%s)\n", prev, potion_type_size(P, prev), potion_type((PN)prev), AS_STR(PN_VTABLE(PN_TYPE((PN)prev)))); #ifdef DEBUG //potion_dump_stack(P); #endif } CuAssert(T, "wrong type for allocated object", ((struct PNObject *)scanptr)->vt <= PN_TUSER); } prev = scanptr; scanptr = (void *)((char *)scanptr + potion_type_size(P, scanptr)); CuAssert(T, "allocated object goes beyond GC pointer", (PN)scanptr <= (PN)M->birth_cur); } }
static inline char *potion_type_name(Potion *P, PN obj) { obj = potion_fwd(obj); return PN_IS_PTR(obj) ? AS_STR(potion_send(PN_VTABLE(PN_TYPE(obj)), PN_string)) : PN_IS_NIL(obj) ? "nil" : PN_IS_NUM(obj) ? "Number" : "Boolean"; }