Exemplo n.º 1
0
static MR_bool
MR_find_zone_for_det_ptr(const MR_Word *ptr, MR_Context **ctxt_ptr,
                         MR_MemoryZone **zone_ptr, int *zone_num_ptr)
{
#ifdef  MR_USE_MINIMAL_MODEL_OWN_STACKS

    const MR_Dlist      *item;
    MR_Context          *ctxt;

    if (MR_find_zone_for_det_ptr_in_context(ptr,
                                            MR_ENGINE(MR_eng_main_context), zone_ptr, zone_num_ptr))
    {
        if (ctxt_ptr != NULL) {
            *ctxt_ptr = MR_ENGINE(MR_eng_main_context);
        }

        return MR_TRUE;
    }

    MR_for_dlist(item, MR_ENGINE(MR_eng_gen_contexts)) {
        ctxt = (MR_Context *) MR_dlist_data(item);
        if (MR_find_zone_for_det_ptr_in_context(ptr, ctxt,
                                                zone_ptr, zone_num_ptr))
        {
            if (ctxt_ptr != NULL) {
                *ctxt_ptr = ctxt;
            }

            return MR_TRUE;
        }
    }
Exemplo n.º 2
0
void
MR_agc_dump_roots(MR_RootList roots)
{
#ifndef MR_HIGHLEVEL_CODE
    MR_Word saved_regs[MR_MAX_FAKE_REG];
    MR_Float saved_f_regs[MR_MAX_VIRTUAL_F_REG];
#endif

    fflush(NULL);
    fprintf(stderr, "Dumping roots\n");

    if (MR_debug_agc_print_vars) {
        while (roots != NULL) {
#ifndef MR_HIGHLEVEL_CODE
            /*
            ** Restore the registers, because we need to save them to a more
            ** permanent backing store (we are going to call Mercury soon,
            ** and we don't want it messing with the saved registers).
            */
            MR_restore_registers();
            MR_copy_regs_to_saved_regs(MR_MAX_FAKE_REG - 1, saved_regs,
                MR_MAX_VIRTUAL_F_REG - 1, saved_f_regs);

            MR_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);
            MR_virtual_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);
#endif /* !MR_HIGHLEVEL_CODE */

            fflush(NULL);
            MR_write_variable(roots->type_info, *roots->root);
            fflush(NULL);
            fprintf(stderr, "\n");

#ifndef MR_HIGHLEVEL_CODE
            MR_copy_saved_regs_to_regs(MR_MAX_FAKE_REG - 1, saved_regs,
                MR_MAX_VIRTUAL_F_REG, saved_f_regs);
            MR_save_registers();
#endif /* !MR_HIGHLEVEL_CODE */
            roots = roots->next;
        }
    }
}
Exemplo n.º 3
0
static void
MR_print_ordinary_regs(FILE *fp)
{
    int         i;
    MR_Integer  value;

    for (i = 0; i < 8; i++) {
        fprintf(fp, "r%d:      ", i + 1);
        value = (MR_Integer) MR_get_reg(i+1);

#ifndef MR_CONSERVATIVE_GC
        if ((MR_Integer) MR_ENGINE(MR_eng_heap_zone)->min <= value
                && value < (MR_Integer) MR_ENGINE(MR_eng_heap_zone)->top)
        {
            fprintf(fp, "(heap) ");
        }
#endif

        fprintf(fp, "%ld %lx\n", (long) value, (long) value);
    }
}
Exemplo n.º 4
0
void
MR_print_heapptr(FILE *fp, const MR_Word *s)
{
#ifdef  MR_CONSERVATIVE_GC
    fprintf(fp, "heap %" MR_INTEGER_LENGTH_MODIFIER "d", (MR_Integer) s);
#else
    fprintf(fp, "heap %3ld",
            (long) (MR_Integer) (s - MR_ENGINE(MR_eng_heap_zone)->MR_zone_min));
#endif

    if (MR_print_raw_addrs) {
        fprintf(fp, " (%p)", (const void *) s);
    }
}
Exemplo n.º 5
0
void
MR_printheap(FILE *fp, const MR_Word *h)
{
#ifndef MR_CONSERVATIVE_GC
    if (MR_print_raw_addrs) {
        fprintf(fp, "ptr %p, ", (const void *) h);
    }

    fprintf(fp, "offset %6ld words\n",
            (long) (MR_Integer) (h - MR_ENGINE(MR_eng_heap_zone)->min));
#else
    fprintf(fp, "ptr %p\n", (const void *) h);
#endif
}
Exemplo n.º 6
0
void
MR_reg_msg(FILE *fp)
{
    int         i;
    MR_Integer  x;

    if (!MR_lld_print_enabled) {
        return;
    }

    for (i=1; i<=8; i++) {
        x = (MR_Integer) MR_get_reg(i);
#ifndef MR_CONSERVATIVE_GC
        if ((MR_Integer) MR_ENGINE(MR_eng_heap_zone)->MR_zone_min <= x
                && x < (MR_Integer) MR_ENGINE(MR_eng_heap_zone)->MR_zone_top)
        {
            x -= (MR_Integer) MR_ENGINE(MR_eng_heap_zone)->MR_zone_min;
        }
#endif
        fprintf(fp, "%8lx ", (long) x);
    }
    fprintf(fp, "\n");
}
Exemplo n.º 7
0
static void
MR_dump_live_variables(const MR_LabelLayout *label_layout,
    MR_MemoryZone *heap_zone, MR_bool top_frame,
    MR_Word *stack_pointer, MR_Word *current_frame)
{
    int                 short_var_count;
    int                 long_var_count;
    int                 i;
    MR_TypeInfo         type_info;
    MR_Word             value;
    MR_TypeInfoParams   type_params;
    MR_Word             saved_regs[MR_MAX_FAKE_REG];
    MR_Float            saved_f_regs[MR_MAX_VIRTUAL_F_REG];
    MR_Word             *current_regs;
    MR_Float            *current_f_regs;

    long_var_count = MR_long_desc_var_count(label_layout);
    short_var_count = MR_short_desc_var_count(label_layout);

    // For the top stack frame, we should pass a pointer to a filled-in
    // saved_regs instead of NULL. For other stack frames, passing NULL
    // is fine, since output arguments are not live yet for any call
    // except the top one.

    MR_restore_registers();
    MR_copy_regs_to_saved_regs(MR_MAX_FAKE_REG - 1, saved_regs,
        MR_MAX_VIRTUAL_F_REG - 1, saved_f_regs);
    if (top_frame) {
        current_regs = saved_regs;
        current_f_regs = saved_f_regs;
    } else {
        current_regs = NULL;
        current_f_regs = NULL;
    }
    type_params = MR_materialize_type_params_base(label_layout,
        current_regs, stack_pointer, current_frame);

    for (i = 0; i < long_var_count; i++) {
        fprintf(stderr, "%-12s\t", "");
        if (MR_PROC_LAYOUT_HAS_PROC_ID(label_layout->MR_sll_entry)) {
            MR_print_proc_id(stderr, label_layout->MR_sll_entry);
        }

        MR_dump_long_value(MR_long_desc_var_locn(label_layout, i),
            heap_zone, stack_pointer, current_frame, top_frame);
        fprintf(stderr, "\n");
        fflush(NULL);

        if (MR_debug_agc_print_vars) {
            // Call Mercury but use the debugging heap.

            MR_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);
            MR_virtual_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);

            if (MR_get_type_and_value_base(label_layout, i,
                    current_regs, stack_pointer, current_frame, current_f_regs,
                    type_params, &type_info, &value)) {
                printf("\t");
                MR_write_variable(type_info, value);
                printf("\n");
            }

            fflush(NULL);
        }
    }

    for (i = 0; i < short_var_count; i++) {
        fprintf(stderr, "%-12s\t", "");
        if (MR_PROC_LAYOUT_HAS_PROC_ID(label_layout->MR_sll_entry)) {
            MR_print_proc_id(stderr, label_layout->MR_sll_entry);
        }

        MR_dump_short_value(MR_short_desc_var_locn(label_layout, i),
            heap_zone, stack_pointer, current_frame, top_frame);
        fprintf(stderr, "\n");
        fflush(NULL);

        if (MR_debug_agc_print_vars) {
            // Call Mercury but use the debugging heap.

            MR_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);
            MR_virtual_hp_word = MR_ENGINE(MR_eng_debug_heap_zone->MR_zone_min);

            if (MR_get_type_and_value_base(label_layout, i,
                    current_regs, stack_pointer, current_frame, current_f_regs,
                    type_params, &type_info, &value)) {
                printf("\t");
                MR_write_variable(type_info, value);
                printf("\n");
            }

            fflush(NULL);
        }
    }

    MR_copy_saved_regs_to_regs(MR_MAX_FAKE_REG - 1, saved_regs,
        MR_MAX_VIRTUAL_F_REG - 1, saved_f_regs);
    MR_save_registers();
    MR_free(type_params);
}
Exemplo n.º 8
0
MR_Word *
MR_new_nondetstack_segment(MR_Word *maxfr, int incr)
{
    MR_Word         *sentinel_maxfr;
    MR_Word         *old_maxfr;
    MR_Word         *old_curfr;
    MR_MemoryZone   *new_cur_zone;
    MR_MemoryZones  *new_prev_zones;

    old_maxfr = maxfr;
    old_curfr = MR_curfr;

#ifdef  MR_DEBUG_STACK_SEGMENTS
    printf("\nadding new nondet stack segment");
    printf("\ncontext: %p", &MR_ENGINE(MR_eng_context));
    printf("\nold maxfr: ");
    MR_printnondetstack(stdout, old_maxfr);
    printf("\nold curfr: ");
    MR_printnondetstack(stdout, old_curfr);
    printf("\n");
#endif

    new_cur_zone = MR_rewind_nondetstack_segments(maxfr);
    if (new_cur_zone == NULL) {
        // There is no old segment to reuse in the nondet stack itself,
        // so allocate a new one (possibly one that was freed earlier).
        //
        // Note that we perform explicit overflow checks, so redzones
        // would just waste space.

        new_cur_zone = MR_create_or_reuse_zone("nondetstack_segment",
            MR_nondetstack_size, 0, 0, MR_default_handler);
    }

#ifdef  MR_DEBUG_STACK_SEGMENTS
    printf("\nbefore creating new nondet segment:\n");
    MR_print_zone(stdout, MR_CONTEXT(MR_ctxt_nondetstack_zone));
    printf("\n");
#endif

    new_prev_zones = MR_GC_malloc_uncollectable_attrib(sizeof(MR_MemoryZones),
        MR_ALLOC_SITE_RUNTIME);
    new_prev_zones->MR_zones_head = MR_CONTEXT(MR_ctxt_nondetstack_zone);
    new_prev_zones->MR_zones_tail = MR_CONTEXT(MR_ctxt_prev_nondetstack_zones);
    MR_CONTEXT(MR_ctxt_prev_nondetstack_zones) = new_prev_zones;
    MR_CONTEXT(MR_ctxt_nondetstack_zone) = new_cur_zone;
    MR_CONTEXT(MR_ctxt_maxfr) = new_cur_zone->MR_zone_min;

    MR_maxfr_word = (MR_Word) MR_CONTEXT(MR_ctxt_maxfr);

#ifdef  MR_DEBUG_STACK_SEGMENTS
    printf("\nafter creating new nondet segment\n");
    printf("new maxfr: ");
    MR_printnondetstack(stdout, MR_maxfr);
    printf("\nnew cur zone:\n");
    MR_print_zone(stdout, MR_CONTEXT(MR_ctxt_nondetstack_zone));
    printf("new prev zones:\n");
    MR_print_zones(stdout, MR_CONTEXT(MR_ctxt_prev_nondetstack_zones));
    printf("\n");
    fflush(stdout);
#endif

    // The stack trace tracing code needs to know the size of each nondet
    // stack frame, since it uses the size to classify frames as temp or
    // ordinary. The size is given by the difference in address between
    // the address of the frame and the address of the previous frame.
    // This difference would yield an incorrect size and hence an incorrect
    // frame classification if a temp frame were allowed to have a frame
    // on a different segment as its immediate predecessor.
    //
    // We prevent this by putting an ordinary (i.e. non-temp) frame at the
    // bottom of every new nondet stack segment as a sentinel. We hand-build
    // this frame, since it is not an "ordinary" ordinary frame. It is not
    // created by a call, so it has no meaningful success continuation,
    // and since it does not make any calls, no other frame's success
    // continuation can point to it either.
    //
    // We store three pieces of information in the sentinel frame.
    //
    // - The maxfr at the time the sentinel frame was created, which we store
    //   in the prevfr slot. This is actually the address of the logically
    //   previous frame, so we are using the slot for its intended purpose,
    //   but the difference between the addresses of the two frames is NOT
    //   the size of the sentinel frame.
    //
    // - The curfr at the time the sentinel frame was created, which we store
    //   in the succfr slot. This is NOT actually the frame of the success
    //   continuation; we can store it there because this frame HAS no
    //   meaningful success continuation, so the slot is not needed for its
    //   intended purpose.
    //
    // - The address of the MR_MemoryZone structure of the zone containing
    //   the sentinel frame, which we store in framevar 1. This is used by
    //   the code of MR_pop_nondetstack_segment.

    sentinel_maxfr = MR_maxfr + (MR_NONDET_FIXED_SIZE + 1);
    MR_prevfr_slot_word(sentinel_maxfr) = (MR_Word) old_maxfr;
    MR_succfr_slot_word(sentinel_maxfr) = (MR_Word) old_curfr;
    MR_succip_slot_word(sentinel_maxfr) =
        (MR_Word) MR_ENTRY(MR_do_not_reached);
    MR_redofr_slot_word(sentinel_maxfr) = (MR_Word) sentinel_maxfr;
    MR_redoip_slot_word(sentinel_maxfr) =
        (MR_Word) MR_ENTRY(MR_pop_nondetstack_segment);
    MR_based_framevar(sentinel_maxfr, 1) = (MR_Word) new_cur_zone;

#ifdef  MR_DEBUG_STACK_SEGMENTS
    printf("creating sentinel frame:\n");
    printf("sentinel_maxfr: ");
    MR_printnondetstack(stdout, sentinel_maxfr);
    printf("\nsentinel frame's prevfr slot: ");
    MR_printnondetstack(stdout, MR_prevfr_slot(sentinel_maxfr));
    printf("\nsentinel frame's succfr slot: ");
    MR_printnondetstack(stdout, MR_succfr_slot(sentinel_maxfr));
    printf("\nsentinel frame's redofr slot: ");
    MR_printnondetstack(stdout, MR_redofr_slot(sentinel_maxfr));
    printf("\n");
#endif

    // Reserve space for the new nondet stack frame on top of the
    // sentinel frame.

    MR_maxfr_word = (MR_Word) (sentinel_maxfr + incr);

#ifdef  MR_DEBUG_STACK_SEGMENTS
    printf("after creating sentinel frame and reserving %d words:\n", incr);
    printf("new maxfr: ");
    MR_printnondetstack(stdout, MR_maxfr);
    printf("\n");
    fflush(stdout);
#endif

    return MR_maxfr;
}