[m-dev.] GCC back-end: fix GC bug

Fergus Henderson fjh at cs.mu.OZ.AU
Sun Jan 21 03:57:05 AEDT 2001


Estimated hours taken: 3

Fix a bug where GCC's garbage collector was prematurely collecting
tree nodes that were referenced only from Mercury data structures.

compiler/gcc.m:
	Add interfaces to ggc_push_context() and ggc_pop_context().

compiler/mlds_to_gcc.m:
	Call them.

----------

cvs diff: Diffing .
Index: gcc.m
===================================================================
RCS file: /home/mercury1/repository/mercury/compiler/gcc.m,v
retrieving revision 1.16
diff -u -d -u -r1.16 gcc.m
--- gcc.m	2001/01/18 15:43:42	1.16
+++ gcc.m	2001/01/20 16:27:39
@@ -29,6 +29,16 @@
 % gcc back-end; we only define interfaces to those parts of the gcc
 % back-end that we need for compiling Mercury.
 %
+% GARBAGE COLLECTION
+%
+% The GCC compiler uses its own garbage collector (see gcc/ggc.h).
+% This garbage collector only collects memory when ggc_collect()
+% is called, which currently only happens in rest_of_compilation(),
+% which is called from gcc__end_function//0.  But it requires
+% that all pointers to the GCC heap be either explicitly registered
+% with e.g. ggc_register_tree_root(), or protected by calling
+% gcc__push_context//0 and gcc__pop_context//0.
+%
 % REFERENCES
 %
 % For more information about the GCC compiler back-end,
@@ -466,6 +477,22 @@
 
 %-----------------------------------------------------------------------------%
 %
+% Routines to protect memory from being collected by the GCC garbage
+% collector (see gcc/ggc.h).
+%
+
+	% This starts a new GGC context.  Memory allocated in previous contexts
+	% will not be collected while the new context is active.
+:- pred push_gc_context(io__state, io__state).
+:- mode push_gc_context(di, uo) is det.
+
+	% Finish a GC context.  Any uncollected memory in the new context
+	% will be merged with the old context.
+:- pred pop_gc_context(io__state, io__state).
+:- mode pop_gc_context(di, uo) is det.
+
+%-----------------------------------------------------------------------------%
+%
 % Functions
 %
 
@@ -474,6 +501,13 @@
 :- mode start_function(in, di, uo) is det.
 
 	% finish generating code for a function
+	% WARNING: this will invoke the GCC garbage collector.
+	% So any GCC tree nodes which are referenced only from the stack(s),
+	% from Mercury data structures, or from global variables, and which
+	% were allocated since the most recent call to gcc__push_gc_context,
+	% must be registered as roots (e.g. using ggc_add_tree_root())
+	% when this is called.  Generally it is easier to call
+	% gcc__push_gc_context.
 :- pred end_function(io__state, io__state).
 :- mode end_function(di, uo) is det.
 
@@ -608,6 +642,7 @@
 #include ""gcc/tree.h""
 /* XXX we should eliminate the dependency on the C front-end */
 #include ""gcc/c-tree.h""
+#include ""gcc/ggc.h""
 
 #include ""gcc/mercury/mercury-gcc.h""
 
@@ -1196,6 +1234,18 @@
 	Expr = (MR_Word) build(CONSTRUCTOR, (tree) Type, NULL_TREE,
 		(tree) InitList);
 ").
+
+%-----------------------------------------------------------------------------%
+%
+% Routines to protect memory from being collected by the GCC garbage
+% collector (see gcc/ggc.h).
+%
+
+:- pragma import(push_gc_context(di, uo), [will_not_call_mercury],
+	"ggc_push_context").
+
+:- pragma import(pop_gc_context(di, uo), [will_not_call_mercury],
+	"ggc_pop_context").
 
 %-----------------------------------------------------------------------------%
 %
Index: mlds_to_gcc.m
===================================================================
RCS file: /home/mercury1/repository/mercury/compiler/mlds_to_gcc.m,v
retrieving revision 1.23
diff -u -d -u -r1.23 mlds_to_gcc.m
--- mlds_to_gcc.m	2001/01/20 15:42:46	1.23
+++ mlds_to_gcc.m	2001/01/20 16:28:57
@@ -1500,6 +1500,7 @@
 		{ MaybeBody = no }
 	;
 		{ MaybeBody = yes(Body) },
+		gcc__push_gc_context,
 		make_func_decl_for_defn(Name, Signature, GlobalInfo0,
 			FuncDecl, SymbolTable),
 		add_func_decl_flags(Flags, FuncDecl),
@@ -1511,7 +1512,8 @@
 		% mlds_maybe_output_time_profile_instr(Context, Name)
 		gen_statement(DefnInfo, Body),
 		set_context(Context),
-		gcc__end_function
+		gcc__end_function,
+		gcc__pop_gc_context
 	).
 
 	%
cvs diff: Diffing notes

-- 
Fergus Henderson <fjh at cs.mu.oz.au>  |  "I have always known that the pursuit
                                    |  of excellence is a lethal habit"
WWW: <http://www.cs.mu.oz.au/~fjh>  |     -- the last words of T. S. Garp.
--------------------------------------------------------------------------
mercury-developers mailing list
Post messages to:       mercury-developers at cs.mu.oz.au
Administrative Queries: owner-mercury-developers at cs.mu.oz.au
Subscriptions:          mercury-developers-request at cs.mu.oz.au
--------------------------------------------------------------------------



More information about the developers mailing list