1
0
mirror of https://github.com/golang/go synced 2024-10-05 16:31:21 -06:00

[dev.ssa] cmd/compile: log line numbers in generated rewrite rules

This makes it easier to investigate and
understand rewrite behavior.

Change-Id: I790e8964922caf98362ce8a6d6972f52d83eefa8
Reviewed-on: https://go-review.googlesource.com/13588
Reviewed-by: Keith Randall <khr@golang.org>
This commit is contained in:
Josh Bleecher Snyder 2015-08-12 13:54:04 -07:00
parent 3d23afb913
commit 514ab7c385
4 changed files with 1398 additions and 41 deletions

View File

@ -45,6 +45,35 @@ import (
// If multiple rules match, the first one in file order is selected.
type Rule struct {
rule string
lineno int
}
func (r Rule) String() string {
return fmt.Sprintf("rule %q at line %d", r.rule, r.lineno)
}
func (r Rule) hash() string {
return fmt.Sprintf("%02x", md5.Sum([]byte(r.rule)))
}
// parse returns the matching part of the rule, additional conditions, and the result.
func (r Rule) parse() (match, cond, result string) {
s := strings.Split(r.rule, "->")
if len(s) != 2 {
log.Fatalf("no arrow in %s", r)
}
match = strings.TrimSpace(s[0])
result = strings.TrimSpace(s[1])
cond = ""
if i := strings.Index(match, "&&"); i >= 0 {
cond = strings.TrimSpace(match[i+2:])
match = strings.TrimSpace(match[:i])
}
return match, cond, result
}
func genRules(arch arch) {
// Open input file.
text, err := os.Open(arch.name + ".rules")
@ -53,13 +82,15 @@ func genRules(arch arch) {
}
// oprules contains a list of rules for each block and opcode
blockrules := map[string][]string{}
oprules := map[string][]string{}
blockrules := map[string][]Rule{}
oprules := map[string][]Rule{}
// read rule file
scanner := bufio.NewScanner(text)
rule := ""
var lineno int
for scanner.Scan() {
lineno++
line := scanner.Text()
if i := strings.Index(line, "//"); i >= 0 {
// Remove comments. Note that this isn't string safe, so
@ -85,24 +116,25 @@ func genRules(arch arch) {
op = op[:len(op)-1] // rule has only opcode, e.g. (ConstNil) -> ...
}
if isBlock(op, arch) {
blockrules[op] = append(blockrules[op], rule)
blockrules[op] = append(blockrules[op], Rule{rule: rule, lineno: lineno})
} else {
oprules[op] = append(oprules[op], rule)
oprules[op] = append(oprules[op], Rule{rule: rule, lineno: lineno})
}
rule = ""
}
if unbalanced(rule) {
log.Fatalf("unbalanced rule: %v\n", rule)
}
if err := scanner.Err(); err != nil {
log.Fatalf("scanner failed: %v\n", err)
}
if unbalanced(rule) {
log.Fatalf("unbalanced rule at line %d: %v\n", lineno, rule)
}
// Start output buffer, write header.
w := new(bytes.Buffer)
fmt.Fprintf(w, "// autogenerated from gen/%s.rules: do not edit!\n", arch.name)
fmt.Fprintln(w, "// generated with: cd gen; go run *.go")
fmt.Fprintln(w, "package ssa")
fmt.Fprintln(w, "import \"fmt\"")
fmt.Fprintf(w, "func rewriteValue%s(v *Value, config *Config) bool {\n", arch.name)
fmt.Fprintln(w, "b := v.Block")
@ -120,24 +152,9 @@ func genRules(arch arch) {
// identity is invariant to adding/removing rules elsewhere
// in the rules file. This is useful to squash spurious
// diffs that would occur if we used rule index.
rulehash := fmt.Sprintf("%02x", md5.Sum([]byte(rule)))
// split at ->
s := strings.Split(rule, "->")
if len(s) != 2 {
log.Fatalf("rule must contain exactly one arrow: %s", rule)
}
lhs := strings.TrimSpace(s[0])
result := strings.TrimSpace(s[1])
// split match into matching part and additional condition
match := lhs
cond := ""
if i := strings.Index(match, "&&"); i >= 0 {
cond = strings.TrimSpace(match[i+2:])
match = strings.TrimSpace(match[:i])
}
rulehash := rule.hash()
match, cond, result := rule.parse()
fmt.Fprintf(w, "// match: %s\n", match)
fmt.Fprintf(w, "// cond: %s\n", cond)
fmt.Fprintf(w, "// result: %s\n", result)
@ -152,6 +169,9 @@ func genRules(arch arch) {
}
genResult(w, arch, result)
fmt.Fprintf(w, "if logRewriteRules {\n")
fmt.Fprintf(w, " fmt.Println(\"rewrite %s.rules:%d\")", arch.name, rule.lineno)
fmt.Fprintf(w, "}\n")
fmt.Fprintf(w, "return true\n")
fmt.Fprintf(w, "}\n")
@ -174,23 +194,9 @@ func genRules(arch arch) {
for _, op := range ops {
fmt.Fprintf(w, "case %s:\n", blockName(op, arch))
for _, rule := range blockrules[op] {
rulehash := fmt.Sprintf("%02x", md5.Sum([]byte(rule)))
// split at ->
s := strings.Split(rule, "->")
if len(s) != 2 {
log.Fatalf("no arrow in rule %s", rule)
}
lhs := strings.TrimSpace(s[0])
result := strings.TrimSpace(s[1])
// split match into matching part and additional condition
match := lhs
cond := ""
if i := strings.Index(match, "&&"); i >= 0 {
cond = strings.TrimSpace(match[i+2:])
match = strings.TrimSpace(match[:i])
}
rulehash := rule.hash()
match, cond, result := rule.parse()
fmt.Fprintf(w, "// match: %s\n", match)
fmt.Fprintf(w, "// cond: %s\n", cond)
fmt.Fprintf(w, "// result: %s\n", result)
@ -198,7 +204,8 @@ func genRules(arch arch) {
fail := fmt.Sprintf("{\ngoto end%s\n}\n", rulehash)
fmt.Fprintf(w, "{\n")
s = split(match[1 : len(match)-1]) // remove parens, then split
s := split(match[1 : len(match)-1]) // remove parens, then split
// check match of control value
if s[1] != "nil" {
@ -268,6 +275,9 @@ func genRules(arch arch) {
fmt.Fprintln(w, "b.Likely = BranchUnknown")
}
fmt.Fprintf(w, "if logRewriteRules {\n")
fmt.Fprintf(w, " fmt.Println(\"rewrite %s.rules:%d\")", arch.name, rule.lineno)
fmt.Fprintf(w, "}\n")
fmt.Fprintf(w, "return true\n")
fmt.Fprintf(w, "}\n")

View File

@ -6,6 +6,11 @@ package ssa
import "fmt"
// Set to true to log all rewrite rules as they occur.
// This is useful for figuring out whether a rule is triggering
// and which rules are most heavily used.
const logRewriteRules = false
func applyRewrite(f *Func, rb func(*Block) bool, rv func(*Value, *Config) bool) {
// repeat rewrites until we find no more rewrites
var curb *Block

File diff suppressed because it is too large Load Diff

View File

@ -2,6 +2,8 @@
// generated with: cd gen; go run *.go
package ssa
import "fmt"
func rewriteValuegeneric(v *Value, config *Config) bool {
b := v.Block
switch v.Op {
@ -23,6 +25,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.AuxInt = c + d
if logRewriteRules {
fmt.Println("rewrite generic.rules:23")
}
return true
}
goto end8c46df6f85a11cb1d594076b0e467908
@ -46,6 +51,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.AuxInt = c + d
if logRewriteRules {
fmt.Println("rewrite generic.rules:24")
}
return true
}
goto end145c1aec793b2befff34bc8983b48a38
@ -72,6 +80,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v0.AddArg(idx)
v.AddArg(v0)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:59")
}
return true
}
goto end4894dd7b58383fee5f8a92be08437c33
@ -92,6 +103,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = x.Type
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:38")
}
return true
}
goto end1ea17710dd4dd7ba4e710e0e4c7b5a56
@ -112,6 +126,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = x.Type
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:39")
}
return true
}
goto end9a04ed536496e292c27bef4414128cbf
@ -132,6 +149,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = x.Type
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:40")
}
return true
}
goto ended44e29d5968f0f7b86972b7bf417ab3
@ -152,6 +172,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = x.Type
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:37")
}
return true
}
goto end4d92ff3ba567d9afd38fc9ca113602ad
@ -178,6 +201,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v2.Type = config.Frontend().TypeUintptr()
v2.AuxInt = int64(len(s.(string)))
v.AddArg(v2)
if logRewriteRules {
fmt.Println("rewrite generic.rules:68")
}
return true
}
goto end68cc91679848c7c30bd8b0a8ed533843
@ -197,6 +223,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = true
if logRewriteRules {
fmt.Println("rewrite generic.rules:30")
}
return true
}
goto enda503589f9b617e708a5ad3ddb047809f
@ -216,6 +245,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = true
if logRewriteRules {
fmt.Println("rewrite generic.rules:29")
}
return true
}
goto endc94ae3b97d0090257b02152e437b3e17
@ -235,6 +267,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = true
if logRewriteRules {
fmt.Println("rewrite generic.rules:28")
}
return true
}
goto end4d21cead60174989467a9c8202dbb91d
@ -254,6 +289,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = true
if logRewriteRules {
fmt.Println("rewrite generic.rules:31")
}
return true
}
goto end73dce8bba164e4f4a1dd701bf8cfb362
@ -275,6 +313,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.AddArg(y)
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:51")
}
return true
}
goto endcea7f7399afcff860c54d82230a9a934
@ -305,6 +346,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v1.Type = config.Frontend().TypeUintptr()
v1.AuxInt = 0
v.AddArg(v1)
if logRewriteRules {
fmt.Println("rewrite generic.rules:54")
}
return true
}
goto end540dc8dfbc66adcd3db2d7e819c534f6
@ -328,6 +372,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = inBounds(c, d)
if logRewriteRules {
fmt.Println("rewrite generic.rules:27")
}
return true
}
goto enddfd340bc7103ca323354aec96b113c23
@ -362,6 +409,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v1.AddArg(v2)
v1.AddArg(mem)
v.AddArg(v1)
if logRewriteRules {
fmt.Println("rewrite generic.rules:69")
}
return true
}
goto end18afa4a6fdd6d0b92ed292840898c8f6
@ -385,6 +435,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.AuxInt = c * d
if logRewriteRules {
fmt.Println("rewrite generic.rules:25")
}
return true
}
goto end7aea1048b5d1230974b97f17238380ae
@ -408,6 +461,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.AuxInt = c * d
if logRewriteRules {
fmt.Println("rewrite generic.rules:26")
}
return true
}
goto end808c190f346658bb1ad032bf37a1059f
@ -427,6 +483,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = false
if logRewriteRules {
fmt.Println("rewrite generic.rules:34")
}
return true
}
goto end192755dd3c2be992e9d3deb53794a8d2
@ -446,6 +505,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = false
if logRewriteRules {
fmt.Println("rewrite generic.rules:33")
}
return true
}
goto endeb23619fc85950a8df7b31126252c4dd
@ -465,6 +527,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = false
if logRewriteRules {
fmt.Println("rewrite generic.rules:32")
}
return true
}
goto endfc6eea780fb4056afb9e4287076da60c
@ -484,6 +549,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.Aux = nil
v.resetArgs()
v.Aux = false
if logRewriteRules {
fmt.Println("rewrite generic.rules:35")
}
return true
}
goto endcccf700d93c6d57765b80f92f7b3fa81
@ -505,6 +573,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.AddArg(y)
v.AddArg(x)
if logRewriteRules {
fmt.Println("rewrite generic.rules:52")
}
return true
}
goto end94c68f7dc30c66ed42e507e01c4e5dc7
@ -535,6 +606,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v1.Type = config.Frontend().TypeUintptr()
v1.AuxInt = 0
v.AddArg(v1)
if logRewriteRules {
fmt.Println("rewrite generic.rules:55")
}
return true
}
goto end67d723bb0f39a5c897816abcf411e5cf
@ -561,6 +635,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v1.AuxInt = t.Elem().Size()
v0.AddArg(v1)
v.AddArg(v0)
if logRewriteRules {
fmt.Println("rewrite generic.rules:60")
}
return true
}
goto endf7546737f42c76a99699f241d41f491a
@ -589,6 +666,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v0.AddArg(v1)
v.AddArg(v0)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:46")
}
return true
}
goto end6696811bf6bd45e505d24c1a15c68e70
@ -617,6 +697,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v0.AddArg(v1)
v.AddArg(v0)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:45")
}
return true
}
goto end9844ce3e290e81355493141e653e37d5
@ -638,6 +721,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.AddArg(ptr)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:44")
}
return true
}
goto end459613b83f95b65729d45c2ed663a153
@ -669,6 +755,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.AddArg(dst)
v.AddArg(src)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:65")
}
return true
}
goto end324ffb6d2771808da4267f62c854e9c8
@ -706,6 +795,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v2.AddArg(v3)
v2.AddArg(mem)
v.AddArg(v2)
if logRewriteRules {
fmt.Println("rewrite generic.rules:72")
}
return true
}
goto enddf0c5a150f4b4bf6715fd2bd4bb4cc20
@ -726,6 +818,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = len.Type
v.AddArg(len)
if logRewriteRules {
fmt.Println("rewrite generic.rules:71")
}
return true
}
goto end0d922460b7e5ca88324034f4bd6c027c
@ -746,6 +841,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v.resetArgs()
v.Type = ptr.Type
v.AddArg(ptr)
if logRewriteRules {
fmt.Println("rewrite generic.rules:70")
}
return true
}
goto end061edc5d85c73ad909089af2556d9380
@ -772,6 +870,9 @@ func rewriteValuegeneric(v *Value, config *Config) bool {
v0.AddArg(ptr)
v.AddArg(v0)
v.AddArg(mem)
if logRewriteRules {
fmt.Println("rewrite generic.rules:61")
}
return true
}
goto end16fdb45e1dd08feb36e3cc3fb5ed8935
@ -801,6 +902,9 @@ func rewriteBlockgeneric(b *Block) bool {
b.Succs = b.Succs[:1]
b.Succs[0] = yes
b.Likely = BranchUnknown
if logRewriteRules {
fmt.Println("rewrite generic.rules:74")
}
return true
}
goto end0f2bb0111a86be0436b44210dbd83a90
@ -822,6 +926,9 @@ func rewriteBlockgeneric(b *Block) bool {
b.Succs[0] = no
b.Succs[1] = yes
b.Likely *= -1
if logRewriteRules {
fmt.Println("rewrite generic.rules:76")
}
return true
}
goto endebe19c1c3c3bec068cdb2dd29ef57f96
@ -847,6 +954,9 @@ func rewriteBlockgeneric(b *Block) bool {
b.Succs = b.Succs[:1]
b.Succs[0] = yes
b.Likely = BranchUnknown
if logRewriteRules {
fmt.Println("rewrite generic.rules:77")
}
return true
}
goto end9ff0273f9b1657f4afc287562ca889f0
@ -872,6 +982,9 @@ func rewriteBlockgeneric(b *Block) bool {
b.Succs = b.Succs[:1]
b.Succs[0] = no
b.Likely = BranchUnknown
if logRewriteRules {
fmt.Println("rewrite generic.rules:78")
}
return true
}
goto endf401a4553c3c7c6bed64801da7bba076