[m-rev.] for review: fix a compiler abort trying to reuse static cell

Peter Wang novalazy at gmail.com
Tue Feb 26 15:07:40 AEDT 2008


Estimated hours taken: 4
Branches: main

compiler/var_locn.m:
	Fix a compiler abort where the structure reuse pass would tell the
	code generator to reuse a dead cell, which turns out to be known (at
	compile time) to be static.

tests/valid/Mercury.options:
tests/valid/Mmakefile:
tests/valid/reuse_static.m:
	Add a test case.

Index: compiler/var_locn.m
===================================================================
RCS file: /home/mercury/mercury1/repository/mercury/compiler/var_locn.m,v
retrieving revision 1.60
diff -u -r1.60 var_locn.m
--- compiler/var_locn.m	11 Feb 2008 21:26:12 -0000	1.60
+++ compiler/var_locn.m	26 Feb 2008 03:56:35 -0000
@@ -917,11 +917,28 @@
         MaybeReuse = no_llds_reuse
     ;
         HowToConstruct = reuse_cell(CellToReuse),
-        LldsComment = "Reusing cell on heap for ",
-        assign_reused_cell_to_var(ModuleInfo, Lval, Ptag, Vector, CellToReuse,
-            StartOffset, Label, MaybeReuse, SetupReuseCode, ArgsCode, !VLI),
-        MaybeRegionRval = no,
-        RegionVarCode = empty
+        CellToReuse = cell_to_reuse(ReuseVar, _ReuseConsId, _NeedsUpdates0),
+        var_locn_produce_var(ModuleInfo, ReuseVar, ReuseRval, ReuseVarCode,
+            !VLI),
+        ( ReuseRval = lval(ReuseLval) ->
+            LldsComment = "Reusing cell on heap for ",
+            assign_reused_cell_to_var(ModuleInfo, Lval, Ptag, Vector,
+                CellToReuse, ReuseLval, ReuseVarCode, StartOffset, Label,
+                MaybeReuse, SetupReuseCode, ArgsCode, !VLI),
+            MaybeRegionRval = no,
+            RegionVarCode = empty
+        ;
+            % This can happen if ReuseVar actually points to static data, which
+            % the structure reuse analysis wouldn't have known about.  Fall
+            % back to dynamic allocation.
+            RegionVarCode = empty,
+            MaybeRegionRval = no,
+            LldsComment = "Allocating heap for ",
+            assign_all_cell_args(ModuleInfo, Vector, yes(Ptag), lval(Lval),
+                StartOffset, ArgsCode, !VLI),
+            SetupReuseCode = empty,
+            MaybeReuse = no_llds_reuse
+        )
     ),
     CellCode = node([
         llds_instr(
@@ -933,20 +950,14 @@
     Code = tree_list([SetupReuseCode, CellCode, RegionVarCode, ArgsCode]).
 
 :- pred assign_reused_cell_to_var(module_info::in, lval::in, tag::in,
-    list(maybe(rval))::in, cell_to_reuse::in, int::in, label::in,
-    llds_reuse::out, code_tree::out, code_tree::out,
+    list(maybe(rval))::in, cell_to_reuse::in, lval::in, code_tree::in,
+    int::in, label::in, llds_reuse::out, code_tree::out, code_tree::out,
     var_locn_info::in, var_locn_info::out) is det.
 
 assign_reused_cell_to_var(ModuleInfo, Lval, Ptag, Vector, CellToReuse,
-        StartOffset, Label, MaybeReuse, SetupReuseCode, ArgsCode, !VLI) :-
+        ReuseLval, ReuseVarCode, StartOffset, Label, MaybeReuse,
+        SetupReuseCode, ArgsCode, !VLI) :-
     CellToReuse = cell_to_reuse(ReuseVar, _ReuseConsId, NeedsUpdates0),
-    var_locn_produce_var(ModuleInfo, ReuseVar, ReuseRval, ReuseVarCode, !VLI),
-    ( ReuseRval = lval(ReuseLval0) ->
-        ReuseLval = ReuseLval0
-    ;
-        unexpected(this_file,
-            "var_locn_assign_reused_cell_to_var: reused cell not an lval")
-    ),
 
     % Save any variables which are available only in the reused cell into
     % temporary registers.
Index: tests/valid/Mercury.options
===================================================================
RCS file: /home/mercury/mercury1/repository/tests/valid/Mercury.options,v
retrieving revision 1.44
diff -u -r1.44 Mercury.options
--- tests/valid/Mercury.options	11 Feb 2008 21:27:48 -0000	1.44
+++ tests/valid/Mercury.options	26 Feb 2008 03:56:35 -0000
@@ -97,6 +97,7 @@
 MCFLAGS-par_saved_const 	= -O3 --optimize-saved-vars-const
 MCFLAGS-pred_with_no_modes	= --infer-all
 MCFLAGS-quantifier_warning	= --halt-at-warn
+MCFLAGS-reuse_static		= --ctgc --deforestation
 MCFLAGS-simplify_bug2		= -O3
 MCFLAGS-simplify_bug		= -O-1
 MCFLAGS-solver_type_bug		= --halt-at-warn
Index: tests/valid/Mmakefile
===================================================================
RCS file: /home/mercury/mercury1/repository/tests/valid/Mmakefile,v
retrieving revision 1.206
diff -u -r1.206 Mmakefile
--- tests/valid/Mmakefile	11 Feb 2008 21:27:48 -0000	1.206
+++ tests/valid/Mmakefile	26 Feb 2008 03:56:35 -0000
@@ -190,6 +190,7 @@
 	record_syntax_bug_5 \
 	recursive_no_tag_type \
 	reg_bug \
+	reuse_static \
 	same_length_2 \
 	semidet_disj \
 	shape_type \
Index: tests/valid/reuse_static.m
===================================================================
RCS file: tests/valid/reuse_static.m
diff -N tests/valid/reuse_static.m
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ tests/valid/reuse_static.m	26 Feb 2008 03:56:35 -0000
@@ -0,0 +1,62 @@
+% Regression test.  The compiler aborted if trying the structure reuse pass
+% tried to reuse a cell which later is known, at compile time, to be static
+% data.
+
+:- module reuse_static.
+:- interface.
+
+:- pred gen_gc_trace_func(foo_entity_name::in, foo_code_addr::out,
+    foo_func_params::out, foo_func_params::out) is det.
+
+:- implementation.
+
+:- import_module list.
+:- import_module require.
+
+%-----------------------------------------------------------------------------%
+
+:- type foo_code_addr
+    --->    code_addr_internal(string, foo_func_signature).
+
+:- type foo_type
+     --->      foo_generic_type.
+
+:- type foo_entity_name
+    --->    entity_data
+    ;       entity_function(string).
+
+:- type foo_func_signature
+    --->    foo_func_signature(list(foo_type)).
+
+:- type foo_func_params
+    --->    foo_func_params(list(foo_argument)).
+
+:- type foo_argument
+    --->    foo_argument(foo_entity_name, foo_type).
+
+%-----------------------------------------------------------------------------%
+
+gen_gc_trace_func(FuncName, GCTraceFuncAddr, FuncParams, FuncParams) :-
+    Argument = foo_argument(entity_data, foo_generic_type),
+    Parameters = [Argument],
+    FuncParams = foo_func_params(Parameters), % static data
+    % Deforestation turns the following call into three goals.
+    % The bug is not triggered if we write those goals directly.
+    ParamTypes = foo_map(Parameters),
+    Signature = foo_func_signature(ParamTypes),
+    (
+        FuncName = entity_function(PredLabel),
+        GCTraceFuncAddr = code_addr_internal(PredLabel, Signature)
+    ;
+        FuncName = entity_data,
+        error("gen_gc_trace_func: not a function")
+    ).
+
+:- func foo_map(list(foo_argument)) = list(foo_type).
+
+foo_map([]) = [].
+foo_map([H0 | T0]) = [H | T] :-
+    H0 = foo_argument(_, H),
+    foo_map(T0) = T.
+
+%-----------------------------------------------------------------------------%


--------------------------------------------------------------------------
mercury-reviews mailing list
Post messages to:       mercury-reviews at csse.unimelb.edu.au
Administrative Queries: owner-mercury-reviews at csse.unimelb.edu.au
Subscriptions:          mercury-reviews-request at csse.unimelb.edu.au
--------------------------------------------------------------------------



More information about the reviews mailing list