[m-rev.] diff: implement limited_deconstruct_cc in Mercury.
Peter Ross
pro at missioncriticalit.com
Tue Dec 3 02:52:33 AEDT 2002
Hi,
===================================================================
Estimated hours taken: 2
Branches: main
Implemented limited_deconstruct_cc in Mercury.
library/deconstruct.m:
Implement limited_deconstruct_idcc as a cc_multi predicate
with the success of the predicate encoded into a maybe type,
as it is impossible to implement it as cc_nondet.
Change the C code version of limited_deconstruct_idcc to match
the Mercurys version behaviour.
Delete the bogus modes of limited_deconstruct/5 and implement
them as limited_deconstruct_cc/3 instead.
library/std_util.m:
Change limited_deconstruct_cc to have the correct determinism
and type signature.
runtime/mercury_ml_deconstruct_body.h:
Add a new #define which controls whether we save a success
indicator into SUCCESS_INDICATOR.
NEWS:
Document the changes to interfaces of limited_deconstruct and
limited_deconstruct_cc.
tests/hard_coded/deconstruct_arg.m:
Update the test case to test this new functionality.
Index: NEWS
===================================================================
RCS file: /home/mercury1/repository/mercury/NEWS,v
retrieving revision 1.287
diff -u -r1.287 NEWS
--- NEWS 2 Dec 2002 12:16:02 -0000 1.287
+++ NEWS 2 Dec 2002 15:42:21 -0000
@@ -34,14 +34,17 @@
`is_nan_or_inf/1' to float.m. These predicates are for use only on
systems which support IEEE floating point arithmetic.
-* The determinism of std_util__arg_cc has changed to cc_multi from cc_nondet.
- The success or failure of the argument lookup is now encoded in the
- new maybe_arg type.
+* The determinisms of the following predicates in the `std_util'
+ module have been changed from cc_nondet to cc_multi: arg_cc/3 and
+ limited_deconstruct_cc/3 (formerly limited_deconstruct_cc/5). The
+ success or failure of these predicates is now encoded in a maybe
+ type.
* The incorrect cc_nondet modes of the following predicates in
- the `deconstruct' module have been removed: arg/4. cc_multi version
- of the predicates have been introduced where the success or failure
- of the predicate has been encoded into a maybe type.
+ the `deconstruct' module have been removed: arg/4, limited_deconstruct/6.
+ cc_multi version of the predicates have been introduced where the
+ success or failure of the predicate has been encoded into a maybe
+ type.
Changes to the extras distribution:
Index: library/deconstruct.m
===================================================================
RCS file: /home/mercury1/repository/mercury/library/deconstruct.m,v
retrieving revision 1.17
diff -u -r1.17 deconstruct.m
--- library/deconstruct.m 2 Dec 2002 12:52:21 -0000 1.17
+++ library/deconstruct.m 2 Dec 2002 15:42:22 -0000
@@ -191,6 +191,10 @@
% greater than MaxArity, limited_deconstruct fails. This is useful in
% avoiding bad performance in cases where Data may be a large array.
%
+ % Note that this predicate only returns an answer when NonCanon is
+ % do_not_allow or canonicalize. If you need the include_details_cc
+ % behaviour use deconstruct__limited_deconstruct_cc/3.
+ %
:- pred limited_deconstruct(T, noncanon_handling, int, string, int,
list(univ)).
:- mode limited_deconstruct(in, in(do_not_allow), in, out, out, out)
@@ -198,8 +202,12 @@
:- mode limited_deconstruct(in, in(canonicalize), in, out, out, out)
is semidet.
:- mode limited_deconstruct(in, in(include_details_cc), in, out, out, out)
- is cc_nondet.
-:- mode limited_deconstruct(in, in, in, out, out, out) is cc_nondet.
+ is erroneous.
+:- mode limited_deconstruct(in, in, in, out, out, out) is semidet.
+
+ % See the documentation of std_util__limited_deconstruct_cc.
+:- pred limited_deconstruct_cc(T, int, maybe({string, int, list(univ)})).
+:- mode limited_deconstruct_cc(in, in, out) is cc_multi.
:- implementation.
:- interface.
@@ -364,10 +372,12 @@
Functor, Arity, Arguments)
;
NonCanon = include_details_cc,
- limited_deconstruct_idcc(Term, MaxArity,
- Functor, Arity, Arguments)
+ error("limited_deconstruct called with include_details_cc")
).
+limited_deconstruct_cc(Term, MaxArity, Result) :-
+ limited_deconstruct_idcc(Term, MaxArity, Result).
+
%-----------------------------------------------------------------------------%
:- pred functor_dna(T::in, string::out, int::out) is det.
@@ -632,7 +642,7 @@
:- pred limited_deconstruct_can(T::in, int::in,
string::out, int::out, list(univ)::out) is semidet.
:- pred limited_deconstruct_idcc(T::in, int::in,
- string::out, int::out, list(univ)::out) is cc_nondet.
+ maybe({string, int, list(univ)})::out) is cc_multi.
:- pragma foreign_proc("C",
deconstruct_dna(Term::in, Functor::out, Arity::out, Arguments::out),
@@ -717,6 +727,7 @@
#define ARITY_ARG Arity
#define ARGUMENTS_ARG Arguments
#define NONCANON MR_NONCANON_ABORT
+#define SAVE_SUCCESS
#include ""mercury_ml_deconstruct_body.h""
#undef EXPAND_INFO_TYPE
#undef EXPAND_INFO_CALL
@@ -727,6 +738,7 @@
#undef ARITY_ARG
#undef ARGUMENTS_ARG
#undef NONCANON
+#undef SAVE_SUCCESS
}").
:- pragma foreign_proc("C",
@@ -743,6 +755,7 @@
#define ARITY_ARG Arity
#define ARGUMENTS_ARG Arguments
#define NONCANON MR_NONCANON_ALLOW
+#define SAVE_SUCCESS
#include ""mercury_ml_deconstruct_body.h""
#undef EXPAND_INFO_TYPE
#undef EXPAND_INFO_CALL
@@ -753,34 +766,55 @@
#undef ARITY_ARG
#undef ARGUMENTS_ARG
#undef NONCANON
+#undef SAVE_SUCCESS
}").
:- pragma foreign_proc("C",
- limited_deconstruct_idcc(Term::in, MaxArity::in,
- Functor::out, Arity::out, Arguments::out),
+ limited_deconstruct_idcc(Term::in, MaxArity::in, Maybe::out),
[will_not_call_mercury, thread_safe, promise_pure],
"{
-#define EXPAND_INFO_TYPE MR_Expand_Functor_Args_Limit_Info
-#define EXPAND_INFO_CALL MR_expand_functor_args_limit
-#define TYPEINFO_ARG TypeInfo_for_T
-#define TERM_ARG Term
-#define MAX_ARITY_ARG MaxArity
-#define FUNCTOR_ARG Functor
-#define ARITY_ARG Arity
-#define ARGUMENTS_ARG Arguments
-#define NONCANON MR_NONCANON_CC
-#include ""mercury_ml_deconstruct_body.h""
-#undef EXPAND_INFO_TYPE
-#undef EXPAND_INFO_CALL
-#undef TYPEINFO_ARG
-#undef TERM_ARG
-#undef MAX_ARITY_ARG
-#undef FUNCTOR_ARG
-#undef ARITY_ARG
-#undef ARGUMENTS_ARG
-#undef NONCANON
+ MR_String Functor;
+ MR_Integer Arity;
+ MR_Word Arguments;
+
+ #define EXPAND_INFO_TYPE MR_Expand_Functor_Args_Limit_Info
+ #define EXPAND_INFO_CALL MR_expand_functor_args_limit
+ #define TYPEINFO_ARG TypeInfo_for_T
+ #define TERM_ARG Term
+ #define MAX_ARITY_ARG MaxArity
+ #define FUNCTOR_ARG Functor
+ #define ARITY_ARG Arity
+ #define ARGUMENTS_ARG Arguments
+ #define NONCANON MR_NONCANON_CC
+ #include ""mercury_ml_deconstruct_body.h""
+ #undef EXPAND_INFO_TYPE
+ #undef EXPAND_INFO_CALL
+ #undef TYPEINFO_ARG
+ #undef TERM_ARG
+ #undef MAX_ARITY_ARG
+ #undef FUNCTOR_ARG
+ #undef ARITY_ARG
+ #undef ARGUMENTS_ARG
+ #undef NONCANON
+
+ if (success) {
+ Maybe = ML_construct_idcc_yes(Functor, Arity, Arguments);
+ } else {
+ Maybe = ML_construct_idcc_no();
+ }
}").
+:- func construct_idcc_yes(string, int, list(univ)) =
+ maybe({string, int, list(univ)}).
+:- pragma export(construct_idcc_yes(in, in, in) = out, "ML_construct_idcc_yes").
+construct_idcc_yes(Functor, Arity, Args) = yes({Functor, Arity, Args}).
+
+:- func construct_idcc_no = maybe({string, int, list(univ)}).
+:- pragma export(construct_idcc_no = out, "ML_construct_idcc_no").
+construct_idcc_no = no.
+
+
+
deconstruct_dna(Term::in, Functor::out, Arity::out, Arguments::out) :-
rtti_implementation__deconstruct(Term,
do_not_allow, Functor, Arity, Arguments).
@@ -801,11 +835,14 @@
rtti_implementation__deconstruct(Term,
canonicalize, Functor, Arity, Arguments),
Arity =< MaxArity.
-limited_deconstruct_idcc(_Term::in, _MaxArity::in,
- _Functor::out, _Arity::out, _Arguments::out) :-
- % This version is only used for back-ends for which there is no
- % matching foreign_proc version.
- private_builtin__sorry("limited_deconstruct_idcc/5").
+limited_deconstruct_idcc(Term::in, MaxArity::in, MaybeResult::out) :-
+ rtti_implementation__deconstruct(Term,
+ include_details_cc, Functor, Arity, Arguments),
+ ( Arity =< MaxArity ->
+ MaybeResult = yes({Functor, Arity, Arguments})
+ ;
+ MaybeResult = no
+ ).
%-----------------------------------------------------------------------------%
Index: library/std_util.m
===================================================================
RCS file: /home/mercury1/repository/mercury/library/std_util.m,v
retrieving revision 1.274
diff -u -r1.274 std_util.m
--- library/std_util.m 2 Dec 2002 12:16:04 -0000 1.274
+++ library/std_util.m 2 Dec 2002 15:42:28 -0000
@@ -707,12 +707,13 @@
% avoiding bad performance in cases where Data may be a large array.
%
% limited_deconstruct_cc succeeds even if the first argument is
- % of a non-canonical type.
+ % of a non-canonical type. limited_deconstruct_cc encodes the
+ % possible failure of the predicate by using a maybe type.
%
:- pred limited_deconstruct(T::in, int::in, string::out,
int::out, list(univ)::out) is semidet.
-:- pred limited_deconstruct_cc(T::in, int::in, string::out,
- int::out, list(univ)::out) is cc_nondet.
+:- pred limited_deconstruct_cc(T::in, int::in,
+ maybe({string, int, list(univ)})::out) is cc_multi.
%-----------------------------------------------------------------------------%
@@ -1653,9 +1654,8 @@
deconstruct__limited_deconstruct(Term, canonicalize,
MaxArity, Functor, Arity, Arguments).
-limited_deconstruct_cc(Term, MaxArity, Functor, Arity, Arguments) :-
- deconstruct__limited_deconstruct(Term, include_details_cc,
- MaxArity, Functor, Arity, Arguments).
+limited_deconstruct_cc(Term, MaxArity, Result) :-
+ deconstruct__limited_deconstruct_cc(Term, MaxArity, Result).
det_arg(Type, Index) = Argument :-
deconstruct__det_arg(Type, canonicalize, Index, Argument0),
Index: runtime/mercury_ml_deconstruct_body.h
===================================================================
RCS file: /home/mercury1/repository/mercury/runtime/mercury_ml_deconstruct_body.h,v
retrieving revision 1.3
diff -u -r1.3 mercury_ml_deconstruct_body.h
--- runtime/mercury_ml_deconstruct_body.h 18 Feb 2002 07:01:18 -0000 1.3
+++ runtime/mercury_ml_deconstruct_body.h 2 Dec 2002 15:42:28 -0000
@@ -49,15 +49,21 @@
** MAX_ARITY_ARG If defined, gives the name of the argument whose value
** gives the maximum number of arguments we want to
** succeed for.
+**
+** SAVE_SUCCESS If defined, success is saved into SUCCESS_INDICATOR.
*/
+#if defined(SAVE_SUCCESS) && !defined(MAX_ARITY_ARG)
+ #error "SAVE_SUCCESS requires MAX_ARITY_ARG is defined"
+#endif
+
#ifdef MAX_ARITY_ARG
#define maybe_max_arity_arg MAX_ARITY_ARG,
#define max_arity_check_start \
if (expand_info.limit_reached) { \
- SUCCESS_INDICATOR = MR_FALSE; \
+ success = MR_FALSE; \
} else { \
- SUCCESS_INDICATOR = MR_TRUE;
+ success = MR_TRUE;
#define max_arity_check_end }
#else
#define maybe_max_arity_arg
@@ -65,6 +71,10 @@
#define max_arity_check_end
#endif
+#ifdef MAX_ARITY_ARG
+ MR_bool success;
+#endif
+
EXPAND_INFO_TYPE expand_info;
MR_TypeInfo type_info;
@@ -81,6 +91,10 @@
MR_deconstruct_get_arg_list(expand_info, args, ARGUMENTS_ARG);
MR_deconstruct_free_allocated_arg_type_infos(expand_info, args);
max_arity_check_end
+
+#ifdef SAVE_SUCCESS
+ SUCCESS_INDICATOR = success;
+#endif
#undef maybe_max_arity_arg
#undef max_arity_check_start
Index: tests/hard_coded/deconstruct_arg.m
===================================================================
RCS file: /home/mercury1/repository/tests/hard_coded/deconstruct_arg.m,v
retrieving revision 1.5
diff -u -r1.5 deconstruct_arg.m
--- tests/hard_coded/deconstruct_arg.m 2 Dec 2002 12:16:07 -0000 1.5
+++ tests/hard_coded/deconstruct_arg.m 2 Dec 2002 15:42:28 -0000
@@ -219,10 +219,8 @@
io__write_string(Str),
io__print(T),
io__write_string("\n"),
- (
- { deconstruct__limited_deconstruct(T, include_details_cc,
- Limit, Functor, Arity, Arguments) }
- ->
+ { deconstruct__limited_deconstruct_cc(T, Limit, Result) },
+ ( { Result = yes({Functor, Arity, Arguments}) } ->
{ string__format("functor %s arity %d ",
[s(Functor), i(Arity)], Str2) },
io__write_string(Str2),
--------------------------------------------------------------------------
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