Files
mercury/runtime/mercury_misc.c
Zoltan Somogyi 566cec5b30 Prefix everything defined in runtime/mercury_{stacks,tags}.h MR_.
Estimated hours taken: 3

Prefix everything defined in runtime/mercury_{stacks,tags}.h MR_.
In the process, get rid of the grade component MR_DEBUG_NONDET_STACK,
since this makes the update to mercury_stacks.h simpler and its use is
long obsolete.

runtime/mercury_tags.h:
	Put MR_ prefixes in front of everything defined here.

runtime/mercury_stacks.h:
	Put MR_ prefixes in front of everything defined here.

	Remove support for MR_DEBUG_NONDET_STACK. Replace most of the
	lost functionality by calling an updated mkframe_msg.

	Remove the definitions of push() and pop(). Their use conflicts with
	the idea that everything on the det stack is part of a frame, which
	the RTTI stuff depends on.

runtime/mercury_bootstrap.h:
	Add backward compatibility macros for the old names in the above two
	files.

	Remove some old entries in this file which are no longer needed.

runtime/mercury_wrapper.c:
	Remove the only uses of push() and pop().

	Put MR_ in front of some things that need them.

runtime/mercury_engine.c:
	Put MR_ in front of some things that need them.

runtime/mercury_misc.[ch]:
	Make mkframe_msg get the name of the procedure that owns the stack
	frame from an explicitly passed argument, rather than the prednm slot
	(which no longer exists). This actually improves low-level debugging
	support without MR_DEBUG_NONDET_STACK.

	Remove unnecessary return statements.

runtime/mercury_debug.h:
	Pass on the new arg of mkframe_msg.

	Fix long lines.

runtime/mercury_conf_param.h:
	Remove the documentation of MR_DEBUG_NONDET_STACK.

runtime/mercury_grade.h:
	Remove the grade component of MR_DEBUG_NONDET_STACK.

doc/reference_manual.texi:
	Document the MR_ prefixed versions of list_empty, list_cons etc.

library/io.m:
library/std_util.m:
library/string.m:
	Add prefixes to some references to the runtime.
1999-04-30 04:25:43 +00:00

498 lines
9.5 KiB
C

/*
** Copyright (C) 1996-1999 The University of Melbourne.
** This file may only be copied under the terms of the GNU Library General
** Public License - see the file COPYING.LIB in the Mercury distribution.
*/
#include "mercury_imp.h"
#include "mercury_dlist.h"
#include "mercury_regs.h"
#include "mercury_trace_base.h"
#include "mercury_label.h"
#include "mercury_misc.h"
#include <stdio.h>
#include <stdarg.h>
/*--------------------------------------------------------------------*/
static void print_ordinary_regs(void);
/* debugging messages */
#ifdef MR_LOWLEVEL_DEBUG
void
mkframe_msg(const char *predname)
{
restore_transient_registers();
printf("\nnew choice point %s for procedure %s\n", predname);
printf("new fr: "); printnondstack(MR_curfr);
printf("prev fr: "); printnondstack(MR_prevfr_slot(MR_curfr));
printf("succ fr: "); printnondstack(MR_succfr_slot(MR_curfr));
printf("succ ip: "); printlabel(MR_succip_slot(MR_curfr));
printf("redo ip: "); printlabel(MR_redoip_slot(MR_curfr));
if (MR_detaildebug) {
dumpnondstack();
}
}
void
succeed_msg(void)
{
restore_transient_registers();
printf("\nsucceeding from procedure\n");
printf("curr fr: "); printnondstack(MR_curfr);
printf("succ fr: "); printnondstack(MR_succfr_slot(MR_curfr));
printf("succ ip: "); printlabel(MR_succip_slot(MR_curfr));
if (MR_detaildebug) {
printregs("registers at success");
}
}
void
succeeddiscard_msg(void)
{
restore_transient_registers();
printf("\nsucceeding from procedure\n");
printf("curr fr: "); printnondstack(MR_curfr);
printf("succ fr: "); printnondstack(MR_succfr_slot(MR_curfr));
printf("succ ip: "); printlabel(MR_succip_slot(MR_curfr));
if (MR_detaildebug) {
printregs("registers at success");
}
}
void
fail_msg(void)
{
restore_transient_registers();
printf("\nfailing from procedure\n");
printf("curr fr: "); printnondstack(MR_curfr);
printf("fail fr: "); printnondstack(MR_prevfr_slot(MR_curfr));
printf("fail ip: "); printlabel(MR_redoip_slot(curprevfr_slot(MR_curfr)));
}
void
redo_msg(void)
{
restore_transient_registers();
printf("\nredo from procedure\n");
printf("curr fr: "); printnondstack(MR_curfr);
printf("redo fr: "); printnondstack(MR_maxfr);
printf("redo ip: "); printlabel(MR_redoip_slot(MR_maxfr));
}
void
call_msg(/* const */ Code *proc, /* const */ Code *succcont)
{
printf("\ncalling "); printlabel(proc);
printf("continuation "); printlabel(succcont);
printregs("registers at call");
}
void
tailcall_msg(/* const */ Code *proc)
{
restore_transient_registers();
printf("\ntail calling "); printlabel(proc);
printf("continuation "); printlabel(MR_succip);
printregs("registers at tailcall");
}
void
proceed_msg(void)
{
printf("\nreturning from determinate procedure\n");
printregs("registers at proceed");
}
void
cr1_msg(Word val0, const Word *addr)
{
printf("put value %9lx at ", (long) (Integer) val0);
printheap(addr);
}
void
cr2_msg(Word val0, Word val1, const Word *addr)
{
printf("put values %9lx,%9lx at ",
(long) (Integer) val0, (long) (Integer) val1);
printheap(addr);
}
void
incr_hp_debug_msg(Word val, const Word *addr)
{
#ifdef CONSERVATIVE_GC
printf("allocated %ld words at %lu\n", (unsigned long) val, addr);
#else
printf("increment hp by %ld from ", (long) (Integer) val);
printheap(addr);
#endif
}
void
incr_sp_msg(Word val, const Word *addr)
{
printf("increment sp by %ld from ", (long) (Integer) val);
printdetstack(addr);
}
void
decr_sp_msg(Word val, const Word *addr)
{
printf("decrement sp by %ld from ", (long) (Integer) val);
printdetstack(addr);
}
void
push_msg(Word val, const Word *addr)
{
printf("push value %9lx to ", (long) (Integer) val);
printdetstack(addr);
}
void
pop_msg(Word val, const Word *addr)
{
printf("pop value %9lx from ", (long) (Integer) val);
printdetstack(addr);
}
#endif /* defined(MR_LOWLEVEL_DEBUG) */
#ifdef MR_DEBUG_GOTOS
void
goto_msg(/* const */ Code *addr)
{
printf("\ngoto ");
printlabel(addr);
}
void
reg_msg(void)
{
int i;
Integer x;
for(i=1; i<=8; i++) {
x = (Integer) get_reg(i);
#ifndef CONSERVATIVE_GC
if ((Integer) MR_ENGINE(heap_zone)->min <= x
&& x < (Integer) MR_ENGINE(heap_zone)->top) {
x -= (Integer) MR_ENGINE(heap_zone)->min;
}
#endif
printf("%8lx ", (long) x);
}
printf("\n");
}
#endif /* defined(MR_DEBUG_GOTOS) */
/*--------------------------------------------------------------------*/
#ifdef MR_LOWLEVEL_DEBUG
/* debugging printing tools */
void
printint(Word n)
{
printf("int %ld\n", (long) (Integer) n);
}
void
printstring(const char *s)
{
printf("string %p %s\n", (const void *) s, s);
}
void
printheap(const Word *h)
{
#ifndef CONSERVATIVE_GC
printf("ptr %p, offset %3ld words\n",
(const void *) h,
(long) (Integer) (h - MR_ENGINE(heap_zone)->min));
#else
printf("ptr %p\n",
(const void *) h);
#endif
}
void
dumpframe(/* const */ Word *fr)
{
reg int i;
printf("frame at ptr %p, offset %3ld words\n",
(const void *) fr,
(long) (Integer) (fr - MR_CONTEXT(nondetstack_zone)->min));
printf("\t succip "); printlabel(MR_succip_slot(fr));
printf("\t redoip "); printlabel(MR_redoip_slot(fr));
printf("\t succfr "); printnondstack(MR_succfr_slot(fr));
printf("\t prevfr "); printnondstack(MR_prevfr_slot(fr));
for (i = 1; &MR_based_framevar(fr,i) > MR_prevfr_slot(fr); i++) {
printf("\t framevar(%d) %ld 0x%lx\n",
i, (long) (Integer) MR_based_framevar(fr,i),
(unsigned long) MR_based_framevar(fr,i));
}
}
void
dumpnondstack(void)
{
reg Word *fr;
printf("\nnondstack dump\n");
for (fr = MR_maxfr; fr > MR_CONTEXT(nondetstack_zone)->min;
fr = MR_prevfr_slot(fr)) {
dumpframe(fr);
}
}
void
printframe(const char *msg)
{
printf("\n%s\n", msg);
dumpframe(MR_curfr);
print_ordinary_regs();
}
void
printregs(const char *msg)
{
restore_transient_registers();
printf("\n%s\n", msg);
printf("%-9s", "succip:"); printlabel(MR_succip);
printf("%-9s", "curfr:"); printnondstack(MR_curfr);
printf("%-9s", "maxfr:"); printnondstack(MR_maxfr);
printf("%-9s", "hp:"); printheap(MR_hp);
printf("%-9s", "sp:"); printdetstack(MR_sp);
print_ordinary_regs();
}
static void
print_ordinary_regs(void)
{
int i;
Integer value;
for (i = 0; i < 8; i++) {
printf("r%d: ", i + 1);
value = (Integer) get_reg(i+1);
#ifndef CONSERVATIVE_GC
if ((Integer) MR_ENGINE(heap_zone)->min <= value &&
value < (Integer) MR_ENGINE(heap_zone)->top) {
printf("(heap) ");
}
#endif
printf("%ld\n", (long) value);
}
}
#endif /* defined(MR_DEBUG_GOTOS) */
void
MR_printdetstackptr(const Word *s)
{
MR_print_detstackptr(stdout, s);
}
void
MR_print_detstackptr(FILE *fp, const Word *s)
{
fprintf(fp, "det %3ld (%p)",
(long) (Integer) (s - MR_CONTEXT(detstack_zone)->min),
(const void *) s);
}
void
printdetstack(const Word *s)
{
printf("ptr %p, offset %3ld words\n",
(const void *) s,
(long) (Integer) (s - MR_CONTEXT(detstack_zone)->min));
}
void
MR_printnondstackptr(const Word *s)
{
MR_print_nondstackptr(stdout, s);
}
void
MR_print_nondstackptr(FILE *fp, const Word *s)
{
fprintf(fp, "non %3ld (%p)",
(long) (Integer) (s - MR_CONTEXT(nondetstack_zone)->min),
(const void *) s);
}
void
printnondstack(const Word *s)
{
printf("ptr %p, offset %3ld words\n",
(const void *) s,
(long) (Integer) (s - MR_CONTEXT(nondetstack_zone)->min));
}
void
printlabel(/* const */ Code *w)
{
MR_Internal *internal;
internal = MR_lookup_internal_by_addr(w);
if (internal != NULL) {
if (internal->i_name != NULL) {
printf("label %s (%p)\n", internal->i_name, w);
} else {
printf("label (%p)\n", w);
}
} else {
#ifdef MR_DEBUG_GOTOS
MR_Entry *entry;
entry = MR_prev_entry_by_addr(w);
if (entry->e_addr == w && entry->e_name != NULL) {
printf("label %s (%p)\n", entry->e_name, w);
} else {
printf("label UNKNOWN (%p)\n", w);
}
#else
printf("label UNKNOWN (%p)\n", w);
#endif /* not MR_DEBUG_GOTOS */
}
}
void *
newmem(size_t n)
{
reg void *p;
#ifdef CONSERVATIVE_GC
p = GC_MALLOC(n);
#else
p = malloc(n);
#endif
if (p == NULL && n != 0) {
fatal_error("ran out of memory");
}
return p;
}
void
oldmem(void *p)
{
#ifdef CONSERVATIVE_GC
GC_FREE(p);
#else
free(p);
#endif
}
void*
resizemem(void *p, size_t size)
{
#ifdef CONSERVATIVE_GC
p = GC_REALLOC(p, size);
#else
p = realloc(p, size);
#endif
if (p == NULL) {
fatal_error("ran out of memory");
}
return p;
}
void
MR_warning(const char *fmt, ...)
{
va_list args;
fflush(stdout); /* in case stdout and stderr are the same */
fprintf(stderr, "Mercury runtime: ");
va_start(args, fmt);
vfprintf(stderr, fmt, args);
va_end(args);
fprintf(stderr, "\n");
fflush(stderr);
}
/*
** XXX will need to modify this to kill other threads if MR_THREAD_SAFE
** (and cleanup resources, etc....)
*/
void
fatal_error(const char *fmt, ...)
{
va_list args;
fflush(stdout); /* in case stdout and stderr are the same */
fprintf(stderr, "Mercury runtime: ");
va_start(args, fmt);
vfprintf(stderr, fmt, args);
va_end(args);
fprintf(stderr, "\n");
MR_trace_report(stderr);
fflush(NULL); /* flushes all stdio output streams */
exit(EXIT_FAILURE);
}
/*
** See the header file for documentation on why we need this function.
*/
void
MR_memcpy(void *dest, const void *src, size_t nbytes)
{
char *d = (char *) dest;
const char *s = (const char *) src;
while (nbytes-- > 0)
*d++ = *s++;
}
/*
** Note that hash_string is actually defined as a macro in mercury_imp.h,
** if we're using GNU C. We define it here whether or not we're using
** gcc, so that users can easily switch between gcc and cc without
** rebuilding the libraries.
*/
#undef hash_string
int
hash_string(Word s)
{
HASH_STRING_FUNC_BODY
}