Estimated hours taken: 10
Branches: main
Merge the foreign_type pragma changes from the dotnet branch to the main
branch, plus do some more development work to generalise the change.
compiler/prog_data.m:
Add a type to hold the data from parsing a pragma foreign_type decl.
compiler/prog_io_pragma.m:
Parse the pragma foreign_type. This code is currently commented
out, while we decide on the syntax.
compiler/hlds_data.m:
Add a new alternative to hlds_type_body where the body of the type
is a foreign type.
compiler/make_hlds.m:
Place the foreign_type pragmas into the HLDS.
compiler/foreign.m:
Implement to_type_string which replaces export__type_to_type_string,
unlike export__type_to_type_string foreign__to_type_string takes an
argument specifying which language the representation is meant to be
in. to_type_string also needs to take a module_info to handle
foreign_types correctly. To avoid the need for the module_info to
be passed around the MLDS backend we provide a new type
exported_type which provides enough information for an alternate
version of to_type_string to be called.
compiler/export.m:
Delete export__type_to_type_string.
compiler/llds.m:
Since foreign__to_type_string needs a module_info, we add a new
field to pragma_c_arg_decl which is the result of calling
foreign__to_type_string. This avoids threading the module_info
around various llds passes.
compiler/mlds.m:
Record with in the mercury_type the exported_type, this avoids
passing the module_info around the MLDS backend.
Also add the foreign_type alternative to mlds__type.
Update mercury_type_to_mlds_type so that it handles types which are
foreign types.
compiler/mlds_to_il.m:
Convert a mlds__foreign_type into an ilds__type.
compiler/ilds.m:
The CLR spec requires that System.Object and System.String be
treated specially in the IL assembly so add them as simple types.
compiler/ilasm.m:
Before outputting a class name into the IL assembly check whether it
it can be simplified to a builtin type, and if so output that name
instead as required by the ECMA spec.
Changes for the addition of string and object as simple types.
doc/reference_manual.texi:
Document the new pragma, this is currently commented out because it
refers to syntax that has not yet been finalised.
compiler/fact_table.m:
compiler/llds_out.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_simplify_switch.m:
compiler/ml_switch_gen.m:
compiler/ml_unify_gen.m:
compiler/mlds_to_c.m:
compiler/mlds_to_csharp.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_java.m:
compiler/mlds_to_mcpp.m:
compiler/pragma_c_gen.m:
compiler/rtti_to_mlds.m:
Changes to handle using foreign__to_type_string.
compiler/hlds_out.m:
compiler/intermod.m:
compiler/magic_util.m:
compiler/ml_type_gen.m:
compiler/recompilation_usage.m:
compiler/recompilation_version.m:
compiler/term_util.m:
compiler/type_ctor_info.m:
compiler/unify_proc.m:
Changes to handle the new hlds_type_body.
compiler/mercury_to_mercury.m:
Output the pragma foreign_type declaration.
compiler/module_qual.m:
Qualify the pragma foreign_type declarations.
compiler/modules.m:
Pragma foreign_type is allowed in the interface.
Estimated hours taken: 18
Branches: main
Add compiler support for deciding when to use reserved addresses,
and for generating code appropriately when they are used.
compiler/options.m:
doc/user_guide.texi:
Add new options `--num-reserved-addresses'
and `--num-reserved-objects'.
compiler/hlds_data.m:
Add new type `reserved_address ---> null_pointer ; small_pointer(int) ;
reserved_object(sym_name, arity)'.
Add new cons_tag alternatives `reserved_address(reserved_address)'
and `shared_with_reserved_address(list(reserved_address), cons_tag)'.
Also add get_secondary_tag, for use by ml_type_gen.m.
compiler/ml_type_gen.m:
Don't generate types for constructors represented using reserved
addresses. For constructors represented using reserved_object,
generate the reserved object.
Also, use get_secondary_tag, rather than just unifying with
shared_remote/2, so that it works for
shared_with_reserved_tag(_, shared_remote(_, _)).
compiler/make_tags.m:
If --tags none and --num-reserved-addresses are both set,
then assign null_pointer and small_pointer(int) representations
to constants up to the value set in num-reserved-addresses.
If --tags none and --high-level-code are both set,
and more constants remain unassigned, then assign reserved_object
representations for those constants, and generate static member
variable declarations for the reserved_objects.
compiler/make_hlds.m:
Pass down the type_id to assign_constructor_tags in make_tags.m,
since it is needed for reserved_object representations.
compiler/ml_unify_gen.m:
compiler/unify_gen.m:
Handle construction, deconstruction, and tag tests for
types represented using reserved tags.
(In unify_gen.m, only null_pointer and small_pointer(int)
are supported; for reserved_object we call sorry/2).
compiler/ml_switch_gen.m:
compiler/switch_gen.m:
compiler/switch_util.m:
Handle switches on types represented using reserved tags.
XXX Currently we always use if-then-else chains for such
switches; this may not be efficient.
compiler/ml_code_util.m:
Add ml_format_reserved_object_name.
Also add accessibility parameter to ml_gen_static_const_defn,
so that it can be used for generating the class member
static constants used for reserved_objects.
compiler/ml_string_switch.m:
compiler/ml_type_gen.m:
compiler/ml_unify_gen.m:
Handle the new parameter to ml_gen_static_const_defn.
compiler/bytecode_gen.m:
Call sorry/2 if types represented using reserved addresses are
encountered.
Estimated hours taken: 2
Branches: main
Merge changes to add attributes to the HLDS, MLDS and ILDS from the
dotnet-foreign branch. We don't merge the changes to add syntax for
attributes, as the syntax is still very experimental.
compiler/hlds_pred.m:
compiler/prog_data.m:
Add attributes to the pred_info (they are a bit like markers,
but are more than just boolean flags).
compiler/ilasm.m:
Add custom attributes to appropriate positions (on assemblies,
IL types and methods).
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_type_gen.m:
compiler/ml_util.m:
compiler/mlds.m:
compiler/mlds_to_c.m:
compiler/mlds_to_csharp.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_java.m:
compiler/mlds_to_mcpp.m:
Add mlds__attributes, which are the MLDS version of custom attributes.
Convert hlds_pred__attributes into mlds__attributes.
Add a list of mlds__attributes to the mlds__function defn.
compiler/mlds_to_il.m:
Convert MLDS attributes to IL custom attributes.
Estimated hours taken: 0.5
Branches: main
compiler/ml_code_util.m:
Fix an XXX: give label functions "local" access.
compiler/ml_unify_gen.m:
Give wrapper functions access "private".
Extra code is needed here to set this
now that label functions have "local" access.
Estimated hours taken: 0.75
Branches: main
Use a new mlds__function_body type to represent function bodies, as the old
usage of maybe/1 was error prone ("no" meant the function had been declared
using :- pragma external, not merely that the body was missing).
compiler/mlds.m:
Add mlds__function_body type.
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_util.m:
compiler/mlds_to_c.m:
compiler/mlds_to_csharp.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_il.m:
compiler/mlds_to_java.m:
compiler/mlds_to_mcpp.m:
Handle this change.
Estimated hours taken: 0.5
Branches: main
ml_code_util.m:
Back out the change to make ml_gen_label_func_decl_flags be
one_copy.
ml_unify_gen.m:
Define a new function ml_gen_wrapper_func for generating wrapper
functions. This function calls ml_gen_label_func but overrides the
per_instance flag to be one_copy.
Estimated hours taken: 40
Branches: main
Refactor the top level of mlds_to_il so that we only do one pass over
the MLDS to generate the ILDS. As a side effect of this change nondet
code now works again.
compiler/mlds_to_il.m:
Do a MLDS to MLDS transformation which places all the procedures and
data into the mercury_code class. Then modify all the qualifiers to
take account of this change to the code.
Rewrite the top level so that it only does one pass over the MLDS
data structure.
Examine the flags when deciding which attributes to place on a
method, field or class.
compiler/mlds.m:
Add a new field to mlds__class_defn which is the list of
defns which are constructors for this class.
Add the functions mlds__append_mercury_code and mlds__append_name
which append either "mercury_code" or an arbitary string to the
module qualifier of a name.
compiler/ml_elim_nested.m:
Rather then hardcoding the generation of the constructor for the
environment class, we generate it here as an MLDS method.
On the IL backend the mercury code is placed in a seperate class to
the environment data, so the env_type decls must be public so as to
be accessible from the code.
compiler/ml_code_util.m:
Wrapper functions should be static methods not instance methods.
Fix ml_gen_label_func_decl_flags to make this true.
compiler/rtti_to_mlds.m:
Rtti data structures should be one_copy (ie static) not per_instance.
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_type_gen.m:
compiler/mlds_to_c.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_java.m:
Misc changes to handle the additon of a list of constructors to the
mlds__class_defn.
compiler/mlds_to_csharp.m:
compiler/mlds_to_mcpp.m:
Use the function class_name rather then mercury_module_name_to_mlds.
Estimated hours taken: 8
Branches: main
Add type information to the array_index operator.
This is needed for both the GCC back-end and the IL back-end.
compiler/builtin_ops.m:
In the array_index constructor for the unary_op type,
add the array element type as a field.
compiler/ml_string_switch.m:
compiler/string_switch.m:
compiler/mlds_to_java.m:
When generating array_index operators, generate the new field.
compiler/bytecode.m:
compiler/llds.m:
compiler/llds_out.m:
compiler/mlds_to_c.m:
compiler/mlds_to_java.m:
When consuming array_index operators, ignore the new field.
compiler/mlds_to_gcc.m:
When consuming array_index operators, use the array element type,
rather than wrongly assuming the element type is always 'MR_Integer'.
compiler/mlds_to_il.m:
Add code to handle the array_index operator,
rather than calling `throw_unimplemented'.
compiler/bytecode.m:
Delete the reverse mode of binop_code. This was not used,
it was just there to get the compiler to check that we didn't
map two different binary operators to the same code. This
mode no longer works, since we map array_index operators to
the same code regardless of the the array element type.
compiler/rtti_to_mlds.m:
compiler/ml_string_switch.m:
compiler/ml_code_util.m:
To avoid code duplication, move ml_string_type, which was defined in
both rtti_to_mlds.m and ml_string_switch.m, into ml_code_util.m.
compiler/ml_string_switch.m:
Minor changes to avoid some code duplication.
compiler/mlds_to_java.m:
Fix a bug where it was using the wrong type for the `args' variable.
Add an XXX comment about what looks to me like another bug.
Estimated hours taken: 4
Branches: main
The .NET backend requires that names are not only qualified with their
namespace but the source package the name comes from. In this change we
back out a previous solution to this problem and implement a much
neater solution where we hide the package name in the abstract type
mlds_module_name.
This solution is neater because the package name shouldn't change once
the name is defined. All that we may have to change is the qualifiers
to the name.
compiler/mlds.m:
Add the package name to the abstract type mlds_module_name.
compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_type_gen.m:
compiler/ml_unify_gen.m:
compiler/ml_util.m:
compiler/mlds_to_c.m:
compiler/mlds_to_csharp.m:
compiler/mlds_to_il.m:
compiler/mlds_to_java.m:
compiler/mlds_to_mcpp.m:
compiler/rtti_to_mlds.m:
Back out previous solution.
Estimated hours taken: 16
Branches: main
The .NET backend requires that names are not only qualified with their
namespace but the source package the name comes from. In this change we
add to the name type the name of the source package which this name is
defined in. This change will be needed for implementing foreign_class
in the .NET backend where it will no longer be possible to determine
the package name from the fully qualified name.
compiler/mlds.m:
Add the new field to the mlds__fully_qualified_name type.
compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_type_gen.m:
compiler/ml_unify_gen.m:
compiler/ml_util.m:
compiler/mlds_to_c.m:
compiler/mlds_to_csharp.m:
compiler/mlds_to_il.m:
compiler/mlds_to_java.m:
compiler/mlds_to_mcpp.m:
compiler/rtti_to_mlds.m:
Propogate the changes around.
Estimated hours taken: 0.5
Branches: main
compiler/ml_code_util.m:
Fix a bug in trd's previous change: it was not setting the "function
without return value" field correctly for predicates.
Estimated hours taken: 5
Branches: main, dotnet-foreign
Minimize the amount of procedure name mangling done by the .NET backend.
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/ml_util.m:
compiler/mlds.m:
compiler/mlds_to_c.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_java.m:
compiler/rtti_to_mlds.m:
Add the code_model and a boolean indicating whether this
function (if it is a function) *doesn't* have a return value
(i.e. it has a non-default mode).
Also move is_output_det_function into ml_code_util.m and rename it
ml_is_output_det_function.
compiler/mlds_to_il.m:
Mangle much more carefully. We still mangle in a predictable,
context-insensitive manner, however we take advantage of the
overloading available in the .NET backend to avoid name clashes
in most cases.
Estimated hours taken: 45
Branches: main
Implement a C# interface for the .NET backend.
To use it, you currently need to set
--backend-foreign-language csharp --use-foreign-language csharp
in your MCFLAGS.
The C# foreign language interface works by introducing a new sort of
MLDS statement called outline_foreign_proc. outline_foreign_proc is expected
to be turned into a separate procedure in a separate file. This is
quite different to normal foreign code which has been renamed as inline
target code, as it is really intended to be generated inline, inside the
generated code.
Because outline_foreign_proc is expected to be generated outside the
normal code, we don't need to generate variable renamings,
initializations, casts and other complicated interfacing code.
Any marshalling is done by the backend, which knows how to marshall
arguments across the boundary into the outline code and back. In the
case of marshalling to C# from the .NET backend, we currently don't do
anything special (part of the point of .NET is that data
representation don't have to change very often just because you are
using different languages, so this is a property we should try to
preserve).
The actual implementation of the foreign code is therefore very simple.
Simply generate an appropriate procedure, and insert the user's code in
the middle.
The bulk of this change to delay the mangling of MLDS var names, so we
can still use the original user's var name when we output the outline
procedure (since the user's foreign code will refer to these var names,
it's important to keep them around).
compiler/foreign.m:
Handle the csharp foreign language.
compiler/globals.m:
Fix an XXX about converting to lowercase to do language name
comparisons.
Add new predicates to make conversion of foreign languages
to strings more uniform.
compiler/handle_options.m:
Don't set backend_foreign_language to the default if it has
already been set by hand.
compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
Delay the mangling of MLDS var names by keeping the variable
number around until the output phase.
Slightly generalize the handling of foreign language interfacing.
Handle C# foreign language interfacing.
Add value_output_vars to the ml_gen_info, which are the variables
returned rather than passed by reference. We need to know
these variables for C# interfacing so that we can handle the return
value of the forwarding function.
Mark the beginning and end of the MLDS foreign language processing as
a "sub-module" (in comments at least). Later I may put this code
into a separate module.
Rename some predicates from c_code to foreign_code.
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_string_switch.m:
compiler/ml_type_gen.m:
compiler/ml_unify_gen.m:
compiler/ml_util.m:
compiler/rtti_to_mlds.m:
Handle the new var_name type, and the new target_code constructors.
compiler/mlds.m:
Add outline_foreign_proc which is handled differently to the old
target_code (which has been renamed inline_target_code).
Change the definiton for mlds__var_name.
compiler/mlds_to_c.m:
Factor out mlds_output_to_file.
Handle the new var_name type, and the new target_code constructors.
compiler/mlds_to_csharp.m:
A new module to generate C# code suitable for foreign language
interfacing. This is largely lifted from the MC++ code, with a few
changes to the output syntax.
compiler/mlds_to_il.m:
Return the set of foreign languages processed instead of a bool
saying wither MC++ was present. This is so we can generate the
appropriate output .cs or .cpp files, and because we need to keep
track of all the external assembly references we need to put in the
.il file.
Handle the inline_target_code and mlds__var_name changes.
compiler/mlds_to_ilasm.m:
Output .cpp and .cs files conditionally.
Factor out output_to_file.
Move MC++ output code to mlds_to_mcpp.m
compiler/mlds_to_java.m:
Factor out output_to_file.
Handle the new var_name type, and the new target_code constructors.
compiler/mlds_to_mcpp.m:
New file to handle generating MC++ code suitable for foreign language
interfacing.
compiler/options.m:
Add a way of setting the backend-foreign-language option.
compiler/passes_aux.m:
Add output_to_file which is used by the MLDS backend to generate
output files.
compiler/prog_data.m:
Uncomment csharp as a foreign language.
Estimated hours taken: 20
General improvements and bug fixes to the MLDS backend, most
of which were prompted by working on the Java backend.
The definition of mlds__lval now includes type information for
variables. This is necessary because if enumerations are treated
as objects (as in the Java backend) rather than integers we need to know
when to create new objects. At the level this occurs there was
previously no way to distinguish between an integer that is an integer,
and one that represents an enumeration.
Added the access specifier `local' to the declaration flags. This fixes
a bug in which the local variables of a function were being declared
`private'.
Redefined ctor_name so that they are fully qualified. This was necessary
because the Java backend represents discriminated unions as nested
classes and we need to be able to determine the fully qualified name of
the constructor in order to call it, do casts, etc.
Added `mlds__unknown_type' to `mlds__type'. This is due to the change
in the definition of mlds_lval above. In ml_code_util.m, env_ptr's are
created as dangling references. The new definition of mlds__lval expects
there to be a type as well, but at this point it hasn't been
generated (and won't be until the ml_elim_nested pass). Rather than just
guess the type we should declare the type to be unknown and print out an
error message if an unknown type makes it through to one of the backends.
Fixed a bug in the `--det-copy-out' option.
Shifted code for detecting entry point to main/2 from mercury_compile.m
to ml_util.m
compiler/mercury_compile.m:
compiler/ml_util.m:
Shifted code for detecting entry point to main/2 from mercury_compile.m
to ml_util.m
compiler/mlds.m:
Added `local' as an access specifier.
Extended definition of mlds__lval to include type information
for variables.
Added `mlds__unknown_type' to the mlds types so that when
the compiler generates variables without yet knowing their
type we can mark them as this, rather than hoping that the
correct types eventually get added.
Redefined ctor_name so that it is fully qualified.
Made changes to comments to reflect above changes.
compiler/ml_code_gen.m:
Mark the generated functions as `one_copy' rather than `per_instance',
so that they get generated as static methods for the Java back-end.
Fixed a bug with the --det-copy-out option.
compiler/ml_code_util.m:
Fixed a bug that was causing the wrong declaration flags to be
set for fields in du constructors.
Changed the name of the predicate `ml_qualify_var' to
`ml_gen_var_lval'.
compiler/ml_type_gen.m:
Mark the generated types as `one_copy' rather than `per_instance',
so that they get generated as static nested classes for the Java
back-end.
Changed comments to reflect that classes and enumeration constants
should be static.
Export functions that generate declaration flags because they
are used in other modules as well.
Added a new predicate `ml_gen_mlds_field_decl' that correctly
generates fields of classes in discriminated unions.
compiler/ml_unify_gen.m:
Changed the code that generates ctor_id's so that it generates
the new sort.
compiler/ml_call_gen.m:
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_string_switch.m:
compiler/ml_tailcall.m:
compiler/mlds_to_il.m:
compiler/mlds_to_c.m:
compiler/mlds_to_gcc.m:
compiler/mlds_to_ilasm.m:
compiler/rtti_to_mlds.m:
Fixed things so that they conform to the changes above.
Estimated hours taken: 12
Fix a bug with the handling of commits in the high-level C back-end.
It was implementing commits via calls to setjmp()/longjmp(),
but ANSI/ISO C says that longjmp() is allowed to clobber the values
of any non-volatile local variables in the function that called setjmp()
which have been modified between the setjmp() and the longjmp().
The fix is that whenever we generate a commit, we put it in its own
nested function, with the local variables (e.g. `succeeded',
plus any outputs from the goal that we're committing over)
remaining in the containing function. This ensures that
none of the variables which get modified between the setjmp()
and the longjmp() and which get referenced after the longjmp()
are local variables in the function containing the setjmp().
[The obvious alternative of declaring the local variables in the
function containing setjmp() as `volatile' doesn't work, since
the assignments to those output variables may be deep in some
function called indirectly from the goal that we're committing
across, and assigning to a volatile-qualified variable via a
non-volatile pointer is undefined behaviour. The only way to
make it work would be to be to declare *every* output argument
that we pass by reference as `volatile T *'. But that would
impose distributed fat and would make interoperability difficult.]
compiler/options.m:
Add a new option `--put-commits-in-own-function'.
compiler/handle_options.m:
If the target is high-level C, set the
`--put-commits-in-own-function' option.
compiler/ml_code_util.m:
Add a routine for accessing the new option.
compiler/ml_code_gen.m:
If the new option is set, generate each commit in its own
nested function.
tests/hard_coded/Mmakefile:
tests/hard_coded/setjmp_test.m:
tests/hard_coded/setjmp_test.exp:
A regression test.
Previous versions of the compiler generated code for this test
case that did the wrong thing on *some* systems.
Estimated hours taken: 6
Eliminated a lot of the dependencies on the the `code_model' type,
and move that type from llds.m into a new module `code_model'.
The aim of this change is to improve the modularity of the compiler by
reducing the number of places in the compiler front-end that depend
on back-end concepts and the number of places in the MLDS back-end
which depend on the LLDS.
compiler/code_model.m:
New module. Contains the code_model type and associated
procedures.
compiler/llds.m:
Move the code_model type into code_model.m.
compiler/hlds_goal.m:
Move the goal_info_get_code_model procedure into code_model.m,
to avoid having the HLDS modules import code_model.
compiler/hlds_out.m:
Delete `hlds_out__write_code_model', since it wasn't being used.
compiler/hlds_pred.m:
Move the proc_info_interface_code_model procedure into code_model.m,
to avoid having the HLDS modules import code_model.
compiler/goal_path.m:
When computing the `maybe_cut' field for `some' goals,
compute it by comparing the determinism rather than by
comparing the goal_infos.
compiler/unique_modes.m:
Use determinism and test for soln_count = at_most_many
rather than using code_model and testing for model_non.
compiler/inlining.m:
Test for determinism nondet/multi rather than testing
for code_model model_non.
compiler/hlds_pred.m:
compiler/det_report.m:
Change valid_code_model_for_eval_method, which succeeded unless
the eval_method was minimal_model and the code_model was model_det,
to valid_determinism_for_eval_method, which succeeds unless the
eval_method is minimal_model and the determinism cannot fail.
As well as avoiding a dependency on code_model in the HLDS
modules, this also fixes a bug where det_report could give
misleading error messages, saying that `multi' was a valid
determinism for `minimal_model' predicates, when in fact the
compiler will always report a determinism error if you declare
a `minimal_model' predicate with determinism `multi'.
(Actually the code in which this bug occurs is in fact
unreachable, but this is no doubt also a bug... I'll address
that one in a separate change.)
compiler/lookup_switch.m:
Simplify the code a bit by using globals__lookup_*_option
rather than globals__get_option and then getopt__lookup_option.
compiler/*.m:
Add `import_module' declarations for `code_model', and in some
cases remove `import_module' declarations for `llds'.
Estimated hours taken: 0.25
compiler/ml_code_util.m:
compiler/mlds.m:
Add some more comments, to clarify things that Tyson
identified in his review of my last change.
Estimated hours taken: 8
Get the MLDS back-end to generate better code for string switches.
compiler/ml_code_util.m:
compiler/ml_unify_gen.m:
Move the routines for generating static constants from
ml_unify_gen.m to ml_code_util.m, for use by ml_string_switch.m.
compiler/ml_string_switch.m:
New file, adapted from string_switch.m.
This handles generation of string switches for the MLDS back-end.
It generates string switches using string hashing and either
computed gotos or int switches.
compiler/ml_switch_gen.m:
Add support for string switches.
Export the target_supports_* predicates, for use in ml_string_switch.m.
(Perhaps these predicates should be moved into a different module?)
Add `target_supports_goto'.
compiler/notes/compiler_design.html:
Mention the new module. Also mention other MLDS modules that
have been recently added and not yet documented here.
Estimated hours taken: 8
Get the MLDS back-end to generate better code for switches.
It now compiles Mercury switches on int/char/enums into C switches.
compiler/mlds.m:
Add `switch' as a new alternative in the `mlds__stmt' type.
compiler/ml_elim_nested.m:
compiler/ml_optimize.m:
compiler/ml_tailcall.m:
compiler/ml_util.m:
Minor changes to handle the new `switch' statement.
compiler/ml_code_gen.m:
Move the code for handling switches to ml_switch_gen.m.
Export `ml_gen_goal', for use in ml_switch_gen.m.
compiler/ml_switch_gen.m:
compiler/ml_dense_switch.m:
New files, adapted from switch_gen.m and dense_switch.m, but
with significant changes. These now handle three forms of switch:
- dense switches, implemented as computed gotos;
- "direct mapped" switches, which get implemented using the
MLDS switch statement, which in turn gets mapped to the
target language's switch statement;
- if-then-else chains
compiler/ml_code_util.m:
Add a label counter to the ml_gen_info, and define predicates
for allocating new labels.
compiler/mlds_to_c.m:
Output switch statements. Also fix a layout bug in the output:
make sure we output newlines at the end of comments.
compiler/mlds_to_il.m:
Call error/1 for MLDS switch statements. The code generator
will generate MLDS computed_gotos (which map to IL `switch'
instructions) rather than MLDS switch statements, so we should
never get MLDS switch statements here.
compiler/options.m:
Add a new option `--prefer-switch', defaulting to enabled,
which says to generate switches rather than computed gotos
where possible.
Estimated hours taken: 6
Change the MLDS calling convention so that for model_det Mercury functions
with output mode results, the function results get mapped to MLDS function
return values rather than to by-ref parameters. The rationale for this is
to make interoperability simpler (especially for the IL & Java back-ends).
compiler/lambda.m:
Change the rules for compatibility of closures so that for
MLDS grades function closures are not treated as compatible
with predicate closures.
compiler/ml_code_util.m:
Change ml_gen_params so that it takes a pred_or_func parameter, and
for model_det functions it maps the output-moded function results
to MLDS return values.
compiler/ml_code_gen.m:
For model_det functions with output mode results,
return the function result by value.
Rename the `output_vars' field of the ml_gen_info as
`byref_output_vars'.
compiler/ml_call_gen.m:
Pass down the pred_or_func parameter to ml_gen_params.
For calls to model_det functions with output mode results,
return the function result by value.
compiler/hlds_goal.m:
Add new predicate generic_call_pred_or_func, for use by ml_call_gen.m.
compiler/ml_unify_gen.m:
Modify the code for generating wrapper functions for closures so
that it reflects the new calling convention for Mercury functions.
compiler/mlds.m:
compiler/mlds_to_c.m:
compiler/ml_code_gen.m:
Don't handle model_det functions with output mode results specially
in `pragma export' anymore, since the internal MLDS form now
has the same prototype as the exported one.
Estimated hours taken: 20
Fix some bugs in the static ground term optimization for the MLDS
back-end.
compiler/ml_code_util.m:
compiler/ml_code_gen.m:
Ensure that declarations for a goal are generated in such a
way that they scope over the C code generated for any
following goals. This is needed to ensure that we don't
generate references to undeclared names in static constants.
compiler/ml_unify_gen.m:
compiler/ml_code_util.m:
Ensure that all static consts get unique names, so that
ml_elim_nested.m can hoist them to the top level.
Also move ml_gen_static_const_decl_flags from ml_unify_gen.m
to ml_code_util.m, for use by ml_code_gen.m.
compiler/ml_elim_nested.m:
Hoist out the definitions of static constants to the top level
in cases where they might be referenced from nested functions.
Also change the name of the local_vars field of the ml_elim_info
to local_data, to make it clear that it can hold constants too.
compiler/mark_static_terms.m:
Fix some typos in the comments.
compiler/mlds_to_c.m:
Fix an XXX: it was not outputting `static' in the right places.
tests/valid/Mmakefile:
tests/valid/static.m:
Add some regression tests.
Estimated hours taken: 4
Fix problems that stopped the IL backend from working.
Also fix misleading error messages given by sorry/1 and unexpected/1
which I noticed when I was fixing these bugs.
compiler/error_util.m:
compiler/ml_code_util.m:
compiler/mlds_to_il.m:
compiler/mlds_to_ilasm.m:
Add sorry/2 and unexpected/2, which give sorry and unexpected
messages but also take the module name as a parameter.
Implement sorry/1 and unexpected/1 using the more general versions.
Use sorry/2 and unexpected/2.
compiler/handle_options.m:
Only do low-level backend option implications if we are generating
low-level code. This fixes a bug where static ground terms were
being re-activated in the IL backend because -no-lazy-code implies
static ground terms. (The IL backend doesn't support static
ground terms).
compiler/ilasm.m:
Fix some quoting bugs. We were replacing " with \" and then
replacing \" with \\".
compiler/ml_elim_nested.m:
Fix some bugs where we were using the wrong type for
environment "pointers". In IL the env_ptr is actually just an
object reference, not a pointer at all.
We now store the env_ptr type in the elim_info.
compiler/mlds.m:
Add an extra comment about cast.
Estimated hours taken: 220
The .NET MSIL (Microsoft Intermediate Language) backend.
While not complete, this backend implements enough of Mercury to run
programs such as eliza (with an appropriate runtime, which is not part
of this change). The IL backend TODO list is in mlds_to_il.m.
We generate IL "assembler" from MLDS. The IL assembler (ILASM) then
turns this into bytecode in a .DLL or .EXE file.
Pragma C code is put into a separate .cpp file and compiled using the managed
C++ compiler.
compiler/il_peephole.m:
Peephole optimize the IL.
compiler/ilasm.m:
Generate IL assembler from IL.
Also a representation of the entities in the IL assembler
syntax.
compiler/ilds.m:
The IL instruction set.
compiler/mercury_compile.m:
Generate IL if --target il is set.
Define mercury_compile__mlds_has_main/1.
Assemble the IL if --target-code-only is not set.
Use "target_debug" option instead of "c_debug".
compiler/ml_code_gen.m:
If the target is IL and we are generating MLDS for foreign code
that calls continuations (that is, model_non pragma C code),
create a nested function (not implemented in foreign code) to
call the continuation. This is because in managed C++ it isn't
possible to call a continuation, but it's fine to call a method
written in IL that calls the continuation instead.
compiler/ml_code_util.m:
Add unexpected/1 as another error message handler.
Add code for generating indirect calls to success continutation
(via a nested function).
compiler/ml_elim_nested.m:
Generate slightly different code for IL environments. We don't
use the address of the environment variable (like in the C
backend) but use the environment variable directly. We also
have to initialize the environment as a new object.
This is because we use a class to represent the environment,
whereas the C backend uses a struct.
Also, if there is no environment required for nested functions
(that is, the nested functions don't use any of the local
variables of the parent), don't generate an environment.
This is important for the nested functions generated in mangaged
C++ -- otherwise have to be able to handle defining and
initializing environments in managed C++ just to do the continuation
calls for model non pragma C code.
Add field names to elim_info.
compiler/mlds_to_il.m:
The IL code generator.
Also contains the mapping from MLDS type to IL types (which
is useful when generating forieng language stubs to interface
with IL).
compiler/options.m:
Add a debugging option for IL assember -- it prints out each
line of assembler before it executes. This is very much a
developer only option.
Make a "target_debug" option -- the old "c_debug" option is just
an alias for this option. If the target it IL, "target_debug"
can also turn on debugging for IL, allowing the IL debugger to
display IL instructions as it traces execution.
Estimated hours taken: 30
Implement builtin tuple types, similar to those in Haskell.
Tuples are constructed and deconstructed using
the syntax X = {Arg1, Arg2, ...}.
Tuples have type `{Arg1, Arg2, ...}'.
Unary tuples (X = {Arg}) do work, unlike in Haskell. The rationale
for this is that it is useful to be able to construct unary tuples
to be passed to a polymorphic predicate which uses std_util__deconstruct
to deal with a tuple of any arity. Since this is probably the only
use for unary tuples, it's not really worth the effort of treating
them as no_tag types, so we don't.
The type-infos for tuples have the same structure as for higher-order
types. There is a single type_ctor_info for tuples, and the arity
is placed before the argument type_infos.
library/parser.m:
Change the way '{}/N' terms are parsed, so that the parsed
representation is consistent with the way other functors
are represented (previously the arguments were left as
unparsed ','/2 terms). This avoids special case code
in prog_io__parse_qualified_term, term__term_to_type
and term__type_to_term.
compiler/prog_io_dcg.m:
compiler/prog_io_util.m:
Handle the new structure of '{}/N' terms when parsing DCG escapes
by converting the argument list back into a single ','/2 term.
compiler/module_qual.m:
Treat tuples as a builtin type.
compiler/typecheck.m:
Typecheck tuple constructors.
compiler/mode_util.m:
Propagate types into tuple bound insts.
compiler/type_util.m:
Add type_is_tuple/2 and type_id_is_tuple/1 to identify tuple types.
Add tuples to the list of types which are not atomic types.
Handle tuple types in `type_constructors' and
`get_cons_id_arg_types' and `switch_type_num_functors'.
compiler/tabling.m:
Handle tabling of tuples.
compiler/term_util.m:
Handle tuples in the code to compute functor norms.
compiler/magic_util.m:
compiler/rl.m:
compiler/rl_key.m:
Handle tuple types in the Aditi back end.
compiler/mercury_to_mercury.m:
library/io.m:
library/term_io.m:
Handle output of '{}/N' terms.
compiler/higher_order.m:
compiler/simplify.m:
Don't specialize complicated unifications of tuple
types into calls to a specific unification procedure --
even if the procedure were implemented, it probably
wouldn't be that much more efficient.
compiler/unify_proc.m:
Generate unification procedures for complicated unifications
of tuples (other than in-in unifications). These are generated
lazily as required.
compiler/make_hlds.m:
Export add_special_pred for use by unify_proc.m.
compiler/polymorphism.m:
Export polymorphism__process_pred for use by unify_proc.m.
compiler/bytecode_gen.m:
compiler/code_util.m:
compiler/ml_code_util.m:
Handle unify procedure names and tags for tuple types.
compiler/mlds_to_c.m:
Output tuple types as MR_Tuple.
compiler/ml_unify_gen.m:
Compute the field types for tuples.
compiler/polymorphism.m:
compiler/pseudo_type_info.m:
Treat tuple type_infos in a similar way to higher-order type_infos.
compiler/hlds_data.m:
Document how cons_ids for tuple types are represented.
compiler/switch_gen.m:
compiler/table_gen.m:
Add tuple types to switches on type_util__builtin_type.
compiler/llds_out.m:
util/mdemangle.c:
profiler/demangle.m:
Transform items named "{}" to "f_tuple" when mangling symbols.
library/builtin.m:
Define the type_ctor_info used for tuples.
library/private_builtin.m:
Add `builtin_unify_tuple/2' and `builtin_compare_tuple/3',
both of which abort. All comparisons and in-in unifications
of tuples are performed by the generic unification functions
in runtime/mercury_ho_call.c and runtime/mercury.c.
library/std_util.m:
Implement the various RTTI functions for tuples.
Encode tuple `TypeCtorDesc's in a similar way to that
used for higher-order types. This has the consequence that the limit
on the arity of higher-order types is now MAX_VIRTUAL_REG,
rather than 2*MAX_VIRTUAL_REG.
Avoid calling MR_GC_free for the type-info vector returned
from ML_expand() for tuples because unlike the vectors
for du types, it is not copied.
runtime/mercury_type_info.h:
Add macros for extracting fields from tuple type-infos.
These just call the macros for extracting fields from higher-order
type-infos.
Add a macro MR_type_ctor_rep_is_variable_arity(), which
returns TRUE for tuples and higher-order types.
The distinction between higher-order and first-order types
is now misnamed -- the distinction is really between fixed arity
types and builtin variable arity types. I'm not sure whether
it's worth renaming everything.
runtime/mercury.h:
runtime/mercury.c:
Define unification and comparison of tuples in
high-level code grades.
runtime/mercury_deep_copy_body.h:
runtime/mercury_make_type_info_body.h:
runtime/mercury_tabling.c:
runtime/mercury_unify_compare_body.h:
Handle tuple types in code which traverses data using RTTI.
tests/hard_coded/construct.{m,exp}:
tests/hard_coded/expand.{m,exp}:
Test RTTI functions from std_util.m applied to tuples.
tests/hard_coded/tuple_test.{m,exp}:
Test unification, comparison, term_to_type etc. applied to tuples.
tests/hard_coded/deep_copy.{m,exp}:
Test deep copy of tuples.
tests/hard_coded/typeclasses/tuple_instance.{m,exp}:
Test instance declarations for tuples.
tests/tabling/expand_tuple.{m,exp}:
Test tabling of tuples.
tests/hard_coded/write.m:
Add some module qualifications for code which uses
`{}/1' constructors which are not tuples.
tests/invalid/errors2.{m,err_exp,err_exp2}:
Test handling of tuples in type errors messages.
NEWS:
doc/reference_manual.texi:
w3/news/newsdb.inc:
Document tuples.
doc/transition_guide.texi:
Document the change to the parsing of '{}/N' terms.
Estimated hours taken: 0.5
Various fixes for problems fjh pointed out in a review.
compiler/ml_code_util.m:
Fix a typo.
compiler/ml_optimize.m:
compiler/mlds_to_c.m:
Move some comments from mlds_output_assign_args to
generate_assign_args.
Remove mlds_output_assign_args as it is now dead code.
compiler/options.m:
Fix a typo, llds-optimize should be mlds-optimize.
doc/user_guide.texi:
Document --no-mlds-optimize.
Estimated hours taken: 24 (by fjh)
Add new options and grades for the IL back-end.
Implement an option to handle output parameters for nondeterministic
procedures by passing the outputs (by value) to the continuation,
rather than using pass-by-reference. This is needed for IL
because IL does not allow managed pointers (which we used to
implement pass-by-refernece) to be stored as fields of environment
structs.
Also add an option to return outputs by value in det/semidet code.
This is not yet tested, since none of our target languages support
returning multiple values.
(Note that the IL backend is not activated by these changes -- it
hasn't been checked in).
compiler/globals.m:
Use field names for the globals structure.
Add new `target' field to the globals.
compiler/options.m:
compiler/handle_options.m:
Add new options `--target', `--target-only', `--il', and `--il-only'.
`--target' specifies the output langauge (e.g. C or IL).
`--target-only' says to only compile to the output language
(e.g. similar to -C or --compile-to-c option).
`--il' sets target to IL.
`--il-only' sets target to IL and specifies --target-only.
Add new grades `il' and `ilc'.
These grades are used for compiling to il grades. `il' is the
normal `il' grade, while `ilc' uses low-level (C-like) data
representations.
Change `--compile-to-c' from a boolean option to an abbreviation
for `--target c --target-only', and move it from the "Output options"
section to the "Compilation model options" section.
Comment out the documentation for `--generate-prolog' and
`--prolog-dialect', since those options are not yet implemented.
Document the `--infer-all' option.
compiler/mercury_compile.m:
Check the `target_code_only' option rather than `compile_to_c',
since the latter is just an abbreviation now, not a real option.
compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_unify_gen.m:
Use the `--det-copy-out' option to decide whether to pass
output arguments for model_det/model_semi procedures by
reference, or whether to just return multiple values.
Use the `--nondet-copy-out' option to decide whether to pass
output arguments for model_non procedures by reference, or
whether to just pass them to the continuation.
compiler/mlds.m:
Change the mlds__cont_type so that it includes a list of
the continuation's argument types (if any).
compiler/mlds_to_c.m:
Update to reflect the change to mlds.m.
doc/user_guide.texi:
Update the documentation to reflect the above changes.
scripts/parse_grade_options.sh-subr:
Add new options `--target' and `--il'.
scripts/init_grade_options.sh-subr
Add new grades `il' and `ilc'.
scripts/final_grade_options.sh-subr
Make `--target il' imply `--high-level-code'.
Estimated hours taken: 1.25
Fix a bug in the MLDS back-end: handle `pragma export' of procedures
defined in modules other than the current module.
compiler/mlds.m:
Change the entity_name in the pragma_export type to a
qualified_entity_name.
compiler/ml_code_util.m:
Change ml_gen_proc_label so that it returns the module name too,
not just the entity_name.
compiler/ml_code_gen.m:
compiler/mlds_to_c.m:
Modify to reflect the changes described above.
tests/hard_coded/Mmakefile:
tests/hard_coded/pragma_export.m:
tests/hard_coded/pragma_export.exp:
A regression test for the above-mentioned bug fix.
Estimated hours taken: 4
compiler/ml_code_util.m:
Fix a bug introduced in fjh's changed to use generalised code for
boxing/unboxing existentially typed output arguments in the MLDS:
we now need to add existentially typed output args to the list of
output variables of a procedure.
Estimated hours taken: 12
For --high-level-data, use field names rather than offsets
when accessing fields.
compiler/hlds_data.m:
Include the field names in the hlds_cons_defn,
for use by ml_unify_gen.m.
compiler/make_hlds.m:
compiler/typecheck.m:
compiler/post_typecheck.m:
compiler/type_util.m:
Minor changes to handle the change to hlds_cons_defn.
compiler/ml_type_gen.m:
For fields of certain types, such as `float', etc.,
generate the field type as a boxed type (mlds__generic_type).
Don't generate a field for the secondary tag if it isn't
needed. If none of the ctors need a secondary tag, then
skip it entirely. If some but not all ctors need a
secondary tag, then put the secondary tag field in a
separate class derived fom the base class for this type,
and have the classes for the ctors that need it derived
from that class rather than from the base class.
compiler/ml_unify_gen.m:
For --high-level-data, use field names rather than offsets
when accessing data fields and secondary tags.
(XXX the code for closures still uses offsets.)
compiler/ml_code_util.m:
Add two new routines for dealing with fields,
`ml_gen_field_name' and `ml_must_box_field_type',
for use by ml_type_gen.m and ml_unify_gen.m.
compiler/mlds.m:
Change the documentation for the ClassType field in `field'
lvals: rename it as `PtrType', and make it clear that this is
the type of the pointer, not the type of the class pointed to.
Also add a new CtorType field to the `named_field' field_id.
compiler/ml_elim_nested.m:
Minor changes to handle the modifications to mlds.m.
compiler/mlds_to_c.m:
Ensure that we name-mangle struct names and field names.
For named_field field accesses, cast the pointer to the type
specified by the new CtorType field before dereferencing it.
Estimated hours taken: 8
Mork work on implementing the `--high-level-data' option. This change
fixes a problem with unify and compare procedures for equivalence types.
compiler/ml_code_gen.m:
Generalize the code for boxing existentially typed output
variables so that it now handles all cases where the procedure
argument types don't match the types of the head variables in
the body. That can occur for unify and compare procedures
for equivalence types too, not just for procedures with
existentially typed outputs.
compiler/ml_code_util.m:
Make several changes for use by ml_code_gen.m:
- Add a new field to the ml_gen_info containing a map(prog_var, lval).
- Change ml_gen_var so that it checks that map first, and if the
variable occurs in that map it uses the lval from the map.
- Export a new procedure ml_gen_var_with_type.
compiler/ml_call_gen.m:
Change ml_gen_box_or_unbox_lval so that it returns
code to assign both to and from the lval, rather than
just in one direction.
Estimated hours taken: 20
Make a start towards implementing the `--high-level-data' option.
XXX There are still quite a few places in the MLDS code generator,
specifically in ml_unify_gen.m, ml_call_gen.m, and ml_code_gen.m,
that assume `--no-high-level-data'. For example, we still use
the MR_field() macro rather than using named fields.
XXX Equivalence types are not yet supported.
compiler/ml_type_gen.m:
New module. If --high-level-data is enabled, this module
generates MLDS type definitions for HLDS types.
compiler/ml_code_gen.m:
Import ml_type_gen.m, and delete the stub code for
`ml_gen_types', since that is now defined in ml_type_gen.m.
compiler/mlds_to_c.m:
- If --high-level-data is enabled, declare variables whose Mercury
types is user-defined using the MLDS types generated by
ml_type_gen.m, and declare closures with type `MR_ClosurePtr'
rather than `MR_Word'.
- Output type definitions in the header file rather than
then `.c' file.
- Add code to output `mlds__enum' classes as C enums,
and to handle static members and nested types in classes;
these changes are needed because ml_type_gen generates those
constructs.
- Cast the argument of MR_tag() to `MR_Word'.
- Cast the result of MR_new_object() to the appropriate type.
runtime/mercury.h:
- Delete the cast to `MR_Word' in MR_new_object(), because it was
not right for the --high-level-data case; the necessary casts
are now generated by mlds_to_c.m.
- Define the `MR_ClosurePtr' type.
compiler/mlds_to_c.m:
compiler/ml_elim_nested.m:
Fully qualify struct member names. This is needed to avoid
name clashes for the enumeration constants and nested types
that ml_type_gen generates, in particular for the case where
the same constructor name and arity occurs in two or more
different types in a single module. It's also more consistent
with our general approach of fully qualifying all references.
compiler/mlds.m:
- Add a new field of type builtin_type to the mercury_type/2
MLDS type; this holds the type category (enumeration, etc.).
This required adding a module_info parameter to the
mercury_type_to_mlds function.
- Similarly, add a new field of type mlds__class_kind to the
class_type/2 MLDS type.
- Add a function `mlds__append_class_qualifier', for use by mlds_to_c.m
and ml_elim_nested.m.
- Add field names to the `mlds__class_defn' struct.
compiler/ml_code_util.m:
Add a new routine ml_gen_type for converting Mercury types to MLDS.
This just extracts the module_info from the ml_gen_info and then
calls mercury_type_to_mlds.
compiler/*ml*.m:
Change lots of places to use ml_gen_type and/or to pass the
module_info down to mercury_type_to_mlds, and to handle the
new field of mercury_type/3. Similarly, change quite a few
places to handle the new field of class_type/3.
In ml_code_util.m, passing the module_info down had the
pleasant side-effect of enabling the elimination of an
existing XXX: in ml_gen_proc_params_from_rtti,
UseNestedFunctions was not being calculated correctly,
because previously the globals where not easily available at
that point.
Estimated hours taken: 20
Implement static allocation of grounds terms for the
MLDS back-end.
compiler/hlds_goal.m:
Change the `maybe(cell_to_reuse)' field of `construct'
unifications from a `maybe(cell_to_reuse)' into a
`how_to_construct' type with three alternatives,
`reuse_cell(cell_to_reuse)', `construct_dynamically',
and the new alternative `construct_statically(static_cons)'.
`static_cons' is a new type that provides information on
how to construct a static ground term.
compiler/goal_util.m:
compiler/lambda.m:
compiler/magic.m:
compiler/magic_util.m:
compiler/modecheck_unify.m:
compiler/polymorphism.m:
compiler/quantification.m:
Trivial changes to handle the change to the `maybe(cell_to_reuse)'
field of `construct' unifications.
compiler/mark_static_terms.m:
New module. This traverses the HLDS and marks terms which can
be construction unifications which can be allocated statically
with the `construct_statically' flag.
compiler/mercury_compile.m:
For the MLDS back-end, if the static_ground_terms option is set,
invoke the mark_static_terms pass.
compiler/ml_unify_gen.m:
When generating code for construction unifications, pass down
the `how_to_reuse' field. If this is `construct_statically',
then generate a local initialized static constant, rather than
using `new_object' to allocate the memory dynamically.
(This required some fairly substantial reorganization.
I changed ml_gen_construct so that no_tag types and compound
terms, including closures, are handled separately from
constants. I moved some of the code from ml_gen_construct_rep
into ml_gen_construct, and the remainder, which deals with
constants, was simplified and renamed ml_get_constant. The
code for constructing closures was moved into a separate
predicate ml_gen_closure, and was simplified by elimination of
some code duplication. I also added a bunch of new procedures
for generating static constants.)
compiler/mlds.m:
Add a new alternative `mlds__array_type' to the mlds__type type.
This is needed by ml_unify_gen.m for static constants.
compiler/mlds_to_c.m:
Handle `mlds__array_type'. This required splitting
mlds_output_type into mlds_output_type_prefix and
mlds_output_type_suffix.
compiler/ml_code_util.m:
Reorder the code slightly, to improve readability.
Estimated hours taken: 4
Fix a bug in the MLDS back-end that broke
tests/typeclasses/typeclass_exist_method.m.
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
Add code to handle boxing of existentially typed output arguments.
tests/hard_coded/Mmakefile:
tests/hard_coded/existential_float.m:
tests/hard_coded/existential_float.exp:
Add another test case which tests more specifically
for this bug.
Estimated hours taken: 0.5
compiler/ml_code_util.m:
compiler/ml_call_gen.m:
compiler/ml_unify_gen.m:
Eliminate some code duplication, by using the existing
subroutines ml_gen_assign and ml_qualify_var in a number
of places where there code was duplicated.
Estimated hours taken: 12
Fix several bugs in the MLDS back-end:
- a bug in tail recursion optimization
- a bug that lead to duplicate field names in environment structs
- a few miscellaneous fixes for runtime/mercury.{h,c}.
compiler/mlds_to_c.m:
Fix a bug with tail recursion optimization:
for the tail recursive call `p(H1, H2) :- ... p(H2, H1) ...',
it was generating code of the form
void p(MR_Word H1, MR_Word H2) {
for(;;) {
...
{
H1 = H2;
H2 = H1;
continue;
}
...
}
}
which clobbered the value of H1. The fix was to change
it to generate code which assigns the new arguments to
temporary local variables before assigning them to the
headvars:
void p(MR_Word H1, MR_Word H2) {
for(;;) {
...
{
MR_Word H1__tmp_copy = H2;
MR_Word H2__tmp_copy = H1;
H1 = H1__tmp_copy;
H2 = H2__tmp_copy;
continue;
...
}
}
compiler/ml_code_util.m:
Add a new function ml_gen_mlds_var_decl/4, for use by
mlds_to_c.m for the tempoaries it now generates when handling
tail recursion.
compiler/ml_call_gen.m:
Ensure that the temporary conversion variables generated by
ml_gen_box_or_unbox_lval all have distinct names, by including
a sequence number in the name. This is needed because
ml_elim_nested.m assumes that all variables defined in a
function have different names; if two variables are defined in
different scopes with the same name, then when ml_elim_nested
hoists them out, this leads to a duplicate field name in the
environment struct.
compiler/ml_code_util.m:
Add a new counter field to the ml_gen_info and a new predicate
ml_gen_info_new_conv_var for accessing it, for use by
ml_gen_box_or_unbox_lval in ml_call_gen.m.
runtime/mercury.c:
Add definitions for some functions declared `extern inline'
in runtime/mercury_heap.h.
runtime/mercury.h:
- Delete some unnecessary `#ifdef ... #define ... #endif' guards;
everything in this file is already protected by the
`#ifndef MERCURY_H' guard at the top of the file.
- Increase the fixed limit here on the arity of types from 5 to 10,
since some files in the compiler directory use higher-order
types with arities greater than 5.
- Add a macro version of MR_box_float(), using gcc's `({...})'
extension.
Estimated hours taken: 15
Implement typeclasses for the MLDS back-end.
compiler/rtti.m:
Add base_typeclass_info as a new alternative in the
rtti_name and rtti_data types.
compiler/base_typeclass_info.m:
Change it to define base_typeclass_infos as rtti_data
rather than comp_gen_c_data.
compiler/mercury_compile.m:
Modify to reflect the changes to base_typeclass_info.m's
interface.
Also change the order in which we run the MLDS passes: make
sure to generate all the MLDS, including that generated by
rtti_to_mlds.m, before running the MLDS transformation passes
ml_tailcall.m and ml_elim_nested.m, since the wrapper
functions that rtti_to_mlds.m generates for typeclass methods
can contain code which those two MLDS transformation passes
need to transform.
compiler/rtti_out.m:
compiler/rtti_to_mlds.m:
compiler/mlds_to_c.m:
compiler/opt_debug.m:
Handle base_typeclass_infos.
compiler/mlds_to_c.m:
Fix a bug where it was not properly mangling variable names.
Note that polymorphism.m can introduce variable names
that contain operators, e.g. `TypeClassInfo_for_+'.
This bug broke tests/hard_coded/operator_classname.m.
I also changed it to mangle label names.
compiler/rtti_to_mlds.m:
Pass down the module_info, so that ml_gen_init_method
can use it when generate wrapper functions for type
class methods.
compiler/ml_unify_gen.m:
Export the ml_gen_closure_wrapper procedure, for use by
rtti_to_mlds for type class methods.
compiler/ml_code_util.m:
Add a new predicate `ml_gen_info_bump_func_label',
for use by rtti_to_mlds.m when generating wrapper
Add some functions defining magic numbers related to
the representation of type_infos, base_typeclass_infos,
and closures.
compiler/ml_call_gen.m:
Handle type class method calls.
compiler/llds_out.m:
Split the code for outputting a base_typeclass_info name
into a separate subroutine, and export that subroutine,
for use by rtti_out.m.
compiler/llds_out.m:
compiler/rtti_out.m:
Change llds_out.m so that it calls a new predicate
output_base_typeclass_info_storage_type_name, defined in
rtti_out.m, when outputting base_typeclass_info declarations.
This is needed because base_typeclass_infos are now defined
as RTTI constants with type `Code * []', and so need to be
handled as such by rtti_out.m rather than being assumed to
be structs like the other LLDS data_names.
Also move the code for handling dynamic initialization of
method pointers from llds_out.m to rtti_out.m,
at the same time changing it to handle their new definitions
as rtti_data rather than comp_gen_c_data.
compiler/mlds.m:
Delete the type `base_data', since it is no longer needed.
compiler/notes/type_class_transformation.html:
Fix a documentation bug: the second field of
base_typeclass_infos is the number of instance constraints,
not the number of unconstrained type variables.
compiler/notes/compiler_design.html:
Document the use of the rtti modules in the MLDS back-end,
and improve the documentation of their use in the LLDS back-end.
runtime/mercury.h:
Add a typedef for `MR_BaseTypeclassInfo', for use by the
code generated by rtti_to_mlds.m and mlds_to_c.m
for base_typeclass_infos.
Also add another work-around declaration of an MR_TypeCtorInfo;
with this, the browser directory now compiles.
Estimated hours taken: 2
Fix a bug in the MLDS back-end's code generation for
if-then-else goals with nondet conditions.
compiler/ml_code_gen.m:
When generating code for if-then-elses with nondet conditions,
allocate a fresh `cond_<N>' variable for each such
if-then-else, rather than reusing the `succeeded' variable.
This ensures that the boolean variable that we use to figure
out if the condition succeeded won't be clobbered by the
condition or the "then" part of the if-then-else.
compiler/ml_code_util.m:
Add routines for generating `cond_<N>' variables.
Add a new cond_var field to the ml_gen_info;
this is a sequence number used to generate those
variables.
Estimated hours taken: 1
Fix a bug in the MLDS back-end that broke samples/muz.
compiler/ml_code_util.m:
Fix a bug: it was getting the defining module
wrong when generating references to complicated
modes of unification procedures for types defined
in different modules (and likewise for opt_imported
procedures).
Estimated hours taken: 10
Implement RTTI support for the MLDS back-end using the rtti module.
compiler/ml_base_type_info.m:
Delete this file.
compiler/rtti_to_mlds.m:
New file, replaces ml_base_type_info.
This generates MLDS code from the RTTI data structures.
compiler/ml_code_gen.m:
Don't call ml_base_type_info.
compiler/mercury_compile.m:
Call rtti_to_mlds.
Also add a few more comments to the list of
imported modules.
compiler/mercury_compile.m:
compiler/type_ctor_info.m:
Delete the unnecessary second `module_info' parameter from
type_ctor_info_generate_rtti.
compiler/ml_code_util.m:
Add ml_gen_proc_params_from_rtti, for use by gen_init_proc_id
in rtti_to_mlds.
Fix a bug where it was using Arity for both the PredArity
and the TypeArity.
compiler/rtti.m:
compiler/rtti_out.m:
Change the documentation for rtti_out.m to say that it
_is_ intended to depend on LLDS.
Move rtti_data_to_name from rtti_out.m to rtti.m,
since that does not depend on the LLDS.
Add rtti__name_is_exported/1, and implement
rtti_name_linkage using that.
Add some new fields to rtti_proc_label, for use by
ml_gen_proc_params_from_rtti.
compiler/mlds.m:
Add a new alternative `rtti_type(rtti_name)' to mlds__type type,
and a new alternative `rtti_data(rtti_type_id, rtti_name)' to
the mlds__data_name type, so we can represent the names and
types of the RTTI data.
Change the mlds__initializer type to make it a bit more expressive,
so that it can represent e.g. initializers for arrays of structs,
since this is needed for some of the RTTI data.
compiler/ml_code_util.m:
compiler/ml_elim_nested.m:
compiler/mlds_to_c.m:
Handle the new definition of mlds__initializer,
and the new alternatives in the rtti_name and
mlds__data_name types.
Estimated hours taken: 7
Restructure the RTTI implementation to eliminate dependencies on the LLDS,
so that it can be used for the MLDS back-end as well as the LLDS back-end.
(Note that I have not yet modified the MLDS back-end to actually make
use of it; that will be a separate change.)
compiler/rtti.m:
Eliminate the dependency on LLDS, by replacing code_addr with a new
type `rtti_proc_label'. Add a procedure `rtti__make_proc_label' for
constructing these.
compiler/type_ctor_info.m:
Eliminate the dependency on LLDS, by calling rtti__make_proc_label
rather than code_util__make_entry_label.
compiler/ml_code_util.m:
Add a new procedure `ml_gen_pred_label_from_rtti',
for (eventual) use by ml_base_type_info.m.
Restructure the implementation of ml_gen_pred_label so that it
works by first calling rtti__make_proc_label and then calling
ml_gen_pred_label_from_rtti.
compiler/code_util.m:
Add new procedure `make_entry_label_from_rtti', for use by rtti_out.m.
Restructure the implementation of the predicates make_entry_label,
make_local_entry_label, and make_proc_label so that they work by first
calling rtti__make_proc_label. Change make_user_proc_label to take
a boolean rather than an import_status.
Also update the documentation for code_util__compiler_generated,
adding an XXX comment saying that the name is misleading.
compiler/rtti_out.m:
Call code_util__make_entry_label_from_rtti to
convert the rtti_proc_labels in the RTTI into code_addrs.
compiler/rl.m:
Update to reflect the changed interface to
code_util__make_user_proc_label.
Estimated hours taken: 16 (some work done in tandem with fjh)
Extend MLDS to cope with alternate backends, and hopefully to allow
easier implementation of high level data structures in the C backend.
Add type information that is required for more heavily typed backends
(with C you can just cast to void * to escape the type system when it is
inconvenient, with other systems this is impossible, e.g. a Java backend).
Introduce new "cast" unop, that does casts.
compiler/mercury_compile.m:
Split the generation of MLDS from outputting high-level C code.
MLDS can be connected up to other backends.
compiler/ml_base_type_info.m:
compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_tailcall.m:
compiler/ml_unify_gen.m:
Add a type to code address constants (the type signature of the
function).
Add the type of the field and the type of the object to field
instructions.
Add a type to mem_ref (the type of the reference).
Don't create local definitions if the locals are dummy types.
compiler/ml_elim_nested.m:
Add types to code addresses, fields and mem_refs.
Use cast where appropriate.
compiler/mlds.m:
Add cast statement.
Add types to code addresses, fields and mem_refs.
compiler/mlds_to_c.m:
Output casts, generally ignore the types in code addresses,
fields and mem_refs (high level C code doesn't really need them,
although it might be nice to use them in future).
Estimated hours taken: 0.25
compiler/mlds.m:
compiler/mlds_to_c.m:
compiler/ml_unify_gen.m:
compiler/ml_code_util.m:
Rename mlds__int_type, mlds__float_type, etc.
to mlds__native_int_type, mlds__native_float_type, etc.,
to make it clearer that these types are for the native
MLDS types, which may be different from the MLDS types
used to represent the correspondingly-named Mercury types.
Estimated hours taken: 1
Add support for `pragma memo' and `pragma loopcheck'
to the MLDS back-end.
compiler/ml_code_util.m:
Change the interface to ml_gen_mlds_var_decl so that it takes
an mlds__data_name rather than an mlds__var_name, so that it
can be used to generate declarations for tabling_pointer
variables.
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_unify_gen.m:
Change calls to ml_gen_mlds_var_decl to match its new interface.
compiler/ml_code_gen.m:
For tabled procedures, generate a definition of the
variable which holds the table.
compiler/mlds_to_c.m:
Add code to handling output the names of the variables
used to hold tables.
Estimated hours taken: 4
Split up ml_code_gen.m into four modules.
compiler/ml_call_gen.m:
New module, contains the MLDS code generation for
calls and builtins.
compiler/ml_unify_gen.m:
New module, contains the MLDS code generation for
unifications.
compiler/ml_code_util.m:
New module, contains stuff shared between
ml_call_gen.m, ml_unify_gen.m, and ml_code_gen.m.
compiler/ml_code_gen.m:
Move about 60% of the code here into the three new
modules.