updated trail handling

Fergus Henderson fjh at cs.mu.oz.au
Thu Aug 14 01:00:21 AEST 1997


Hi,

Here's the changes that Peter Schachte and I made to generalize the current
support for trailing.

This compiles.  I haven't tested it.  It is not quite ready to be
committed.

---------------------------------------------------------------------

Generalize the current support for trailing.
Previously, the trail was hardwired, either for interfacing to CLP(R),
or (in my alternative not-checked-in version) for backtrackable destructive
arrays.  But it couldn't handle both of these at the same time and it
couldn't be extended.  So we have replaced this with a more generic
trail.  The trail has two sorts of entries, value trail entries and
function trail entries.

XXX TODO:
This change breaks the existing support for CLP(R).
To make it work again, we need to change clpr/svar.m:
(1) It should initialize the CLP(R) engine
(2) Before adding each constraint, the CLP(R) variable `stamp'
    needs to be set from the Mercury variable `MR_ticket_counter'
    using the Mercury function `MR_current_choicepoint_id()'.
    [or perhaps we could just `#define stamp MR_ticket_counter'
    or something like that]
(3) Before adding each constraint, it should
    call MR_trail_function() passing as `datum' the address
    of a struct holding the current values of the CLP(R) global variables
    slack_id, solver_id, and trtop.
    (But we should use MR_ticket_counter to optimize this so that
    it does this at most once per choice.)
    This struct could be allocated either on the heap or
    in a separate data area.  (It might be best to allocate
    chunks from the heap one at a time and then allocate these
    structs from the chunks.)
    The untrail function would restore slack_id, solver_id, and trtop,
    and would call the CLPR function solver_backtrack() on all the
    CLP(R) trail entries between the current trtop and the trtop to be
    restored.

runtime/mercury_trail.h:
runtime/mercury_trail.c:
	New files. They also provide macros MR_trail_value(),
	MR_trail_function(), etc. which are the new interface to
	the Mercury trail.  (All the trailing stuff is done
	inside #ifdef MR_USE_TRAIL.)

	These files also implement the save_ticket(), restore_ticket(),
	and discard_ticket() macros that are used in the C code that
	the Mercury compiler generates.

	These files also define the trail memory zone MR_trail_zone,
	and the new virtual machine registers MR_trail_ptr and
	MR_ticket_counter.  (Perhaps these should instead be in memory.c
	and regs.h respectively?)

runtime/mercury_solver_backtrack.h:
	Deleted, since this file has been replaced by mercury_trail.h.

runtime/imp.h:
	#include "mercury_trail.h" rather than "mercury_solver_backtrack.h"

runtime/Mmakefile:
	Add mercury_trail.c and mercury_trail.h.
	Remove mercury_solver_backtrack.h.

runtime/context.h:
	Add new fields to the Context struct to hold MR_trail_ptr
	and MR_ticket_counter.  Add code to handle these in
	save_context()/load_context().

runtime/context.mod:
	Add code to new_context() to initialize the trail.

runtime/wrapper.h:
runtime/wrapper.mod:
runtime/memory.c:
	Add code to handle setting the trail size via the
	MERCURY_OPTIONS environment variable.
	Remove old stuff to support the solver_stack.

runtime/wrapper.mod:
runtime/regs.h:
runtime/reg_order.h:
	Count the usage of the new virtual machine registers
	MR_trail_ptr and MR_ticket_counter.
	(Currently they are implemented just as global variables,
	not registers.)

---------------------------------------------------------------------

scripts/mgnuc.in:
compiler/handle_options.m:
	Rename the `*.cnstr' grades as `*.tr', and use
	`-DMR_USE_TRAIL' rather than `-DCONSTRAINTS'.

compiler/options.m:
	Rename the `--constraints' option as `--use-trail'.

compiler/code_gen.m:
compiler/disj_gen.m:
compiler/ite_gen.m:
compiler/mercury_compile.m:
	Trivial changes to handle the renaming of the `constraints'
	option as `use_trail'.

---------------------------------------------------------------------

cvs diff: Diffing .
Index: Mmakefile
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/Mmakefile,v
retrieving revision 1.8
diff -u -r1.8 Mmakefile
--- Mmakefile	1997/07/27 15:07:59	1.8
+++ Mmakefile	1997/08/13 10:01:29
@@ -25,8 +25,8 @@
 HDRS		= misc.h calls.h conf.h context.h \
 		  deep_copy.h dlist.h debug.h dummy.h \
 		  engine.h getopt.h goto.h heap.h imp.h init.h label.h \
-		  memory.h mercury_solver_backtrack.h \
-		  mercury_float.h mercury_string.h mercury_types.h \
+		  memory.h mercury_float.h mercury_string.h mercury_trail.h \
+		  mercury_types.h \
 		  overflow.h prof.h prof_mem.h regorder.h regs.h \
 		  spinlock.h std.h stacks.h \
 		  table.h tags.h timing.h type_info.h wrapper.h
@@ -40,7 +40,7 @@
 MOD_OS		= $(MOD_CS:.c=.o)
 ORIG_CS		= deep_copy.c dlist.c dummy.c label.c \
 		  memory.c misc.c regs.c table.c timing.c prof.c prof_mem.c \
-		  spinlock.c mercury_float.c
+		  spinlock.c mercury_float.c mercury_trail.c
 ORIG_OS		= $(ORIG_CS:.c=.o)
 OBJS		= $(MOD_OS) $(ORIG_OS)
 # OBJS		= engine.o wrapper.o call.o \
Index: context.h
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/context.h,v
retrieving revision 1.6
diff -u -r1.6 context.h
--- context.h	1997/07/27 15:08:06	1.6
+++ context.h	1997/08/13 14:17:50
@@ -7,7 +7,7 @@
 /*
 ** context.h - defines Mercury multithreading stuff.
 **
-** A Context is like a thread. It contains a detstack, a nondetstack,
+** A Context is like a thread. It contains a detstack, a nondetstack, a trail,
 ** the various pointers that refer to them, a succip, and a thread-
 ** resumption continuation. Contexts are initally stored in a free-list.
 ** When one is running, the Unix process that is executing it has a pointer
@@ -48,6 +48,7 @@
 #include <sys/types.h>		/* for pid_t */
 
 #include "mercury_types.h"	/* for Word */
+#include "mercury_trail.h"	/* for MR_TrailEntry */
 #include "memory.h"		/* for MemoryZone */
 #include "spinlock.h"		/* for SpinLock */
 #include "goto.h"		/* for GOTO() */
@@ -88,23 +89,35 @@
 		** currently running then `next' points to the next runnable
 		** context in the runqueue.
 		*/
+
 	Code		*resume;
 		/*
 		** a pointer to the code at which execution should resume when
 		** this context is next scheduled.
 		*/
+
 	Code		*context_succip;
 		/* succip for this context */
+
 	MemoryZone	*detstack_zone;
 		/* pointer to the detstack_zone for this context */
 	Word		*context_sp;
 		/* saved stack pointer for this context */
+
 	MemoryZone	*nondetstack_zone;
 		/* pointer to the nondetstack_zone for this context */
 	Word		*context_maxfr;
 		/* saved maxfr pointer for this context */
 	Word		*context_curfr;
 		/* saved curfr pointer for this context */
+
+	MemoryZone	*trail_zone;
+		/* pointer to the MR_trail_zone for this context */
+	MR_TrailEntry	*context_trail_ptr;
+		/* saved MR_trail_ptr for this context */
+	MR_ChoicepointId context_ticket_counter;
+		/* saved MR_trail_ptr for this context */
+
 	Word		*context_hp;
 		/* saved hp for this context */
 	Word		*min_heap_reclamation_point;
@@ -317,6 +330,12 @@
 
 #endif
 
+#ifdef MR_USE_TRAIL
+#define MR_IF_USE_TRAIL(x) x
+#else
+#define MR_IF_USE_TRAIL(x)
+#endif
+
 #define	load_context(cptr)	do {					\
 		Context	*load_context_c;				\
 		load_context_c = (cptr);				\
@@ -326,6 +345,12 @@
 		nondetstack_zone = load_context_c->nondetstack_zone;	\
 		maxfr		= load_context_c->context_maxfr;	\
 		curfr		= load_context_c->context_curfr;	\
+	        MR_IF_USE_TRAIL(					\
+		    MR_trail_zone = load_context_c->trail_zone;		\
+		    MR_trail_ptr = load_context_c->context_trail_ptr;	\
+		    MR_ticket_counter =					\
+				load_context_c->context_ticket_counter;	\
+	    	)							\
 		set_min_heap_reclamation_point(load_context_c);	\
 	} while (0)
 
@@ -338,6 +363,12 @@
 		save_context_c->nondetstack_zone = nondetstack_zone;	\
 		save_context_c->context_maxfr	= maxfr;		\
 		save_context_c->context_curfr	= curfr;		\
+		MR_IF_USE_TRAIL(					\
+		    save_context_c->trail_zone = MR_trail_zone;		\
+		    save_context_c->context_trail_ptr = MR_trail_ptr;	\
+		    save_context_c->context_ticket_counter =		\
+						MR_ticket_counter;	\
+		)							\
 		save_hp_in_context(save_context_c);			\
 	} while (0)
 
Index: context.mod
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/context.mod,v
retrieving revision 1.8
diff -u -r1.8 context.mod
--- context.mod	1997/07/27 15:08:07	1.8
+++ context.mod	1997/08/13 10:36:56
@@ -159,6 +159,18 @@
 	bt_succip(c->context_curfr) = ENTRY(do_not_reached);
 	bt_succfr(c->context_curfr) = NULL;
 
+#ifdef MR_USE_TRAIL
+	if (c->trail_zone != NULL) {
+		reset_zone(c->trail_zone);
+	} else {
+		c->trail_zone = create_zone("trail", 0,
+			trail_size, next_offset(), trail_zone_size, 
+			default_handler);
+	}
+	c->context_trail_ptr = (MR_TrailEntry *) c->trail_zone->min;
+	c->context_ticket_counter = 0;
+#endif
+
 	c->context_hp = NULL;
 
 	return c;
Index: imp.h
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/imp.h,v
retrieving revision 1.109
diff -u -r1.109 imp.h
--- imp.h	1997/07/27 15:08:20	1.109
+++ imp.h	1997/08/13 14:17:50
@@ -43,8 +43,8 @@
 #include	"wrapper.h"
 #include	"context.h"
 #include	"type_info.h"
-#ifdef CONSTRAINTS
-#include	"mercury_solver_backtrack.h"
+#ifdef MR_USE_TRAIL
+#include	"mercury_trail.h"
 #endif
 
 #include	"debug.h"
Index: memory.c
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/memory.c,v
retrieving revision 1.73
diff -u -r1.73 memory.c
--- memory.c	1997/07/27 15:08:25	1.73
+++ memory.c	1997/08/13 10:05:14
@@ -242,6 +242,14 @@
 	nondstack_size      = round_up(nondstack_size * 1024, unit);
 	nondstack_zone_size = round_up(nondstack_zone_size * 1024, unit);
 
+#ifdef MR_USE_TRAIL
+	trail_size       = round_up(trail_size * 1024, unit);
+	trail_zone_size  = round_up(trail_zone_size * 1024, unit);
+#else
+	trail_size	    = 0;
+	trail_zone_size	    = 0;
+#endif
+
 	/*
 	** If the zone sizes were set to something too big, then
 	** set them to a single unit.
@@ -264,6 +272,11 @@
 		nondstack_zone_size = unit;
 	}
 
+#ifdef MR_USE_TRAIL
+	if (trail_zone_size >= trail_size) {
+		trail_zone_size = unit;
+	}
+#endif
 
 	init_memory_arena();
 	init_zones();
Index: mercury_trail.c
===================================================================
RCS file: mercury_trail.c
diff -N mercury_trail.c
--- /dev/null	Thu Aug 14 00:21:10 1997
+++ mercury_trail.c	Wed Aug 13 22:19:39 1997
@@ -0,0 +1,64 @@
+/*
+** Copyright (C) 1997 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.
+*/
+
+/*
+** mercury_trail.c - code for the Mercury trail.
+**
+** The trail is used to record values that need to be
+** restored on backtracking.
+*/
+
+#include "imp.h"
+
+#include "mercury_trail.h"
+
+#include "memory.h"
+#include "misc.h"
+
+MemoryZone	*MR_trail_zone;
+MR_TrailEntry	*MR_trail_ptr_var;
+Unsigned	MR_ticket_counter_var;
+
+void
+MR_untrail_to(MR_TrailEntry *old_trail_ptr, MR_untrail_reason reason)
+{
+    switch (reason) {
+	case MR_commit:
+	    /* Just handle the function trail entries */
+	    while (MR_trail_ptr != old_trail_ptr) {
+	    	MR_trail_ptr--;
+	    	if (MR_trail_ptr->MR_kind == MR_func_entry) {
+		    (*MR_trail_ptr->MR_union.MR_func.MR_untrail_func)(
+				MR_trail_ptr->MR_union.MR_func.MR_datum,
+				reason
+		    );
+		}
+	    }
+	    break;
+
+	case MR_undo:
+	case MR_exception:
+	    /* Handle both function and value trail entries */
+	    while (MR_trail_ptr != old_trail_ptr) {
+		MR_trail_ptr--;
+		if (MR_trail_ptr->MR_kind == MR_func_entry) {
+		    (*MR_trail_ptr->MR_union.MR_func.MR_untrail_func)(
+				MR_trail_ptr->MR_union.MR_func.MR_datum,
+				reason
+		    );
+		} else {
+		    *MR_trail_ptr->MR_union.MR_val.MR_address =
+				MR_trail_ptr->MR_union.MR_val.MR_value;
+		}
+	    }
+	    break;
+	
+	default:
+	    fatal_error("unknown MR_untrail_reason");
+    }
+}
+
+/*---------------------------------------------------------------------------*/
Index: mercury_trail.h
===================================================================
RCS file: mercury_trail.h
diff -N mercury_trail.h
--- /dev/null	Thu Aug 14 00:21:10 1997
+++ mercury_trail.h	Thu Aug 14 00:17:50 1997
@@ -0,0 +1,226 @@
+/*
+** Copyright (C) 1997 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.
+*/
+
+/*
+** mercury_trail.h - code for handling the trail.
+**
+** The trail is used to record values that need to be
+** restored on backtracking.
+*/
+
+#ifndef MERCURY_TRAIL_H
+#define MERCURY_TRAIL_H
+
+#include "memory.h"
+
+/*---------------------------------------------------------------------------*/
+/*
+** The following macros that are used to interface with the code generator.
+**
+** store_ticket()
+**	called when creating a choice point
+** restore_ticket()
+**	called when resuming forward execution after failing
+** discard_ticket()
+**	called when cutting away a choice point
+**
+** XXX what about commits (deep cuts)?
+*/
+/*---------------------------------------------------------------------------*/
+
+/*
+** The following macros define how to store and retrieve a 'ticket' -
+** the  information that we need to be able to backtrack. 
+*/
+
+	/* 
+	** called when we create a choice point
+	** (including semidet choice points)
+	*/
+#define store_ticket(save_trail_ptr)				\
+	do {							\
+		(save_trail_ptr) = (Integer) MR_trail_ptr; 	\
+		++MR_ticket_counter;				\
+	} while(0)
+
+	/* restore the solver to the state given in the ticket starting at x */
+#define restore_and_discard_ticket(old)				\
+	do {							\
+		MR_TrailEntry *old_trail_ptr =  		\
+			(MR_TrailEntry *)old;			\
+		if (MR_trail_ptr != old_trail_ptr) {		\
+			save_transient_registers();		\
+			MR_untrail_to(old_trail_ptr, MR_undo);	\
+			restore_transient_registers();		\
+		}						\
+		--MR_ticket_counter;				\
+	} while(0)
+
+	/* 
+	** discard the top ticket
+	*/
+#define discard_ticket(old_trail_ptr) 			\
+	do {						\
+		save_transient_registers();		\
+		MR_untrail_to((MR_TrailEntry *) old_trail_ptr, MR_commit); \
+		restore_transient_registers();		\
+		--MR_ticket_counter;			\
+	} while(0);
+
+/*---------------------------------------------------------------------------*/
+
+typedef enum { MR_undo, MR_exception, MR_commit, MR_gc } MR_untrail_reason;
+
+/* XXX we should optimize this -- use tag bits */
+typedef struct {
+	enum { MR_val_entry, MR_func_entry } MR_kind;
+	union {
+		struct {
+			Word *MR_address;
+			Word MR_value;
+		} MR_val;
+		struct {
+			void (*MR_untrail_func)(Word datum, MR_untrail_reason);
+			Word MR_datum;
+		} MR_func;
+	} MR_union;
+} MR_TrailEntry;
+
+/* The Mercury trail */
+extern MemoryZone *MR_trail_zone;
+
+/* Pointer to the current top of the Mercury trail */
+/* N.B. Use `MR_trail_ptr', defined in regorder.h, not `MR_trail_ptr_var'. */
+extern MR_TrailEntry *MR_trail_ptr_var;
+
+/*
+** An integer variable that is incremented whenever we create a choice
+** point (including semidet choice points, e.g. in an if-then-else)
+** and decremented whenever we remove one.
+**
+** XXX s/decremented/reset/ ???
+**
+** N.B.  Use `MR_ticket_counter', defined in regorder,h,
+** not `MR_ticket_counter'.
+*/
+extern Unsigned MR_ticket_counter_var;
+
+/*---------------------------------------------------------------------------*/
+/*
+** This is the interface that should be used by C code that wants to
+** do trailing.
+*/
+/*---------------------------------------------------------------------------*/
+
+/*
+** void  MR_trail_value_at_address(Word *address, Word value);
+**
+** Make sure that when the current execution is
+** backtracked over, `value' is placed in `address'.
+*/
+#define MR_trail_value(address, value)		\
+	do {							\
+		MR_trail_ptr->MR_kind = MR_val_entry;		\
+		MR_trail_ptr->MR_union.MR_val.MR_address = (address);	\
+		MR_trail_ptr->MR_union.MR_val.MR_value = (value);	\
+		MR_trail_ptr++;					\
+	} while(0);
+
+/*
+** void  MR_trail_value_at_address(Word *address);
+**
+** Make sure that when the current execution is
+** backtracked over, the value currently in `address'
+** is restored.
+*/
+#define MR_trail_value_at_address(address) \
+	MR_trail_value((address), *(address))
+
+/*
+** void MR_trail_function(void (*untrail_func)(Word, MR_untrail_reason),
+**		Word value);
+**
+** Make sure that when the current execution is
+** backtracked over, (*untrail_func)(value, MR_undo) is called.
+** Also make sure that if the current choicepoint is
+** trimmed without being backtracked over (ie, the
+** current choice is committed to), then
+** (*untrail_func)(value, MR_commit) is called.
+*/
+#define MR_trail_function(untrail_func, datum)				\
+	do {								\
+		MR_trail_ptr->MR_kind = MR_func_entry;			\
+		MR_trail_ptr->MR_union.MR_func.MR_untrail_func =	\
+			(untrail_func); 				\
+		MR_trail_ptr->MR_union.MR_func.MR_datum = (datum);	\
+		MR_trail_ptr++;						\
+	} while(0);
+
+/*
+** Apply all the trail entries between MR_trail_ptr and old_trail_ptr.
+*/
+void MR_untrail_to(MR_TrailEntry *old_trail_ptr, MR_untrail_reason reason);
+
+/* abstract type */
+typedef Unsigned MR_ChoicepointId;
+
+/*
+** MR_ChoicepointId MR_current_choicepoint_id(void);
+**
+** Returns a value indicative of the current
+** choicepoint.  If we execute
+** 
+** 	oldcp = MR_current_choicepoint_id();
+** 	... and a long time later ...
+** 	if (oldcp == MR_current_choicepoint_id()) {A}
+** 
+** then we can be assured that if the choicepoint current
+** at the time of the first call to MR_current_choicepoint()
+** has not been backtracked over before the second call,
+** then code A will be executed if and only if the
+** current choicepoint is the same in both calls.
+*/
+#define MR_current_choicepoint_id() (MR_ticket_counter)
+
+#endif /* not MERCURY_TRAIL_H */
+
+/*---------------------------------------------------------------------------*/
+/*
+** This macro performs the necessary initialisations for the CLPR solver.
+** XXX should be a function.
+** XXX should be defined elsewhere, e.g. in svar.m.
+*/
+#define init_CLPR()					\
+	do {						\
+		init_solver();				\
+		init_solver_goal();			\
+			/* get some memory for */	\
+			/* the CLP(R) trail    */	\
+		trail = checked_malloc(DEF_TRAIL_SZ * sizeof(int)); \
+		trtop = 0;				\
+			/* initialise the      */	\
+			/* CLP(R) streams      */	\
+		error_stream = stderr;			\
+		outfile = stderr;			\
+	} while (0)
+
+/*
+
+:- pragma(c_code, mostly_uniq_array__set(MostlyUniqArray0::mostly_uniq_array_mdi, Index::in,
+		Item::in, MostlyUniqArray::mostly_uniq_array_muo), "{
+	MostlyUniqArrayType *mostly_uniq_array = 
+				(MostlyUniqArrayType *)MostlyUniqArray0;
+	if ((Unsigned) Index >= mostly_uniq_array->size) {
+		fatal_error(""mostly_uniq_array__set: array index out of bounds"");
+	}
+	MR_trail_value_at_address(&mostly_uniq_array->elements[Index]);
+	mostly_uniq_array->elements[Index] = Item;  % destructive update!
+	MostlyUniqArray = MostlyUniqArray0;
+}").
+
+*/
+
+/*---------------------------------------------------------------------------*/
Index: regorder.h
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/regorder.h,v
retrieving revision 1.17
diff -u -r1.17 regorder.h
--- regorder.h	1997/07/27 15:08:38	1.17
+++ regorder.h	1997/08/13 14:17:50
@@ -61,6 +61,10 @@
 #define curfr		LVALUE_CAST(Word *, count_usage(CF_RN, mr8))
 #define maxfr		LVALUE_CAST(Word *, count_usage(MF_RN, mr9))
 
+#define MR_trail_ptr	count_usage(MR_TRAIL_PTR_RN, MR_trail_ptr_var)
+#define MR_ticket_counter	 \
+		count_usage(MR_TICKET_COUNTER_RN, MR_ticket_counter_var)
+
 #define VIRTUAL_REG_MAP_BODY	{ \
 	2, \
 	3, \
Index: regs.h
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/regs.h,v
retrieving revision 1.30
diff -u -r1.30 regs.h
--- regs.h	1997/07/27 15:08:40	1.30
+++ regs.h	1997/08/13 14:17:50
@@ -155,6 +155,8 @@
 #define	SP_RN	(ORD_RN + 2)
 #define	CF_RN	(ORD_RN + 3)
 #define	MF_RN	(ORD_RN + 4)
-#define MAX_RN	(ORD_RN + 5)
+#define MR_TRAIL_PTR_RN		(ORD_RN + 5)
+#define MR_TICKET_COUNTER_RN	(ORD_RN + 6)
+#define MAX_RN			(ORD_RN + 7)
 
 #endif /* not REGS_H */
Index: wrapper.h
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/wrapper.h,v
retrieving revision 1.18
diff -u -r1.18 wrapper.h
--- wrapper.h	1997/07/27 15:08:51	1.18
+++ wrapper.h	1997/08/13 14:17:50
@@ -27,12 +27,14 @@
 extern	size_t		detstack_size;
 extern	size_t		nondstack_size;
 extern	size_t		solutions_heap_size;
+extern	size_t		trail_size;
 
 /* sizes of the red zones */
 extern	size_t		heap_zone_size;
 extern	size_t		detstack_zone_size;
 extern	size_t		nondstack_zone_size;
 extern	size_t		solutions_heap_zone_size;
+extern	size_t		trail_zone_size;
 
 /* size of the primary cache */
 extern	size_t		pcache_size;
Index: wrapper.mod
===================================================================
RCS file: /home/staff/zs/imp/mercury/runtime/wrapper.mod,v
retrieving revision 1.76
diff -u -r1.76 wrapper.mod
--- wrapper.mod	1997/07/27 15:08:53	1.76
+++ wrapper.mod	1997/08/13 11:04:04
@@ -37,6 +37,7 @@
 size_t		detstack_size =  	2048;
 size_t		nondstack_size =  	128;
 size_t		solutions_heap_size =	1024;
+size_t		trail_size =		128;
 
 /* size of the redzones at the end of data areas, in kilobytes */
 /* (but we later multiply by 1024 to convert to bytes) */
@@ -44,6 +45,7 @@
 size_t		detstack_zone_size =	16;
 size_t		nondstack_zone_size =	16;
 size_t		solutions_heap_zone_size = 16;
+size_t		trail_zone_size =	16;
 
 /* primary cache size to optimize for, in kilobytes */
 /* (but we later multiply by 1024 to convert to bytes) */
@@ -72,18 +74,6 @@
 int		mercury_exit_status = 0;
 
 /*
-** Constraint solver trail.
-**
-** XXX this should not be here; it should be in engine.mod
-** or constraints.c or somewhere like that.
-*/
-#ifdef CONSTRAINTS
-int		*mercury_solver_sp;
-int		*mercury_solver_sp_old;
-size_t		solver_ticket_stack_size = SOLVER_STACK_SIZE;
-#endif
-
-/*
 ** The Mercury runtime calls io:run/0 in the Mercury library, and the Mercury
 ** library calls main/2 in the user's program.  The Mercury runtime also calls
 ** init_gc() and init_modules() which are in the automatically generated
@@ -189,14 +179,6 @@
 
 	(*address_of_mercury_init_io)();
 
-#ifdef CONSTRAINTS
-	perform_solver_initialisations();
-		/* convert the stack size to bytes from kb */
-	solver_ticket_stack_size *= 1024;
-	mercury_solver_sp =checked_malloc(solver_ticket_stack_size*sizeof(int));
-	mercury_solver_sp_old = mercury_solver_sp;
-#endif
-
 	/* execute the selected entry point */
 	init_engine();
 	run_code();
@@ -519,9 +501,9 @@
 			else if (optarg[0] == 'l')
 				entry_table_size = size *
 					1024 / (2 * sizeof(List *));
-#ifdef CONSTRAINTS
-			else if (optarg[0] == 's')
-				solver_ticket_stack_size = size;
+#ifdef MR_USE_TRAIL
+			else if (optarg[0] == 't')
+				trail_size = size;
 #endif
 			else
 				usage();
@@ -589,6 +571,10 @@
 				detstack_zone_size = size;
 			else if (optarg[0] == 'n')
 				nondstack_zone_size = size;
+#ifdef MR_USE_TRAIL
+			else if (optarg[0] == 't')
+				trail_zone_size = size;
+#endif
 			else
 				usage();
 
@@ -644,13 +630,16 @@
 		"-sh<n> \t\tallocate n kb for the heap\n"
 		"-sd<n> \t\tallocate n kb for the det stack\n"
 		"-sn<n> \t\tallocate n kb for the nondet stack\n"
-#ifdef CONSTRAINTS
-		"-ss<n> \t\tallocate n kb for the solver ticket stack\n"
+#ifdef MR_USE_TRAIL
+		"-st<n> \t\tallocate n kb for the trail\n"
 #endif
 		"-sl<n> \t\tallocate n kb for the label table\n"
 		"-zh<n> \t\tallocate n kb for the heap redzone\n"
 		"-zd<n> \t\tallocate n kb for the det stack redzone\n"
 		"-zn<n> \t\tallocate n kb for the nondet stack redzone\n"
+#ifdef MR_USE_TRAIL
+		"-zt<n> \t\tallocate n kb for the trail redzone\n"
+#endif
 		"-P<n> \t\tnumber of processes to use for parallel execution\n"
 		"\t\tapplies only if Mercury is configured with --enable-parallel\n"
 		"-p<n> \t\tprimary cache size in kbytes\n"
@@ -769,6 +758,12 @@
 				break;
 			case MF_RN:
 				printf("maxfr");
+				break;
+			case MR_TRAIL_PTR_RN:
+				printf("MR_trail_ptr");
+				break;
+			case MR_TICKET_COUNTER_RN:
+				printf("MR_ticket_counter");
 				break;
 			default:
 				printf("UNKNOWN%d", i);
cvs diff: Diffing machdeps

Index: code_gen.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/code_gen.m,v
retrieving revision 1.30
diff -u -r1.30 code_gen.m
--- code_gen.m	1997/07/27 14:59:56	1.30
+++ code_gen.m	1997/08/13 14:03:55
@@ -945,8 +945,8 @@
 	},
 	code_info__maybe_save_hp(ReclaimHeap, SaveHpCode, MaybeHpSlot),
 
-	{ globals__lookup_bool_option(Globals, constraints, Constraints) },
-	code_info__maybe_save_ticket(Constraints, SaveTicketCode,
+	{ globals__lookup_bool_option(Globals, use_trail, UseTrail) },
+	code_info__maybe_save_ticket(UseTrail, SaveTicketCode,
 		MaybeTicketSlot),
 
 		% Generate the condition as a semi-deterministic goal;
@@ -970,6 +970,7 @@
 		 tree(SaveHpCode,
 		 tree(SaveTicketCode,
 		 tree(GoalCode,
+		 % XXX don't we need `DiscardTicketCode' here?
 		 tree(FailCode,
 		 tree(RestoreContCode,
 		 tree(RestoreTicketCode,
Index: disj_gen.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/disj_gen.m,v
retrieving revision 1.56
diff -u -r1.56 disj_gen.m
--- disj_gen.m	1997/07/27 15:00:12	1.56
+++ disj_gen.m	1997/08/13 14:02:18
@@ -60,13 +60,13 @@
 :- mode disj_gen__generate_pruned_disj(in, in, out, in, out) is det.
 
 disj_gen__generate_pruned_disj(Goals, StoreMap, Code) -->
-		% If we are using constraints, save the current solver state
+		% If we are using a trail, save the current trail state
 		% before the first disjunct.
 	code_info__get_globals(Globals),
 	{ globals__lookup_bool_option(Globals, reclaim_heap_on_semidet_failure,
 		ReclaimHeap) },
-	{ globals__lookup_bool_option(Globals, constraints, Constraints) },
-	code_info__maybe_save_ticket(Constraints, SaveTicketCode,
+	{ globals__lookup_bool_option(Globals, use_trail, UseTrail) },
+	code_info__maybe_save_ticket(UseTrail, SaveTicketCode,
 		MaybeTicketSlot),
 
 		% Rather than saving the heap pointer here,
@@ -231,11 +231,11 @@
 		Goals = [_, _ | _]
 	},
 
-		% If we are using constraints, save the current solver state
+		% If we are using a trail, save the current trail state
 		% before the first disjunct.
 	code_info__get_globals(Globals),
-	{ globals__lookup_bool_option(Globals, constraints, Constraints) },
-	code_info__maybe_save_ticket(Constraints, SaveTicketCode,
+	{ globals__lookup_bool_option(Globals, use_trail, UseTrail) },
+	code_info__maybe_save_ticket(UseTrail, SaveTicketCode,
 		MaybeTicketSlot),
 
 		% With nondet disjunctions, we must recover memory across
Index: ite_gen.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/ite_gen.m,v
retrieving revision 1.44
diff -u -r1.44 ite_gen.m
--- ite_gen.m	1997/07/27 15:00:41	1.44
+++ ite_gen.m	1997/08/13 14:04:54
@@ -92,10 +92,9 @@
 	},
 	code_info__maybe_save_hp(ReclaimHeap, SaveHPCode, MaybeHpSlot),
 
-		% Maybe save the solver state current before the condition
-	{ globals__lookup_bool_option(Globals, constraints, Constraints) },
-	code_info__maybe_save_ticket(Constraints, SaveTicketCode,
-		MaybeTicketSlot),
+		% Maybe save the current trail state before the condition
+	{ globals__lookup_bool_option(Globals, use_trail, UseTrail) },
+	code_info__maybe_save_ticket(UseTrail, SaveTicketCode, MaybeTicketSlot),
 
 	code_info__grab_code_info(CodeInfo),
 
@@ -205,10 +204,9 @@
 	},
 	code_info__maybe_save_hp(ReclaimHeap, SaveHPCode, MaybeHpSlot),
 
-		% Maybe save the current solver state before the condition
-	{ globals__lookup_bool_option(Globals, constraints, Constraints) },
-	code_info__maybe_save_ticket(Constraints, SaveTicketCode,
-		MaybeTicketSlot),
+		% Maybe save the current trail state before the condition
+	{ globals__lookup_bool_option(Globals, use_trail, UseTrail) },
+	code_info__maybe_save_ticket(UseTrail, SaveTicketCode, MaybeTicketSlot),
 
 	code_info__grab_code_info(CodeInfo),
 
Index: mercury_compile.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/mercury_compile.m,v
retrieving revision 1.51
diff -u -r1.51 mercury_compile.m
--- mercury_compile.m	1997/07/29 01:03:38	1.51
+++ mercury_compile.m	1997/08/13 13:40:57
@@ -1679,11 +1679,11 @@
 	;
 		CompilerType = unknown
 	},
-	globals__io_lookup_bool_option(constraints, Constraints),
-	{ Constraints = yes ->
-		ConstraintsOpt = "-DCONSTRAINTS "
+	globals__io_lookup_bool_option(use_trail, UseTrail),
+	{ UseTrail = yes ->
+		UseTrailOpt = "-DMR_USE_TRAIL "
 	;
-		ConstraintsOpt = ""
+		UseTrailOpt = ""
 	},
 	globals__io_get_args_method(ArgsMethod),
 	{ ArgsMethod = compact ->
@@ -1741,7 +1741,7 @@
 		RegOpt, GotoOpt, AsmOpt,
 		CFLAGS_FOR_REGS, " ", CFLAGS_FOR_GOTOS, " ",
 		GC_Opt, ProfileOpt, TagsOpt, NumTagBitsOpt, DebugOpt,
-		ConstraintsOpt, ArgsOpt, TypeInfoOpt, TypeLayoutOpt,
+		UseTrailOpt, ArgsOpt, TypeInfoOpt, TypeLayoutOpt,
 		InlineAllocOpt, WarningOpt, CFLAGS,
 		" -c ", C_File, " -o ", O_File], Command) },
 	invoke_system_command(Command, Succeeded),
Index: handle_options.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/handle_options.m,v
retrieving revision 1.27
diff -u -r1.27 handle_options.m
--- handle_options.m	1997/07/28 14:57:42	1.27
+++ handle_options.m	1997/08/13 13:48:53
@@ -306,12 +306,12 @@
 	is semidet.
 
 convert_grade_option(Grade0) -->
-	( { string__remove_suffix(Grade0, ".cnstr", Grade1) } ->
+	( { string__remove_suffix(Grade0, ".tr", Grade1) } ->
 		{ Grade2 = Grade1 },
-		set_bool_opt(constraints, yes)
+		set_bool_opt(use_trail, yes)
 	;
 		{ Grade2 = Grade0 },
-		set_bool_opt(constraints, no)
+		set_bool_opt(use_trail, no)
 	),
 	( { string__remove_suffix(Grade2, ".prof", Grade3) } ->
 		{ Grade4 = Grade3 },
Index: options.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/options.m,v
retrieving revision 1.201
diff -u -r1.201 options.m
--- options.m	1997/07/27 15:01:18	1.201
+++ options.m	1997/08/13 13:48:29
@@ -93,7 +93,7 @@
 		;	asm_labels
 		;	gc
 		;	profiling
-		;	constraints
+		;	use_trail
 		;	debug
 		;	debug_data
 		;	tags
@@ -320,7 +320,7 @@
 	asm_labels		-	bool(yes),
 	gc			-	string("conservative"),
 	profiling		-	bool(no),
-	constraints		-	bool(no),
+	use_trail		-	bool(no),
 	debug			-	bool(no),
 	tags			-	string("low"),
 	num_tag_bits		-	int(-1),
@@ -1198,14 +1198,17 @@
 	io__write_string("\t\t\t\t\tother grades use `--gc none'.)\n"),
 	io__write_string("\t\tSpecify which method of garbage collection to use\n"),
 	io__write_string("\t\t(default: conservative).  `accurate' GC is not yet implemented.\n"),
+	io__write_string("\t--use-trail\n"),
+	io__write_string("\t(grades: any grade ending in `.tr')\n"),
+	io__write_string("\t\tEnable use of a trail.\n"),
+	io__write_string("\t\tThis is necessary for interfacing with constraint solvers,\n"),
+	io__write_string("\t\tor for backtrackable destructive update.\n"),
 	io__write_string("\t--profiling\t\t"),
 	io__write_string("\t(grades: any grade ending in `.prof')\n"),
 	io__write_string("\t\tEnable profiling.  Insert profiling hooks in the\n"),
 	io__write_string("\t\tgenerated code, and also output some profiling\n"),
 	io__write_string("\t\tinformation (the static call graph) to the file\n"),
 	io__write_string("\t\t`<module>.prof'.\n"),
-	%io__write_string("\t--constraints\n"),
-	%io__write_string("\t\tInterface with the CLP(R) constraint solver.\n"),
 	io__write_string("\t--debug\t\t\t"),
 	io__write_string("\t(grades: debug)\n"),
 	io__write_string("\t\tEnable debugging.\n"),

Index: mgnuc.in
===================================================================
RCS file: /home/staff/zs/imp/mercury/scripts/mgnuc.in,v
retrieving revision 1.41
diff -u -r1.41 mgnuc.in
--- mgnuc.in	1997/07/27 15:09:32	1.41
+++ mgnuc.in	1997/08/13 14:22:14
@@ -143,8 +143,8 @@
 done
 
 case "$grade" in
-	*.cnstr) CNSTR_OPTS="-DCONSTRAINTS"
-		grade="` expr $grade : '\(.*\).cnstr' `"
+	*.tr) CNSTR_OPTS="-DMR_USE_TRAIL"
+		grade="` expr $grade : '\(.*\).tr' `"
 		;;
 	*)
 		CNSTR_OPTS=""
-- 
Fergus Henderson <fjh at cs.mu.oz.au>   |  "I have always known that the pursuit
WWW: <http://www.cs.mu.oz.au/~fjh>   |  of excellence is a lethal habit"
PGP: finger fjh at 128.250.37.3         |     -- the last words of T. S. Garp.



More information about the developers mailing list