Example #1
0
/*
   destroy the given context and associated memory files (if not in use by a shared context)
   exit interpreter if all contexts are destroyed.
 */
XPAPI void xpost_destroy(Xpost_Context *ctx)
{

    if (!xpost_dict_known_key(ctx, ctx->gl, xpost_stack_bottomup_fetch(ctx->lo, ctx->ds, 0), xpost_name_cons(ctx, "QUIET")))
    {
        printf("bye!\n");
        fflush(NULL);
    }
    /*xpost_garbage_collect(itpdata->ctab->gl, 1, 1); */
    /*xpost_garbage_collect(itpdata->ctab->lo, 1, 1); */
#if 0
#ifndef XPOST_NO_GC
    xpost_garbage_collect(ctx->gl, 1, 1);
    xpost_garbage_collect(ctx->lo, 1, 0);
#endif
#endif

    /* exit if all contexts are destroyed */
    /*xpost_interpreter_exit(itpdata); */
    /*free(itpdata); */
}
Example #2
0
/*
   determine GLOBAL/LOCAL
   clear all marks,
   mark all root stacks,
   sweep.
   return reclaimed size or -1 if error occured.
 */
int xpost_garbage_collect(Xpost_Memory_File *mem, int dosweep, int markall)
{
    unsigned int i;
    unsigned int *cid;
    Xpost_Context *ctx = NULL;
    int isglobal;
    unsigned int sz = 0;
    unsigned int ad;
    int ret;

    if (mem->interpreter_get_initializing()) /* do not collect while initializing */
        return 0;

    /* printf("\ncollect:\n"); */

    /* determine global/local */
    isglobal = 0;
    ret = xpost_memory_table_get_addr(mem,
            XPOST_MEMORY_TABLE_SPECIAL_CONTEXT_LIST, &ad);
    if (!ret)
    {
        XPOST_LOG_ERR("cannot load context list");
        return -1;
    }
    cid = (void *)(mem->base + ad);
    for (i = 0; i < MAXCONTEXT && cid[i]; i++) {
        ctx = mem->interpreter_cid_get_context(cid[i]);
        if (ctx->state != 0) {
            if (mem == ctx->gl) {
                isglobal = 1;
                break;
            }
        }
    }
#ifdef DEBUG_GC
    printf("using cid=%d\n", ctx->id);
#endif

    if (isglobal) {
        return 0; /* do not perform global collections at this time */

        _xpost_garbage_unmark(mem);

        ret = xpost_memory_table_get_addr(mem,
                XPOST_MEMORY_TABLE_SPECIAL_SAVE_STACK, &ad);
        if (!ret)
        {
            XPOST_LOG_ERR("cannot load save stack for %s memory",
                    mem == ctx->gl? "global" : "local");
            return -1;
        }
        if (!_xpost_garbage_mark_save(ctx, mem, ad))
            return -1;
        ret = xpost_memory_table_get_addr(mem,
                XPOST_MEMORY_TABLE_SPECIAL_NAME_STACK, &ad);
        if (!ret)
        {
            XPOST_LOG_ERR("cannot load name stack for %s memory",
                    mem == ctx->gl? "global" : "local");
            return -1;
        }
        if (!_xpost_garbage_mark_stack(ctx, mem, ad, markall))
            return -1;

        for (i = 0; i < MAXCONTEXT && cid[i]; i++) {
            ctx = mem->interpreter_cid_get_context(cid[i]);
            xpost_garbage_collect(ctx->lo, 0, markall);
        }

    } else { /* local */
        //printf("collect!\n");
        _xpost_garbage_unmark(mem);

        ret = xpost_memory_table_get_addr(mem,
                XPOST_MEMORY_TABLE_SPECIAL_SAVE_STACK, &ad);
        if (!ret)
        {
            XPOST_LOG_ERR("cannot load save stack for %s memory",
                    mem == ctx->gl? "global" : "local");
            return -1;
        }
        if (!_xpost_garbage_mark_save(ctx, mem, ad))
            return -1;
        ret = xpost_memory_table_get_addr(mem, 
                XPOST_MEMORY_TABLE_SPECIAL_NAME_STACK, &ad);
        if (!ret)
        {
            XPOST_LOG_ERR("cannot load name stack for %s memory",
                    mem == ctx->gl? "global" : "local");
            return -1;
        }
#ifdef DEBUG_GC
        printf("marking name stack\n");
#endif
        if (!_xpost_garbage_mark_stack(ctx, mem, ad, markall))
            return -1;

        for (i = 0; i < MAXCONTEXT && cid[i]; i++) {
            ctx = mem->interpreter_cid_get_context(cid[i]);

#ifdef DEBUG_GC
            printf("marking os\n");
#endif
            if (!_xpost_garbage_mark_stack(ctx, mem, ctx->os, markall))
                return -1;

#ifdef DEBUG_GC
            printf("marking ds\n");
#endif
            if (!_xpost_garbage_mark_stack(ctx, mem, ctx->ds, markall))
                return -1;

#ifdef DEBUG_GC
            printf("marking es\n");
#endif
            if (!_xpost_garbage_mark_stack(ctx, mem, ctx->es, markall))
                return -1;

#ifdef DEBUG_GC
            printf("marking hold\n");
#endif
            if (!_xpost_garbage_mark_stack(ctx, mem, ctx->hold, markall))
                return -1;
#ifdef DEBUG_GC
            printf("marking window device\n");
#endif
            if (!_xpost_garbage_mark_object(ctx, mem, ctx->window_device, markall))
                return -1;
        }
    }

    if (dosweep) {
#ifdef DEBUG_GC
        printf("sweep\n");
#endif
        sz += _xpost_garbage_sweep(mem);
        if (isglobal) {
            for (i = 0; i < MAXCONTEXT && cid[i]; i++) {
                ctx = mem->interpreter_cid_get_context(cid[i]);
                sz += _xpost_garbage_sweep(ctx->lo);
            }
        }
    }

    printf("collect recovered %u bytes\n", sz);
    return sz;
}