Rationalise the code that simplifies calls.

The code of simplify_goal_plain_call used have a pretty odd structure:

    if the call is to @< or similar predicates then
        replace the call with a call to builtin.compare and test the result
    else
        if the call is to an obsolete predicate then
            generate obsolete warning
        if the call is an infinitely recursive call then
            generate an infinitely recursion warning

        if the call is a duplicate then
            generate a duplicate call warning
            and replace the call with assignments (if allowed)
        else if the call can be evaluated at compile time then
            evaluate the call at compile time
        else
            replace the call with the cheaper call, if possible

This structure, which as far as I can tell just grew without an overall
design, had several flaws. Some have to do with handling calls to @<
too early:

- It did not generate warnings for duplicate calls to @< and the like.
- It did not optimise duplicate calls to @< and the like.

Some do not:

- If the compiler has seen e.g. X := 1 + 2 earlier, it preferred to
  replace a later Y := 1 + 2 with Y := X rather than Y := 3, even though
  the former may require saving X on the stack across calls.

This diff changes the structure of simplify_goal_plain_call to

    if the call is to an obsolete predicate then
        generate obsolete warning
    if the call is an infinitely recursive call then
        generate an infinite recursion warning

    if the call can be evaluated at compile time then
        evaluate the call at compile time
    else if the call is a duplicate then
        generate a duplicate call warning
        if allowed then
            replace the call with assignments
        else
            replace the call with a cheaper call, if possible
    else
        replace the call with a cheaper call, if possible

    The code for improving calls to @< etc is still there, but now it is
    in the code for "replace the call with a cheaper call, if possible".

compiler/simplify_goal_call.m:
    Change the overall logic of simplify_goal_plain_call, as described above.

    Move the code that generates warnings if needed to their own predicates,
    to allow the code implementing the above structure to be small enough
    to be understood all at once.

    Put the predicates into a more logical order: top level predicates
    called from simplify_goal.m, predicates that generate warnings, and
    predicates that transform the code.

    Don't export predicates that don't need to be exported.

    Delay looking up options until their values are needed.

    Exploit the changes to common.m, const_prop.m. and simplify_info.m.

    Add XXXs to code that could be further improved.

compiler/simplify_info.m:
    Add a single predicate that simplify_goal_call.m can use to test
    whether it wants to call common.m.

compiler/const_prop.m:
    Take a globals instead of a module_info, since the rest of the module_info
    is not needed. (We could take just the values of the options we need,
    but that would require exposing too much information that is properly
    private to const_prop.m.)

    Put the arguments of predicates into a better order by not putting
    unrelated stuff into the middle of an argument list that describes
    a call.

    Delay looking up options until their values are needed.

    Improve some comments.

compiler/common.m:
    Instead of always returning a new goal, return a new goal only if it is
    an optimized version of the old goal. This simplifies the code of our
    caller.

    Do not require the several callers of common_optimise_call or its
    higher_order_call variant to test the purity of the call; do it here,
    where all the other checks for whether the call is duplicate-eliminable
    are done.

library/builtin.m:
    Update a comment about code in simplify_goal_call.m.