[m-rev.] For review: RTTI for Java
James Goddard
goddardjames at yahoo.com
Thu Feb 26 18:31:30 AEDT 2004
Estimated hours taken: 30
Branches: main
Implement RTTI for the Java-backend (incomplete)
java/runtime/PseudoTypeInfo.java:
java/runtime/TypeCtorInfo_Struct.java:
java/runtime/TypeInfo_Struct.java:
Implement the `unify' operation for these classes. This implementation
actually just compares them.
library/rtti_implementation.m:
Change the foreign type of `type_info' from `TypeInfo_Struct' to
`PseudoTypeInfo' in Java.
Define the foreign type of `type_layout' as `TypeLayout' in Java.
Correct an off-by-one error in type_ctor_and_args/3.
Implement deconstruct/8 for TypeCtorRep = enum.
Implement the following predicates in Java:
get_var_arity_typeinfo_arity/1
get_pti_from_arg_types/2
typeinfo_is_variable/2
get_type_ctor_info/1
get_primary_tag/1
get_remote_secondary_tag/1
ptag_index/2
sectag_locn/1
du_sectag_alternatives/2
type_info_index/2
type_ctor_arity/1
type_ctor_rep/1
type_ctor_module_name/1
type_ctor_name/1
type_ctor_functors/1
type_layout/1
unsafe_cast/1
du_functor_desc/3
du_functor_name/1
du_functor_arity/1
du_functor_arg_type_contains_var/1
du_functor_sectag_locn/1
du_functor_primary/1
du_functor_secondary/1
du_functor_ordinal/1
du_functor_arg_types/1
du_functor_arg_names/1
du_functor_exist_info/1
enum_functor_desc/3
enum_functor_name/1
enum_functor_ordinal/1
notag_functor_desc/3
notag_functor_name/1
notag_functor_arg_type/1
notag_functor_arg_name/1
null/1
null_string/0
unsafe_get_enum_value/1
library/type_desc.m:
Implement the following procedures for Java:
type_of/1
has_type/1
type_ctor_and_args/3
type_ctor_name_and_arity/4
Implement the Java classes `type_desc_0' and `type_ctor_desc_0'.
Index: java/runtime/PseudoTypeInfo.java
===================================================================
RCS file: /home/mercury1/repository/mercury/java/runtime/PseudoTypeInfo.java,v
retrieving revision 1.3
diff -u -d -r1.3 PseudoTypeInfo.java
--- java/runtime/PseudoTypeInfo.java 19 Feb 2004 09:37:20 -0000 1.3
+++ java/runtime/PseudoTypeInfo.java 20 Feb 2004 04:11:35 -0000
@@ -25,4 +25,13 @@
public int variable_number;
public PseudoTypeInfo(int n) { variable_number = n; }
protected PseudoTypeInfo() { variable_number = -1; }
+
+ public boolean unify(PseudoTypeInfo ti) {
+ if (this.getClass() == TypeInfo_Struct.class &&
+ ti.getClass() == TypeInfo_Struct.class) {
+ return ((TypeInfo_Struct) this).unify(
+ (TypeInfo_Struct) ti);
+ }
+ return variable_number == ti.variable_number;
+ }
}
Index: java/runtime/TypeCtorInfo_Struct.java
===================================================================
RCS file: /home/mercury1/repository/mercury/java/runtime/TypeCtorInfo_Struct.java,v
retrieving revision 1.6
diff -u -d -r1.6 TypeCtorInfo_Struct.java
--- java/runtime/TypeCtorInfo_Struct.java 9 Feb 2004 11:54:51 -0000 1.6
+++ java/runtime/TypeCtorInfo_Struct.java 22 Feb 2004 03:45:50 -0000
@@ -48,4 +48,13 @@
value_ordered_functor_descs;
type_ctor_flags = flags;
}
+
+ public boolean unify(TypeCtorInfo_Struct tci) {
+ return this == tci;
+ /*
+ return type_ctor_module_name.equals(tci.type_ctor_module_name)
+ && type_ctor_name.equals(tci.type_ctor_name)
+ && arity == tci.arity;
+ */
+ }
}
Index: java/runtime/TypeInfo_Struct.java
===================================================================
RCS file: /home/mercury1/repository/mercury/java/runtime/TypeInfo_Struct.java,v
retrieving revision 1.4
diff -u -d -r1.4 TypeInfo_Struct.java
--- java/runtime/TypeInfo_Struct.java 19 Feb 2004 09:37:20 -0000 1.4
+++ java/runtime/TypeInfo_Struct.java 22 Feb 2004 03:44:50 -0000
@@ -125,4 +125,31 @@
}
}
}
+
+ public boolean unify(TypeInfo_Struct ti) {
+ if (this == ti) {
+ return true;
+ }
+
+ if (type_ctor.unify(ti.type_ctor) == false) {
+ return false;
+ }
+
+ if (args == null || ti.args == null) {
+ if (args == null && ti.args == null) {
+ return true;
+ }
+ return false;
+ }
+
+ for (int i = 0; i < args.length || i < ti.args.length; i++) {
+ if (i == args.length || i == ti.args.length) {
+ return false;
+ }
+ if (args[i].unify(ti.args[i]) == false) {
+ return false;
+ }
+ }
+ return true;
+ }
}
Index: library/rtti_implementation.m
===================================================================
RCS file: /home/mercury1/repository/mercury/library/rtti_implementation.m,v
retrieving revision 1.51
diff -u -d -r1.51 rtti_implementation.m
--- library/rtti_implementation.m 20 Feb 2004 01:56:33 -0000 1.51
+++ library/rtti_implementation.m 26 Feb 2004 07:29:55 -0000
@@ -24,6 +24,13 @@
% The plan is to migrate most of the Mercury level data structures in
% compiler/rtti.m here, and to interpret them, instead of relying on access
% to C level data structures.
+%
+% XXX The Java implementation of this module is incomplete. Currently, it can
+% handle strings, ints, floats and enumerated types, but anything more
+% complicated will throw exceptions. This is mainly due to the fact that a lot
+% of the low-level procedures have yet to be implemented for the Java back-end.
+%
+% XXX Also, the existing Java code needs to be reviewed.
%-----------------------------------------------------------------------------%
%-----------------------------------------------------------------------------%
@@ -32,7 +39,8 @@
:- interface.
-:- import_module deconstruct, list.
+:- import_module deconstruct.
+:- import_module list.
:- use_module std_util.
:- use_module type_desc.
@@ -85,7 +93,11 @@
:- implementation.
-:- import_module array, bool, int, require, string.
+:- import_module array.
+:- import_module bool.
+:- import_module int.
+:- import_module require.
+:- import_module string.
% std_util has a lot of types and functions with the same names,
% so we prefer to keep the namespace separate.
@@ -147,11 +159,14 @@
:- type type_info ---> type_info(c_pointer).
:- pragma foreign_type("Java", type_info,
- % XXX should this be "mercury.runtime.PseudoTypeInfo" instead?
- "mercury.runtime.TypeInfo_Struct").
+ % XXX should this be "mercury.runtime.TypeInfo_Struct" instead?
+ "mercury.runtime.PseudoTypeInfo").
:- type compare_pred ---> compare_pred(c_pointer).
+
:- type type_layout ---> type_layout(c_pointer).
+:- pragma foreign_type("Java", type_layout, "mercury.runtime.TypeLayout").
+
:- type pred_type ---> pred_type(c_pointer).
:- type pseudo_type_info ---> pred_type(c_pointer).
@@ -503,7 +518,7 @@
get_var_arity_typeinfo_arity(TypeInfo::in) = (Arity::out),
[will_not_call_mercury, promise_pure, thread_safe],
"
- Arity = TypeInfo.args.length;
+ Arity = ((TypeInfo_Struct) TypeInfo).args.length;
").
:- pragma foreign_proc("C#",
@@ -950,12 +965,13 @@
type_ctor_is_variable_arity(TypeCtorInfo)
->
Arity = get_var_arity_typeinfo_arity(TypeInfo),
- TypeArgs = iterate(1, Arity,
+ % XXX Do indexes start at 0?
+ TypeArgs = iterate(0, Arity - 1,
(func(X) = TypeInfo ^ var_arity_type_info_index(X))
)
;
Arity = type_ctor_arity(TypeCtorInfo),
- TypeArgs = iterate(1, Arity,
+ TypeArgs = iterate(0, Arity - 1,
(func(X) = TypeInfo ^ type_info_index(X))
)
).
@@ -1011,7 +1027,10 @@
NonCanon, Functor, Arity, Arguments)
;
TypeCtorRep = enum,
- Functor = "some_enum",
+ TypeFunctors = type_ctor_functors(TypeCtorInfo),
+ EnumFunctorDesc = enum_functor_desc(TypeCtorRep,
+ unsafe_get_enum_value(Term), TypeFunctors),
+ Functor = enum_functor_name(EnumFunctorDesc),
Arity = 0,
Arguments = []
;
@@ -1490,6 +1509,16 @@
get_pti_from_arg_types(_::in, _::in) = (42::out) :-
det_unimplemented("get_pti_from_arg_types").
+:- pragma foreign_proc("Java",
+ get_pti_from_arg_types(ArgTypes::in, Index::in) = (ArgTypeInfo::out),
+ [will_not_call_mercury, promise_pure],
+"
+ // XXX Should this be something else?
+ TypeInfo_for_T = null;
+
+ ArgTypeInfo = ArgTypes[Index];
+").
+
:- pragma foreign_proc("C#",
get_pti_from_arg_types(ArgTypes::in, Index::in) =
(ArgTypeInfo::out), [promise_pure], "
@@ -1591,6 +1620,21 @@
}
").
+:- pragma foreign_proc("Java",
+ typeinfo_is_variable(TypeInfo::in, VarNum::out),
+ [will_not_call_mercury, promise_pure],
+"
+ succeeded = (TypeInfo.getClass() ==
+ mercury.runtime.PseudoTypeInfo.class);
+ if (succeeded) {
+ // This number is used to index into an array, hence the -1
+ VarNum = ((mercury.runtime.PseudoTypeInfo)TypeInfo).
+ variable_number - 1;
+ } else {
+ VarNum = -1; // just to keep the compiler happy
+ }
+").
+
% Tests for universal and existentially quantified variables.
:- pred type_variable_is_univ_quant(int::in) is semidet.
@@ -1688,6 +1732,13 @@
}
").
+:- pragma foreign_proc("Java",
+ get_type_ctor_info(TypeInfo::in) = (TypeCtorInfo::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ TypeCtorInfo = ((mercury.runtime.TypeInfo_Struct) TypeInfo).type_ctor;
+").
+
:- pragma foreign_proc("C",
get_type_ctor_info(TypeInfo::in) = (TypeCtorInfo::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -1756,6 +1807,28 @@
}
").
+:- pragma foreign_proc("Java",
+ get_primary_tag(_X::in) = (Tag::out), [promise_pure],
+"
+ // For the Java back-end, there is no primary tag, so always return 0.
+ Tag = 0;
+").
+
+:- pragma foreign_proc("Java",
+ get_remote_secondary_tag(X::in) = (Tag::out), [promise_pure],
+"
+ // If there is a secondary tag, it will be in a member called
+ // `data_tag', which we obtain by reflection. Otherwise we return -1.
+ // XXX Is this the correct behaviour?
+
+ try {
+ Tag = X.getClass().getField(""data_tag"").getInt(X);
+ }
+ catch (java.lang.Exception e) {
+ return -1;
+ }
+").
+
:- type sectag_locn ---> none ; local ; remote ; variable.
% :- pragma foreign_type("Java", sectag_locn, "mercury.runtime.Sectag_Locn").
@@ -1791,6 +1864,12 @@
PtagEntry = (object[]) TypeLayout[X];
").
+:- pragma foreign_proc("Java",
+ ptag_index(X::in, TypeLayout::in) = (PtagEntry::out), [promise_pure],
+"
+ PtagEntry = TypeLayout.layout_du()[X];
+").
+
:- func sectag_locn(ptag_entry) = sectag_locn.
sectag_locn(PTagEntry::in) = (unsafe_cast(PTagEntry)::out) :-
@@ -1802,6 +1881,15 @@
PTagEntry[(int) ptag_layout_field_nums.sectag_locn]);
").
+:- pragma foreign_proc("Java",
+ sectag_locn(PTagEntry::in) = (SectagLocn::out), [promise_pure],
+"
+ mercury.runtime.Sectag_Locn SL_struct = PTagEntry.sectag_locn;
+
+ SectagLocn = new mercury.rtti_implementation.sectag_locn_0(
+ SL_struct.value);
+").
+
:- func du_sectag_alternatives(int, ptag_entry) = du_functor_desc.
du_sectag_alternatives(_::in, PTagEntry::in) = (unsafe_cast(PTagEntry)::out) :-
@@ -1816,6 +1904,13 @@
FunctorDescriptor = (object []) sectag_alternatives[X];
").
+:- pragma foreign_proc("Java",
+ du_sectag_alternatives(X::in, PTagEntry::in) =
+ (FunctorDescriptor::out), [promise_pure],
+"
+ FunctorDescriptor = PTagEntry.sectag_alternatives[X];
+").
+
:- func typeinfo_locns_index(int, exist_info) = typeinfo_locn.
typeinfo_locns_index(X::in, _::in) = (unsafe_cast(X)::out) :-
@@ -1920,6 +2015,14 @@
type_info_index(_::in, TypeInfo::in) = (TypeInfo::out) :-
det_unimplemented("type_info_index").
+:- pragma foreign_proc("Java",
+ type_info_index(X::in, TypeInfo::in) = (TypeInfoAtIndex::out),
+ [will_not_call_mercury, promise_pure],
+"
+ TypeInfoAtIndex = (TypeInfo_Struct)
+ ((TypeInfo_Struct) TypeInfo).args[X];
+").
+
:- pragma foreign_proc("C#",
type_info_index(X::in, TypeInfo::in) = (TypeInfoAtIndex::out),
[will_not_call_mercury, promise_pure],
@@ -1967,6 +2070,12 @@
Arity = (int) TypeCtorInfo[
(int) type_ctor_info_field_nums.type_ctor_arity];
").
+:- pragma foreign_proc("Java",
+ type_ctor_arity(TypeCtorInfo::in) = (Arity::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Arity = ((TypeCtorInfo_Struct) TypeCtorInfo).arity;
+").
:- pragma foreign_proc("C",
type_ctor_arity(TypeCtorInfo::in) = (Arity::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -2031,6 +2140,14 @@
(int) type_ctor_info_field_nums.type_ctor_rep];
TypeCtorRep = mercury.runtime.LowLevelData.make_enum(rep);
").
+:- pragma foreign_proc("Java",
+ type_ctor_rep(TypeCtorInfo::in) = (TypeCtorRep::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ TypeCtorRep = new type_ctor_rep_0(
+ ((mercury.runtime.TypeCtorInfo_Struct) TypeCtorInfo).
+ type_ctor_rep.value);
+").
:- pragma foreign_proc("C",
type_ctor_rep(TypeCtorInfo::in) = (TypeCtorRep::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -2054,6 +2171,13 @@
type_ctor_info_field_nums.type_ctor_module_name];
").
+:- pragma foreign_proc("Java",
+ type_ctor_module_name(TypeCtorInfo::in) = (Name::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Name = TypeCtorInfo.type_ctor_module_name;
+").
+
:- pragma foreign_proc("C",
type_ctor_module_name(TypeCtorInfo::in) = (Name::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -2076,6 +2200,12 @@
Name = (string)
TypeCtorInfo[(int) type_ctor_info_field_nums.type_ctor_name];
").
+:- pragma foreign_proc("Java",
+ type_ctor_name(TypeCtorInfo::in) = (Name::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Name = TypeCtorInfo.type_ctor_name;
+").
:- pragma foreign_proc("C",
type_ctor_name(TypeCtorInfo::in) = (Name::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -2101,6 +2231,13 @@
TypeCtorInfo[(int) type_ctor_info_field_nums.type_functors];
").
+:- pragma foreign_proc("Java",
+ type_ctor_functors(TypeCtorInfo::in) = (Functors::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Functors = TypeCtorInfo.type_functors;
+").
+
type_ctor_functors(_) = _ :-
% This version is only used for back-ends for which there is no
% matching foreign_proc version.
@@ -2117,6 +2254,12 @@
TypeLayout = (object[])
TypeCtorInfo[(int) type_ctor_info_field_nums.type_layout];
").
+:- pragma foreign_proc("Java",
+ type_layout(TypeCtorInfo::in) = (TypeLayout::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ TypeLayout = TypeCtorInfo.type_layout;
+").
:- pragma foreign_proc("C",
type_layout(TypeCtorInfo::in) = (TypeLayout::out),
[will_not_call_mercury, promise_pure, thread_safe],
@@ -2158,6 +2301,12 @@
"
VarOut = VarIn;
").
+:- pragma foreign_proc("Java",
+ unsafe_cast(VarIn::in) = (VarOut::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ VarOut = VarIn;
+").
unsafe_cast(_) = _ :-
% This version is only used for back-ends for which there is no
@@ -2195,43 +2344,136 @@
du_functor_desc(_, Num, TypeFunctors) = DuFunctorDesc :-
DuFunctorDesc = TypeFunctors ^ unsafe_index(Num).
+:- pragma foreign_proc("Java",
+ du_functor_desc(_TypeCtorRep::in(du), X::in, TypeFunctors::in) =
+ (DuFunctorDesc::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ DuFunctorDesc = TypeFunctors.functors_du()[X];
+").
+
:- func du_functor_name(du_functor_desc) = string.
+
du_functor_name(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(0).
+:- pragma foreign_proc("Java",
+ du_functor_name(DuFunctorDesc::in) = (Name::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Name = DuFunctorDesc.du_functor_name;
+").
+
:- func du_functor_arity(du_functor_desc) = int.
+
du_functor_arity(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(1).
+:- pragma foreign_proc("Java",
+ du_functor_arity(DuFunctorDesc::in) = (Arity::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Arity = DuFunctorDesc.du_functor_orig_arity;
+").
+
:- func du_functor_arg_type_contains_var(du_functor_desc) = int.
+
du_functor_arg_type_contains_var(DuFunctorDesc) =
DuFunctorDesc ^ unsafe_index(2).
+:- pragma foreign_proc("Java",
+ du_functor_arg_type_contains_var(DuFunctorDesc::in) = (Contains::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Contains = DuFunctorDesc.du_functor_arg_type_contains_var;
+").
+
:- func du_functor_sectag_locn(du_functor_desc) = sectag_locn.
+
du_functor_sectag_locn(DuFunctorDesc) =
unsafe_make_enum(DuFunctorDesc ^ unsafe_index(3)).
+:- pragma foreign_proc("Java",
+ du_functor_sectag_locn(DuFunctorDesc::in) = (SectagLocn::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ SectagLocn = DuFunctorDesc.du_functor_sectag_locn;
+").
+
:- func du_functor_primary(du_functor_desc) = int.
+
du_functor_primary(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(4).
+:- pragma foreign_proc("Java",
+ du_functor_primary(DuFunctorDesc::in) = (Primary::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Primary = DuFunctorDesc.du_functor_primary;
+").
+
:- func du_functor_secondary(du_functor_desc) = int.
+
du_functor_secondary(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(5).
+:- pragma foreign_proc("Java",
+ du_functor_secondary(DuFunctorDesc::in) = (Secondary::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Secondary = DuFunctorDesc.du_functor_secondary;
+").
+
:- func du_functor_ordinal(du_functor_desc) = int.
+
du_functor_ordinal(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(6).
+:- pragma foreign_proc("Java",
+ du_functor_ordinal(DuFunctorDesc::in) = (Ordinal::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Ordinal = DuFunctorDesc.du_functor_ordinal;
+").
+
:- func du_functor_arg_types(du_functor_desc) = arg_types.
+
du_functor_arg_types(DuFunctorDesc) = DuFunctorDesc ^ unsafe_index(7).
-:- func du_functor_arg_names(du_functor_desc::in) = (arg_names::out) is semidet.
+:- pragma foreign_proc("Java",
+ du_functor_arg_types(DuFunctorDesc::in) = (ArgTypes::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ ArgTypes = DuFunctorDesc.du_functor_arg_types;
+").
+
+:- func du_functor_arg_names(du_functor_desc::in) =
+ (arg_names::out) is semidet.
+
du_functor_arg_names(DuFunctorDesc) = ArgNames :-
ArgNames = DuFunctorDesc ^ unsafe_index(8),
not null(ArgNames).
+:- pragma foreign_proc("Java",
+ du_functor_arg_names(DuFunctorDesc::in) = (ArgNames::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ ArgNames = DuFunctorDesc.du_functor_arg_names;
+
+ succeeded = (ArgNames != null);
+").
+
:- func du_functor_exist_info(du_functor_desc::in) =
(exist_info::out) is semidet.
+
du_functor_exist_info(DuFunctorDesc) = ExistInfo :-
ExistInfo = DuFunctorDesc ^ unsafe_index(9),
not null(ExistInfo).
+:- pragma foreign_proc("Java",
+ du_functor_exist_info(DuFunctorDesc::in) = (ExistInfo::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ ExistInfo = DuFunctorDesc.du_functor_exist_info;
+
+ succeeded = (ExistInfo != null);
+").
+
%--------------------------%
:- func enum_functor_desc(type_ctor_rep, int, type_functors)
@@ -2241,12 +2483,36 @@
enum_functor_desc(_, Num, TypeFunctors) = EnumFunctorDesc :-
EnumFunctorDesc = TypeFunctors ^ unsafe_index(Num).
+:- pragma foreign_proc("Java",
+ enum_functor_desc(_TypeCtorRep::in(enum), X::in, TypeFunctors::in) =
+ (EnumFunctorDesc::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ EnumFunctorDesc = (TypeFunctors.functors_enum())[X];
+").
+
:- func enum_functor_name(enum_functor_desc) = string.
+
enum_functor_name(EnumFunctorDesc) = EnumFunctorDesc ^ unsafe_index(0).
+:- pragma foreign_proc("Java",
+ enum_functor_name(EnumFunctorDesc::in) = (Name::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Name = EnumFunctorDesc.enum_functor_name;
+").
+
:- func enum_functor_ordinal(enum_functor_desc) = int.
+
enum_functor_ordinal(EnumFunctorDesc) = EnumFunctorDesc ^ unsafe_index(1).
+:- pragma foreign_proc("Java",
+ enum_functor_ordinal(EnumFunctorDesc::in) = (Ordinal::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Ordinal = EnumFunctorDesc.enum_functor_ordinal;
+").
+
%--------------------------%
:- func notag_functor_desc(type_ctor_rep, int, type_functors)
@@ -2256,15 +2522,47 @@
notag_functor_desc(_, Num, TypeFunctors) = NoTagFunctorDesc :-
NoTagFunctorDesc = TypeFunctors ^ unsafe_index(Num).
+:- pragma foreign_proc("Java",
+ notag_functor_desc(_TypeCtorRep::in(notag), _X::in, TypeFunctors::in) =
+ (NotagFunctorDesc::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ NotagFunctorDesc = TypeFunctors.functors_notag();
+").
+
:- func notag_functor_name(notag_functor_desc) = string.
+
notag_functor_name(NoTagFunctorDesc) = NoTagFunctorDesc ^ unsafe_index(0).
+:- pragma foreign_proc("Java",
+ notag_functor_name(NotagFunctorDesc::in) = (Name::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Name = NotagFunctorDesc.no_tag_functor_name;
+").
+
:- func notag_functor_arg_type(notag_functor_desc) = type_info.
+
notag_functor_arg_type(NoTagFunctorDesc) = NoTagFunctorDesc ^ unsafe_index(1).
+:- pragma foreign_proc("Java",
+ notag_functor_arg_type(NotagFunctorDesc::in) = (ArgType::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ ArgType = NotagFunctorDesc.no_tag_functor_arg_type;
+").
+
:- func notag_functor_arg_name(notag_functor_desc) = string.
+
notag_functor_arg_name(NoTagFunctorDesc) = NoTagFunctorDesc ^ unsafe_index(2).
+:- pragma foreign_proc("Java",
+ notag_functor_arg_name(NotagFunctorDesc::in) = (ArgName::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ ArgName = NotagFunctorDesc.no_tag_functor_arg_name;
+").
+
%-----------------------------------------------------------------------------%
%-----------------------------------------------------------------------------%
@@ -2304,6 +2602,12 @@
"
SUCCESS_INDICATOR = (S == null);
").
+:- pragma foreign_proc("Java",
+ null(S::in),
+ [will_not_call_mercury, thread_safe, promise_pure],
+"
+ succeeded = (S == null);
+").
null(_) :-
% This version is only used for back-ends for which there is no
% matching foreign_proc version.
@@ -2324,10 +2628,39 @@
"
Str = null;
").
+:- pragma foreign_proc("Java",
+ null_string = (Str::out),
+ [will_not_call_mercury, thread_safe, promise_pure],
+"
+ Str = null;
+").
null_string = _ :-
% This version is only used for back-ends for which there is no
% matching foreign_proc version.
private_builtin__sorry("rtti_implementation__null_string/0").
+
+ %--------------------------%
+
+:- func unsafe_get_enum_value(T) = int.
+
+:- pragma foreign_proc("Java",
+ unsafe_get_enum_value(Enum::in) = (Value::out),
+ [will_not_call_mercury, thread_safe, promise_pure],
+"
+ try {
+ Value = Enum.getClass().getField(""value"").getInt(Enum);
+ }
+ catch (java.lang.Exception e) {
+ throw new java.lang.RuntimeException(
+ ""unsafe_get_enum_value/1 called on an "" +
+ ""object which is not of enumerated type."");
+ }
+").
+
+unsafe_get_enum_value(_) = _ :-
+ % This version is only used for back-ends for which there is no
+ % matching foreign_proc version.
+ private_builtin__sorry("rtti_implementation__unsafe_get_enum_value/1").
%-----------------------------------------------------------------------------%
%-----------------------------------------------------------------------------%
Index: library/type_desc.m
===================================================================
RCS file: /home/mercury1/repository/mercury/library/type_desc.m,v
retrieving revision 1.23
diff -u -d -r1.23 type_desc.m
--- library/type_desc.m 1 Dec 2003 13:17:11 -0000 1.23
+++ library/type_desc.m 20 Feb 2004 09:11:02 -0000
@@ -253,7 +253,8 @@
type_of(_Value::unused) = (TypeInfo::out),
[will_not_call_mercury, thread_safe, promise_pure],
"
- TypeInfo = TypeInfo_for_T;
+ TypeInfo = new mercury.type_desc.type_desc_0(
+ (mercury.runtime.TypeInfo_Struct) TypeInfo_for_T);
").
@@ -275,7 +276,7 @@
has_type(_Arg::unused, TypeInfo::in),
[will_not_call_mercury, thread_safe, promise_pure],
"
- TypeInfo_for_T = TypeInfo;
+ TypeInfo_for_T = ((mercury.type_desc.type_desc_0) TypeInfo).struct;
").
@@ -404,6 +405,29 @@
MR_restore_transient_registers();
}").
+:- pragma foreign_proc("Java",
+ type_ctor_and_args(TypeDesc::in, TypeCtorDesc::out, ArgTypes::out),
+ [may_call_mercury, thread_safe, promise_pure],
+"
+ java.lang.Object [] result =
+ mercury.rtti_implementation.type_ctor_and_args_3_p_0(
+ ((mercury.type_desc.type_desc_0) TypeDesc).struct);
+
+ TypeCtorDesc = new type_ctor_desc_0((TypeCtorInfo_Struct) result[0]);
+ ArgTypes = result[1];
+
+ // Convert list from TypeInfo_Struct to type_desc_0
+ mercury.list.list_1 type_list = (mercury.list.list_1) ArgTypes;
+ while (type_list.data_tag == 1) {
+ ((mercury.list.list_1.f_cons_2) type_list).F1 =
+ new mercury.type_desc.type_desc_0(
+ (TypeInfo_Struct)
+ ((mercury.list.list_1.f_cons_2) type_list).F1);
+ type_list = (mercury.list.list_1)
+ ((mercury.list.list_1.f_cons_2) type_list).F2;
+ }
+").
+
type_ctor_and_args(TypeDesc::in, TypeCtorDesc::out, ArgTypes::out) :-
rtti_implementation__type_ctor_and_args(
rtti_implementation__unsafe_cast(TypeDesc),
@@ -514,6 +538,20 @@
}
}").
+:- pragma foreign_proc("Java",
+ type_ctor_name_and_arity(TypeCtorDesc::in, TypeCtorModuleName::out,
+ TypeCtorName::out, TypeCtorArity::out),
+ [will_not_call_mercury, thread_safe, promise_pure],
+"
+ Object[] result = mercury.rtti_implementation.
+ type_ctor_name_and_arity_4_p_0(
+ ((type_ctor_desc_0) TypeCtorDesc).struct);
+
+ TypeCtorModuleName = (java.lang.String) result[0];
+ TypeCtorName = (java.lang.String) result[1];
+ TypeCtorArity = ((java.lang.Integer) result[2]).intValue();
+").
+
type_ctor_name_and_arity(TypeCtorDesc::in, ModuleName::out,
TypeCtorName::out, TypeCtorArity::out) :-
rtti_implementation__type_ctor_name_and_arity(
@@ -541,20 +579,28 @@
%-----------------------------------------------------------------------------%
:- pragma foreign_code("Java", "
- public class type_desc_0 {
- // stub only
+ public static class type_desc_0 {
+ public mercury.runtime.TypeInfo_Struct struct;
+
+ public type_desc_0(mercury.runtime.TypeInfo_Struct init) {
+ struct = init;
+ }
}
- public class type_ctor_desc_0 {
- // stub only
+ public static class type_ctor_desc_0 {
+ public mercury.runtime.TypeCtorInfo_Struct struct;
+
+ public type_ctor_desc_0(
+ mercury.runtime.TypeCtorInfo_Struct init)
+ {
+ struct = init;
+ }
}
public static boolean
__Unify____type_desc_0_0(mercury.type_desc.type_desc_0 x,
mercury.type_desc.type_desc_0 y)
{
- // stub only
- throw new java.lang.Error
- (""unify/2 called for type_desc type not implemented"");
+ return x.struct.unify(y.struct);
}
public static boolean
--------------------------------------------------------------------------
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