Commit Graph

27 Commits

Author SHA1 Message Date
Zoltan Somogyi
07f877bc3f Carve term_context.m out of term.m.
library/term.m:
library/term_context.m:
    As above.

    Rename the term.context type as term_context.term_context, with
    term.context now being defined as an equivalence type.

    Replace the context_init function and predicate and the dummy_context_init
    function with just one function: dummy_context. This name includes
    the important part (the fact that it return a *dummy* context) and deletes
    the nonimportant part (dummy contexts are just about never updated,
    so the function does not really "initialize" them).

    Reduce function/predicate pairs that do the same thing to just a function.

library/MODULES_DOC:
library/library.m:
    Add the new module to the list of standard library modules.

NEWS:
    Mention the new module, and the obsoleting of the moved predicates
    and functions in term.m.

compiler/*.m:
library/*.m:
    Conform to the changes above.
2022-08-23 12:56:37 +10:00
Zoltan Somogyi
d787ee9355 Store var_tables in proc_infos.
This fixes the performance problem reported in Mantis bug #562.

compiler/hlds_pred.m:
    Instead of storing a varset and a vartypes in each proc_info,
    store just a var_table. Update the predicates that create
    or clone procedures accordingly.

    Where we had operations on proc_infos that had two versions,
    one operating on a varset/vartypes pair and one operating on var_table,
    keep only the latter, with the (shorter) name of the former.

    Delete the arity argument of proc_info_init, because the only
    valid value of that argument is the length of the list of the
    argument types. (In other words, this arg has been redundant
    all along.)

    Change the operations that create new variables in a procedure
    to get the caller to specify the (base) name of the new variable
    up front.

    Delete the unused predicate proc_info_ensure_unique_names.

compiler/type_util.m:
    Due to the change above, we now construct var_tables during the
    construction of the HLDS. The code that does that needs to fill in
    the field that says whether the type of each variable in the table
    is a dummy type or not. However, at this time, the pass that decides
    type representations has not been run yet. The code of is_type_a_dummy
    used to throw an exception in such situations.

    Change this so that in such situations, is_type_a_dummy returns
    a placeholder, not-guaranteed-to-be-correct value. Document why
    this is ok.

compiler/post_typecheck.m:
    Replace the placeholder values in vte_is_dummy fields in all
    the entries in the var_tables in all (valid) predicates with valid data.
    (If there are any invalid predicates, the compilation will fail anyway.)
    The clause_to_proc pass will copy these updated var_tables
    to be the initial var_tables in procedures.

compiler/make_goal.m:
    Change the operations that create new variables in a procedure
    to get the caller to specify the (base) name of the new variable
    up front. This is simpler than the old method, which created new
    variables without a name, and had the caller give them a name as
    a separate operation. And since var_tables need this info,
    get the caller to also specify whether the type is a dummy,
    if the type is not a builtin type which is known not to be a dummy.

compiler/var_table.m:
    Document the times when the types and is_dummy fields in var_table
    entries become meaningful.

    Fix a potential bug: when performing type substitutions in
    var_table entries, updating a variable's type may change whether
    that variable is a dummy or not, so recompute that info.
    It is quite possible that we *never* replace a nondummy type
    with a dummy type or vice versa, but in the absence of a convincing
    correctness argument for that proposition, better safe than sorry.

    Export the previously-private predicate transform_var_table
    to post_typecheck.

    Add code to implement the unused predicate deleted from hlds_pred.m:
    at the time I wrote it, I haven't yet realised that it was unused.
    The code I wrote here is therefore unused as well, so it is commented out.
    I did not delete it, because it may be useful later on.

compiler/direct_arg_in_out.m:
    Don't make and split var_tables, since it is no longer needed.

compiler/accumulator.m:
compiler/add_class.m:
compiler/add_clause.m:
compiler/add_heap_ops.m:
compiler/add_pred.m:
compiler/add_special_pred.m:
compiler/add_trail_ops.m:
compiler/arg_info.m:
compiler/build_mode_constraints.m:
compiler/bytecode_gen.m:
compiler/check_typeclass.m:
compiler/clause_to_proc.m:
compiler/closure_analysis.m:
compiler/code_gen.m:
compiler/code_loc_dep.m:
compiler/complexity.m:
compiler/continuation_info.m:
compiler/cse_detection.m:
compiler/ctgc.livedata.m:
compiler/deep_profiling.m:
compiler/default_func_mode.m:
compiler/deforest.m:
compiler/delay_construct.m:
compiler/delay_partial_inst.m:
compiler/dep_par_conj.m:
compiler/det_analysis.m:
compiler/det_report.m:
compiler/distance_granularity.m:
compiler/equiv_type_hlds.m:
compiler/exception_analysis.m:
compiler/float_regs.m:
compiler/follow_code.m:
compiler/goal_mode.m:
compiler/goal_path.m:
compiler/higher_order.m:
compiler/hlds_out_pred.m:
compiler/hlds_rtti.m:
compiler/hlds_statistics.m:
compiler/inlining.m:
compiler/intermod.m:
compiler/intermod_analysis.m:
compiler/introduce_exists_casts.m:
compiler/introduce_parallelism.m:
compiler/lambda.m:
compiler/lco.m:
compiler/live_vars.m:
compiler/liveness.m:
compiler/loop_inv.m:
compiler/mark_tail_calls.m:
compiler/ml_accurate_gc.m:
compiler/ml_args_util.m:
compiler/ml_closure_gen.m:
compiler/ml_gen_info.m:
compiler/ml_proc_gen.m:
compiler/mode_errors.m:
compiler/mode_info.m:
compiler/modecheck_goal.m:
compiler/par_loop_control.m:
compiler/pd_debug.m:
compiler/pd_info.m:
compiler/pd_util.m:
compiler/polymorphism_info.m:
compiler/post_typecheck.m:
compiler/proc_gen.m:
compiler/proc_requests.m:
compiler/purity.m:
compiler/push_goals_together.m:
compiler/quantification.m:
compiler/rbmm.add_rbmm_goal_infos.m:
compiler/rbmm.live_variable_analysis.m:
compiler/rbmm.points_to_analysis.m:
compiler/rbmm.points_to_graph.m:
compiler/rbmm.points_to_info.m:
compiler/rbmm.region_liveness_info.m:
compiler/rbmm.region_transformation.m:
compiler/recompute_instmap_deltas.m:
compiler/saved_vars.m:
compiler/simplify_goal_unify.m:
compiler/simplify_info.m:
compiler/simplify_proc.m:
compiler/size_prof.m:
compiler/ssdebug.m:
compiler/stack_alloc.m:
compiler/stack_layout.m:
compiler/stack_opt.m:
compiler/stm_expand.m:
compiler/store_alloc.m:
compiler/structure_reuse.analysis.m:
compiler/structure_reuse.direct.choose_reuse.m:
compiler/structure_reuse.direct.detect_garbage.m:
compiler/structure_reuse.domain.m:
compiler/structure_reuse.indirect.m:
compiler/structure_reuse.lbu.m:
compiler/structure_reuse.lfu.m:
compiler/structure_reuse.versions.m:
compiler/structure_sharing.analysis.m:
compiler/structure_sharing.domain.m:
compiler/switch_detection.m:
compiler/table_gen.m:
compiler/tabling_analysis.m:
compiler/term_constr_build.m:
compiler/term_constr_initial.m:
compiler/term_errors.m:
compiler/term_pass1.m:
compiler/term_pass2.m:
compiler/trace_gen.m:
compiler/trailing_analysis.m:
compiler/try_expand.m:
compiler/tupling.m:
compiler/unneeded_code.m:
compiler/untupling.m:
compiler/unused_args.m:
compiler/unused_imports.m:
    Conform to the changes above. Mostly this means

    - not passing a module_info to get a var_table out of a proc_info, but
    - having to pass a module_info to code that either constructs a var_table,
      or adds entries to a var_table (since we now need the type table
      to figure out whether variables' types are dummies).
2022-08-18 18:53:15 +10:00
Zoltan Somogyi
03c9135991 Stop using varsets/vartypes in the MLDS backend.
compiler/ml_args_util.m:
compiler/ml_closure_gen.m:
compiler/ml_code_util.m:
compiler/ml_proc_gen.m:
    As above.

compiler/hlds_pred.m:
    The code in the MLDS code generator that handles calls reuses
    some code in ml_args_util.m that it uses for the clause head,
    and thus derived the names of some MLDS variables from the
    varset of the callee. In the case where the callee is a unify
    or compare predicate for an imported type, the varset contained
    the names of the argument variables, but not their type. This means
    that looking up their names in the var_table instead of the varset
    requires the var_table to contain every variable that the varset contains,
    so change the code that constructs the var_table to ensure this.

    Add a var_table version of another predicate to prepare for a future
    change.

tests/invalid/try_detism.err_exp:
    Update the variable number of an unnamed variable after the changes
    in hlds_pred.m.
2022-05-15 11:49:22 +10:00
Zoltan Somogyi
ea4f95a7ed Use var_tables in lco.m, and when dumping goals.
Since this is the first converted module that dumps out goals when
debugging trace flags are enabled, this required generalizing the code
that does that, to take either varsets or var_tables as a means of
specifying the names of variables. We do this via a new type,
var_name_source, which contains either a varset or a var_table.

Almost all of this diff is there to implement this generalization.
A large part of it affects code in the parse_tree package that we use
to write out the parts of HLDS goals that are defined by types defined
in that package. Since we want to avoid making any part of the parse_tree
package dependent on the hlds package, this required defining the
var_name_source type in the parse_tree package, which in turn requires
var_table.m to be in that same package.

compiler/lco.m:
    Convert this module to use var_tables instead of varsets and vartypes.

compiler/var_table.m:
    Move this module from the hlds package to the parse_tree package.

    To make this, possible, move the parts that required access to the HLDS
    to hlds_pred.m, from where it was usually invoked.

    Export some utility predicates to allow the moved code to work
    in hlds_pred.m without access to the actual definition of the
    var_table type.

    Define the var_name_source type.

    Add some utility functions for use by code writing out variable names.

compiler/hlds_pred.m:
    Add the code moved from var_table.m.

compiler/vartypes.m:
    Move this module from the hlds package to the parse_tree package,
    for symmetry with var_table.m. It did not depend on being in hlds
    in any way.

compiler/hlds.m:
compiler/parse_tree.m:
    Move vartypes.m and var_table.m from the hlds package
    to the parse_tree package.

compiler/hlds_out_goal.m:
    Change all the predicates in this module to take a var_name_source
    instead of a prog_varset.

    Fix some comments.

compiler/hlds_out_util.m:
    Change some of the predicates in this module (those called from
    hlds_out_goal.m) to take a var_name_source instead of a prog_varset.

compiler/parse_tree_out_term.m:
    Provide variants of some existing predicates and functions that take
    var_name_sources instead of varsets. The code of the copies
    duplicates the logic of the originals, though I hope that this
    duplication can be done away with at the end of the transition.
    (The best solution would be to use a typeclass with methods
    that convert vars to their names, but we would want to ensure
    that the compiler can specialize all the affected predicates
    and functions to the two instances of this typeclass, which is
    something that we cannot do yet. In the meantime, the lack of
    any generalization in the old versions preserves their performance.)

tools/sort_imports:
tools/filter_sort_imports:
    A new tool that automatically sorts any occurrences of consecutive
    ":- import_module" declarations in the named files. The sorting is done
    in filter_sort_imports; sort_imports loops over the named files.

    After automatically replacing all occurrences of hlds.{vartypes,var_table}
    in import_module declarations with their parse_tree versions, the updated
    import_module declarations were usually out of order with respect to
    their neighbours. I used this script to fix that, and some earlier
    out-of-order imports.

compiler/accumulator.m:
compiler/add_class.m:
compiler/add_clause.m:
compiler/add_foreign_proc.m:
compiler/add_heap_ops.m:
compiler/add_pragma_type_spec.m:
compiler/add_pred.m:
compiler/add_trail_ops.m:
compiler/analysis.m:
compiler/arg_info.m:
compiler/build_mode_constraints.m:
compiler/bytecode_gen.m:
compiler/call_gen.m:
compiler/check_promise.m:
compiler/closure_analysis.m:
compiler/closure_gen.m:
compiler/code_info.m:
compiler/code_loc_dep.m:
compiler/common.m:
compiler/compile_target_code.m:
compiler/complexity.m:
compiler/const_prop.m:
compiler/constraint.m:
compiler/continuation_info.m:
compiler/convert_parse_tree.m:
compiler/coverage_profiling.m:
compiler/cse_detection.m:
compiler/ctgc.datastruct.m:
compiler/ctgc.util.m:
compiler/dead_proc_elim.m:
compiler/deep_profiling.m:
compiler/deforest.m:
compiler/delay_construct.m:
compiler/delay_partial_inst.m:
compiler/dep_par_conj.m:
compiler/det_analysis.m:
compiler/det_report.m:
compiler/det_util.m:
compiler/direct_arg_in_out.m:
compiler/disj_gen.m:
compiler/distance_granularity.m:
compiler/equiv_type_hlds.m:
compiler/exception_analysis.m:
compiler/file_names.m:
compiler/float_regs.m:
compiler/follow_vars.m:
compiler/format_call.m:
compiler/generate_dep_d_files.m:
compiler/get_dependencies.m:
compiler/goal_expr_to_goal.m:
compiler/goal_mode.m:
compiler/goal_path.m:
compiler/goal_store.m:
compiler/goal_util.m:
compiler/granularity.m:
compiler/hhf.m:
compiler/higher_order.m:
compiler/hlds_clauses.m:
compiler/hlds_code_util.m:
compiler/hlds_error_util.m:
compiler/hlds_goal.m:
compiler/hlds_llds.m:
compiler/hlds_out_pred.m:
compiler/hlds_rtti.m:
compiler/hlds_statistics.m:
compiler/inlining.m:
compiler/inst_check.m:
compiler/inst_test.m:
compiler/inst_user.m:
compiler/instance_method_clauses.m:
compiler/instmap.m:
compiler/intermod.m:
compiler/intermod_analysis.m:
compiler/interval.m:
compiler/introduce_exists_casts.m:
compiler/introduce_parallelism.m:
compiler/item_util.m:
compiler/lambda.m:
compiler/live_vars.m:
compiler/liveness.m:
compiler/llds.m:
compiler/llds_out_data.m:
compiler/llds_out_file.m:
compiler/llds_out_util.m:
compiler/lookup_switch.m:
compiler/loop_inv.m:
compiler/make.module_target.m:
compiler/make.util.m:
compiler/make_goal.m:
compiler/make_hlds_separate_items.m:
compiler/make_hlds_types.m:
compiler/mark_tail_calls.m:
compiler/mercury_compile_mlds_back_end.m:
compiler/middle_rec.m:
compiler/ml_accurate_gc.m:
compiler/ml_args_util.m:
compiler/ml_call_gen.m:
compiler/ml_closure_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_commit_gen.m:
compiler/ml_disj_gen.m:
compiler/ml_foreign_proc_gen.m:
compiler/ml_gen_info.m:
compiler/ml_lookup_switch.m:
compiler/ml_proc_gen.m:
compiler/ml_simplify_switch.m:
compiler/ml_switch_gen.m:
compiler/ml_tag_switch.m:
compiler/ml_unify_gen.m:
compiler/ml_unify_gen_construct.m:
compiler/ml_unify_gen_deconstruct.m:
compiler/ml_unify_gen_test.m:
compiler/ml_unify_gen_util.m:
compiler/mlds_to_c_data.m:
compiler/mlds_to_c_func.m:
compiler/mlds_to_c_global.m:
compiler/mlds_to_cs_class.m:
compiler/mlds_to_cs_file.m:
compiler/mlds_to_java_data.m:
compiler/mlds_to_java_file.m:
compiler/mlds_to_java_stmt.m:
compiler/mlds_to_java_type.m:
compiler/mmc_analysis.m:
compiler/mode_comparison.m:
compiler/mode_constraints.m:
compiler/mode_debug.m:
compiler/mode_errors.m:
compiler/mode_info.m:
compiler/mode_ordering.m:
compiler/modecheck_call.m:
compiler/modecheck_coerce.m:
compiler/modecheck_goal.m:
compiler/modecheck_unify.m:
compiler/modecheck_util.m:
compiler/modes.m:
compiler/module_cmds.m:
compiler/old_type_constraints.m:
compiler/opt_debug.m:
compiler/optimize.m:
compiler/options_file.m:
compiler/ordering_mode_constraints.m:
compiler/par_loop_control.m:
compiler/parse_item.m:
compiler/parse_string_format.m:
compiler/parse_tree_out_inst.m:
compiler/parse_tree_to_term.m:
compiler/parse_util.m:
compiler/pd_debug.m:
compiler/pd_info.m:
compiler/pd_util.m:
compiler/peephole.m:
compiler/polymorphism.m:
compiler/polymorphism_info.m:
compiler/polymorphism_lambda.m:
compiler/polymorphism_type_class_info.m:
compiler/polymorphism_type_info.m:
compiler/post_typecheck.m:
compiler/pragma_c_gen.m:
compiler/pred_name.m:
compiler/pred_table.m:
compiler/prog_item.m:
compiler/prog_rep.m:
compiler/prop_mode_constraints.m:
compiler/purity.m:
compiler/push_goals_together.m:
compiler/qual_info.m:
compiler/quantification.m:
compiler/rbmm.execution_path.m:
compiler/rbmm.m:
compiler/rbmm.points_to_analysis.m:
compiler/rbmm.points_to_graph.m:
compiler/rbmm.points_to_info.m:
compiler/rbmm.region_resurrection_renaming.m:
compiler/rbmm.region_transformation.m:
compiler/recompilation.used_file.m:
compiler/recompilation.version.m:
compiler/recompute_instmap_deltas.m:
compiler/resolve_unify_functor.m:
compiler/rtti.m:
compiler/rtti_out.m:
compiler/rtti_to_mlds.m:
compiler/saved_vars.m:
compiler/set_of_var.m:
compiler/simplify_goal_call.m:
compiler/simplify_goal_conj.m:
compiler/simplify_goal_disj.m:
compiler/simplify_goal_ite.m:
compiler/simplify_goal_scope.m:
compiler/simplify_goal_switch.m:
compiler/simplify_goal_unify.m:
compiler/simplify_info.m:
compiler/simplify_proc.m:
compiler/size_prof.m:
compiler/smm_common.m:
compiler/ssdebug.m:
compiler/stack_alloc.m:
compiler/stack_layout.m:
compiler/stack_opt.m:
compiler/stm_expand.m:
compiler/store_alloc.m:
compiler/structure_reuse.analysis.m:
compiler/structure_reuse.direct.choose_reuse.m:
compiler/structure_reuse.direct.detect_garbage.m:
compiler/structure_reuse.domain.m:
compiler/structure_reuse.indirect.m:
compiler/structure_reuse.lbu.m:
compiler/structure_reuse.lfu.m:
compiler/structure_sharing.analysis.m:
compiler/structure_sharing.domain.m:
compiler/superhomogeneous.m:
compiler/switch_detection.m:
compiler/switch_gen.m:
compiler/switch_util.m:
compiler/table_gen.m:
compiler/tabling_analysis.m:
compiler/term_constr_build.m:
compiler/term_constr_data.m:
compiler/term_constr_initial.m:
compiler/term_constr_main.m:
compiler/term_constr_main_types.m:
compiler/term_constr_util.m:
compiler/term_pass1.m:
compiler/term_traversal.m:
compiler/term_util.m:
compiler/trace_gen.m:
compiler/trailing_analysis.m:
compiler/transform_llds.m:
compiler/try_expand.m:
compiler/tupling.m:
compiler/type_assign.m:
compiler/type_ctor_info.m:
compiler/type_util.m:
compiler/typecheck.m:
compiler/typecheck_debug.m:
compiler/typecheck_errors.m:
compiler/typecheck_info.m:
compiler/unify_gen_construct.m:
compiler/unify_gen_deconstruct.m:
compiler/unify_proc.m:
compiler/unique_modes.m:
compiler/unneeded_code.m:
compiler/untupling.m:
compiler/unused_args.m:
compiler/unused_imports.m:
compiler/var_locn.m:
compiler/write_deps_file.m:
compiler/write_module_interface_files.m:
    Conform to the changes above.
2022-04-18 02:00:38 +10:00
Zoltan Somogyi
3f3045c9e2 Get and set varsets/vartypes in proc_infos together.
compiler/hlds_pred.m:
    We eventually want to replace the varset and vartypes fields in
    each proc_info with a var_table, but it is not practical to do so
    at once; it will have to be done gradually, a few modules at most
    at a time. During this process, we will need a way either

    - to let already converted modules get a var_table out of the proc_info,
      and put an updated var_table back into a proc_info, even though
      proc_infos still contain varset and vartypes fields, or

    - to let not-yet-converted modules get varsets and vartypes out of the
      proc_info, and put updated varsets and vartypes back into a proc_info,
      even though proc_infos already store a var_table.

    The latter cannot be done in two halves (i.e. set the varset half
    of the var_table, and then set its vartypes half), and while the former
    *can* be done that way, it is more efficient to do them at the same time.

    Therefore as a first step, this diff replaces the indiviual getter
    and setter predicates of the varset and vartypes fields of proc_info
    with a getter that gets both and a setter that sets both.

    Put the varset and vartypes next to each other in a structure.

compiler/code_info.m:
    Delete a function that duplicates a function in var_table.m.

    Conform to the change above.

compiler/det_report.m:
    Factor out some common code.

    Conform to the change above.

compiler/det_util.m:
    Delete a no-longer-needed predicate.

    Conform to the change above.

compiler/higher_order.m:
    Fix an old oversight: when deleting variables from the vartypes,
    delete them from the varset as well.

    Conform to the change above.

compiler/liveness.m:
    Avoid constructing and traversing a list unnecessarily.

    Conform to the change above.

compiler/accumulator.m:
compiler/add_heap_ops.m:
compiler/add_trail_ops.m:
compiler/arg_info.m:
compiler/build_mode_constraints.m:
compiler/bytecode_gen.m:
compiler/call_gen.m:
compiler/clause_to_proc.m:
compiler/closure_analysis.m:
compiler/code_gen.m:
compiler/code_loc_dep.m:
compiler/complexity.m:
compiler/continuation_info.m:
compiler/cse_detection.m:
compiler/ctgc.datastruct.m:
compiler/ctgc.util.m:
compiler/deep_profiling.m:
compiler/deforest.m:
compiler/delay_construct.m:
compiler/delay_partial_inst.m:
compiler/dep_par_conj.m:
compiler/det_analysis.m:
compiler/direct_arg_in_out.m:
compiler/disj_gen.m:
compiler/equiv_type_hlds.m:
compiler/exception_analysis.m:
compiler/float_regs.m:
compiler/follow_code.m:
compiler/goal_mode.m:
compiler/goal_path.m:
compiler/hlds_out_pred.m:
compiler/hlds_rtti.m:
compiler/hlds_statistics.m:
compiler/inlining.m:
compiler/intermod.m:
compiler/intermod_analysis.m:
compiler/introduce_exists_casts.m:
compiler/introduce_parallelism.m:
compiler/lambda.m:
compiler/lco.m:
compiler/live_vars.m:
compiler/loop_inv.m:
compiler/mark_tail_calls.m:
compiler/ml_accurate_gc.m:
compiler/ml_args_util.m:
compiler/ml_closure_gen.m:
compiler/ml_gen_info.m:
compiler/ml_proc_gen.m:
compiler/mode_info.m:
compiler/modecheck_goal.m:
compiler/modes.m:
compiler/par_loop_control.m:
compiler/pd_debug.m:
compiler/pd_info.m:
compiler/pd_util.m:
compiler/polymorphism_info.m:
compiler/proc_gen.m:
compiler/purity.m:
compiler/push_goals_together.m:
compiler/quantification.m:
compiler/rbmm.add_rbmm_goal_infos.m:
compiler/rbmm.live_variable_analysis.m:
compiler/rbmm.points_to_graph.m:
compiler/rbmm.points_to_info.m:
compiler/rbmm.region_liveness_info.m:
compiler/rbmm.region_transformation.m:
compiler/recompute_instmap_deltas.m:
compiler/saved_vars.m:
compiler/simplify_goal_unify.m:
compiler/simplify_info.m:
compiler/simplify_proc.m:
compiler/size_prof.m:
compiler/ssdebug.m:
compiler/stack_alloc.m:
compiler/stack_layout.m:
compiler/stack_opt.m:
compiler/stm_expand.m:
compiler/store_alloc.m:
compiler/structure_reuse.analysis.m:
compiler/structure_reuse.direct.choose_reuse.m:
compiler/structure_reuse.direct.detect_garbage.m:
compiler/structure_reuse.indirect.m:
compiler/structure_reuse.lbu.m:
compiler/structure_reuse.lfu.m:
compiler/structure_sharing.analysis.m:
compiler/structure_sharing.domain.m:
compiler/switch_detection.m:
compiler/table_gen.m:
compiler/tabling_analysis.m:
compiler/term_constr_build.m:
compiler/term_constr_initial.m:
compiler/term_errors.m:
compiler/term_pass1.m:
compiler/term_pass2.m:
compiler/trace_gen.m:
compiler/trailing_analysis.m:
compiler/try_expand.m:
compiler/tupling.m:
compiler/unneeded_code.m:
compiler/untupling.m:
compiler/unused_args.m:
compiler/unused_imports.m:
    Conform to the change above.
2022-04-07 21:22:21 +10:00
Zoltan Somogyi
8ebe125a6a Introduce var_table.m.
Most compiler passes need to know both the names and the types
of the variables they operate on. Until now, they had to pass along
two separate data structures for that, the varset and the vartypes,
and many operations required looking a variable up in both of these.

The var table is a single data structure that records for each variable

- its name, as the varset has traditionally done,
- its type, as the vartypes has traditionally done,
- the is_dummy_type flag which says whether its type is a dummy type,
  which traditionally had to computed afresh at each lookup.

Switch the MLDS code generator to use var_tables instead of varsets and
vartypes. The code generator often needs to know the name and the type
of a variable at the same time, and it often needs to know which variables'
types are dummies, often enough that precomputing this info should be a win.

compiler/var_table.m:
    Add this new module which defines the var_table.

    Its operations are modelled after the operation in var_types.m.

compiler/hlds.m:
compiler/notes/compiler_design.html:
    Add the new module to the hlds package.

compiler/prog_type.m:
compiler/type_util.m:
    Move the is_dummy_type from type_util.m, which is in the
    check_hlds package, to prog_type.m, which in the parse_tree package,
    to avoid having this part of the hlds package depend on check_hlds.
    (It already depends on parse_tree, for a lot of different things.)

    Given a function and a predicate that each took a vartypes arg,
    make new versions that take a var_table arg instead.
    Rationalize the argument list of the function.

compiler/ml_gen_info.m:
    Replace the varset and vartypes fields of the ml_gen_info with a
    var_table field.

compiler/ml_code_util.m:
    Replace code that used to operate on varsets and vartypes with code
    that operates on var_tables.

    Create new versions of a few operations to exploit the info in var_tables.

    Give some predicates more meaningful names.

compiler/ml_accurate_gc.m:
compiler/ml_args_util.m:
compiler/ml_call_gen.m:
compiler/ml_closure_gen.m:
compiler/ml_code_gen.m:
compiler/ml_commit_gen.m:
compiler/ml_disj_gen.m:
compiler/ml_foreign_proc_gen.m:
compiler/ml_lookup_switch.m:
compiler/ml_proc_gen.m:
compiler/ml_switch_gen.m:
compiler/ml_tag_switch.m:
compiler/ml_unify_gen.m:
compiler/ml_unify_gen_construct.m:
compiler/ml_unify_gen_deconstruct.m:
compiler/ml_unify_gen_test.m:
compiler/ml_unify_gen_util.m:
    Replace code that used to operate on varsets and vartypes with code
    that operates on var_tables.

    In ml_switch_gen.m and ml_tag_switch.m, put some predicates' arguments
    into an reasonable order by moving related args next to each other.

compiler/vartypes.m:
    Delete an operation that was only needed in the MLDS backend,
    in code that this diff replaces.

compiler/switch_util.m:
    Put the larger input first in the arg list of a predicate.

compiler/closure_gen.m:
compiler/code_info.m:
compiler/code_loc_dep.m:
compiler/export.m:
compiler/lambda.m:
compiler/live_vars.m:
compiler/liveness.m:
compiler/llds.m:
compiler/llds_out_instr.m:
compiler/mark_tail_calls.m:
compiler/opt_debug.m:
compiler/opt_util.m:
compiler/stack_alloc.m:
compiler/stack_layout.m:
compiler/tag_switch.m:
compiler/term_constr_util.m:
compiler/tupling.m:
compiler/unify_gen.m:
compiler/unify_gen_deconstruct.m:
compiler/var_locn.m:
    Conform to the changes above.
2022-03-28 10:20:49 +11:00
Zoltan Somogyi
d76c7bf617 Break up inst_util.m and mode_util.m.
This step significantly improves module cohesion.

compiler/inst_abstract_unify.m:
    New module carved out of inst_util.m, which does abstract unifications
    on insts.

compiler/inst_merge.m:
    New module carved out of inst_util.m, which merges insts.

compiler/inst_lookup.m:
    New module carved partly out of inst_util.m and partly out of mode_util.m,
    which looks up insts in the module_info, and then possibly expands out
    the result.

compiler/mode_test.m:
    New module carved out of mode_util.m, whose predicates
    perform tests on modes.

compiler/mode_top_functor.m:
    New module carved out of mode_util.m, which computes top_functor_modes
    from modes.

compiler/inst_mode_type_prop.m:
    New module carved out of mode_util.m, which propagates type information
    into both insts and modes.

compiler/recompute_instmap_deltas.m:
    New module carved out of mode_util.m, which recomputes goals'
    instmap_deltas.

compiler/inst_test.m:
    Move here the predicates in inst_util.m that perform tests on insts.

compiler/inst_util.m:
compiler/mode_util.m:
    Delete the code that this diff moves to other modules.

compiler/check_hlds.m:
    Add the new modules to the check_hlds package, the package that also
    contains inst_util.m and mode_util.m. (Some of these modules could
    be argued to fit better in the hlds package, but moving them there
    would not be desirable while they depend on code that is still in the
    check_hlds package.)

compiler/notes/compiler_design.html:
    Document the new modules.

compiler/add_pragma_tabling.m:
compiler/arg_info.m:
compiler/bytecode_gen.m:
compiler/closure_analysis.m:
compiler/complexity.m:
compiler/deep_profiling.m:
compiler/deforest.m:
compiler/dep_par_conj.m:
compiler/det_report.m:
compiler/direct_arg_in_out.m:
compiler/distance_granularity.m:
compiler/equiv_type_hlds.m:
compiler/error_msg_inst.m:
compiler/fact_table.m:
compiler/float_regs.m:
compiler/follow_code.m:
compiler/goal_util.m:
compiler/higher_order.m:
compiler/hlds_pred.m:
compiler/hlds_rtti.m:
compiler/inlining.m:
compiler/inst_match.m:
compiler/inst_user.m:
compiler/instmap.m:
compiler/intermod.m:
compiler/interval.m:
compiler/introduce_exists_casts.m:
compiler/lambda.m:
compiler/lco.m:
compiler/liveness.m:
compiler/lookup_util.m:
compiler/loop_inv.m:
compiler/mark_tail_calls.m:
compiler/ml_args_util.m:
compiler/ml_code_util.m:
compiler/ml_foreign_proc_gen.m:
compiler/ml_unify_gen_construct.m:
compiler/ml_unify_gen_util.m:
compiler/mode_constraints.m:
compiler/mode_errors.m:
compiler/modecheck_call.m:
compiler/modecheck_coerce.m:
compiler/modecheck_goal.m:
compiler/modecheck_unify.m:
compiler/modecheck_util.m:
compiler/modes.m:
compiler/oisu_check.m:
compiler/par_conj_gen.m:
compiler/pd_util.m:
compiler/post_typecheck.m:
compiler/pragma_c_gen.m:
compiler/proc_requests.m:
compiler/prog_rep.m:
compiler/push_goals_together.m:
compiler/rbmm.region_transformation.m:
compiler/saved_vars.m:
compiler/simplify_goal_switch.m:
compiler/simplify_proc.m:
compiler/size_prof.m:
compiler/ssdebug.m:
compiler/stack_opt.m:
compiler/stm_expand.m:
compiler/stratify.m:
compiler/structure_reuse.versions.m:
compiler/structure_sharing.domain.m:
compiler/superhomogeneous.m:
compiler/table_gen.m:
compiler/term_constr_build.m:
compiler/term_pass2.m:
compiler/term_util.m:
compiler/tupling.m:
compiler/unify_gen_construct.m:
compiler/unify_gen_util.m:
compiler/unique_modes.m:
compiler/unneeded_code.m:
compiler/untupling.m:
compiler/unused_args.m:
    Conform to the changes above by importing the required new modules,
    sometimes in addition to inst_util.m or mode_util.m, but more usually
    instead of them.
2021-12-16 01:31:35 +11:00
Zoltan Somogyi
0d7c8a7654 Specify pred or func for all pragmas.
*/*.m:
    As above.

configure.ac:
    Require the installed compiler to support this capability.
2021-06-16 15:23:58 +10:00
Zoltan Somogyi
955a69efff Give better names to some functions.
compiler/type_util.m:
    Rename the "check_dummy_type" function to "is_type_a_dummy", since this
    expresses its job more clearly.

    Make the implementation of "is_type_a_dummy" slightly more efficient,
    by avoiding some redundant actions.

    Provide a new function "is_either_type_a_dummy" that does
    what its name says, and which is somewhat more efficient than
    two separate calls to "is_type_a_dummy".

compiler/prog_type.m:
    Rename the "check_builtin_dummy_type_ctor" function to
    "is_type_ctor_a_builtin_dummy", since this expresses its job
    more clearly.

compiler/ml_unify_gen.m:
    Conform to the name changes.

    Use the new function where relevant to simplify some code.

    Fix some comments.

compiler/code_info.m:
compiler/code_loc_dep.m:
compiler/continuation_info.m:
compiler/erl_call_gen.m:
compiler/erl_code_gen.m:
compiler/erl_code_util.m:
compiler/erl_unify_gen.m:
compiler/export.m:
compiler/higher_order.m:
compiler/hlds_pred.m:
compiler/live_vars.m:
compiler/llds_out_instr.m:
compiler/mark_tail_calls.m:
compiler/ml_args_util.m:
compiler/ml_call_gen.m:
compiler/ml_closure_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_commit_gen.m:
compiler/ml_foreign_proc_gen.m:
compiler/pragma_c_gen.m:
compiler/stack_layout.m:
compiler/term_constr_util.m:
compiler/trace_gen.m:
compiler/unify_gen.m:
compiler/unify_proc.m:
compiler/var_locn.m:
compiler/write_module_interface_files.m:
    Use the new function where relevant.
2018-02-28 13:48:44 +11:00
Zoltan Somogyi
f1906ece65 Fix some too-long lines. 2017-12-14 14:12:30 +11:00
Zoltan Somogyi
d1438fd51a Improve a comment. 2017-11-08 23:03:43 +11:00
Zoltan Somogyi
996d689219 Support tail recursion between funcs and preds.
Generalize the mechanism we use to implement mutual tail recursion optimization
in the MLDS backend to handle TSCCs that contain both predicates and functions.
This generalization also simplifies the split of responsibilities between
the MLDS functions that implement each TSCC procedure for external callers
(which we now call the container function) on the one hand, and their main
components, the bodies of the procedures themselves (which we now call the
wrapped procedures, since each container function wraps up the bodies
of *all* the procedures in the TSCC).

In the new scheme, wrapped functions always give output arguments
to container functions by value. It is the job of the container functions
to return these output arguments to the caller according to the requirements
imposed by the container function's calling convention. This allows
different container functions to return output arguments differently
(some may return an output by value, while some may do so by reference)
while still allowing the wrapped procedure bodies to be generated just once
and then duplicated for each container function.

compiler/notes/mlds_tail_recursion.html:
    A new file explaining both the scheme we use to generate code for
    TSCCs, and the reasons why we use that scheme.

compiler/notes/Mmakefile:
    Include the new file in the list of compiler notes files.

compiler/ml_args_util.m:
    Update the code that generated code fragments handling arguments
    for TSCCs to follow the updated scheme. Use the terminology in the
    new notes file to clarify variable names where relevant. Group
    related arguments together.

compiler/ml_proc_gen.m:
    Update the code that created wrapped procedures and container functions
    to follow the updated scheme. Use the terminology in the new notes file
    to clarify both function and variable names where relevant. Delete the
    documentation which is now in notes/mlds_tail_recursion.html (in greatly
    enhanced form).

    Split the predicate for adding local variable definitions to MLDS
    functions, since when generating code for TSCCs using the new scheme,
    we only need one of its two halves.

compiler/mlds.m:
    Add the new forms of compiler generated variables needed by the new
    translation scheme.

compiler/ml_gen_info.m:
    Change the type of the field containing the byref output vars
    from a list to a set. All its users want to treat it as a set,
    so it is simpler and faster to convert it just once, when it is set,
    instead of on every use.

compiler/ml_code_util.m:
compiler/ml_commit_gen.m:
    Conform to the change in ml_gen_info.m.
2017-10-10 02:40:16 +11:00
Zoltan Somogyi
49e89ef569 Extend mutual tail recursion optimization to functions.
Det functions have a copy-out output argument, i.e. the return value,
which is *not* returned by reference. So instead of handling such arguments
like this:

    arg_type * tscc_output_var_N;

    HeadVarN = tscc_output_var_N;
    ...
    ... body of procedure assigns to *HeadVarN
    ...
    return;

we handle them like like this:

    arg_type tscc_output_var_N;

    ...
    ... body of procedure assigns to HeadVarN
    ...
    tscc_output_var_N = HeadVarN;
    return tscc_output_var_N;

For the non-C backends, there may be more than one return value.
This scheme should work for them as well, but until that is tested,
it is not turned on.

compiler/ml_args_util.m:
    When computing the information needed for tscc arguments, don't assume
    that there are no copy-out output arguments. Instead, compute the
    information ml_proc_gen.m needs to handle them. This means returning
    a full function signature (including return values), the list of rvals
    to return, and the list of pre-return assignment statements.

    Simplify the code of ml_append_return_statement. Since ml_proc_gen.m
    now computes its own return statements (based on the information mentioned
    in the previous paragraph) by making it handle only the situation it was
    originally designed for: simple procedure bodies that are *not* parts
    of TSCCs. Simplify its code also by requiring its callers to give it
    the return values as rvals, not lvals, because the callers can give it
    the return values in this form just as easily, and it is more efficient,
    since it lets us avoid the construction of a list.

compiler/ml_proc_gen.m:
    Let det functions be part of TSCCs. Handle their return values as described
    above. Handle the construction of return statements for procedure bodies
    in TSCCs separately from return statements in standalone procedures.

compiler/ml_closure_gen.m:
    Conform to the changes in ml_args_util.m.
2017-09-13 19:06:54 +10:00
Zoltan Somogyi
b0edecbc7e Return information about output args in an assoc list.
compiler/ml_args_util.m:
    Change the interface of the ml_gen_args predicate, which is used
    to generate argument passing code at call sites. Instead of returning
    information about output arguments in two lists, return a single list
    of pairs, since this encodes the relevant invariant (the two lists
    have to be of equal length) in the type.

compiler/ml_gen_info.m:
    Make the same change in the representation of information about
    output variables in success continuations. These continuations
    are often constructed from the data returned by ml_gen_args.

compiler/ml_call_gen.m:
compiler/ml_code_gen.m:
compiler/ml_code_util.m:
compiler/ml_commit_gen.m:
compiler/ml_proc_gen.m:
    Conform to the change above.

compiler/ml_closure_gen.m:
    Conform to the change above.

    Use the new list of pairs representation to greatly simplify
    a piece of code that used higher order constructs to excess.
2017-09-12 00:52:39 +10:00
Zoltan Somogyi
d412bd410e Use arg tuples to simplify more code.
compiler/ml_args_util.m:
    I recently changed most predicates that generate a description
    of a procedure's parameter passing interface by first constructing
    a tuple for each parameter containing the information that is relevant
    to the decision about how that parameter should be passed. This diff
    makes those predicates return these tuples, since some callers can
    also benefit from having this information in this convenient form.

    Use this kind of tuple when generating a description of the input
    parameters of mutually-tail-recursive procedures.

    Change ml_gen_args and its friends (the predicates that generate code
    for actually passing parameters) to take information about the value
    being passed as ml_call_args, which have either one of two forms.
    One is just the prog_var being passed; the other is a tuple containing
    the MLDS var representing the parameter, its lval, and its actual type
    (which may differ from the type of the corresponding formal parameter,
    by being its instance). The former should be used far more frequently
    (the second is used only when constructing closure wrapper functions),
    and in this case, our caller will have to construct just one list
    (a list of wrapped prog_vars) instead of three (the MLDS var names,
    the MLDS var lvals, and the actual types), and will have to do fewer tests.

    Export the copy_out_when type, and the function that computes the right
    copy_out_when value for a given procedure, for use by ml_closure_gen.m.

    In some predicates, put related parameters together.

    In some predicates, change the names of variables to state explicitly
    whether they contain information about the caller or the callee side
    of parameter passing.

    Use Head and Tail prefixes in variable names more consistently.

compiler/ml_call_gen.m:
    Use ml_call_args to represent the arguments of calls.

    In some predicates, put related parameters together.

    In some predicates, change the names of variables to state explicitly
    whether they contain information about the caller or the callee side
    of parameter passing.

compiler/ml_code_gen.m:
    When handling calls, simply pass the argument variables to ml_call_gen.m;
    let *it* decide how it wants to construct the argument passing code.

compiler/ml_closure_gen.m:
    Use ml_call_args (in their more complicated form) to represent
    the arguments of the single unusual call inside closure wrapper
    function definitions. (It is unusual because some parameters
    are not HLDS variables.)

    Use the tuple description of the callee's parameters to simplify
    the code generating the lvals used as the arguments of that call.

    In some predicates, put related parameters together.

compiler/ml_proc_gen.m:
    Use the tuples constructed by ml_args_util.m to describe procedures'
    arguments to simplify the code that boxes or unboxes arguments as needed.

compiler/ml_top_gen.m:
    Conform to the changes in ml_args_util.m.
2017-09-11 15:06:44 +10:00
Zoltan Somogyi
977f5b54be Use just one piece of code to make a decision again.
compiler/ml_proc_gen.m:
    Use the recently unified code in ml_args_util.m to partition a procedure's
    output arguments into the set of arguments passed by reference and the set
    of output arguments returned via a return statement, instead of doing
    its job yet again in *two* separate predicates (ml_det_copy_out_vars
    for model det/semi procedures, and ml_set_up_initial_success_cont
    for model non procedures).

    Also, avoid the old dance where the ml_gen_info's by_ref_outputs field
    was initialized to contain *all* output arguments, using a *third*
    algorithm, and then had one of the two predicates mentioned above
    overwrite this incorrect-to-specification value with the correct value,
    i.e. the *actual* set of arguments passed by reference.

    The three algorithms mentioned here differed from each other in whether
    they considered top_out arguments to be outputs if their type was
    a dummy type. The only reason this inconsistency wasn't a problem was that
    the generated code was affected only by the code in ml_args_util.m,
    and the versions *there* are consistent (they do NOT consider them
    to be outputs).

compiler/ml_gen_info.m:
    Do not set the by_ref_outputs field to the set of all outputs,
    since ml_proc_gen.m does not need this anymore. Instead, leave
    a value explicitly identified as a dummy there.

compiler/ml_args_util.m:
    To make the change in ml_proc_gen.m possible, make the predicates
    that compute the parameter list of a procedure return the HLDS variables
    containing (a) the byref nondummy output args, and (b) the copied
    (i.e. returned via return statement) nondummy output args.

    Those predicates thus now require, for each argument, its HLDS variable,
    as well as its MLDS variable, its type and its top_functor_mode.
    Instead of passing four separate lists of equal length, two of which
    we have to construct (the ModuleInfo already contains lists of the
    arg vars and their types, but we have to compute the MLDS var and the
    top_functor_mode for each arg), construct and pass a list of tuples,
    one tuple per argument, since this makes the argument classification code
    simpler. (The new approach allocates a tuple and a cons cell per arg,
    while the old approach allocated two cons cells here, and more in
    ml_proc_gen.m and ml_gen_info.m when they did their redundant copies
    of this work.)

compiler/ml_closure_gen.m:
    Don't generate argument lists for wrapper procedures with incorrect
    gc statements, only to delete those statements; generate them with
    no gc statements to start with. Besides being the right thing to do,
    this allows us to delete a variant of the "generate the parameter list
    for this procedure" in ml_args_util.m that was specific to this call site.

compiler/ml_call_gen.m:
    Conform to the change in ml_args_util.m.
2017-09-09 14:24:49 +10:00
Zoltan Somogyi
a95b34e75d Use just one piece of code to make a decision.
compiler/ml_args_util.m:
    The callers of a procedure, and the procedure as a callee must partition
    the set of output arguments of the procedure the same way. They must
    decide, for each output variable, whether

    - the argument is passed by reference, or
    - it is returned via a return statement.

    We used to use one piece of code to do this partition when generating
    procedure's argument lists (the callee side), and a completely different
    piece of code (different looking, and executed at a different place)
    when generating the arguments of ml_stmt_calls (the caller side).

    Add a single function to make this decision. Replace both pieces of code
    with code that calls this function and then implements its decision,
    using code that is as close to identical as possible.
2017-09-08 22:06:08 +10:00
Zoltan Somogyi
f4e0059a49 Eliminate hlc_nest and hl_nest grades ...
... by eliminating the grade component that calls for the use of gcc nested
functions.

runtime/mercury_grade.h:
compiler/compute_grade.m:
    Delete the gcc_nested_functions grade component, and the C macro
    that specifies its presence, MR_USE_GCC_NESTED_FUNCTIONS.

scripts/canonical_grade.sh-subr:
scripts/init_grade_options.sh-subr:
scripts/mgnuc.in:
scripts/parse_grade_options.sh-subr:
    Delete the code that parses the deleted grade component,
    and delete the code that signals its absence in other grades.

compiler/options.m:
    Delete the gcc_nested_functions grade option.

    Delete also the gcc_local_labels option, since it was useful
    only if gcc_nested_functions was set.

configure.ac:
    Delete the code that sometimes added hl*_nest grades to the list of grades
    to be installed.

    Fix a bunch of comments.

compiler/compile_target_code.m:
compiler/handle_options.m:
compiler/mercury_compile_mlds_back_end.m:
compiler/ml_args_util.m:
compiler/ml_call_gen.m:
compiler/ml_code_util.m:
compiler/ml_commit_gen.m:
compiler/ml_gen_info.m:
compiler/mlds_to_c.m:
library/backjump.m:
library/exception.m:
runtime/mercury_hlc_types.h:
runtime/mercury_tabling.c:
runtime/mercury_tabling.h:
    Delete code that was active only in grades with the deleted grade
    component.

compiler/ml_accurate_gc.m:
compiler/notes/grade_library.html:
runtime/mercury_conf_param.h:
    Delete mentions of the deleted grade component.

compiler/ml_code_gen.m:
    Delete mentions of the deleted grade component, and a bunch of other
    obsolete comments.

doc/user_guide.texi:
    Fix a line break.
2017-09-07 03:01:55 +10:00
Zoltan Somogyi
a4b6ca3b83 Eliminate repeated lookups of two options.
compiler/ml_gen_info.m:
    Store the values of the det_copy_out and nondet_copy_out options
    in the ml_gen_info.

compiler/ml_call_gen.m:
compiler/ml_closure_gen.m:
compiler/ml_commit_gen.m:
compiler/ml_proc_gen.m:
    Get the values of those options from the ml_gen_info.

compiler/ml_args_util.m:
    Get the values of those options from the ml_gen_info when it is available.

    Keep private a predicate that (after the changes to the modules above)
    isn't used outside this module anymore.
2017-09-06 13:43:29 +10:00
Zoltan Somogyi
c3fb6d4d42 Replace a bool with a bespoke type. 2017-09-06 00:02:08 +10:00
Zoltan Somogyi
573c5f50ef Address Julien's review comments. 2017-09-02 23:53:38 +10:00
Zoltan Somogyi
9428ae048c Improve a comment. 2017-09-01 21:41:37 +10:00
Zoltan Somogyi
217a363181 Fix unreachable return statements.
My recent change to ml_args_util.m broke bootchecking in java grades,
because it added an explicit return statement after every procedure body,
even those that end with target language code that throws an exception.
The Java compiler generates an error for throws followed by returns.

compiler/ml_args_util.m:
    Append a return statement after procedure bodies that don't return
    anything only if an option asks us to do so.

compiler/ml_proc_gen.m:
    When generating code for single procedure bodies, let ml_args_util.m
    not add return statements.

    When generating code for procedure bodies in TSCCs, require ml_args_util.m
    to add return statements, since without that, when one procedure succeeds,
    you would get a fall-through to the start of the next procedure in the
    TSCC. To make sure this return does not cause any problems, don't include
    procedures that cannot succeed in TSCCs.

compiler/ml_closure_gen.m:
    Conform to the change in ml_args_util.m.
2017-09-01 20:22:13 +10:00
Zoltan Somogyi
f0b2444b11 Generate MLDS return statements in just one place.
compiler/ml_args_util.m
    Always generate return statements in the predicate that usually generates
    them, even if they aren't needed because of the implicit return at the
    end of MLDS functions.

compiler/ml_proc_gen.m:
    Delete the code that added return statements at the end of the translations
    of procedure bodies when the translation of more than one procedure body
    was wrapped up in the *same* MLDS function.
2017-08-31 22:17:42 +10:00
Zoltan Somogyi
eccd0bfab4 Implement mutual tail call optimization for the MLDS.
It does not (yet) optimize all the calls that the LLDS backend optimizes,
with the most significant limitation being that it handles only calls to
procedures that return all their arguments by reference. This rules out
det functions (thought it includes *semidet* functions), as well as the
backends that use copy-out. Lifting those limitations is future work.

compiler/ml_proc_gen.m:
    Make the change described above.

compiler/mlds.m:
    Add two new kinds of compiler-generated local variables to represent
    the input and output arguments of procedures in TSCCs respectively.
    They are key to allowing the code generation scheme used by ml_proc_gen.m
    to work *without* having to rename apart either sets of HLDS variables
    or set of MLDS variables. (Both those renames would be a lot of work.)

    Add a new kind of compiler-generated local variable to represent
    the identity of the tail-called procedure if the code generator is asked
    not to use labels and gotos.

compiler/ml_args_util.m:
    Provide a predicate that ml_proc_gen.m uses to generate argument handling
    code for mutually recursive procedures.

compiler/ml_gen_info.m:
    Generalize the existing support for self-tail-recursive calls
    to also handle mutually-tail-recursive calls.

compiler/ml_call_gen.m:
    Use the new generalized support to generate code for
    mutually-tail-recursive calls as well as for self-tail-recursive calls.
    For each call to a procedure that the ml_gen_info records as a potential
    target for a tail recursive call (i.e. for each procedure in the TSCC
    we are generating code for), record what kinds of calls we *do* generate
    to it, for use by ml_proc_gen.m.

compiler/ml_code_util.m:
    Add a slightly different form of an existing utility function,
    to allow new code in ml_proc_gen.m to use it without doing redundant work.

    Expand out a function's definition to allow mdb breakpoints on its
    components.

compiler/options.m:
    Provide developer-only options to control aspects of how ml_proc_gen.m
    handles tail call optimization.

compiler/mlds_to_c.m:
compiler/mlds_to_cs.m:
compiler/mlds_to_java.m:
    Provide a way for the MLDS to specify the printing of a blank line:
    a comment containing an empty string. Some code in ml_proc_gen.m uses this
    to make the comments it generates look nicer.

compiler/hlds_desc.m:
    Add two utility functions that we now use to include descriptions
    of TSCCs in the generated MLDS code, to help debug that code.

compiler/proc_gen.m:
    Delete code that can now be replaced by calling one of the new utility
    functions in hlds_desc.m. (The deleted code was used as the original
    template for the code of that function.)

    Delete an unused type.

compiler/rtti_to_mlds.m:
    Conform to the changes in ml_gen_info.m.
2017-08-31 14:38:45 +10:00
Zoltan Somogyi
57d58da6ff Factor out some common code.
compiler/ml_proc_gen.m:
    Prepare for translating all HLDS procedures in a TSCC all at once to MLDS,
    by taking some chunks of code that will be useful in this process
    out of the predicate that translates a single HLDS procedure to MLDS
    and making them predicates in their own right. The new mechanism for
    translating a whole TSCC at once will take these pieces and put them,
    or modified/generalized versions of them, together in different ways.

compiler/ml_args_util.m:
    Factor out some code that is common to all exported predicates
    that generate argument lists.

    Add a "_no_gc_stmts" suffix to the names of the predicates that generate
    argument lists that do not fill in the gc stmt field in the generated
    mlds_arguments.

compiler/ml_gen_info.m:
    Instead of storing the pred_id and proc_id of the procedure being
    translated separately, store them together as a pred_proc_id, because
    most users of ml_gen_info need both at the same time.

compiler/ml_code_util.m:
    Make several predicates take pred_proc_ids instead of separate pred_ids
    and proc_ids.

compiler/ml_accurate_gc.m:
compiler/ml_call_gen.m:
compiler/ml_foreign_proc_gen.m:
compiler/ml_top_gen.m:
compiler/ml_unify_gen.m:
compiler/rtti_to_mlds.m:
    Conform to the changes above.
2017-08-13 13:48:44 +02:00
Zoltan Somogyi
bbd6c44a26 Create ml_args_util.m.
Both ml_code_util.m and ml_call_gen.m had predicates that used the same logic
to process lists of arguments. This is not a coincidence; they both process
argument lists, one from the point of the callee, the other from the point
of view of the caller. These have to be kept in lockstep. This is easier
if they are next to each other. This diff therefore moves those predicates
to the same module, a new module named ml_args_util.m.

compiler/ml_call_gen.m:
compiler/ml_code_util.m:
    Delete the new code now in ml_args_util.m.

compiler/ml_args_util.m:
    The new module.

compiler/ml_backend.m:
compiler/notes/compiler_design.html:
    Mention the new module.

compiler/ml_closure_gen.m:
compiler/ml_proc_gen.m:
compiler/ml_top_gen.m:
compiler/rtti_to_mlds.m:
    Conform to the changes above.
2017-08-13 02:06:26 +02:00