Fixes a bug whereby, for example, "guild compile --target=i686-linux-gnu"
running on x86_64 would generate invalid code for 'bytevector-u32-native-set!'
because 'target-most-positive-fixnum' was called from the top-level
when (language tree-il compile-cps) was loaded.
Consequently, the .go files under prebuilt/ would be invalid, leading to
build failures on 32-bit platforms.
This issue became apparent with cb8cabe85f.
* module/language/tree-il/compile-cps.scm (bytevector-ref-converter)[tag]:
Turn into a lambda so that 'target-most-positive-fixnum' is called in
the right context.
(bytevector-set-converter)[integer-unboxer]: Likewise.
* module/language/cps/cse.scm (eliminate-common-subexpressions-in-fun):
I think it's possible to get an orphan loop, with predecessors
after successors in the original RPO. Handle that here.
* bootstrap/Makefile.am (GUILE_OPTIMIZATIONS): Change to just -O1.
* module/language/tree-il/spec.scm (choose-compiler): Use CPS for -O2
and higher.
* module/system/base/optimize.scm (available-optimizations): CPS for -O2
and higher, but -Oresolve-primitives now at -O1 also.
* module/language/cps/cse.scm (propagate-analysis): New helper.
(eliminate-common-subexpressions-in-fun): Recompute avail and bool set
in response to simplifications in predecessor CFG. Allows much better
compilation of pattern-matching idioms!
* module/language/cps/cse.scm (forward-cont, forward-branch)
(compute-avail-and-bool-edge): New helpers.
(add-equivalent-expression!): Allow idempotent adds; can happen now
when revisiting a cont after changes to its predecessors.
(fold-branch): New helper.
(eliminate-common-subexpressions-in-fun): Allow for reductions to
branch predecessors. In that case, revisit the branch, as the CFG
will have changed.
* module/language/cps/cse.scm (elide-predecessor, prune-branch)
(prune-successors, term-successors): New helpers.
(eliminate-common-subexpressions-in-fun): When we modify the CFG,
update the analysis. Also, thread the substs map through CSE so that
closures in high-level CPS can take advantage of eliminated variables.
(fold-renumbered-functions): Take multiple seeds.
(eliminate-common-subexpressions): Thread var substs map through CSE.
* module/language/cps/cse.scm (<analysis>): New data type, grouping
available expression analysis, predecessor map, etc.
(eliminate-common-subexpressions-in-fun): Instead of having a static
analysis, thread it through the CSE pass so that we can update the CFG
as we go.
* module/language/cps/cse.scm (compute-available-expressions): Take a
clobber map instead of an effects map.
(compute-singly-referenced): Remove unused function.
(eliminate-common-subexpressions-in-fun): Keep a preds map. Use it
add entries to the equiv-set and var-substs at expression
continuations instead of at the expression terms themselves.
* module/language/cps/cse.scm (compute-truthy-expressions): Operate on a
single function.
(eliminate-common-subexpressions-in-fun): Instead of computing a set
of labels to eliminate, go ahead and do the elimination as we go.
(fold-renumbered-functions): Can just use a single seed now.
(eliminate-common-subexpressions): Simplify to just fold over
functions, building up renamed output as we go.
* module/language/cps/cse.scm (fold-renumbered-functions): New helper.
(compute-equivalent-expressions): Use new helper.
(compute-equivalent-expressions-in-fun): Lift to top-level.
(eliminate-common-subexpressions): Adapt.
* module/language/tree-il/optimize.scm (make-optimizer): New procedure,
to compute an optimizer given options, lazily loading optimization
modules.
(optimize): Use make-optimizer.
(make-lowerer): Use make-optimizer, so as to only load needed
optimizations. Speeds up bootstrap times.
* module/language/tree-il/primitives.scm (expand-eq): Just expand out to
binary comparisons. Also expand eq?, which was missing. Leave
strength reduction to peval.
(character-comparison-expander): Move down, as it depends on <, <=,
and so on.
* module/language/tree-il/peval.scm (peval): Robustly reduce equal? and
eqv?.
* test-suite/tests/peval.test ("partial evaluation"): Expect fixnum
comparison to reduce to eq?.
("eqv?", "equal?"): A new battery of tests.
* test-suite/tests/tree-il.test ("primitives"): Remove reduction tests.
* module/language/tree-il.scm (with-lexicals): New public helper.
* .dir-locals.el (with-lexicals): Add indentation rule.
* module/language/tree-il/compile-bytecode.scm (canonicalize): Use
with-lexicals.
* module/language/tree-il/compile-cps.scm (canonicalize): Use
with-lexicals from tree-il.
* module/language/tree-il/primitives.scm (chained-comparison-expander):
Remove duplicate expander definitions for <, <=, and so on.
* module/language/tree-il/primitives.scm (maybe-simplify-to-eq): Avoid
inadvertent code duplication by using with-lexicals.
(expand-chained-comparisons): Likewise.
(call-with-prompt): Simplify to use with-lexicals.
* module/language/cps/optimize.scm (define-optimizer):
(optimize-higher-order-cps, optimize-first-order-cps):
(make-cps-lowerer):
* module/language/tree-il/optimize.scm (optimize, make-lowerer): In an
embarrassing bug, after parsing optimization arguments, we were
aconsing them instead of the expected cons*. This meant the bootstrap
was running all Tree-IL optimizations! Change to have optimizers not
have defaults and use alists after parsing.
* module/language/tree-il/compile-bytecode.scm (compile-closure):
for-value-at and for-values-at take indexes instead of environments to
denote destination.
* module/language/cps/optimize.scm (cps-optimizations):
* module/language/tree-il/optimize.scm (tree-il-optimizations):
* module/system/base/optimize.scm (available-optimizations): Invert the
dependency tree to hold the names and default optimization levels in a
central place instead of in the optimizers. It moves definitions
farther from uses, but it avoids us having to load the CPS optimizer
if we don't need it, which improves bootstrap times.
* module/language/tree-il/compile-bytecode.scm (compile-closure): Make
it so that for-tail is actually tail-recursive. Likewise improve tail
recursion for the other helpers.
* module/language/tree-il/compile-bytecode.scm (emit-box-set!): Fix to
reference by SCM, not word.
(emit-box-ref): New helper.
(emit-cached-module-box, emit-cached-toplevel-box, emit-toplevel-box):
Add bound? arg. Before these could produce #f instead of a variable,
and unbound variable errors weren't any good as they didn't have the
variable name.
(compile-closure): Use more box-ref and box-set!. Pass bound? arg to
the helpers.
* module/language/cps/reify-primitives.scm (reify-lookup):
* module/language/tree-il/compile-cps.scm (toplevel-box): Instead of
checking that the result of module-variable is a variable, and
possibly checking that it's bound, we just call intrinsics that throw
exceptions if the variable isn't bound. This reduces useless inlining
that can't inform CPS optimizations, as they are tangled in diamond
control flow.
* module/language/tree-il/spec.scm (join): Use match rather than
pmatch.
(tree-il): Declare compiler to bytecode.
(choose-compiler): New implementation. Note, the baseline compiler
probably doesn't even work!!!
* module/system/base/compile.scm (next-pass): Invoke the language's
compiler chooser if there is more than one compiler.
(compute-compiler): Ensure from and to are languages.
* module/system/base/language.scm (<language>): Add compiler-chooser
field.
* module/language/brainfuck/spec.scm (choose-compiler, brainfuck):
Define a compiler chooser.
* module/language/cps/compile-bytecode.scm (compile-bytecode):
* module/language/tree-il/compile-bytecode.scm (compile-bytecode):
* module/language/tree-il/compile-cps.scm (compile-cps): Rely on
compiler to lower incoming term already.
* module/language/tree-il/optimize.scm (make-lowerer): New procedure.
* module/system/base/compile.scm (compute-lowerer): New procedure,
replaceing add-default-optimizations.
(compute-compiler): Lower before running compiler.
* module/system/base/language.scm (<language>): Change
optimizations-for-level field to "lowerer".
* module/scripts/compile.scm (%options, compile): Parse -O0, -O1 and so
on to #:optimization-level instead of expanding to all the
optimization flags.
* module/language/cps/optimize.scm (lower-cps): Move here from
compile-bytecode.scm.
(make-cps-lowerer): New function.
* module/language/cps/spec.scm (cps): Declare lowerer.