72 lines
1.8 KiB
Go
72 lines
1.8 KiB
Go
package optimizer
|
|
|
|
import "strings"
|
|
|
|
// Optimize applies all enabled peephole passes to the generated ASM lines.
|
|
// Each pass runs sequentially on a parsed representation of the lines.
|
|
// @@OPT markers are stripped from output.
|
|
// Returns optimized lines and the set of dissolved REGISTER variable names
|
|
// (variables that had all their stores/loads eliminated).
|
|
func Optimize(lines []string, cfg *Config) ([]string, map[string]bool) {
|
|
dissolved := map[string]bool{}
|
|
|
|
if cfg == nil || !cfg.Any() {
|
|
return lines, dissolved
|
|
}
|
|
|
|
parsed := parseLines(lines)
|
|
original := parsed
|
|
|
|
if cfg.EnableStoreLoad {
|
|
parsed = passStoreReload(parsed, cfg)
|
|
}
|
|
if cfg.EnableLoad {
|
|
parsed = passLoadElimination(parsed, cfg)
|
|
}
|
|
if cfg.EnableImm {
|
|
parsed = passImmElimination(parsed)
|
|
}
|
|
if cfg.EnableJmp {
|
|
parsed = passJmpNext(parsed)
|
|
}
|
|
if cfg.EnableSelf {
|
|
parsed = passSelfAssignment(parsed)
|
|
}
|
|
if cfg.EnableRegisterVars && len(cfg.RegisterVars) > 0 {
|
|
parsed = passRegDead(parsed, cfg.RegisterVars)
|
|
}
|
|
|
|
parsed = stripOptMarkers(parsed)
|
|
if cfg.Debug {
|
|
original = stripOptMarkers(original)
|
|
parsed = debugDiff(original, parsed)
|
|
}
|
|
|
|
resultLines := linesToString(parsed)
|
|
|
|
if len(cfg.RegisterVars) > 0 {
|
|
dissolved = computeDissolved(resultLines, cfg.RegisterVars)
|
|
}
|
|
|
|
return resultLines, dissolved
|
|
}
|
|
|
|
// computeDissolved finds REGISTER variables that have no remaining references
|
|
// in the output and can have their memory allocation elided.
|
|
func computeDissolved(outputLines []string, registerVars map[string]bool) map[string]bool {
|
|
dissolved := map[string]bool{}
|
|
for name := range registerVars {
|
|
dissolved[name] = true
|
|
}
|
|
for _, line := range outputLines {
|
|
for name := range dissolved {
|
|
if strings.Contains(line, name) {
|
|
delete(dissolved, name)
|
|
}
|
|
}
|
|
if len(dissolved) == 0 {
|
|
break
|
|
}
|
|
}
|
|
return dissolved
|
|
}
|