[m-rev.] for review: work around bug #142
Peter Wang
novalazy at gmail.com
Mon May 10 12:37:03 AEST 2010
I don't know what the proper fix should be.
Branches: main, 10.04
Work around bug #142. The symptom is an assertion failure in
hlds.hlds_rtti.apply_substs_to_constraint_map. It occurs when:
- a variable holding a typeclass_info is used multiple times in a call;
- the called procedure is inlined into the caller;
- the corresponding head variables have class constraints with functional
dependencies;
- the type variables in those constraints should be unified, but type variables
in the ranges of functional dependencies are not unified;
- a single typeclass_info variable ends up being for two different constraints.
The work around adopted here is to prevent inlining of a call when a single
typeclass_info variable appears multiple times in the argument list, for which
the head variables have differing class constraints.
compiler/inlining.m:
As above.
tests/valid/Mercury.options:
tests/valid/Mmakefile:
tests/valid/bug142.m:
Add test case.
diff --git a/compiler/inlining.m b/compiler/inlining.m
index 87574a3..1e04d3f 100644
--- a/compiler/inlining.m
+++ b/compiler/inlining.m
@@ -169,6 +169,7 @@
:- import_module int.
:- import_module list.
:- import_module maybe.
+:- import_module multi_map.
:- import_module pair.
:- import_module set.
:- import_module svset.
@@ -647,7 +648,9 @@ inlining_in_call(PredId, ProcId, ArgVars, Builtin,
list.length(CalleeListOfVars, CalleeThisMany),
TotalVars = ThisMany + CalleeThisMany,
TotalVars =< VarThresh
- )
+ ),
+ % XXX Work around bug #142.
+ not may_encounter_bug_142(ProcInfo, ArgVars)
->
do_inline_call(HeadTypeParams, ArgVars, PredInfo, ProcInfo,
VarSet0, VarSet, VarTypes0, VarTypes, TypeVarSet0, TypeVarSet,
@@ -699,6 +702,33 @@ inlining_in_call(PredId, ProcId, ArgVars, Builtin,
GoalInfo = GoalInfo0
).
+:- pred may_encounter_bug_142(proc_info::in, list(prog_var)::in) is semidet.
+
+may_encounter_bug_142(CalleeProcInfo, ArgVars) :-
+ proc_info_get_rtti_varmaps(CalleeProcInfo, RttiVarMaps),
+ proc_info_get_headvars(CalleeProcInfo, HeadVars),
+ multi_map.from_corresponding_lists(ArgVars, HeadVars, MultiMap),
+ some [ArgVar] (
+ list.member(ArgVar, ArgVars),
+ multi_map.lookup(MultiMap, ArgVar, HeadVarsForArgVar),
+ HeadVarsForArgVar = [_ | _],
+ tci_vars_different_constraints(RttiVarMaps, HeadVarsForArgVar)
+ ).
+
+:- pred tci_vars_different_constraints(rtti_varmaps::in, list(prog_var)::in)
+ is semidet.
+
+tci_vars_different_constraints(RttiVarMaps, [VarA, VarB | Vars]) :-
+ (
+ rtti_varmaps_var_info(RttiVarMaps, VarA, VarInfoA),
+ rtti_varmaps_var_info(RttiVarMaps, VarB, VarInfoB),
+ VarInfoA = typeclass_info_var(ConstraintA),
+ VarInfoB = typeclass_info_var(ConstraintB),
+ ConstraintA \= ConstraintB
+ ;
+ tci_vars_different_constraints(RttiVarMaps, [VarB | Vars])
+ ).
+
%-----------------------------------------------------------------------------%
do_inline_call(HeadTypeParams, ArgVars, PredInfo, ProcInfo,
diff --git a/tests/valid/Mercury.options b/tests/valid/Mercury.options
index 4718a74..bc84b5f 100644
--- a/tests/valid/Mercury.options
+++ b/tests/valid/Mercury.options
@@ -41,6 +41,7 @@ MCFLAGS-builtin_false = --intermodule-optimization
MCFLAGS-bug85 = -O0 --deforestation
MCFLAGS-bug100 = --halt-at-warn
MCFLAGS-bug134 = --no-static-ground-terms --no-optimize-dead-procs
+MCFLAGS-bug142 = --optimise-higher-order --inline-single-use
MCFLAGS-compl_unify_bug = -O3
MCFLAGS-constraint_prop_bug = -O0 --common-struct --local-constraint-propagation
MCFLAGS-csharp_hello = --no-intermodule-optimization
diff --git a/tests/valid/Mmakefile b/tests/valid/Mmakefile
index 755156f..3871fe2 100644
--- a/tests/valid/Mmakefile
+++ b/tests/valid/Mmakefile
@@ -66,6 +66,7 @@ OTHER_PROGS= \
bug85 \
bug100 \
bug134 \
+ bug142 \
builtin_false \
call_failure \
common_struct_bug \
diff --git a/tests/valid/bug142.m b/tests/valid/bug142.m
new file mode 100644
index 0000000..6a514c9
--- /dev/null
+++ b/tests/valid/bug142.m
@@ -0,0 +1,53 @@
+% Regression test for bug 142.
+%
+% mmc --optimise-higher-order --inline-single-use -C bug142.m
+% Uncaught Mercury exception:
+% Software Error: hlds_rtti.m: Unexpected: inconsistent typeclass_infos
+
+:- module bug142.
+:- interface.
+
+:- type r(T)
+ ---> ok(T)
+ ; err.
+
+:- type dcg(T, State) == (pred(r(T), State, State)).
+:- mode dcg == in(pred(out, in, out) is det).
+
+:- typeclass dcg(Token, State) <= ((State -> (Token))) where [
+].
+
+:- pred or(dcg(T, State)::dcg, dcg(T, State)::dcg,
+ r(T)::out, State::in, State::out) is det <= dcg(Token, State).
+
+:- pred orr(dcg(T, State)::dcg, dcg(T, State)::dcg, dcg(T, State)::dcg,
+ r(T)::out, State::in, State::out) is det <= dcg(Token, State).
+
+%------------------------------------------------------------------------------%
+%------------------------------------------------------------------------------%
+
+:- implementation.
+
+or(PA, PB, Result, S0, S) :-
+ PA(RA, S0, S1),
+ (
+ RA = ok(V),
+ S = S1,
+ Result = ok(V)
+ ;
+ RA = err,
+ PB(RB, S0, S),
+ (
+ RB = ok(V),
+ Result = ok(V)
+ ;
+ RB = err,
+ Result = err
+ )
+ ).
+
+orr(PA, PB, PC, Result, S0, S) :-
+ or(or(PA, PB), PC, Result, S0, S).
+
+%------------------------------------------------------------------------------%
+% vim: ft=mercury ts=4 sw=4 et
--------------------------------------------------------------------------
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