Estimated hours taken: 3
Implement the generation of base_type_info structures
for the MLDS back-end. (Generation of base_type_functors
and base_type_layouts is still not yet implemented, though.)
compiler/ml_base_type_info.m:
New file. This generates the base_type_info structures.
It is similar to base_type_info.m, but for the MLDS back-end.
compiler/ml_code_gen.m:
Change ml_gen_types to call ml_base_type_info__generate_mlds.
Export ml_gen_pred_label, for use by ml_base_type_info.m.
compiler/mlds.m:
Add a new MLDS type `mlds__base_type_info_type',
for base_type_infos.
compiler/mlds_to_c.m:
Add code to handle `mlds__base_type_info_type'.
Handle complex initializers.
Generate proper module qualifiers for data names.
compiler/base_type_info.m:
Delete an obsolete comment.
Add a comment warning that any changes here may also require
changes to ml_base_type_info.m.
compiler/notes/compiler_design.html:
Mention the new module.
Estimated hours taken: 30
Modify the MLDS back-end to support the `--no-gcc-nested-functions' option.
compiler/ml_elim_nested.m:
New module. Contains an MLDS->MLDS transformation pass
to eliminated nested functions.
compiler/mercury_compile.m:
Call the new pass.
compiler/notes/compiler_design.html:
Mention the new module.
compiler/ml_code_gen.m:
If --no-gcc-nested-functions is specified, then pass
environment pointers to the nested continuation functions.
Note that most of the work of converting nested functions
into non-nested functions is deferred to the ml_elim_nested
pass. But the passing of environment pointers affects the
calling convention, and so it really needs to be done
here -- it can't be done in any semantics-preserving
MLDS transformation later one. Also it is easier to do
it in this pass anyway.
Also fix a bug where it was miscalculating the set of
variables to declare.
compiler/mlds.m:
- Add a new alternative `mlds__generic_env_ptr_type',
used for environment pointers.
- Add a new alternative `mlds__class_type' to the
`mlds__type' discriminated union, so that types
can include user-defined types. This is needed so
that we can define struct types for the nested
function enviroments.
As part of that change, rename `mlds__class' as `mlds__class_defn'.
- Change the argument type for the `do_commit' and `try_commit'
instructions from `var' to `rval'/`lval'. This is needed so that
these instructions can refer to references defined in the
containing function via the environment pointer.
compiler/mlds_to_c.m:
- Changed to reflect the renaming of `mlds__class'
as `mlds__class_defn'.
- Changed to reflect the change to the `do_commit' and `try_commit'
argument types.
- For the `mlds__cont_type' type, output it as either
`MR_NestedCont' or `MR_Cont', depending on whether
the `--gcc-nested-functions' option is enabled.
- Fix a bug where it would incorrectly parenthesizing
the left-hand operand of `->'.
- Insert some additional blank lines in the output,
for readability.
runtime/mercury_types.h:
- Rename the old `Cont' type as `MR_NestedCont',
and add a new `MR_Cont' type.
Estimated hours taken: 10
Handle quantification analysis of bi-implication (`<=>') goals correctly.
Previously we used to expand bi-implications before doing quantification
analysis, which stuffed up the results of quantification analysis for
those goals. We need to do quantification analysis first, and only
then can we expand bi-implications. In addition, elimination of double
negation needs to come after expansion of bi-implication, so I moved
that from make_hlds.m to purity.m.
compiler/hlds_goal.m:
Add a new alternative to the HLDS goal type for bi-implications.
Also add a new predicate negate_goal, for use by purity.m.
compiler/make_hlds.m:
Don't expand bi-implication here, instead just use the new
bi_implication/2 HLDS goal type.
Don't eliminated double negation here.
compiler/quantification.m:
Handle quantification for bi-implications.
Expand bi-implications.
compiler/purity.m:
Eliminate double negation.
compiler/hlds_out.m:
Add code to print out bi-implication goals.
compiler/*.m:
Trivial changes to handle the new bi_implication/2
alternative in the HLDS goal type.
compiler/notes/compiler_design.html:
Document the above changes.
tests/hard_coded/Mmakefile:
tests/hard_coded/quantifier2.m:
tests/hard_coded/quantifier2.exp:
A regression test for the above change.
Estimated hours taken: 0.25
Add some documentation in the compiler notes.
compiler/notes/compiler_design.html:
Mention lp.m in the termination analysis section.
Mention par_conj.m in the parallel conjunction section.
Estimated hours taken: 56
Extend the assertion system by
* handling assertions in the interface of a module differently to
those in the implementation.
* testing an assertion for the commutivity property.
compiler/polymorphism.m:
Remove the resolving of function calls and data constructors, do it
in post_typecheck instead so that assertions are fully resolved.
compiler/post_typecheck.m:
Add the resolving of function calls and data constructors.
Also call assertion__in_interface_check, if an assertion is in the
interface.
compiler/purity.m:
post_typecheck__finish_assertion can now print error messages so
pass the io__states.
compiler/hlds_data.m:
Add assertion_table_pred_ids, so that intermod knows which pred_ids
are assertions.
compiler/hlds_out.m:
Add predicate hlds_out__write_assertion, which is used by intermod
to write assertions to .opt files.
Change the behaviour of outputing a call, so that if the call is a
function it gets written out in functional syntax. This is
necessary because the resolving of function symbols now occurs in
post_typecheck (pre writing .opt files) rather than in polymorphism
(post writing .opt files).
compiler/intermod.m:
Change intermod so that it writes out any assertion in the
interface to the .opt file.
compiler/modules.m:
Ensure that assertions in the interface are not written to the
.int files. Assertions should only appear in .opt files.
compiler/dead_proc_elim.m:
When intermodule optimization is turned on dead_proc_elim gets run
before typechecking and the assertion predicates are removed. This
change makes dead_proc_elim keep assertions.
compiler/make_hlds.m:
The head variables for an assertion are already known, so initialise
the clause_info structure to those variables rather then creating
Arity fresh variables.
Also don't insert unifications with the head of the assertion, since
we already know that only variables are in the head.
compiler/goal_util.m:
Add mode `goal_calls_pred_id(in, out) is nondet' for use by
assertion__record_preds_used_in.
compiler/assertion.m:
Add a predicate assertion__is_comutativity_assertion, which given
an assertion_id determines whether or not that assertion declares
the commutivity of a pred/func.
Add a predicate assertion__in_interface_check, which checks that an
assertion doesn't refer to any constructors, functions and
predicates defined in the implementation of that module (note
doesn't handle modules imported in the implementation section
correctly).
Rewrite assertion__record_preds_used_in to use the nondet mode of
goal_calls_pred_id.
compiler/accumulator.m:
Remove the facts which declare '+' and '*' to be commutative, and
instead use the new assertion__is_commutivity_assertion predicate.
Also remove the bool from assoc_fact which is the commutivity of the
predicate, since only associative predicates reside in the table
now.
library/int.m:
Add commutivity declarations for '+' and '*', now that they have
been removed from the assoc_fact table. This allows me to test that
all of these changes actually work!
compiler/hlds_goal.m:
Clear up the documentation (I hope) for the type call_unify_context,
so that it is clear that the unification may also have been a
function application.
doc/reference_manual.texi:
doc/transition_guide.texi:
Document assertions.
Estimated hours taken: 40
A very very rough prototype of the MLDS code generator.
compiler/ml_code_gen.m:
New module. This converts HLDS to MLDS.
Still quite incomplete.
compiler/mlds.m:
A few minor changes to make things easier for ml_code_gen.m:
- add the type `mlds__statements == list(mlds__statement).'
- for special_preds, only store the declaring module name if
it is different from the defining module name.
- a couple of small bugs (one occurrence of class_id should
have been hlds_data__class_id, and the definition of the
function abstractness_mask was wrong).
compiler/mlds_to_c.m:
- Implement code for outputting code_addrs.
- Minor changes to make the output look better.
compiler/mercury_to_c.m:
Delete this module, since it is now obsolete --
it has been replaced by the MLDS back-end.
compiler/mercury_compile.m:
Add code for invoking the MLDS back-end.
When the --high-level-C option is specified,
invoke the MLDS back-end rather than mercury_to_c.m.
compiler/notes/compiler_design.html:
Delete the stuff about mercury_to_c.m.
Delete the "not yet committed" comment about ml_code_gen.m.
Estimated hours taken: 30
A batch of changes related to the development of the new MLDS back-end.
compiler/notes/compiler_design.html:
Reorganize the documentation to reflect the multi-target /
multiple back-end nature of the compiler.
Document mlds.m and the new modules c_util.m and mlds_to_c.m.
compiler/mlds_to_c.m:
New module. This converts MLDS to C/C++ code.
This version compiles, but it is still quite incomplete;
there's lots of parts which are still not yet implemented.
compiler/llds_out.m:
compiler/c_util.m:
Move some procedures from llds_out.m into a new module c_util.m,
so that they can also be used by mlds_to_c.m.
compiler/mlds.m:
- Add new functions for use by mlds_to_c.m:
* get_prog_context/1, for getting the prog_context from an
mlds__context
* get_module_name/1, for getting the module name from the mlds
* module_name_to_sym_name/1, for converting an mlds_module_name
to a sym_name
- Change the mlds__func_signature type to
* allow multiple return values, for consistency with the
MLDS `return' statement;
* include the names of the parameters.
- Undo the premature over-optimization of making the `constness'
and `finality' flags share the same flag bit.
Estimated hours taken: 0.25
compiler/post_typecheck.m:
compiler/purity.m:
compiler/notes/compiler_design.html:
Fix some documentation bugs: conversion of unifications
into function calls is now done in polymorphism.m, not
modecheck_unify.m.
compiler/purity.m:
Delete imports of modules modecheck_unify and modecheck_call,
since they weren't needed.
Estimated hours taken: 8
Record in which predicate an assertion is used.
compiler/accumulator.m:
compiler/lambda.m:
compiler/magic.m:
Initialise the assertions field in the new pred_info.
compiler/assertion.m:
An abstract interface to the assertion table (hopefully).
compiler/hlds_data.m:
Modify assertion_table_add_assertion to return the assert_id of the
inserted assertion.
compiler/hlds_pred.m:
Record in the pred_info the set of assertions that mention the pred.
compiler/post_typecheck.m:
Now record which predicates are used in assertions.
compiler/notes/compiler_design.html:
Document assertion.m
Estimated hours taken: 2.5
Some more changes to minimize the complexity of the intermodule dependencies.
In particular, ensure that bytecode.m does not need to import llds.m.
compiler/llds.m:
compiler/builtin_ops.m:
Move the definitions of the unary_op and binary_op types into
a new module `builtin_ops'. These types are used by three of the
different back-ends (bytecode, llds, and mlds) and therefore deserve
to be in their own module.
compiler/bytecode.m:
Define a type `byte_reg_type' and use that instead of llds__reg_type.
Delete the import of module llds.
compiler/notes/compiler_design.html:
Document the new module builtin_ops.
compiler/rl_exprn.m:
Add a comment explaining why we need to import llds (and builtin_ops).
compiler/base_type_layout.m:
compiler/bytecode.m:
compiler/code_util.m:
compiler/dense_switch.m:
compiler/ite_gen.m:
compiler/jumpopt.m:
compiler/llds_out.m:
compiler/lookup_switch.m:
compiler/middle_rec.m:
compiler/opt_debug.m:
compiler/opt_util.m:
compiler/rl_exprn.m:
compiler/string_switch.m:
compiler/tag_switch.m:
compiler/transform_llds.m:
compiler/unify_gen.m:
compiler/value_number.m:
compiler/vn_block.m:
compiler/vn_cost.m:
compiler/vn_flush.m:
compiler/vn_type.m:
compiler/vn_util.m:
compiler/vn_verify.m:
Add imports of module builtin_ops to lots of modules that
imported llds.
Estimated hours taken: 0.25
Add the infrastructure for assertions into the compiler.
compiler/notes/compiler_design.html:
Update documentation about exactly where quantification is done.
compiler/notes/glossary.html:
Define what an assertion is.
Estimated hours taken: 4
Merge in the changes from the existential_types_2 branch.
This change adds support for mode re-ordering of code involving
existential types. The change required modifying the order of the
compiler passes so that polymorphism comes before mode analysis,
so that mode analysis can check the modes of the `type_info' or
`typeclass_info' variables that polymorphism introduces, so that
it can thus re-order the code accordingly.
This change also includes some more steps towards making existential data
types work. In particular, you should be able to declare existentially
typed data types, the compiler will generate appropriate unification
and compare/3 routines for them, and deconstruction unifications for them
should work OK. However, currently there's no way to construct them
except via `pragam c_code', and we don't generate correct RTTI for them,
so you can't use `io__write' etc. on them.
library/private_builtin.m:
compiler/accumulator.m:
compiler/bytecode_gen.m:
compiler/check_typeclass.m:
compiler/clause_to_proc.m:
compiler/code_util.m:
compiler/common.m:
compiler/dead_proc_elim.m:
compiler/dependency_graph.m:
compiler/det_analysis.m:
compiler/det_report.m:
compiler/follow_code.m:
compiler/follow_vars.m:
compiler/goal_util.m:
compiler/higher_order.m:
compiler/hlds_goal.m:
compiler/hlds_out.m:
compiler/hlds_pred.m:
compiler/intermod.m:
compiler/lambda.m:
compiler/live_vars.m:
compiler/magic.m:
compiler/make_hlds.m:
compiler/mercury_compile.m:
compiler/mercury_to_c.m:
compiler/mode_errors.m:
compiler/mode_info.m:
compiler/mode_util.m:
compiler/modecheck_call.m:
compiler/modecheck_unify.m:
compiler/modes.m:
compiler/pd_cost.m:
compiler/polymorphism.m:
compiler/post_typecheck.m:
compiler/purity.m:
compiler/quantification.m:
compiler/rl_exprn.m:
compiler/rl_key.m:
compiler/simplify.m:
compiler/table_gen.m:
compiler/term_traversal.m:
compiler/type_util.m:
compiler/typecheck.m:
compiler/unify_gen.m:
compiler/unify_proc.m:
compiler/unique_modes.m:
compiler/unused_args.m:
compiler/notes/compiler_design.html:
doc/reference_manual.texi:
tests/hard_coded/typeclasses/Mmakefile:
tests/hard_coded/typeclasses/existential_data_types.m:
tests/hard_coded/typeclasses/existential_data_types.exp:
tests/warnings/simple_code.exp:
tests/hard_coded/Mmakefile:
tests/term/arit_exp.trans_opt_exp:
tests/term/associative.trans_opt_exp:
tests/term/pl5_2_2.trans_opt_exp:
tests/term/vangelder.trans_opt_exp:
tests/term/arit_exp.trans_opt_exp:
tests/term/associative.trans_opt_exp:
tests/term/pl5_2_2.trans_opt_exp:
tests/term/vangelder.trans_opt_exp:
tests/invalid/errors2.err_exp2:
tests/invalid/prog_io_erroneous.err_exp2:
tests/invalid/type_inf_loop.err_exp2:
tests/invalid/types.err_exp2:
tests/invalid/polymorphic_unification.err_exp:
tests/invalid/Mmakefile:
tests/warnings/simple_code.exp:
tests/debugger/queens.exp:
tests/hard_coded/Mmakefile:
tests/hard_coded/existential_reordering.m:
tests/hard_coded/existential_reordering.exp:
Merge in the changes from the existential_types_2 branch.
Estimated hours taken: 500
Add a new pass to the compiler, that attempts to introduce accumulators
into a procedure so as to make that procedure tail recursive.
WORK_IN_PROGRESS:
Document that the transformation now exists.
compiler/goal_util.m:
Create goal_util__can_reorder_goals, which is a version of
pd_util__can_reorder_goals that will work on the alias branch.
compiler/instmap.m:
Add instmap__changed_vars. This predicate is meant to provide the
same functionality as instmap_delta_changed_vars, but work on the
alias branch.
Also add comment to instmap_delta_changed_vars about using
instmap_changed_vars
compiler/accumulator.m:
The transformation.
compiler/mercury_compile.m:
Call the transformation.
compiler/options.m:
Add the option to turn the transformation on.
doc/user_guide.texi:
Document the option.
profiler/demangle.m:
util/mdemangle.c:
Demangle the accumulator version of the procedure labels.
compiler/notes/compiler_design.html:
Add the new pass to the documentation.
Estimated hours taken: 0.25
compiler/notes/compiler_design.html:
Update the description of the check_typeclass phase to indicate
that it:
- comes before type checking
- performs a source-to-source transformation
to defer most
of the checking to later passes.
Also delete mention of qualifying pred and func names in
check_typeclass.m; all that work gets done by the later passes now.
Estimated hours taken: 0.25
compiler/notes/compiler_design.html:
Improve the documentation of Aditi code generation by
splitting out the section describing the modules involved
in the output from those involved in code generation.
Estimated hours taken: 1200
Aditi compilation.
compiler/options.m:
The documentation for these is commented out because the Aditi
system is not currently useful to the general public.
--aditi: enable Aditi compilation.
--dump-rl: write the intermediate RL to `<module>.rl_dump'.
--dump-rl-bytecode: write a text version of the bytecodes
to `<module>.rla'
--aditi-only: don't produce a `.c' file.
--filenames-from-stdin: accept a list of filenames to compile
from stdin. This is used by the query shell.
--optimize-rl, --optimize-rl-cse, --optimize-rl-invariants,
--optimize-rl-index, --detect-rl-streams:
Options to control RL optimization passes.
--aditi-user:
Default owner of any Aditi procedures,
defaults to $USER or "guest".
--generate-schemas:
write schemas for base relations to `<module>'.base_schema
and schemas for derived relations to `<module>'.derived_schema.
This is used by the query shell.
compiler/handle_options.m:
Handle the default for --aditi-user.
compiler/hlds_pred.m:
compiler/prog_data.m:
compiler/prog_io_pragma.m:
compiler/make_hlds.m:
Add some Aditi pragma declarations - `aditi', `supp_magic', `context',
`naive', `psn' (predicate semi-naive), `aditi_memo', `aditi_no_memo',
`base_relation', `owner' and `index'.
Separate out code to parse a predicate name and arity.
compiler/hlds_pred.m:
Add predicates to identify Aditi procedures.
Added markers `generate_inline' and `aditi_interface', which
are used internally for Aditi code generation.
Add an `owner' field to pred_infos, which is used for database
security checks.
Add a field to pred_infos to hold the list of indexes for a base
relation.
compiler/make_hlds.m:
Some pragmas must be exported if the corresponding predicates
are exported, check this.
Make sure stratification of Aditi procedures is checked.
Predicates with a mode declaration but no type declaration
are no longer assumed to be local.
Set the `do_aditi_compilation' field of the module_info if there
are any local Aditi procedures or base relations.
Check that `--aditi' is set if Aditi compilation is required.
compiler/post_typecheck.m:
Check that every Aditi predicate has an `aditi__state' argument,
which is used to ensure sequencing of updates and that Aditi
procedures are only called within transactions.
compiler/dnf.m:
Changed the definition of disjunctive normal form slightly
so that a call followed by some atomic goals not including
any database calls is considered atomic. magic.m can handle
this kind of goal, and it results in more efficient RL code.
compiler/hlds_module.m:
compiler/dependency_graph.m:
Added dependency_graph__get_scc_entry_points which finds
the procedures in an SCC which could be called from outside.
Added a new field to the dependency_info, the
aditi_dependency_ordering. This contains all Aditi SCCs of
the original program, with multiple SCCs merged where
possible to improve the effectiveness of differential evaluation
and the low level RL optimizations.
compiler/hlds_module.m:
Add a field to record whether there are any local Aditi procedures
in the current module.
Added versions of module_info_pred_proc_info and
module_info_set_pred_proc_info which take a pred_proc_id,
not a separate pred_id and proc_id.
compiler/polymorphism.m:
compiler/lambda.m:
Make sure that predicates created for closures in Aditi procedures
have the correct markers.
compiler/goal_util.m:
Added goal_util__switch_to_disjunction,
goal_util__case_to_disjunct (factored out from simplify.m)
and goal_util__if_then_else_to_disjunction. These are
require because supplementary magic sets can't handle
if-then-elses or switches.
compiler/type_util.m:
Added type_is_aditi_state/1.
compiler/mode_util.m:
Added partition_args/5 which partitions a list of arguments
into inputs and others.
compiler/inlining.m:
Don't inline memoed procedures.
Don't inline Aditi procedures into non-Aditi procedures.
compiler/intermod.m:
Handle Aditi markers.
Clean up handling of markers which should not appear in `.opt' files.
compiler/simplify.m:
Export a slightly different interface for use by magic.m.
Remove explicit quantifications where possible.
Merge multiple nested quantifications.
Don't report infinite recursion warnings for Aditi procedures.
compiler/prog_out.m:
Generalised the code to output a module list to write any list.
compiler/code_gen.m:
compiler/arg_info.m:
Don't process Aditi procedures.
compiler/mercury_compile.m:
Call magic.m and rl_gen.m.
Don't perform the low-level annotation passes on Aditi procedures.
Remove calls to constraint.m - sometime soon a rewritten version
will be called directly from deforestation.
compiler/passes_aux.m:
Add predicates to process only non-Aditi procedures.
compiler/llds.m:
compiler/llds_out.m:
Added new `code_addr' enum members, do_{det,semidet,nondet}_aditi_call,
which are defined in extras/aditi/aditi.m.
compiler/call_gen.m:
Handle generation of do_*_aditi_call.
compiler/llds_out.m:
Write the RL code for the module as a constant char array
in the `.c' file.
compiler/term_errors.m:
compiler/error_util.m:
Move code to describe predicates into error_util.m
Allow the caller to explicitly add line breaks.
Added error_util:list_to_pieces to format a list of
strings.
Reordered some arguments for currying.
compiler/hlds_out.m:
Don't try to print clauses if there are none.
runtime/mercury_init.h:
util/mkinit.c:
scripts/c2init.in:
Added a function `mercury__load_aditi_rl_code()' to the generated
`<module>_init.c' file which throws all the RL code for the program
at the database. This should be called at connection time by
`aditi__connect'.
Added an option `--aditi' which controls the output
`mercury__load_aditi_rl_code()'.
compiler/notes/compiler_design.html:
Document the new files.
Mmakefile:
bindist/Mmakefile:
Don't distribute extras/aditi yet.
New files:
compiler/magic.m:
compiler/magic_util.m:
Supplementary magic sets transformation. Report errors
for constructs that Aditi can't handle.
compiler/context.m:
Supplementary context transformation.
compiler/rl_gen.m:
compiler/rl_relops.m:
Aditi code generation.
compiler/rl_info.m:
Code generator state.
compiler/rl.m:
Intermediate RL representation.
compiler/rl_util:
Predicates to collect information about RL instructions.
compiler/rl_dump.m:
Print out the representation in rl.m.
compiler/rl_opt.m:
Control low-level RL optimizations.
compiler/rl_block.m:
Break a procedure into basic blocks.
compiler/rl_analyse.m:
Generic dataflow analysis for RL procedures.
compiler/rl_liveness.m:
Make sure all relations are initialised before used, clear
references to relations that are no longer required.
compiler/rl_loop.m:
Loop invariant removal.
compiler/rl_block_opt.m:
CSE and instruction merging on basic blocks.
compiler/rl_key.m:
Detect upper/lower bounds for which a goal could succeed.
compiler/rl_sort.m:
Use indexing for joins and projections.
Optimize away unnecessary sorting and indexing.
compiler/rl_stream.m:
Detect relations which don't need to be materialised.
compiler/rl_code.m:
RL bytecode definitions. Automatically generated from the Aditi
header files.
compiler/rl_out.m:
compiler/rl_file.m:
Output the RL bytecodes in binary to <module>.rlo (for use by Aditi)
and in text to <module>.rla (for use by the RL interpreter).
Also output the schema information if --generate-schemas is set.
compiler/rl_exprn.m:
Generate bytecodes for join conditions.
extras/aditi/Mmakefile:
extras/aditi/aditi.m:
Definitions of some Aditi library predicates and the
interfacing and transaction processing code.
Estimated hours taken: 50
Rework the handling of types in higher_order.m.
- Fix bugs in higher_order.m that stopped it working with --typeinfo-liveness.
- Perform type and typeclass specialisation.
compiler/polymorphism.m:
Previously the type of typeclass_infos variables did not contain
any information about the constraint about which the variable contains
information. Now the type of a typeclass_info is
`private_builtin:typeclass_info(
private_builtin:constraint([ClassName, ConstrainedTypes]))'.
This allows predicates such as type_list_subsumes to check that
the class constraints match.
Note that `private_builtin:constraint' has no declaration, so
a lookup in the type definition map will fail. That's OK, because
type_to_type_id will fail on it, so it will be treated as a type
variable by any code which doesn't manipulate types directly.
Added polymorphism__typeclass_info_class_constraint to get the
class_constraint from a typeclass_info's type. This isn't used yet.
Also, fix a bug in extract_type_info: an entry in the typeinfo_var_map
was being overwritten using an entry from a dummy typevarset. Actually
the optimization to overwrite the location of the type_info after
extracting it from a typeclass_info was wrong because the type_info
won't be in that location in other branches.
compiler/higher_order.m:
Rework the handling of type substitutions. Now the types of the
called procedure are `inlined' into the calling procedure, rather
than building up the types of the specialised version using the
higher-order arguments. The advantage of this is that the code is
a bit simpler and handles extra type_infos properly. The disadvantage
is that the argument types for specialised versions may be more
specific than they need to be, so in some cases more specialised
versions will be created than before.
Also, don't actually rebuild the higher-order terms in the specialised
versions - just pass the terms through in case they are needed.
Handle the extra typeinfos required for --typeinfo-liveness.
Specialize calls to unify/2, index/2 and compare/3.
Specialize class_method_calls.
Specialize calls to the predicates in private_builtin.m which
manipulate typeclass_infos.
compiler/type_util.m:
type_to_type_id now fails on the dummy `constraint' type.
Remove typeinfos for non-variable types from the typeinfo_varmap
after inlining and higher-order specialisation.
compiler/inlining.m:
Factor out some common code to handle type substitutions
for use by higher_order.m.
compiler/hlds_pred.m:
Return the list of extra type_info variables added to the
argument list.
compiler/goal_util.m:
Take a set of non-locals as an argument to
goal_util__extra_nonlocal_typeinfos rather than extracting
them from a goal.
compiler/special_pred.m:
Handle unmangled unify/compare/index in special_pred_get_type.
compiler/base_type_layout.m:
Don't generate references to the typeinfo for
`private_builtin:constraint' - it doesn't exist.
compiler/unused_args.m:
Don't barf on specialised unification predicate names.
compiler/options.m:
Added options:
`--type-specialization' (default off).
`--higher-order-size-limit' - restrict the size of specialized
versions produced by higher_order.m.
`--disable-opt-for-trace' (default on) - where possible don't
change the options to make the trace match the source code.
compiler/handle_options.m:
Don't disable higher_order.m when --typeinfo-liveness is set.
Handle `--disable-opt-for-trace'.
compiler/hlds_data.m:
compiler/*.m:
Add the instance number to `base_typeclass_info_const' cons_ids,
so that higher_order.m can easily index into the list of instances
for a class to find the methods.
compiler/hlds_out.m:
Use the correct varset when printing out the constraint proofs.
Write the typeclass_info_varmap for each procedure.
compiler/mercury_to_mercury.m:
Print type variables with variable numbers.
library/private_builtin.m:
Add the argument to the typeclass_info type to hold the representation
of the constraint.
runtime/mercury_ho_call.c:
Semidet and nondet class_method_calls where
(0 < num_arg_typeclass_infos < 4) were aborting at runtime
because arguments were being placed starting at r1 rather
than at r(1 + num_arg_typeclass_infos).
doc/user_guide.texi
Document the new options.
compiler/notes/compiler_design.html:
Update the role of higher_order.m.
tests/hard_coded/typeclasses/extra_typeinfo.m:
Test case for the mercury_ho_call.c bug and the polymorphism.m
extract_typeinfo bug and for updating the typeclass_info_varmap
for specialised versions.
Estimated hours taken: 2
Improve the modularity of the code in purity.m by splitting it into two
modules and fix a purity-related bug by moving some code from typecheck.m
into the new module.
compiler/post_typecheck.m:
New module. Handles the typechecking stuff that happens
after typecheck.m.
compiler/purity.m:
Move the typechecking related code in purity.m into post_typecheck.m.
compiler/typecheck.m:
Move the code for copying clauses to the proc_infos, etc. into
new predicates in post_typecheck.m. This code is now called
from purity.m rather than from typecheck.m.
(I think the fact that it was being done in typecheck.m was a
bug -- it meant that the goal_info flags computed by purity.m
were not being copied across to the proc_infos.)
compiler/mercury_compile.m:
compiler/typecheck.m:
Don't pass the ModeError parameter down to typecheck_pred,
since with the above change it isn't needed anymore.
compiler/mercury_compile.m:
Run purity checking before writing the `.opt' files.
This is necessary because writing out the `.opt' files
requires that code in post_typecheck__finish_pred
(formerly in typecheck.m) has been run.
compiler/notes/compiler_design.html:
Document these changes.
Estimated hours taken: 250
Add support for tabling.
This change allows for model_det, model_semidet and model_non memoing,
minimal model and loop detection tabling.
compiler/base_type_layout.m:
Update comments to reflect new runtime naming standard.
compiler/det_analysis.m:
Allow tabling to change the result of det analysis. This is
necessary in the case of minimal model tabling which can
turn a det procedure into a semidet one.
compiler/det_report.m:
compiler/hlds_data.m:
Add code to report error messages for various non compatible
tabling methods and determinism.
compiler/hlds_out.m:
compiler/modules.m:
Remove reference to the old memo marker.
compiler/hlds_pred.m:
Create new type (eval_method) to define which of the available
evaluation methods should be used each procedure.
Add new field to the proc_info structure.
Add several new predicates relating to the new eval_method type.
compiler/inlining.m:
compiler/intermod.m:
Make sure only procedures with normal evaluation are inlined.
compiler/make_hlds.m:
Add code to process new tabling pragmas.
compiler/mercury_compile.m:
Call the tabling transformation code.
compiler/modes.m:
Make sure that all procedures with non normal evaluation have
no unique/partially instantiated modes. Produce error messages
if they do. Support for partially instantiated modes is currently
missing as it represents a large amount of work for a case that
is currently not used.
compiler/module_qual.m:
compile/prog_data.m:
compiler/prog_io_pragma.m:
Add three new pragma types:
`memo'
`loop_check'
`minimal_model'
and code to support them.
compiler/simplify.m:
Don't report infinite recursion warning if a procedure has
minimal model evaluation.
compiler/stratify.m:
Change the stratification analyser so that it reports cases of
definite non-stratification. Rather than reporting warnings for
any code that is not definitely stratified.
Remove reference to the old memo marker.
compiler/switch_detection.m:
Fix a small bug where goal were being placed in reverse order.
Call list__reverse on the list of goals.
compiler/table_gen.m:
New module to do the actual tabling transformation.
compiler/notes/compiler_design.html:
Document addition of new tabling pass to the compiler.
doc/reference_manual.texi:
Fix mistake in example.
library/mercury_builtin.m:
Add many new predicates for support of tabling.
library/std_util.m:
library/store.m:
Move the functions :
ML_compare_type_info
ML_collapse_equivalences
ML_create_type_info
to the runtime.
runtime/mercury_deep_copy.c:
runtime/mercury_type_info.h:
runtime/mercury_type_info.c:
Move the make_type_info function into the mercury_type_info module
and make it public.
runtime/Mmakefile:
runtime/mercury_imp.h:
Add references to new files added for tabling support.
runtime/mercury_string.h:
Change hash macro so it does not cause a name clash with any
variable called "hash".
runtime/mercury_type_info.c:
runtime/mercury_type_info.h:
Add three new functions taken from the library :
MR_compare_type_info
MR_collapse_equivalences
MR_create_type_info.
runtime/mercury_table_any.c:
runtime/mercury_table_any.h:
runtime/mercury_table_enum.c:
runtime/mercury_table_enum.h:
runtime/mercury_table_int_float_string.c:
runtime/mercury_table_int_float_string.h:
runtime/mercury_table_type_info.c:
runtime/mercury_table_type_info.h:
runtime/mercury_tabling.h:
New modules for the support of tabling.
Estimated hours taken: 400
Deforestation.
This increases the code size of the compiler by ~80k when compiling
with --intermodule-optimization --deforestation.
The improvement from deforestation is not measurable for mmc -C make_hlds.m.
Compile time for make_hlds.m increased from 50.7 seconds to 52.2 seconds
when running deforestation.
compiler/simplify.m
compiler/common.m
Provide a nicer interface for simplifying a goal,
not an entire procedure.
Rework the interface to avoid manipulating lots of booleans.
Return an estimate of the improvement in cost from simplification.
Remove failing cases and disjuncts.
Add an option to optimize common structures even across calls.
Remove code to merge branched goals, since that is now
done by deforestation.
Fix a bug: the code to collect instmap_deltas for cases was not
including the switched-on variable in the instmap_delta,
which caused an abort in merge_instmap_delta if the switched
on variable was further instantiated in the switch.
This came up while compiling the compiler with --deforestation.
compiler/det_report.
Output duplicate call warnings even if --warn-simple-code is not set.
XXX fix the same problem with `:- pragma obsolete'.
compiler/code_aux.m
Update code_aux__cannot_loop to use termination information.
compiler/hlds_pred.m
compiler/dnf.m
Pass the type_info_varmap and typeclass_info_varmap
into hlds_pred__define_new_pred.
Restrict the variables of the new procedure onto the variables
of the goal.
Make sure all relevant type_infos are passed into the new
procedure if --typeinfo-liveness is set.
compiler/modes.m
compiler/unique_modes.m
compiler/mode_info.m
compiler/modecheck_unify.m
Put `how_to_check_goal' into the mode_info, rather
than passing it around.
Add a field to the `check_unique_modes' case which
controls whether unique modes is allowed to choose
a different procedure. For deforestation, this is
not allowed, since it could result in choosing a less
efficient procedure after generalisation.
compiler/options.m
New options:
--deforestation
--deforestation-depth-limit
Safety net for termination of the algorithm.
--deforestation-cost-factor
Fudge factor for working out whether deforestation
was worthwhile.
--deforestation-vars-threshold
Like --inline-vars-threshold.
Enable deforestation at -O3.
Removed an unnecessary mode for option_defaults_2, since it
resulted in a warning about disjuncts which cannot succeed.
compiler/handle_options.m
--no-reorder-conj implies --no-deforestation.
compiler/inlining.m
Separate code to rename goals into inlining__do_inline_call.
compiler/hlds_goal.m
Added predicates goal_list_nonlocals, goal_list_instmap_delta
and goal_list_determinism to approximate information about
conjunctions.
compiler/hlds_module.m
Added module_info_set_pred_proc_info to put an updated
pred_info and proc_info back into the module_info.
compiler/hlds_out.m
Exported hlds_out__write_instmap for debugging of deforestation.
Bracket module names on constructors where necessary.
compiler/mercury_compile.m
Call deforestation.
Use the new interface to simplify.m.
compiler/intermod.m
Put recursive predicates with a top-level branched goal
into `.opt' files.
goal_util.m
Added goal_calls_pred_id to work out if a predicate is
recursive before mode analysis.
Export goal_util__goals_goal_vars for use by deforestation.
Give a better message for a missing variable in a substitution.
compiler/instmap.m
Give a better message for inst_merge failing.
compiler/notes/compiler_design.m
Document the new modules.
library/varset.m
Add varset__select to project a varset's names and values
onto a set of variables.
doc/user_guide.texi
Document deforestation.
Remove a reference to a non-existent option, --no-specialize.
util/mdemangle.c
profiler/demangle.m
tests/misc_tests/mdemangle_test.{exp,inp}
Handle the `DeforestationIn__' predicate names introduced by
deforestation, similar to the `IntroducedFrom__' for lambda goals.
New files:
deforest.m Deforestation.
pd_cost.m Cost estimation.
pd_debug.m Debugging output.
pd_info.m State type and version control.
pd_term.m Termination checking.
pd_util.m Utility predicates
Estimated hours taken: 0.25
compiler/notes/compiler_design.html:
Document why the first `simplify' pass is considered part of the
semantic analysis phase, not the high-level transformation phase
(the answer is because it can report warnings).
Estimated hours taken: 20
Add support for `pragma import', which is a simplified form of
`pragma c_code'. With `pragma import', the user specifies only
the C function name, rather than a C code fragment, and the
Mercury compiler handles the argument-passing automatically.
TODO
- add documentation to doc/reference_manual.texi.
WISHLIST
- change `pragma import' and `pragma export'
to take an additional parameter indicating the language
(e.g. C, Prolog, Ada, Fortran, etc.) and/or calling
convention
compiler/prog_data.m:
Add `pragma import' to the parse tree data structure.
compiler/prog_io_pragma.m:
Add code to parse `pragma import' declarations.
compiler/mercury_to_mercury.m:
Add code to pretty-print `pragma import' declarations.
compiler/module_qual.m:
Add code to module-qualify `pragma import' declarations.
compiler/make_hlds.m:
Add code to process `pragma import' declarations,
by converting them to clauses with HLDS `c_code' instructions.
compiler/export.m:
Declare `export__exclude_argument_type' in the interface,
for use by the code for handling `pragma import' in make_hlds.m.
Change the documentation to say that this procedure is used for
both exported and imported procedures.
compiler/notes/compiler_design.html:
Document how the compiler handles `pragma import' declarations.
tests/hard_coded/Mmakefile:
tests/hard_coded/pragma_import.m:
tests/hard_coded/pragma_import.exp:
Add some test cases for `pragma import'.
Estimated hours taken: 1/2
A few minor changes, including fixing the syntax of a typeclass declaration.
The methods inside a typeclass declaration no longer have a ":-" at the start.
compiler/make_hlds.m:
Give an error message is a typeclass is multiply defined.
compiler/prog_io.m:
Export parse_decl, and make the output a maybe_item_and_context so
that it is more useful to prog_io_typeclass.
compiler/prog_io_typeclass.m:
Use parse_decl rather than parse_item to parse the class methods. This
way the ":-" is left off.
compiler/notes/compiler_design.html:
Document why check_typeclass is the final semantic analysis pass.
Estimated hours taken: 8
Clean up the handling of unbound type variables.
Fix a bug with unbound type variables in lambda expressions.
Run purity analysis, modechecking etc. even if there were type errors.
compiler/mercury_compile.m:
Run purity analysis, modechecking etc. even if there were type
errors. This fixes a bug (inconsistency between the code and
the comments) that seems to have been introduced in stayl's
change to mercury_compile.m (revision 1.25) to add intermodule
unused argument elimination: the comment said "continue,
even if type checking found errors", but the code did not
continue.
This change was needed to ensure that we still report a warning
message about unused type variables for tests/invalid/error2.m;
without it, we stop after type checking and don't do purity
analysis, and so don't report the warning.
compiler/typecheck.m:
compiler/purity.m:
Move the code for checking for unbound type variables
from typecheck.m to purity.m. It needs to be done
*after* type inference has been completed, so it
can't be done in the ordinary type checking/inference
passes. Add code to purity.m to bind the
unbound type variables to the builtin type `void'.
compiler/polymorphism.m:
Comment out old code to bind unbound type variables
to `void'; the old code was incomplete, and this
is now done in purity.m.
compiler/notes/compiler_design.html:
Document the above changes.
tests/valid/Mmakefile:
tests/valid/unbound_tvar_in_lambda.m:
Regression test for the above-mentioned bug with unbound type
variables in lambda expressions.
tests/warnings/singleton_test.exp:
tests/invalid/errors2.err_exp:
Change the expected warning message for unbound type variables.
The error context is not as precise as it used to be, I'm afraid:
we only know which function/predicate the error occurred in,
not which clause. Also it now comes out in a different order
relative to the other error messages.
tests/invalid/errors2.err_exp:
tests/invalid/funcs_as_preds.err_exp:
Add some new error/warning messages that are output now that
we run mode and determinism analysis even if there are type errors.
Estimated hours taken: 60
A rewrite of termination analysis to make it significantly easier to modify,
and to extend its capabilities.
compiler/error_util.m:
A new file containing code that makes it easier to generate
nicely formatted error messages.
compiler/termination.m:
Updates to reflect the changes to the representation of termination
information.
Instead of doing pass 1 on all SCCs and then pass 2 on all SCCs,
we now do both pass 1 and 2 on an SCC before moving on to the next.
Do not insist that either all procedures in an SCC are
compiler-generated or all are user-written, since this need not be
true in the presence of user-defined equality predicates.
Clarify the structure of the code that handles builtins and compiler
generated predicates.
Concentrate all the code for updating module_infos in this module.
Previously it was scattered in several places in several files.
Put all the code for writing out termination information at the
end of the module in a logical order.
compiler/term_traversal.m:
A new file containing code used by both pass 1 and pass 2 to
traverse procedure bodies.
compiler/term_pass1.m:
Use the new traversal module.
Clarify the fixpoint computation on the set of output supplier
arguments.
Remove duplicates from the list of equations given to the solver.
This avoids a det stack overflow in lp.m when doing termination
analysis on options.m.
If an output argument of a predicate makes sense only in the absence
of errors, then return it only in the absence of errors.
compiler/term_pass2.m:
Use the new traversal module. Unlike the previous code, this allows us
to ignore recursive calls with input arguments bigger than the head
if those calls occur after goals that cannot succeed (since those
calls will never be reached).
Implement a better way of doing single argument analysis, which
(unlike the previous version) works in the presence of mutual recursion
and other calls between the recursive call and the start of the clause.
Implement a more precise way of checking for recursions that don't
cause termination problems. We now allow calls from p to q in which
the recursive input supplier arguments can grow, provided that on
any path on which q can call p, directly or indirectly, the recursive
input supplier arguments shrink by a greater amount.
If an output argument of a predicate makes sense only in the absence
of errors, then return it only in the absence of errors.
compiler/term_util.m:
Updates to reflect the changes to the representation of termination
information.
Reorder to put related code together.
Change the interface of several predicates to better reflect the
way they are used.
Add some more utility predicates.
compiler/term_errors.m:
Small changes to the set of possible errors, and major changes in
the way the messages are printed out (we now use error_util).
compiler/options.m:
Change --term-single-arg from being a bool to an int option,
whose value indicates the maximum size of an SCC in which we try
single argument analysis. (Large SCCs can cause single-arg analysis
to require a lot of iterations.)
Add an (int) option that controls the max number of paths
that we are willing to analyze (analyzing too many paths can cause
det stack overflow).
Add an (int) option that controls the max number of causes of
nontermination that we print out.
compiler/hlds_pred.m:
Use two separate slots in the proc_info to hold argument size data
and termination info, instead of the single slot used until now.
The two kinds of information are produced and used separately.
Make the layout of the get and set procedures for proc_infos more
regular, to facilitate later updates.
The procedures proc_info_{,set_}variables did the same work as
proc_info_{,set_}varset. To eliminate potential confusion, I
removed the first set.
compiler/*.m:
Change proc_info_{,set_}variables to proc_info_{,set_}varset.
compiler/hlds_out.m:
compiler/make_hlds.m:
compiler/mercury_to_mercury.m:
Change the code to handle the arg size data and the termination
info separately.
compiler/prog_data.m:
Change the internal representation of termination_info pragmas to
hold the arg size data and the termination info separately.
compiler/prog_io_pragma.m:
Change the external representation of termination_info pragmas to
group the arg size data together with the output supplier data,
to which it is logically connected.
compiler/module_qual.m:
compiler/modules.m:
Change the code to accommodate the change to the internal
representation of termination_info pragmas.
compiler/notes/compiler_design.html:
Fix some documentation rot, and clarify some points.
Document termination analysis.
doc/user_guide.texi:
Document --term-single-arg and the new options.
Remove spaces from the ends of lines.
library/bag.m:
Add a new predicate, bag__least_upper_bound.
Fix code that would do the wrong thing if executed by Prolog.
Remove spaces from the ends of lines.
library/list.m:
Add a new predicate, list__take_upto.
library/set{,_ordlist}.m:
Add a new predicate, set{,_ordlist}__count.
tests/term/*:
A bunch of new test cases to test the behaviour of termination
analysis. They are the small benchmark suite from our paper.
tests/Mmakefile:
Enable the new test case directory.
Estimated hours taken: 20
Give duplicate code elimination more teeth in dealing with similar arguments
of different function symbols. For the source code
:- type t1 ---> f(int)
; g(int, int).
:- pred p1(t1::in, int::out) is det.
p1(f(Y), Y).
p1(g(Y, _), Y).
we now generate the C code
Define_entry(mercury__xdup__p1_2_0);
r1 = const_mask_field(r1, (Integer) 0);
proceed();
thus avoiding the cost of testing the function symbol.
runtime/mercury_tags.h:
Add two new macros, mask_field and const_mask_field, that behave
just like field and const_field except that instead of stripping
off a known tag from the pointer, they strip (mask) off an unknown
tag.
compiler/llds.m:
Change the first argument of the lval field/3 from tag to maybe(tag).
Make the comments on some types more readable.
compiler/llds_out.m:
If the first arg of the lval field/3 is no, emit a (const_)mask_field
macro; otherwise, emit a (const_)field macro.
compiler/basic_block.m:
New module to convert sequences of instructions to sequences of
basic blocks and vice versa. Used in the new dupelim.m.
compiler/dupelim.m:
Complete rewrite to give duplicate code elimination more teeth.
Whereas previously we eliminated blocks of code only if they exactly
duplicated other blocks of code, we now look for blocks that can be
"anti-unified". For example, the blocks
r1 = field(mktag(0), r2, 0)
goto L1
and
r1 = field(mktag(1), r2, 0)
<fall through to L1>
anti-unify, with the most specific common generalization being
r1 = mask_field(r2, 0)
goto L1
If several basic blocks antiunify, we replace one copy with the
antiunified block and try to eliminate the others. We do not
eliminate blocks that can be fallen into, since eliminating them
would require introducing a goto, which would slow the code down.
compiler/peephole,m:
If a conditional branch to a label is followed by that label or
by an unconditional branch to that label, eliminate the branch.
Dupelim produces this kind of code.
compiler/{code_exprn,exprn_aux,lookup_switch,opt_debug,unify_gen}.m:
Minor changes required by the change to field/3.
compiler/{frameopt,jumpopt,labelopt,mercury_compile,optimize,value_number}.m:
s/__main/_main/ in predicate names.
compiler/jumpopt.m:
Add some documentation.
compiler/unify_gen.m:
Fix a module qualified predicate name reference that would not
work in Prolog.
compiler/notes/compiler_design.html:
Document the new file basic_block.m.
Estimated hours taken: 500 or so
This change implements typeclasses. Included are the necessary changes to
the compiler, runtime and library.
compiler/typecheck.m:
Typecheck the constraints on a pred by adding constraints for each
call to a pred/func with constraints, and eliminating constraints
by applying context reduction.
While reducing the constraints, keep track of the proofs so that
polymorphism can produce the tyepclass_infos for eliminated
constraints.
compiler/polymorphism.m:
Perform the source-to-source transformation which turns code with
typeclass constraints into code without constraints, but with extra
"typeclass_info", or "dictionary" parameters.
Also, rather than always having a type_info directly for each type
variable, sometimes the type_info is hidden inside a typeclass_info.
compiler/bytecode*.m:
Insert some code to abort if bytecode generation is used when
typeclasses are used.
compiler/call_gen.m:
Generate code for a class_method_call, which forms the body of a class
method (by selecting the appropriate proc from the typeclass_info).
compiler/dead_proc_elim.m:
Don't eliminate class methods if they are potentially used outside
the module
compiler/hlds_data.m:
Define data types to store:
- the typeclass definitions
- the instances of a class
- "constraint_proof". ie. the proofs of redundancy of a
constraint. This info is used by polymorphism to construct the
typeclass_infos for a constraint.
- the "base_tyepclass_info_constant", which is analagous the
the base_type_info_constant
compiler/hlds_data.m:
Define the class_method_call goal. This goal is inserted into the
body of class method procs, and is responsible for selecting the
appropriate part of the typeclass_info to call.
compiler/hlds_data.m:
Add the class table and instance table to the module_info.
compiler/hlds_out.m:
Output info about base_typeclass_infos and class_method_calls
compiler/hlds_pred.m:
Change the representation of the locations of type_infos from "var"
to type_info_locn, which is either a var, or part of a typeclass_info,
since now the typeclass_infos contain the type_infos for the type that
they constrain.
Add constraints to the pred_info.
Add constraint_proofs to the pred_info (so that typeclass.m can
annotate the pred_info with the reasons that constraints were
eliminated, so that polymorphism.m can in turn generate the
typeclass_infos for the constraints).
Add the "class_method" marker.
compiler/lambda.m:
A feable attempt at adding class ontexts to lambda expressions,
untested and almost certainly not working.
compiler/llds_out.m:
Output the code addresses for do_*det_class_method, and output
appropriately mangled symbol names for base_typeclass_infos.
compiler/make_hlds.m:
Add constraints to the types on pred and func decls, and add
class and instance declarations to the class_table and instance_table
respectively.
compiler/mercury_compile.m:
Add the check_typeclass pass.
compiler/mercury_to_mercury.m:
Output constraints of pred and funcs, and output typeclass and instance
declarations.
compiler/module_qual.m:
Module qualify typeclass names in pred class contexts, and qualify the
typeclass and instance decls themselves.
compiler/modules.m:
Output typeclass declarations in the short interface too.
compiler/prog_data.m:
Add the "typeclass" and "instance" items. Define the types to store
information about the declarations, including class contexts on pred
and func decls.
compiler/prog_io.m:
Parse constraints on pred and func declarations.
compiler/prod_out.m:
Output class contexts on pred and func decls.
compiler/type_util.m:
Add preds to apply a substitution to a class_constraint, and to
a list of class constraints. Add type_list_matches_exactly/2. Also
add typeclass_info and base_typeclass_info as types which should not
be optimised as no_tag types (seeing that we cheat a bit about their
representation).
compiler/notes/compiler_design.html:
Add notes on module qualification of class contexts. Needs expansion
to include more stuff on typeclasses.
compiler/*.m:
Various minor changes.
New Files:
compiler/base_typeclass_info.m:
Produce one base_typeclass_info for each instance declaration.
compiler/prog_io_typeclass.m:
Parse typeclass and instance declarations.
compiler/check_typeclass.m:
Check the conformance of an instance declaration to the typeclass
declaration, including building up a proof of how superclass
constraints are satisfied so that polymorphism.m is able to construct
the typeclass_info, including the superclass typeclass_infos.
library/mercury_builtin.m:
Implement that base_typeclass_info and typeclass_info types, as
well as the predicates type_info_from_typeclass_info/3 to extract
a type_info from a typeclass_info, and superclass_from_typeclass_info/3
for extracting superclasses.
library/ops.m:
Add "typeclass" and "instance" as operators.
library/string.m:
Add a (in, uo) mode for string__length/3.
runtime/mercury_ho_call.c:
Implement do_call_*det_class_method, which are the pieces of code
responsible for extracting the correct code address from the
typeclass_info, setting up the arguments correctly, then executing
the code.
runtime/mercury_type_info.h:
Macros for accessing the typeclass_info structure.
The purpose of this diff is to allow Mercury programs to contain
impure Mercury code without the compiler changing its behavior
inappropriately, while still allowing the compiler to aggressively
optimize pure code. To do this, we require impure predicates to be so
declared, and calls to impure predicates to be flagged as such. We
also allow predicates implemented in terms of impure predicates to be
promised to be pure; lacking such a promise, any predicate that calls
an impure predicate is assumed to be impure.
At the moment, we don't allow impure functions (only predicates),
though some of the work necessary to support them has been done.
Note that to make the operators work properly, the precedence of the
`pred' and `func' operators has been changed from 1199 to 800.
Estimated hours taken: 150
compiler/purity.m:
New compiler pass for purity checking.
compiler/hlds_goal.m:
Add `impure' and `semipure' to the goal_feature enum.
compiler/hlds_out.m:
compiler/typecheck.m:
compiler/special_pred.m:
Fixed code that prints predicate name to write something more
helpful for special (compiler-generated) predicates. Added
code to print new markers. Added purity argument to
mercury_output_pred_type. New public predicate
special_pred_description/2 provides an english description for
each compiler-generated predicate.
compiler/hlds_pred.m:
Add `impure' and `semipure' to marker enum. Added new
public predicates to get predicate purity and whether or not
it's promised to be pure.
compiler/prog_data.m:
compiler/mercury_to_mercury.m:
compiler/prog_io.m:
compiler/prog_io_goal.m:
compiler/prog_io_pragma.m:
compiler/prog_io_dcg.m:
compiler/prog_util.m:
compiler/equiv_type.m:
compiler/intermod.m:
compiler/mercury_to_c.m:
compiler/module_qual.m:
Add purity argument to pred and func items. Add new `impure'
and `semipure' operators. Add promise_pure pragma. Add
purity/2 wrapper to goal_expr type.
compiler/make_hlds.m:
compiler/mercury_to_goedel.m:
Added purity argument to module_add_{pred,func},
clauses_info_add_pragma_c_code, and to pred and func items.
Handle promise_pure pragma. Handle purity/2 wrapper used to
handle user-written impurity annotations on goals.
compiler/mercury_compile.m:
Add purity checking pass between type and mode checking.
compiler/mode_errors.m:
Distinguish mode errors caused by impure goals preventing
goals being delayed.
compiler/modes.m:
Don't delay impure goals, and ensure before scheduling an
impure goal that no goals are delayed. Actually, we go ahead
and try to schedule goals even if impurity causes a problem,
and then if it still doesn't mode check, then we report an
ordinary mode error. Only if the clause would be mode correct
except for an impure goal do we report it as an impurity problem.
compiler/simplify.m:
Don't optimize away non-pure duplicate calls. We could do
better and still optimize duplicate semipure goals without an
intervening impure goal, but it's probably not worth the
trouble. Also don't eliminate impure goals on a failing branch.
compiler/notes/compiler_design.html:
Documented purity checking pass.
doc/reference_manual.texi:
Document purity system.
doc/transition_guide.texi:
library/nc_builtin.nl:
library/ops.m:
library/sp_builtin.nl:
New operators and new precdence for `pred' and `func'
operators.
tests/hard_coded/purity.m
tests/hard_coded/purity.exp
tests/hard_coded/Mmakefile:
tests/invalid/purity.m
tests/invalid/purity_nonsense.m
tests/invalid/purity.err_exp
tests/invalid/purity_nonsense.err_exp
tests/invalid/Mmakefile:
Test cases for purity.
Estimated hours taken: 50
Generate stack layouts for accurate garbage collection.
compiler/base_type_layout.m:
Change the order of some arguments so that threaded data
structures are more often in the final two arguments (allows
easy use of higher order predicates).
Simplify some code using higher order preds.
Export base_type_layout__construct_pseudo_type_info, as
stack_layout.m needs to be able to generate pseudo_type_infos
too.
Fix problems with cell numbers being re-used -- get the next
cell number from module_info, and update module_info
after processing base_type_layouts.
compiler/code_gen.m:
Add information about each procedure to the continuation info.
Handle new field in c_procedure.
compiler/continuation_info.m:
Redesign most of this module to deal with labels
that are continuation points for multiple calls.
Change the order of some arguments so that threaded data
structures are in the final two arguments.
Cleaned up and documented code.
compiler/dupelim.m:
compiler/exprn_aux.m:
Handle new label_entry data type.
compiler/export.m:
compiler/opt_debug.m:
Handle new label_entry and general data types.
compiler/llds_out.m:
Add an argument to get_proc_label to control whether a
"mercury_" prefix is wanted.
Handle new label_entry and general data types.
compiler/llds.m:
Add a new alternative for data_const - a label_entry.
Add a new alternative for data_name - general, which
allows any sort of data, with names generated elsewhere.
Add the pred_proc_id as a field of c_procedure.
compiler/optimize.m:
compiler/llds_common.m:
compiler/optimize.m:
Handle new field in c_procedure.
compiler/mercury_compile.m:
Generate layout information after code has been generated,
and output stack layouts.
compiler/notes/compiler_design.html:
Document new stack_layout module.
compiler/stack_layout.m:
New file - generates the LLDS code that defines
global constants to hold the stack_layout structures.
compiler/options.m:
compiler/handle_options.m:
Add --stack-layout option which outputs stack layouts.
Make accurate gc imply stack_layout.
Estimated hours taken: 10
Add constant propagation within modules. This occurs during simplification
and simply attempts to evaluate "known" calls that have all their inputs
bound to constants and replaces the call with constructions of the outputs.
Currently the "known" calls are (most) of the arithmetic predicates, and
the comparison of ints and floats.
compiler/instmap.m:
add merge_instmap_deltas which merges a list of intmap deltas
rather than just two of them.
compiler/mercury_compile.m:
compiler/options.m:
add (and use) the option --optimize-constant-propagation
compiler/simplify.m:
add a bool to the simplify struct to turn on/off constant
propagation.
in the simplification of calls, check to see if all the inputs
are bound to constants. If we know how to evaluate this call
at compile time, then do so. This may change the instmap delta.
For branched goals, we merge the instmap deltas to recompute the
instmap delta for the goal as a whole so that we know when every
branch binds a variable to the same constant.
compiler/notes/compiler_design.html:
mention constant propagation.
doc/user_guide.texi:
mention constant propagation.
compiler/const_prop.m:
code that attempts to evaluate calls at compile time.
It contains tables of calls that we know how to evaluate.
Estimated hours taken: 0.05
Update compiler design notes.
compiler/notes/compiler_design.html:
Update design notes with regard to continutation_info.m, and
remove mention of garbage_out.m and shapes.m.
Estimated hours taken: 20
Reorganisation of modules to do with the inst data type.
This is actually the first installment of the alias tracking mode
checker in disguise. A very good disguise. The rationale for
this reorganisation is to reduce coupling in the part of the mode
checker which is _not_ in this change (ie most of it).
Alias tracking requires a new kind of inst, alias(inst_key), where
an inst_key is a handle on some other sub-inst. With it goes a
data structure in which to store dereferenced insts and all the
operations which go with it. This code will go in the new module
inst.m so that it doesn't have to go in prog_data.m. (I briefly
considered putting it in instmap.m however this introduces some
bad coupling since instmap.m imports hlds_module.m. Putting it
in prog_data.m would cause hlds_*.m to depend on prog_data.m,
but we have designed things so that the dependencies go in the
other direction.)
The remainder of the reorganisation is a general cleanup: the
inst testing predicates (inst_is_*) have been moved out of
mode_util because they are not actually operations on modes at
all, and have been moved into inst_match. inst_match has then
been split because otherwise it would be 2000 lines long and
will get significantly bigger when aliasing is added. Roughly
speaking, any operations which create new insts from old ones
have been moved into a new module, inst_util while any operations
which test the values of insts remain in inst_match.
Also included are the removal of some NU-Prologisms since the
NU-Prolog version of the compiler is no longer supported. Two
changes here:
- Removal of some when declarations.
- A gross hack in inst_is_*_2, where two copies of
the same inst were passed into the predicate so that
one could be switched on. Thank NU-Prolog's lack of
common subexpression elimination.
compiler/inst.m:
New module which contains the data types inst, uniqueness,
pred_inst_info, bound_inst.
compiler/inst_util.m:
New module which contains predicates which perform mode
checking-like operations on insts.
Moved in:
abstractly_unify_inst, abstractly_unify_inst_functor,
inst_merge, make_mostly_uniq_inst (from inst_match.m)
compiler/inst_match.m:
Moved out:
inst_merge, make_mostly_uniq_inst,
abstractly_unify_inst, abstractly_unify_inst_functor
(to inst_util.m)
Moved in:
inst_is_*, inst_list_is_*, bound_inst_list_is_*
(from mode_util.m)
Now exported:
unique_matches_initial/2, unique_matches_final/2
inst_contains_instname/3, pred_inst_matches/3
(They are required by inst_util.m, and they are
useful in their own right.)
compiler/instmap.m:
instmap_delta_lookup_var/3 reincarnated as
instmap_delta_search_var/3. The reason for this change is
that previously, instmap_delta_lookup_var simply returned
`free' if the searched-for var did not occur in the
instmap_delta. This is somewhat non-obvious behaviour.
instmap_delta_search_var/3 fails in such a situation.
compiler/mode_util.m:
Moved out:
inst_is_*, inst_list_is_*, bound_inst_list_is_*
(to inst_match.m)
(These are not really operations on modes.)
compiler/modecheck_call.m:
Moved in modecheck_higher_order_func_call/5, from modecheck_unify.m
compiler/modecheck_unify.m:
Moved out modecheck_higher_order_func_call/5, to modecheck_call.m
where it should have been all along.
compiler/prog_data.m:
Moved out the types inst, uniqueness, pred_inst_info,
bound_inst (to inst.m).
compiler/common.m:
compiler/cse_detection.m:
compiler/fact_table.m:
compiler/higher_order.m:
compiler/hlds_data.m:
compiler/hlds_goal.m:
compiler/hlds_out.m:
compiler/intermod.m:
compiler/liveness.m:
compiler/llds.m:
compiler/make_hlds.m:
compiler/mercury_to_mercury.m:
compiler/mode_debug.m:
compiler/mode_errors.m:
compiler/mode_info.m:
compiler/modes.m:
compiler/module_qual.m:
compiler/polymorphism.m:
compiler/prog_io.m:
compiler/prog_io_util.m:
compiler/prog_util.m:
compiler/simplify.m:
compiler/switch_detection.m:
compiler/unify_proc.m:
compiler/unique_modes.m:
Miscellaneous minor changes to cope with the above changes.
compiler/notes/compiler_design.html:
Document the new modules.
Estimated hours taken: 0.25
compiler/notes/compiler_design.html:
Mention that common.m also does elimination of duplicate procedure
calls, not just of common structs.
Estimated hours taken: 0.1
[This was stayl's change to COMPILER_DESIGN that somehow didn't get
incorporated when COMPILER_DESIGN became compiler_desing.html.]
compiler/notes/compiler_design.html:
Added some more documentation on module qualification.
Estimated hours taken: 4
Translated plain text docs to HTML. This obviously creates
a dual update problem. We should solve this by putting
the plain text docs in the attic and retaining the HTML.
Also added the HTML files to the Mmakefile so they are installed
on the web pages.
The other documents in compiler/notes will be HTMLized soon.
compiler/notes/
Mmakefiles
ALLOCATION.html
AUTHORS.html
CODING_STANDARDS.html
COMPILER_DESIGN.html
GC_AND_C_CODE.html
GLOSSARY.html
MODULE_SYSTEM.html
RELEASE_CHECKLIST.html
REVIEWS.html
TODO.html