[m-rev.] for review: allow paths with field names for subterm tracking
Ian MacLarty
maclarty at cs.mu.OZ.AU
Mon Feb 6 01:59:33 AEDT 2006
For reeview by anyone.
Estimated hours taken: 5
Branches: main
Allow field names to be used in the paths used with subterm dependency
tracking.
Allow the user to cd to the return value of a function by giving the
number of arguments plus one as an argument to the `cd' command.
browser/browse.m:
Export the predicate that removed ".." from paths.
Make the return value of this predicate a subtype, so we can be
sure the simplification has been applied to the path.
Allow the user to do `cd N', where N is the number of arguments of
a function plus one. This will cd to the return value of the function.
Add some more aliases for the directory name of the return value of a
function.
browser/browser_info.m:
Use the new simplified_dirs inst.
When converting a list of directories to a term path, look at the
value the path applies to to resolve field names in the path.
browser/declarative_user.m:
Report an error if the user tries to track an I/O action.
Call the new version of convert_dirs_to_term_path which handles
field names in the path.
browser/term_rep.m:
Add predicates to lookup a subterm in a term representation and
also to look up a named field in a term representation.
tests/debugger/declarative/Mercury.options:
tests/debugger/declarative/Mmakefile:
tests/debugger/declarative/named_fields.exp:
tests/debugger/declarative/named_fields.inp:
tests/debugger/declarative/named_fields.m:
Test tracking of subterms using a path with a field name.
tests/debugger/polymorphic_output.exp*
The output of this test has changed, because cd's to the return value
of a function, using a number, are now allowed.
Index: browser/browse.m
===================================================================
RCS file: /home/mercury1/repository/mercury/browser/browse.m,v
retrieving revision 1.54
diff -u -r1.54 browse.m
--- browser/browse.m 2 Nov 2005 14:02:05 -0000 1.54
+++ browser/browse.m 5 Feb 2006 10:01:53 -0000
@@ -145,6 +145,18 @@
:- pred save_term_to_file_xml(string::in, browser_term::in,
io__output_stream::in, io::di, io::uo) is cc_multi.
+ % Remove "/dir/../" sequences from a list of directories to yield
+ % a form that lacks ".." entries.
+ % If there are more ".." entries than normal entries then the
+ % empty list is returned.
+ %
+:- pred simplify_dirs(list(dir)::in, list(dir)::out(simplified_dirs)) is det.
+
+ % True if the given string can be used to cd to the return value of a
+ % function.
+ %
+:- pred string_is_return_value_alias(string::in) is semidet.
+
%---------------------------------------------------------------------------%
:- implementation.
@@ -1390,19 +1402,20 @@
(
(
Step = child_num(N),
- % The first argument of a non-array
- % is numbered argument 1.
- list__index1(Args, N, ArgUniv)
- ;
- Step = child_name(Name),
- MaybeReturn = yes(ArgUniv),
- ( Name = "r"
- ; Name = "res"
- ; Name = "result"
+ (
+ N = list.length(Args) + 1,
+ MaybeReturn = yes(ReturnValue)
+ ->
+ ArgUniv = ReturnValue
+ ;
+ % The first argument of a non-array
+ % is numbered argument 1.
+ list__index1(Args, N, ArgUniv)
)
;
- Step = parent,
- error("deref_subterm: found parent")
+ Step = child_name(Name),
+ string_is_return_value_alias(Name),
+ MaybeReturn = yes(ArgUniv)
)
->
deref_subterm_2(ArgUniv, SimplifiedPathTail,
@@ -1414,6 +1427,13 @@
)
).
+string_is_return_value_alias("r").
+string_is_return_value_alias("res").
+string_is_return_value_alias("rv").
+string_is_return_value_alias("result").
+string_is_return_value_alias("return").
+string_is_return_value_alias("ret").
+
:- pred deref_result_univ_to_browser_term(deref_result(univ)::in,
deref_result(browser_term)::out) is det.
@@ -1649,11 +1669,6 @@
not_slash(C) :-
C \= ('/').
- % Remove "/dir/../" sequences from a list of directories to yield
- % a form that lacks ".." entries.
- %
-:- pred simplify_dirs(list(dir)::in, list(dir)::out) is det.
-
simplify_dirs(Dirs, SimpleDirs) :-
list.reverse(Dirs, RevDirs),
simplify_rev_dirs(RevDirs, 0, [], SimpleDirs).
@@ -1666,14 +1681,16 @@
% SoFar accumulates the simplified dirs processed so far so we can be
% tail recursive.
%
-:- pred simplify_rev_dirs(list(dir)::in, int::in, list(dir)::in,
- list(dir)::out) is det.
+:- pred simplify_rev_dirs(list(dir)::in, int::in,
+ list(dir)::in(simplified_dirs), list(dir)::out(simplified_dirs)) is det.
simplify_rev_dirs([], _, SimpleDirs, SimpleDirs).
simplify_rev_dirs([Dir | Dirs], N, SoFar, SimpleDirs) :-
- ( Dir = parent ->
+ (
+ Dir = parent,
simplify_rev_dirs(Dirs, N+1, SoFar, SimpleDirs)
;
+ ( Dir = child_num(_) ; Dir = child_name(_) ),
( N > 0 ->
simplify_rev_dirs(Dirs, N-1, SoFar, SimpleDirs)
;
Index: browser/browser_info.m
===================================================================
RCS file: /home/mercury1/repository/mercury/browser/browser_info.m,v
retrieving revision 1.21
diff -u -r1.21 browser_info.m
--- browser/browser_info.m 2 Nov 2005 14:02:05 -0000 1.21
+++ browser/browser_info.m 5 Feb 2006 00:08:12 -0000
@@ -16,6 +16,7 @@
:- import_module mdb.browser_term.
:- import_module mdb.parse.
+:- import_module mdb.term_rep.
:- import_module mdbcomp.program_representation.
:- import_module bool.
@@ -95,6 +96,12 @@
; child_num(int)
; child_name(string).
+:- inst dir_no_parent
+ ---> child_num(ground)
+ ; child_name(ground).
+
+:- inst simplified_dirs == list_skel(dir_no_parent).
+
% The browser is required to behave differently for different
% caller circumstances. The following type enumerates the
% various possibilities.
@@ -160,7 +167,8 @@
:- func browser_info__get_num_printed_io_actions(browser_persistent_state)
= int.
-:- pred convert_dirs_to_term_path(list(dir)::in, term_path::out) is det.
+:- pred convert_dirs_to_term_path(term_rep::in,
+ list(dir)::in(simplified_dirs), term_path::out) is det.
%---------------------------------------------------------------------------%
@@ -243,8 +251,12 @@
:- implementation.
:- import_module deconstruct.
+:- import_module int.
:- import_module io.
:- import_module require.
+:- import_module string.
+
+:- import_module mdb.term_rep.
:- pragma export(browser_info__init_persistent_state(out),
"ML_BROWSE_init_persistent_state").
@@ -711,12 +723,26 @@
%---------------------------------------------------------------------------%
-convert_dirs_to_term_path([], []).
-convert_dirs_to_term_path([child_num(N) | Dirs], [N | TermPath]) :-
- convert_dirs_to_term_path(Dirs, TermPath).
-convert_dirs_to_term_path([child_name(_) | _], _) :-
- error("convert_dirs_to_term_path: not in canonical form").
-convert_dirs_to_term_path([parent | _], _) :-
- error("convert_dirs_to_term_path: not in canonical form").
+convert_dirs_to_term_path(_, [], []).
+convert_dirs_to_term_path(Term, [child_num(N) | Dirs], [N | TermPath]) :-
+ (
+ term_rep.argument(Term, N, Subterm)
+ ->
+ convert_dirs_to_term_path(Subterm, Dirs, TermPath)
+ ;
+ error("convert_dirs_to_term_path:" ++
+ "invalid argument")
+ ).
+convert_dirs_to_term_path(Term, [child_name(Name) | Dirs], [N | TermPath]) :-
+ (
+ term_rep.field_pos(Name, Term, Pos),
+ term_rep.argument(Term, Pos, Subterm)
+ ->
+ convert_dirs_to_term_path(Subterm, Dirs, TermPath),
+ N = Pos
+ ;
+ error("convert_dirs_to_term_path:" ++
+ "invalid field name")
+ ).
%---------------------------------------------------------------------------%
Index: browser/declarative_user.m
===================================================================
RCS file: /home/mercury1/repository/mercury/browser/declarative_user.m,v
retrieving revision 1.55
diff -u -r1.55 declarative_user.m
--- browser/declarative_user.m 4 Nov 2005 07:27:24 -0000 1.55
+++ browser/declarative_user.m 5 Feb 2006 13:26:16 -0000
@@ -525,12 +525,19 @@
:- pred browse_io_action(io_action::in, maybe_track_subterm(term_path)::out,
user_state::in, user_state::out, io::di, io::uo) is cc_multi.
-browse_io_action(IoAction, MaybeTrack, !User, !IO) :-
+browse_io_action(IoAction, no_track, !User, !IO) :-
Term = io_action_to_browser_term(IoAction),
browse_browser_term(Term, !.User ^ instr, !.User ^ outstr, no,
MaybeTrackDirs, !.User ^ browser, Browser, !IO),
- convert_maybe_track_dirs_to_term_path(MaybeTrackDirs,
- MaybeTrack),
+ (
+ MaybeTrackDirs = track(_, _, _),
+ io.write_string(!.User ^ outstr,
+ "Sorry, tracking of I/O actions is not yet " ++
+ "supported.\n", !IO),
+ browse_io_action(IoAction, _, !User, !IO)
+ ;
+ MaybeTrackDirs = no_track
+ ),
!:User = !.User ^ browser := Browser.
:- pred browse_decl_bug(decl_bug::in, maybe(int)::in, user_state::in,
@@ -578,7 +585,7 @@
yes(get_subterm_mode_from_atoms_for_arg(ArgNum,
InitAtom, FinalAtom)),
MaybeTrackDirs, !.User ^ browser, Browser, !IO),
- convert_maybe_track_dirs_to_term_path(
+ convert_maybe_track_dirs_to_term_path_from_arg(ArgRep,
MaybeTrackDirs, MaybeTrack),
!:User = !.User ^ browser := Browser
;
@@ -622,7 +629,7 @@
browse_browser_term(BrowserTerm, !.User ^ instr, !.User ^ outstr,
yes(get_subterm_mode_from_atoms(InitAtom, FinalAtom)),
MaybeTrackDirs, !.User ^ browser, Browser, !IO),
- convert_maybe_track_dirs_to_term_path(
+ convert_maybe_track_dirs_to_term_path_from_atom(FinalAtom,
MaybeTrackDirs, MaybeTrack),
!:User = !.User ^ browser := Browser.
@@ -641,11 +648,11 @@
save_and_browse_browser_term_xml(BrowserTerm, User ^ outstr,
User ^ outstr, User ^ browser, !IO).
-:- func get_subterm_mode_from_atoms(trace_atom, trace_atom, list(dir))
- = browser_term_mode.
+:- func get_subterm_mode_from_atoms(trace_atom::in, trace_atom::in,
+ list(dir)::in(simplified_dirs)) = (browser_term_mode::out) is det.
get_subterm_mode_from_atoms(InitAtom, FinalAtom, Dirs) = Mode :-
- convert_dirs_to_term_path(Dirs, Path),
+ convert_dirs_to_term_path_from_atom(FinalAtom, Dirs, Path),
(
Path = [ArgNum | TermPath],
ArgPos = arg_num_to_arg_pos(ArgNum),
@@ -669,12 +676,13 @@
Mode = unbound
).
-:- func get_subterm_mode_from_atoms_for_arg(int, trace_atom, trace_atom,
- list(dir)) = browser_term_mode.
+:- func get_subterm_mode_from_atoms_for_arg(int::in, trace_atom::in,
+ trace_atom::in, list(dir)::in(simplified_dirs)) =
+ (browser_term_mode::out) is det.
get_subterm_mode_from_atoms_for_arg(ArgNum, InitAtom, FinalAtom, Dirs)
= Mode :-
- convert_dirs_to_term_path(Dirs, TermPath),
+ convert_dirs_to_term_path_from_atom(FinalAtom, Dirs, TermPath),
ArgPos = arg_num_to_arg_pos(ArgNum),
Mode = get_subterm_mode_from_atoms_and_term_path(InitAtom, FinalAtom,
ArgPos, TermPath).
@@ -734,14 +742,29 @@
OK = no
).
-:- pred convert_maybe_track_dirs_to_term_path(
- maybe_track_subterm(list(dir))::in,
+:- pred convert_maybe_track_dirs_to_term_path_from_atom(
+ trace_atom::in,
+ maybe_track_subterm(list(dir))::in,
+ maybe_track_subterm(term_path)::out) is det.
+
+convert_maybe_track_dirs_to_term_path_from_atom(_, no_track, no_track).
+convert_maybe_track_dirs_to_term_path_from_atom(Atom,
+ track(HowTrack, ShouldAssertInvalid, Dirs),
+ track(HowTrack, ShouldAssertInvalid, TermPath)) :-
+ simplify_dirs(Dirs, SimplifiedDirs),
+ convert_dirs_to_term_path_from_atom(Atom, SimplifiedDirs, TermPath).
+
+:- pred convert_maybe_track_dirs_to_term_path_from_arg(
+ term_rep::in,
+ maybe_track_subterm(list(dir))::in,
maybe_track_subterm(term_path)::out) is det.
-convert_maybe_track_dirs_to_term_path(no_track, no_track).
-convert_maybe_track_dirs_to_term_path(track(HowTrack, ShouldAssertInvalid,
- Dirs), track(HowTrack, ShouldAssertInvalid, TermPath)) :-
- convert_dirs_to_term_path(Dirs, TermPath).
+convert_maybe_track_dirs_to_term_path_from_arg(_, no_track, no_track).
+convert_maybe_track_dirs_to_term_path_from_arg(Term,
+ track(HowTrack, ShouldAssertInvalid, Dirs),
+ track(HowTrack, ShouldAssertInvalid, TermPath)) :-
+ simplify_dirs(Dirs, SimplifiedDirs),
+ convert_dirs_to_term_path(Term, SimplifiedDirs, TermPath).
% Reverse the first argument and append the second to it.
%
@@ -1274,3 +1297,52 @@
set_user_testing_flag(Testing, User, User ^ testing := Testing).
%-----------------------------------------------------------------------------%
+
+:- pred convert_dirs_to_term_path_from_atom(trace_atom::in,
+ list(dir)::in(simplified_dirs), term_path::out) is det.
+
+convert_dirs_to_term_path_from_atom(_, [], []).
+convert_dirs_to_term_path_from_atom(atom(_, Args), [Dir | Dirs], TermPath) :-
+ (
+ Dir = child_num(Pos),
+ Arg = list.det_index1(Args, Pos),
+ Arg = arg_info(_, _, MaybeValue)
+ ;
+ Dir = child_name(Name),
+ ( string_is_return_value_alias(Name) ->
+ ( list.last(Args, LastArg) ->
+ LastArg = arg_info(_, _, MaybeValue),
+ Pos = list.length(Args)
+ ;
+ throw(internal_error(
+ "convert_dirs_to_term_path_from_atom",
+ "argument list empty"))
+ )
+ ;
+ throw(internal_error(
+ "convert_dirs_to_term_path_from_atom",
+ "argument of atom cannot be named"))
+ )
+ ),
+ (
+ MaybeValue = yes(TermRep),
+ convert_dirs_to_term_path(TermRep, Dirs, TermPath0),
+ TermPath = [Pos | TermPath0]
+ ;
+ MaybeValue = no,
+ (
+ % The user can cd to an unbound argument, but they
+ % can't cd into subterms of an unbound argument.
+ (
+ Dirs = [],
+ TermPath = [Pos]
+ ;
+ Dirs = [_ | _],
+ throw(internal_error(
+ "convert_dirs_to_term_path_from_atom",
+ "no value for first position in path"))
+ )
+ )
+ ).
+
+%-----------------------------------------------------------------------------%
Index: browser/term_rep.m
===================================================================
RCS file: /home/mercury1/repository/mercury/browser/term_rep.m,v
retrieving revision 1.5
diff -u -r1.5 term_rep.m
--- browser/term_rep.m 2 Nov 2005 14:02:07 -0000 1.5
+++ browser/term_rep.m 5 Feb 2006 09:35:46 -0000
@@ -30,14 +30,28 @@
:- pred rep_to_univ(term_rep::in, univ::out) is det.
+ % argumnet(Term, N, Subterm).
+ % True iff Subterm is the Nth argument of Term.
+ %
+:- pred argument(term_rep::in, int::in, term_rep::out) is semidet.
+
:- pred deref_path(term_rep::in, term_path::in, term_rep::out) is semidet.
+ % field_pos(FieldName, Term, N).
+ % True iff argument N of Term has the name FieldName.
+ %
+:- pred field_pos(string::in, term_rep::in, int::out) is semidet.
+
%-----------------------------------------------------------------------------%
:- implementation.
+:- import_module exception.
:- import_module int.
:- import_module list.
+:- import_module string.
+
+:- import_module mdb.declarative_debugger.
:- type term_rep
---> term_rep(univ)
@@ -75,17 +89,84 @@
SubTerm = Term
;
Path = [Head | Tail],
- %
- % There is only one representation of a subterm, given
- % the representation of the containing term and a term path.
- %
- promise_equivalent_solutions [NextSubTerm] (
- rep_to_univ(Term, Univ),
- % Argument indexes in the term path start from one, but
- % the argument function wants argument indexes to
- % start from zero.
- SubUniv = argument(univ_value(Univ), Head - 1),
- univ_to_rep(SubUniv, NextSubTerm)
- ),
+ argument(Term, Head, NextSubTerm),
deref_path(NextSubTerm, Tail, SubTerm)
).
+
+argument(Term, N, Arg) :-
+ %
+ % There is only one representation of a subterm, given
+ % the representation of the containing term and a term path.
+ %
+ promise_equivalent_solutions [MaybeArg] (
+ rep_to_univ(Term, Univ),
+ % Argument indexes in the term path start from one, but
+ % the argument function wants argument indexes to
+ % start from zero.
+ argument_cc(univ_value(Univ), N - 1, MaybeSubUniv),
+ (
+ MaybeSubUniv = yes(SubUniv),
+ univ_to_rep(SubUniv, Arg0),
+ MaybeArg = yes(Arg0)
+ ;
+ MaybeSubUniv = no,
+ MaybeArg = no
+ )
+ ),
+ MaybeArg = yes(Arg).
+
+field_pos(FieldName, Term, Pos) :-
+ %
+ % There is only one or zero positions of a field
+ % given a representation of a term and the field name.
+ %
+ promise_equivalent_solutions [MaybePos] (
+ rep_to_univ(Term, Univ),
+ Value = univ_value(Univ),
+ deconstruct_cc(Value, Functor, Arity, _Args),
+ Type = type_of(Value),
+ find_functor(1, num_functors(Type), Type, Functor, Arity,
+ MaybeFunctorNum),
+ (
+ MaybeFunctorNum = yes(FunctorNum),
+ (
+ get_functor_with_names(Type, FunctorNum - 1,
+ _FunctorName, _Arity, _ArgTypes,
+ ArgNames)
+ ->
+ (
+ nth_member_search(ArgNames,
+ yes(FieldName), Pos0)
+ ->
+ MaybePos = yes(Pos0)
+ ;
+ MaybePos = no
+ )
+ ;
+ throw(internal_error("field_pos",
+ "get_functor_with_names " ++
+ "couldn't find functor"))
+ )
+ ;
+ MaybeFunctorNum = no,
+ throw(internal_error("field_pos",
+ "find_functor couldn't find functor"))
+ )
+ ),
+ MaybePos = yes(Pos).
+
+:- pred find_functor(int::in, int::in, type_desc::in, string::in, int::in,
+ maybe(int)::out) is det.
+
+find_functor(Current, NumFunctors, Type, FunctorName, Arity, MaybeFunctorNum)
+ :-
+ ( if Current =< NumFunctors then
+ ( get_functor(Type, Current - 1, FunctorName, Arity, _) ->
+ MaybeFunctorNum = yes(Current)
+ ;
+ find_functor(Current + 1, NumFunctors, Type,
+ FunctorName, Arity, MaybeFunctorNum)
+ )
+ else
+ MaybeFunctorNum = no
+ ).
Index: tests/debugger/polymorphic_output.exp3
===================================================================
RCS file: /home/mercury1/repository/tests/debugger/polymorphic_output.exp3,v
retrieving revision 1.10
diff -u -r1.10 polymorphic_output.exp3
--- tests/debugger/polymorphic_output.exp3 16 Nov 2004 00:16:39 -0000 1.10
+++ tests/debugger/polymorphic_output.exp3 5 Feb 2006 13:54:10 -0000
@@ -40,13 +40,12 @@
browser> p
two("three", 3, three("four", 4, "one", 1, empty, empty, empty), two("two", 2, empty, empty))
browser> ^..^2
-error: there is no subterm 2
browser> p
-two("three", 3, three("four", 4, "one", 1, empty, empty, empty), two("two", 2, empty, empty))
+'_'
browser> ^..^3
error: there is no subterm 3
browser> p
-two("three", 3, three("four", 4, "one", 1, empty, empty, empty), two("two", 2, empty, empty))
+'_'
browser> ^..^r
browser> p
'_'
Index: tests/debugger/declarative/Mercury.options
===================================================================
RCS file: /home/mercury1/repository/tests/debugger/declarative/Mercury.options,v
retrieving revision 1.13
diff -u -r1.13 Mercury.options
--- tests/debugger/declarative/Mercury.options 2 Nov 2005 14:17:37 -0000 1.13
+++ tests/debugger/declarative/Mercury.options 5 Feb 2006 09:36:22 -0000
@@ -1,5 +1,6 @@
MCFLAGS-deep_sub=--trace rep --suppress-trace context
MCFLAGS-io_tab_impure=--trace rep --trace-table-io-all
+MCFLAGS-named_fields=--trace rep --trace-table-io-all
MCFLAGS-nodescend_tracking=--trace rep --trace-table-io-all
MCFLAGS-shallow_2=--trace shallow
MCFLAGS-tabled_read_decl=--trace rep --trace-table-io-all
Index: tests/debugger/declarative/Mmakefile
===================================================================
RCS file: /home/mercury1/repository/tests/debugger/declarative/Mmakefile,v
retrieving revision 1.88
diff -u -r1.88 Mmakefile
--- tests/debugger/declarative/Mmakefile 8 Dec 2005 20:38:45 -0000 1.88
+++ tests/debugger/declarative/Mmakefile 5 Feb 2006 10:24:56 -0000
@@ -49,6 +49,7 @@
lpe_example \
mapinit \
mismatch_on_call \
+ named_fields \
negation \
neg_conj \
nodescend_tracking \
@@ -408,6 +409,11 @@
> nodescend_tracking.out 2>&1 \
|| { grep . $@ /dev/null; exit 1; }
+named_fields.out: named_fields named_fields.inp
+ $(MDB_STD) ./named_fields < named_fields.inp \
+ > named_fields.out 2>&1 \
+ || { grep . $@ /dev/null; exit 1; }
+
negation.out: negation negation.inp
$(MDB) ./negation < negation.inp > negation.out 2>&1 \
|| { grep . $@ /dev/null; exit 1; }
Index: tests/debugger/declarative/named_fields.exp
===================================================================
RCS file: tests/debugger/declarative/named_fields.exp
diff -N tests/debugger/declarative/named_fields.exp
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ tests/debugger/declarative/named_fields.exp 5 Feb 2006 13:38:32 -0000
@@ -0,0 +1,101 @@
+ E1: C1 CALL pred named_fields.main/2-0 (det) named_fields.m:11
+mdb> mdb> mdb> I/O tabling started.
+mdb> echo on
+Command echo enabled.
+mdb> break swap
+ 0: + stop interface func named_fields.swap/1-0 (det)
+mdb> c
+ E2: C2 CALL func named_fields.swap/1-0 (det) named_fields.m:27 (named_fields.m:13)
+mdb> f
+ E3: C2 EXIT func named_fields.swap/1-0 (det) named_fields.m:27 (named_fields.m:13)
+mdb> dd -a
+swap(t(1, 2)) = t(2, 1)
+Valid? browse
+browser> cd 1/field1
+browser> ls
+1
+browser> track
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse 1
+browser> cd field1
+browser> ls
+1
+browser> track
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse
+browser> cd 2/field2
+browser> ls
+1
+browser> track
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse
+browser> cd result/field2
+browser> ls
+1
+browser> track
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse 2
+browser> cd field2
+browser> ls
+1
+browser> track
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse 2
+browser> track field2
+gen_t(t(1, 2))
+Valid? info
+Context of current question : named_fields.m:23 (named_fields.m:12)
+Search mode : top down
+The current question was chosen because the marked subterm was bound by
+the unification inside the predicate named_fields.gen_t/1
+(named_fields.m:23). The path to the subterm in the atom is 1/1.
+dd> undo
+swap(t(1, 2)) = t(2, 1)
+Valid? browse 2
+browser> track field3
+error: cannot track subterm
+browser> quit
+dd> quit
+Diagnosis aborted.
+ E3: C2 EXIT func named_fields.swap/1-0 (det) named_fields.m:27 (named_fields.m:13)
+mdb> quit -y
Index: tests/debugger/declarative/named_fields.inp
===================================================================
RCS file: tests/debugger/declarative/named_fields.inp
diff -N tests/debugger/declarative/named_fields.inp
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ tests/debugger/declarative/named_fields.inp 5 Feb 2006 13:38:16 -0000
@@ -0,0 +1,47 @@
+register --quiet
+table_io allow
+table_io start
+echo on
+break swap
+c
+f
+dd -a
+browse
+cd 1/field1
+ls
+track
+info
+undo
+browse 1
+cd field1
+ls
+track
+info
+undo
+browse
+cd 2/field2
+ls
+track
+info
+undo
+browse
+cd result/field2
+ls
+track
+info
+undo
+browse 2
+cd field2
+ls
+track
+info
+undo
+browse 2
+track field2
+info
+undo
+browse 2
+track field3
+quit
+quit
+quit -y
Index: tests/debugger/declarative/named_fields.m
===================================================================
RCS file: tests/debugger/declarative/named_fields.m
diff -N tests/debugger/declarative/named_fields.m
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ tests/debugger/declarative/named_fields.m 5 Feb 2006 13:35:37 -0000
@@ -0,0 +1,27 @@
+:- module named_fields.
+
+:- interface.
+
+:- import_module io.
+
+:- pred main(io::di, io::uo) is det.
+
+:- implementation.
+
+main(!IO) :-
+ gen_t(T),
+ _ = swap(T).
+
+:- type t --->
+ t(
+ field1 :: int,
+ field2 :: int
+ ).
+
+:- pred gen_t(t :: out) is det.
+
+gen_t(t(1, 2)).
+
+:- func swap(t) = t.
+
+swap(t(X, Y)) = t(Y, X).
--------------------------------------------------------------------------
mercury-reviews mailing list
post: mercury-reviews at cs.mu.oz.au
administrative address: owner-mercury-reviews at cs.mu.oz.au
unsubscribe: Address: mercury-reviews-request at cs.mu.oz.au Message: unsubscribe
subscribe: Address: mercury-reviews-request at cs.mu.oz.au Message: subscribe
--------------------------------------------------------------------------
More information about the reviews
mailing list