[m-dev.] diff: bug fix for infinite loop in mode analysis
Fergus Henderson
fjh at cs.mu.oz.au
Mon Jun 16 18:02:46 AEST 1997
Hi,
I wrote:
> Tom, can you please review this one?
>
> compiler/inst_match.m:
> Fix an infinite loop in inst_matches_final for higher-order
> recursive insts.
>
> compiler/mode_util.m:
> Avoid creating insts of the form `typed_inst(..., typed_inst(...))',
> because that is unnecessary, and could lead to inefficiencies or
> perhaps even infinite loops (?).
Sorry, I included the wrong diff with that one. Here is the correct diff.
Index: inst_match.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/inst_match.m,v
retrieving revision 1.29
diff -u -r1.29 inst_match.m
--- inst_match.m 1997/04/10 20:18:32 1.29
+++ inst_match.m 1997/06/16 07:58:37
@@ -265,32 +265,48 @@
% This is true if they both have the same PredOrFunc indicator
% and the same determinism, and if the arguments match
% using pred_inst_argmodes_match.
+ % pred_inst_matches_2(PredInstA, PredInstB, ModuleInfo, Expansions)
+ % Same as pred_inst_matches_2, except that inst pairs in
+ % Expansions are assumed to match_final each other.
+ % (This avoids infinite loops when calling inst_matches_final
+ % on higher-order recursive insts.)
%
:- pred pred_inst_matches(pred_inst_info, pred_inst_info, module_info).
:- mode pred_inst_matches(in, in, in) is semidet.
-pred_inst_matches(pred_inst_info(PredOrFunc, ModesA, Det),
- pred_inst_info(PredOrFunc, ModesB, Det), ModuleInfo) :-
- pred_inst_argmodes_matches(ModesA, ModesB, ModuleInfo).
+pred_inst_matches(PredInstA, PredInstB, ModuleInfo) :-
+ set__init(Expansions),
+ pred_inst_matches_2(PredInstA, PredInstB, ModuleInfo, Expansions).
+
+:- pred pred_inst_matches_2(pred_inst_info, pred_inst_info, module_info,
+ expansions).
+:- mode pred_inst_matches_2(in, in, in, in) is semidet.
+
+pred_inst_matches_2(pred_inst_info(PredOrFunc, ModesA, Det),
+ pred_inst_info(PredOrFunc, ModesB, Det),
+ ModuleInfo, Expansions) :-
+ pred_inst_argmodes_matches(ModesA, ModesB, ModuleInfo, Expansions).
- % pred_inst_matches_argmodes(ModesA, ModesB, ModuleInfo):
+ % pred_inst_matches_argmodes(ModesA, ModesB, ModuleInfo, Expansions):
% succeeds if the initial insts of ModesB specify at least as
% much information as, and the same binding as, the initial
% insts of ModesA; and the final insts of ModesA specify at
% least as much information as, and the same binding as, the
- % final insts of ModesB.
+ % final insts of ModesB. Any inst pairs in Expansions are assumed
+ % to match_final each other.
%
-:- pred pred_inst_argmodes_matches(list(mode), list(mode), module_info).
-:- mode pred_inst_argmodes_matches(in, in, in) is semidet.
+:- pred pred_inst_argmodes_matches(list(mode), list(mode),
+ module_info, expansions).
+:- mode pred_inst_argmodes_matches(in, in, in, in) is semidet.
-pred_inst_argmodes_matches([], [], _).
+pred_inst_argmodes_matches([], [], _, _).
pred_inst_argmodes_matches([ModeA|ModeAs], [ModeB|ModeBs],
- ModuleInfo) :-
+ ModuleInfo, Expansions) :-
mode_get_insts(ModuleInfo, ModeA, InitialA, FinalA),
mode_get_insts(ModuleInfo, ModeB, InitialB, FinalB),
- inst_matches_final(InitialB, InitialA, ModuleInfo),
- inst_matches_final(FinalA, FinalB, ModuleInfo),
- pred_inst_argmodes_matches(ModeAs, ModeBs, ModuleInfo).
+ inst_matches_final_2(InitialB, InitialA, ModuleInfo, Expansions),
+ inst_matches_final_2(FinalA, FinalB, ModuleInfo, Expansions),
+ pred_inst_argmodes_matches(ModeAs, ModeBs, ModuleInfo, Expansions).
:- pred unique_matches_initial(uniqueness, uniqueness).
:- mode unique_matches_initial(in, in) is semidet.
@@ -456,8 +472,9 @@
% of all the constructors for the type in question.
%%% error("not implemented: `ground' matches_final `bound(...)'").
inst_matches_final_3(ground(UniqA, PredInstA), ground(UniqB, PredInstB),
- ModuleInfo, _) :-
- maybe_pred_inst_matches_final(PredInstA, PredInstB, ModuleInfo),
+ ModuleInfo, Expansions) :-
+ maybe_pred_inst_matches_final(PredInstA, PredInstB,
+ ModuleInfo, Expansions),
unique_matches_final(UniqA, UniqB).
/* not yet:
inst_matches_final_2(abstract_inst(_, _), any(shared), _, _).
@@ -468,13 +485,14 @@
inst_matches_final_3(not_reached, _, _, _).
:- pred maybe_pred_inst_matches_final(maybe(pred_inst_info),
- maybe(pred_inst_info), module_info).
-:- mode maybe_pred_inst_matches_final(in, in, in) is semidet.
+ maybe(pred_inst_info), module_info, expansions).
+:- mode maybe_pred_inst_matches_final(in, in, in, in) is semidet.
-maybe_pred_inst_matches_final(no, no, _).
-maybe_pred_inst_matches_final(yes(_), no, _).
-maybe_pred_inst_matches_final(yes(PredInstA), yes(PredInstB), ModuleInfo) :-
- pred_inst_matches(PredInstA, PredInstB, ModuleInfo).
+maybe_pred_inst_matches_final(no, no, _, _).
+maybe_pred_inst_matches_final(yes(_), no, _, _).
+maybe_pred_inst_matches_final(yes(PredInstA), yes(PredInstB),
+ ModuleInfo, Expansions) :-
+ pred_inst_matches_2(PredInstA, PredInstB, ModuleInfo, Expansions).
:- pred inst_list_matches_final(list(inst), list(inst), module_info,
expansions).
Index: mode_util.m
===================================================================
RCS file: /home/staff/zs/imp/mercury/compiler/mode_util.m,v
retrieving revision 1.92
diff -u -r1.92 mode_util.m
--- mode_util.m 1997/06/16 07:19:53 1.92
+++ mode_util.m 1997/06/16 07:52:15
@@ -1258,7 +1258,17 @@
propagate_ctor_info_lazily(defined_inst(InstName0), Type0, Subst, _,
defined_inst(InstName)) :-
apply_type_subst(Type0, Subst, Type),
- InstName = typed_inst(Type, InstName0).
+ ( InstName0 = typed_inst(_, _) ->
+ % If this happens, it means that we have already
+ % lazily propagated type info into this inst.
+ % We want to avoid creating insts of the form
+ % typed_inst(_, typed_inst(...)), because that would be
+ % unnecessary, and could cause efficiency problems
+ % or perhaps even infinite loops (?).
+ InstName = InstName0
+ ;
+ InstName = typed_inst(Type, InstName0)
+ ).
%
% If the user does not explicitly specify a higher-order inst
--
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