From db87c9f2d0cc0e695bc7686bdcd04ea075b28deb Mon Sep 17 00:00:00 2001 From: "Bryan C. Mills" Date: Fri, 27 Sep 2019 13:03:07 -0400 Subject: cmd/go: do not reject internal double-dots in path elements The relative path element ".." is already rejected by the checks for leading and trailing dots. Fixes #27299 Change-Id: Ia8ab543c93288cdc0615abd6d22521d44bc56d72 Reviewed-on: https://go-review.googlesource.com/c/go/+/197720 Run-TryBot: Bryan C. Mills Reviewed-by: Jay Conrod TryBot-Result: Gobot Gobot --- src/cmd/go/internal/get/path.go | 3 --- src/cmd/go/internal/module/module.go | 3 --- src/cmd/go/internal/module/module_test.go | 3 ++- 3 files changed, 2 insertions(+), 7 deletions(-) (limited to 'src') diff --git a/src/cmd/go/internal/get/path.go b/src/cmd/go/internal/get/path.go index 67d7b8a47c..95169fa5f1 100644 --- a/src/cmd/go/internal/get/path.go +++ b/src/cmd/go/internal/get/path.go @@ -44,9 +44,6 @@ func checkPath(path string, fileName bool) error { if path[0] == '-' { return fmt.Errorf("leading dash") } - if strings.Contains(path, "..") { - return fmt.Errorf("double dot") - } if strings.Contains(path, "//") { return fmt.Errorf("double slash") } diff --git a/src/cmd/go/internal/module/module.go b/src/cmd/go/internal/module/module.go index 3d1ad27628..3b70574e23 100644 --- a/src/cmd/go/internal/module/module.go +++ b/src/cmd/go/internal/module/module.go @@ -231,9 +231,6 @@ func checkPath(path string, fileName bool) error { if path[0] == '-' { return fmt.Errorf("leading dash") } - if strings.Contains(path, "..") { - return fmt.Errorf("double dot") - } if strings.Contains(path, "//") { return fmt.Errorf("double slash") } diff --git a/src/cmd/go/internal/module/module_test.go b/src/cmd/go/internal/module/module_test.go index b9f07bf57d..2c22ee7939 100644 --- a/src/cmd/go/internal/module/module_test.go +++ b/src/cmd/go/internal/module/module_test.go @@ -80,7 +80,7 @@ var checkPathTests = []struct { {"x./z", false, false, false}, {".x/z", false, false, true}, {"-x/z", false, false, false}, - {"x..y/z", false, false, false}, + {"x..y/z", true, true, true}, {"x.y/z/../../w", false, false, false}, {"x.y//z", false, false, false}, {"x.y/z//w", false, false, false}, @@ -173,6 +173,7 @@ var checkPathTests = []struct { // When we do, we'll enable them everywhere, not just for GitHub. {"github.com/user/unicode/испытание", false, false, true}, + {".../x", false, false, false}, {"../x", false, false, false}, {"./y", false, false, false}, {"x:y", false, false, false}, -- cgit v1.3 From 683ef8c8441d100590f5ed5c9d662e217a7130ce Mon Sep 17 00:00:00 2001 From: Justin Nuß Date: Sun, 26 Nov 2017 11:05:53 +0100 Subject: html/template: document handling of namespaced and data- attributes Attributes with a namespace or a data- prefix are handled as if they had no namespace/data- prefix. There is also a special case, where attributes with a "xmlns" namespace are always treated as containing URLs. This could surprise users of the package, since this behaviour was not documented anywhere, so this change adds some documentation for all three cases. Fixes #12648 Change-Id: If57a2ec49fec91a330fc04795726e8cffa9b75c0 Reviewed-on: https://go-review.googlesource.com/c/go/+/79895 Run-TryBot: Andrew Bonventre TryBot-Result: Gobot Gobot Reviewed-by: Andrew Bonventre --- src/html/template/doc.go | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) (limited to 'src') diff --git a/src/html/template/doc.go b/src/html/template/doc.go index 290ec81b96..650e7147a3 100644 --- a/src/html/template/doc.go +++ b/src/html/template/doc.go @@ -73,6 +73,51 @@ functions. For these internal escaping functions, if an action pipeline evaluates to a nil interface value, it is treated as though it were an empty string. +Namespaced and data- attributes + +Attributes with a namespace are treated as if they had no namespace. +Given the excerpt + + + +At parse time the attribute will be treated as if it were just "href". +So at parse time the template becomes: + + + +Similarly to attributes with namespaces, attributes with a "data-" prefix are +treated as if they had no "data-" prefix. So given + + + +At parse time this becomes + + + +If an attribute has both a namespace and a "data-" prefix, only the namespace +will be removed when determining the context. For example + + + +This is handled as if "my:data-href" was just "data-href" and not "href" as +it would be if the "data-" prefix were to be ignored too. Thus at parse +time this becomes just + + + +As a special case, attributes with the namespace "xmlns" are always treated +as containing URLs. Given the excerpts + + + + + +At parse time they become: + + + + + Errors See the documentation of ErrorCode for details. -- cgit v1.3 From 95b8cbfee93766274583bacfb98b3b0cc1dbb6cf Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Mon, 23 Sep 2019 14:25:22 -0700 Subject: cmd/compile: add column details to export data This CL updates the export data format to include column details when writing out position data. cmd/compile is updated to generate and make use of the new details, but go/internal/gcimporter only knows how to read the data. It doesn't yet actually make use of it. Experimentally across a wide range of packages, this increases export data size by around 4%. However, it has no impact on binary size. (Notably, it actually shrinks k8s.io/kubernetes/cmd/kubelet's binary size by 24kB, but it's unclear to me why at this time.) Updates #28259. Change-Id: I351fb340839df8d3adced49b3757c4537fb91b3f Reviewed-on: https://go-review.googlesource.com/c/go/+/196963 Run-TryBot: Matthew Dempsky TryBot-Result: Gobot Gobot Reviewed-by: Robert Griesemer Reviewed-by: Rob Pike --- src/cmd/compile/internal/gc/iexport.go | 59 +++++++++++++++++++++------------- src/cmd/compile/internal/gc/iimport.go | 25 +++++++------- src/go/internal/gcimporter/bimport.go | 6 ++-- src/go/internal/gcimporter/iimport.go | 42 ++++++++++++++++++------ 4 files changed, 85 insertions(+), 47 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/iexport.go b/src/cmd/compile/internal/gc/iexport.go index 873de46fa4..a5acd26c7f 100644 --- a/src/cmd/compile/internal/gc/iexport.go +++ b/src/cmd/compile/internal/gc/iexport.go @@ -184,8 +184,9 @@ // } // // -// Pos encodes a file:line pair, incorporating a simple delta encoding -// scheme within a data object. See exportWriter.pos for details. +// Pos encodes a file:line:column triple, incorporating a simple delta +// encoding scheme within a data object. See exportWriter.pos for +// details. // // // Compiler-specific details. @@ -212,8 +213,9 @@ import ( ) // Current indexed export format version. Increase with each format change. +// 1: added column details to Pos // 0: Go1.11 encoding -const iexportVersion = 0 +const iexportVersion = 1 // predeclReserved is the number of type offsets reserved for types // implicitly declared in the universe block. @@ -401,10 +403,11 @@ func (p *iexporter) pushDecl(n *Node) { type exportWriter struct { p *iexporter - data intWriter - currPkg *types.Pkg - prevFile string - prevLine int64 + data intWriter + currPkg *types.Pkg + prevFile string + prevLine int64 + prevColumn int64 } func (p *iexporter) doDecl(n *Node) { @@ -510,29 +513,39 @@ func (w *exportWriter) pos(pos src.XPos) { p := Ctxt.PosTable.Pos(pos) file := p.Base().AbsFilename() line := int64(p.RelLine()) + column := int64(p.RelCol()) - // When file is the same as the last position (common case), - // we can save a few bytes by delta encoding just the line - // number. + // Encode position relative to the last position: column + // delta, then line delta, then file name. We reserve the + // bottom bit of the column and line deltas to encode whether + // the remaining fields are present. // // Note: Because data objects may be read out of order (or not // at all), we can only apply delta encoding within a single - // object. This is handled implicitly by tracking prevFile and - // prevLine as fields of exportWriter. - - if file == w.prevFile { - delta := line - w.prevLine - w.int64(delta) - if delta == deltaNewFile { - w.int64(-1) + // object. This is handled implicitly by tracking prevFile, + // prevLine, and prevColumn as fields of exportWriter. + + deltaColumn := (column - w.prevColumn) << 1 + deltaLine := (line - w.prevLine) << 1 + + if file != w.prevFile { + deltaLine |= 1 + } + if deltaLine != 0 { + deltaColumn |= 1 + } + + w.int64(deltaColumn) + if deltaColumn&1 != 0 { + w.int64(deltaLine) + if deltaLine&1 != 0 { + w.string(file) } - } else { - w.int64(deltaNewFile) - w.int64(line) // line >= 0 - w.string(file) - w.prevFile = file } + + w.prevFile = file w.prevLine = line + w.prevColumn = column } func (w *exportWriter) pkg(pkg *types.Pkg) { diff --git a/src/cmd/compile/internal/gc/iimport.go b/src/cmd/compile/internal/gc/iimport.go index 28808c51c5..64c554d187 100644 --- a/src/cmd/compile/internal/gc/iimport.go +++ b/src/cmd/compile/internal/gc/iimport.go @@ -242,9 +242,10 @@ type importReader struct { strings.Reader p *iimporter - currPkg *types.Pkg - prevBase *src.PosBase - prevLine int64 + currPkg *types.Pkg + prevBase *src.PosBase + prevLine int64 + prevColumn int64 } func (p *iimporter) newReader(off uint64, pkg *types.Pkg) *importReader { @@ -446,16 +447,16 @@ func (r *importReader) qualifiedIdent() *types.Sym { func (r *importReader) pos() src.XPos { delta := r.int64() - if delta != deltaNewFile { - r.prevLine += delta - } else if l := r.int64(); l == -1 { - r.prevLine += deltaNewFile - } else { - r.prevBase = r.posBase() - r.prevLine = l + r.prevColumn += delta >> 1 + if delta&1 != 0 { + delta = r.int64() + r.prevLine += delta >> 1 + if delta&1 != 0 { + r.prevBase = r.posBase() + } } - if (r.prevBase == nil || r.prevBase.AbsFilename() == "") && r.prevLine == 0 { + if (r.prevBase == nil || r.prevBase.AbsFilename() == "") && r.prevLine == 0 && r.prevColumn == 0 { // TODO(mdempsky): Remove once we reliably write // position information for all nodes. return src.NoXPos @@ -464,7 +465,7 @@ func (r *importReader) pos() src.XPos { if r.prevBase == nil { Fatalf("missing posbase") } - pos := src.MakePos(r.prevBase, uint(r.prevLine), 0) + pos := src.MakePos(r.prevBase, uint(r.prevLine), uint(r.prevColumn)) return Ctxt.PosTable.XPos(pos) } diff --git a/src/go/internal/gcimporter/bimport.go b/src/go/internal/gcimporter/bimport.go index cf03632aa2..1019ccb8f7 100644 --- a/src/go/internal/gcimporter/bimport.go +++ b/src/go/internal/gcimporter/bimport.go @@ -328,7 +328,7 @@ func (p *importer) pos() token.Pos { p.prevFile = file p.prevLine = line - return p.fake.pos(file, line) + return p.fake.pos(file, line, 0) } // Synthesize a token.Pos @@ -337,7 +337,9 @@ type fakeFileSet struct { files map[string]*token.File } -func (s *fakeFileSet) pos(file string, line int) token.Pos { +func (s *fakeFileSet) pos(file string, line, column int) token.Pos { + // TODO(mdempsky): Make use of column. + // Since we don't know the set of needed file positions, we // reserve maxlines positions per file. const maxlines = 64 * 1024 diff --git a/src/go/internal/gcimporter/iimport.go b/src/go/internal/gcimporter/iimport.go index bf480641df..c59dd16533 100644 --- a/src/go/internal/gcimporter/iimport.go +++ b/src/go/internal/gcimporter/iimport.go @@ -61,8 +61,8 @@ const ( // If the export data version is not recognized or the format is otherwise // compromised, an error is returned. func iImportData(fset *token.FileSet, imports map[string]*types.Package, data []byte, path string) (_ int, pkg *types.Package, err error) { - const currentVersion = 0 - version := -1 + const currentVersion = 1 + version := int64(-1) defer func() { if e := recover(); e != nil { if version > currentVersion { @@ -75,9 +75,9 @@ func iImportData(fset *token.FileSet, imports map[string]*types.Package, data [] r := &intReader{bytes.NewReader(data), path} - version = int(r.uint64()) + version = int64(r.uint64()) switch version { - case currentVersion: + case currentVersion, 0: default: errorf("unknown iexport format version %d", version) } @@ -91,7 +91,8 @@ func iImportData(fset *token.FileSet, imports map[string]*types.Package, data [] r.Seek(sLen+dLen, io.SeekCurrent) p := iimporter{ - ipath: path, + ipath: path, + version: int(version), stringData: stringData, stringCache: make(map[uint64]string), @@ -169,7 +170,8 @@ func iImportData(fset *token.FileSet, imports map[string]*types.Package, data [] } type iimporter struct { - ipath string + ipath string + version int stringData []byte stringCache map[uint64]string @@ -249,6 +251,7 @@ type importReader struct { currPkg *types.Package prevFile string prevLine int64 + prevColumn int64 } func (r *importReader) obj(name string) { @@ -438,6 +441,19 @@ func (r *importReader) qualifiedIdent() (*types.Package, string) { } func (r *importReader) pos() token.Pos { + if r.p.version >= 1 { + r.posv1() + } else { + r.posv0() + } + + if r.prevFile == "" && r.prevLine == 0 && r.prevColumn == 0 { + return token.NoPos + } + return r.p.fake.pos(r.prevFile, int(r.prevLine), int(r.prevColumn)) +} + +func (r *importReader) posv0() { delta := r.int64() if delta != deltaNewFile { r.prevLine += delta @@ -447,12 +463,18 @@ func (r *importReader) pos() token.Pos { r.prevFile = r.string() r.prevLine = l } +} - if r.prevFile == "" && r.prevLine == 0 { - return token.NoPos +func (r *importReader) posv1() { + delta := r.int64() + r.prevColumn += delta >> 1 + if delta&1 != 0 { + delta = r.int64() + r.prevLine += delta >> 1 + if delta&1 != 0 { + r.prevFile = r.string() + } } - - return r.p.fake.pos(r.prevFile, int(r.prevLine)) } func (r *importReader) typ() types.Type { -- cgit v1.3 From bdf0fe54480034cd21e36cfed6e44f10f4cb5c92 Mon Sep 17 00:00:00 2001 From: Daniel Martí Date: Mon, 23 Sep 2019 23:10:25 +0100 Subject: cmd/compile: minor simplifications in rulegen MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit First, be consistent about declaring typ as &b.Func.Config.Types and not &config.Types. Not particularly better, and it barely changes the output, but we're more consistent now. Second, remove a bit of duplication when handling the typ, auxint, and aux variables. Third and last, remove a stray canFail assignment; we ended up setting that in add, not breakf, so it's not necessary to set it manually if we don't use breakf. Updates #33644. Change-Id: I75999cb223a201969266fbfeae043599fa27fac5 Reviewed-on: https://go-review.googlesource.com/c/go/+/196803 Run-TryBot: Daniel Martí Reviewed-by: Keith Randall TryBot-Result: Gobot Gobot --- src/cmd/compile/internal/ssa/gen/rulegen.go | 34 +++++++++++----------------- src/cmd/compile/internal/ssa/rewriteS390X.go | 3 +-- 2 files changed, 14 insertions(+), 23 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/gen/rulegen.go b/src/cmd/compile/internal/ssa/gen/rulegen.go index 994e5b932f..7c02778181 100644 --- a/src/cmd/compile/internal/ssa/gen/rulegen.go +++ b/src/cmd/compile/internal/ssa/gen/rulegen.go @@ -237,7 +237,7 @@ func genRulesSuffix(arch arch, suff string) { // so we can make this one function with a switch. fn = &Func{kind: "Block"} fn.add(declf("config", "b.Func.Config")) - fn.add(declf("typ", "&config.Types")) + fn.add(declf("typ", "&b.Func.Config.Types")) fn.add(declf("v", "b.Control")) sw = &Switch{expr: exprf("b.Kind")} @@ -851,28 +851,21 @@ func genMatch0(rr *RuleRewrite, arch arch, match, v string) (pos, checkOp string pos = v + ".Pos" } - if typ != "" { - if !token.IsIdentifier(typ) || rr.declared(typ) { - // code or variable - rr.add(breakf("%s.Type != %s", v, typ)) - } else { - rr.add(declf(typ, "%s.Type", v)) - } - } - if auxint != "" { - if !token.IsIdentifier(auxint) || rr.declared(auxint) { - // code or variable - rr.add(breakf("%s.AuxInt != %s", v, auxint)) - } else { - rr.add(declf(auxint, "%s.AuxInt", v)) + for _, e := range []struct { + name, field string + }{ + {typ, "Type"}, + {auxint, "AuxInt"}, + {aux, "Aux"}, + } { + if e.name == "" { + continue } - } - if aux != "" { - if !token.IsIdentifier(aux) || rr.declared(aux) { + if !token.IsIdentifier(e.name) || rr.declared(e.name) { // code or variable - rr.add(breakf("%s.Aux != %s", v, aux)) + rr.add(breakf("%s.%s != %s", v, e.field, e.name)) } else { - rr.add(declf(aux, "%s.Aux", v)) + rr.add(declf(e.name, "%s.%s", v, e.field)) } } @@ -921,7 +914,6 @@ func genMatch0(rr *RuleRewrite, arch arch, match, v string) (pos, checkOp string rr.add(declf(argname, "%s.Args[%d]", v, i)) bexpr := exprf("%s.Op != addLater", argname) rr.add(&CondBreak{expr: bexpr}) - rr.canFail = true // since we're not using breakf argPos, argCheckOp := genMatch0(rr, arch, arg, argname) bexpr.(*ast.BinaryExpr).Y.(*ast.Ident).Name = argCheckOp diff --git a/src/cmd/compile/internal/ssa/rewriteS390X.go b/src/cmd/compile/internal/ssa/rewriteS390X.go index ac2fbf80b8..84fe1473c0 100644 --- a/src/cmd/compile/internal/ssa/rewriteS390X.go +++ b/src/cmd/compile/internal/ssa/rewriteS390X.go @@ -36448,8 +36448,7 @@ func rewriteValueS390X_OpZeroExt8to64_0(v *Value) bool { } } func rewriteBlockS390X(b *Block) bool { - config := b.Func.Config - typ := &config.Types + typ := &b.Func.Config.Types v := b.Control switch b.Kind { case BlockS390XBRC: -- cgit v1.3 From 739bf6b929b66ac1715268e269da01c8199f034b Mon Sep 17 00:00:00 2001 From: Hasit Bhatt Date: Wed, 25 Sep 2019 00:02:29 +0530 Subject: cmd: update x/tools version to enforce only one %w As mentioned in https://golang.org/issue/34062#issuecomment-529692313 src/cmd refers to older version of golang.org/x/tools. Hence, not checking if multiple errors are used in the same fmt.Errorf. Updating golang.org/x/tools version to latest in src/cmd. Fixes #34062 Change-Id: I358dec2c3d3af2b19add766b8488b919109b81d6 Reviewed-on: https://go-review.googlesource.com/c/go/+/196843 Run-TryBot: Michael Matloob TryBot-Result: Gobot Gobot Reviewed-by: Michael Matloob --- src/cmd/go.mod | 2 +- src/cmd/go.sum | 8 +-- .../golang.org/x/tools/go/analysis/analysis.go | 21 ++---- .../golang.org/x/tools/go/analysis/diagnostic.go | 48 ++++++++++++++ .../vendor/golang.org/x/tools/go/analysis/doc.go | 16 ++--- .../go/analysis/internal/analysisflags/flags.go | 6 +- .../x/tools/go/analysis/internal/facts/facts.go | 22 ++++++- .../x/tools/go/analysis/passes/assign/assign.go | 10 ++- .../x/tools/go/analysis/passes/cgocall/cgocall.go | 4 +- .../go/analysis/passes/composite/whitelist.go | 1 + .../tools/go/analysis/passes/ctrlflow/ctrlflow.go | 9 +-- .../tools/go/analysis/passes/errorsas/errorsas.go | 2 +- .../x/tools/go/analysis/passes/printf/printf.go | 76 +++++++++++++++------- .../x/tools/go/analysis/passes/printf/types.go | 8 ++- .../go/analysis/passes/structtag/structtag.go | 6 +- .../x/tools/go/analysis/unitchecker/unitchecker.go | 8 +++ .../golang.org/x/tools/go/analysis/validate.go | 2 +- .../vendor/golang.org/x/tools/go/cfg/builder.go | 2 +- .../x/tools/go/types/objectpath/objectpath.go | 2 +- src/cmd/vendor/modules.txt | 2 +- src/fmt/errors_test.go | 10 ++- 21 files changed, 189 insertions(+), 76 deletions(-) create mode 100644 src/cmd/vendor/golang.org/x/tools/go/analysis/diagnostic.go (limited to 'src') diff --git a/src/cmd/go.mod b/src/cmd/go.mod index 19496a3c67..d8172ad2f5 100644 --- a/src/cmd/go.mod +++ b/src/cmd/go.mod @@ -8,5 +8,5 @@ require ( golang.org/x/arch v0.0.0-20190815191158-8a70ba74b3a1 golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82 // indirect - golang.org/x/tools v0.0.0-20190611154301-25a4f137592f + golang.org/x/tools v0.0.0-20190925211824-e4ea94538f5b ) diff --git a/src/cmd/go.sum b/src/cmd/go.sum index 9aa94eee7b..7c3ee7304b 100644 --- a/src/cmd/go.sum +++ b/src/cmd/go.sum @@ -7,14 +7,14 @@ golang.org/x/arch v0.0.0-20190815191158-8a70ba74b3a1/go.mod h1:flIaEI6LNU6xOCD5P golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c h1:Vj5n4GlwjmQteupaxJ9+0FNOmBrHfq7vN4btdGoDZgI= golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= -golang.org/x/net v0.0.0-20190311183353-d8887717615a h1:oWX7TPOiFAMXLq8o0ikBYfCJVlRHBcsciT5bXOrH628= -golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82 h1:vsphBvatvfbhlb4PO1BYSr9dzugGxJ/SQHoNufZJq1w= golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= -golang.org/x/tools v0.0.0-20190611154301-25a4f137592f h1:6awn5JC4pwVI5HiBqs7MDtRxnwV9PpO5iSA9v6P09pA= -golang.org/x/tools v0.0.0-20190611154301-25a4f137592f/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= +golang.org/x/tools v0.0.0-20190925211824-e4ea94538f5b h1:gyG4T6EqWG9fqSgT0VbHhzp8bHbFux5mvlgz1gUkEaQ= +golang.org/x/tools v0.0.0-20190925211824-e4ea94538f5b/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= rsc.io/pdf v0.1.1/go.mod h1:n8OzWcQ6Sp37PL01nO98y4iUCRdTGarVfzxY20ICaU4= diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/analysis.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/analysis.go index 19e1e421a3..bc58c31c9f 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/analysis.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/analysis.go @@ -128,11 +128,13 @@ type Pass struct { // See comments for ExportObjectFact. ExportPackageFact func(fact Fact) - // AllPackageFacts returns a new slice containing all package facts in unspecified order. + // AllPackageFacts returns a new slice containing all package facts of the analysis's FactTypes + // in unspecified order. // WARNING: This is an experimental API and may change in the future. AllPackageFacts func() []PackageFact - // AllObjectFacts returns a new slice containing all object facts in unspecified order. + // AllObjectFacts returns a new slice containing all object facts of the analysis's FactTypes + // in unspecified order. // WARNING: This is an experimental API and may change in the future. AllObjectFacts func() []ObjectFact @@ -211,18 +213,3 @@ func (pass *Pass) String() string { type Fact interface { AFact() // dummy method to avoid type errors } - -// A Diagnostic is a message associated with a source location or range. -// -// An Analyzer may return a variety of diagnostics; the optional Category, -// which should be a constant, may be used to classify them. -// It is primarily intended to make it easy to look up documentation. -// -// If End is provided, the diagnostic is specified to apply to the range between -// Pos and End. -type Diagnostic struct { - Pos token.Pos - End token.Pos // optional - Category string // optional - Message string -} diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/diagnostic.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/diagnostic.go new file mode 100644 index 0000000000..744072cd79 --- /dev/null +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/diagnostic.go @@ -0,0 +1,48 @@ +package analysis + +import "go/token" + +// A Diagnostic is a message associated with a source location or range. +// +// An Analyzer may return a variety of diagnostics; the optional Category, +// which should be a constant, may be used to classify them. +// It is primarily intended to make it easy to look up documentation. +// +// If End is provided, the diagnostic is specified to apply to the range between +// Pos and End. +type Diagnostic struct { + Pos token.Pos + End token.Pos // optional + Category string // optional + Message string + + // SuggestedFixes contains suggested fixes for a diagnostic which can be used to perform + // edits to a file that address the diagnostic. + // TODO(matloob): Should multiple SuggestedFixes be allowed for a diagnostic? + // Diagnostics should not contain SuggestedFixes that overlap. + // Experimental: This API is experimental and may change in the future. + SuggestedFixes []SuggestedFix // optional +} + +// A SuggestedFix is a code change associated with a Diagnostic that a user can choose +// to apply to their code. Usually the SuggestedFix is meant to fix the issue flagged +// by the diagnostic. +// TextEdits for a SuggestedFix should not overlap. TextEdits for a SuggestedFix +// should not contain edits for other packages. +// Experimental: This API is experimental and may change in the future. +type SuggestedFix struct { + // A description for this suggested fix to be shown to a user deciding + // whether to accept it. + Message string + TextEdits []TextEdit +} + +// A TextEdit represents the replacement of the code between Pos and End with the new text. +// Each TextEdit should apply to a single file. End should not be earlier in the file than Pos. +// Experimental: This API is experimental and may change in the future. +type TextEdit struct { + // For a pure insertion, End can either be set to Pos or token.NoPos. + Pos token.Pos + End token.Pos + NewText []byte +} diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/doc.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/doc.go index 2d44b0458a..a2353fc88b 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/doc.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/doc.go @@ -67,7 +67,7 @@ To add a new Analyzer to an existing driver, add another item to the list: } A driver may use the name, flags, and documentation to provide on-line -help that describes the analyses its performs. +help that describes the analyses it performs. The doc comment contains a brief one-line summary, optionally followed by paragraphs of explanation. The vet command, shown below, is an example of a driver that runs @@ -169,7 +169,7 @@ type information, and source positions for a single package of Go code. The OtherFiles field provides the names, but not the contents, of non-Go files such as assembly that are part of this package. See the "asmdecl" -or "buildtags" analyzers for examples of loading non-Go files and report +or "buildtags" analyzers for examples of loading non-Go files and reporting diagnostics against them. The ResultOf field provides the results computed by the analyzers @@ -231,7 +231,7 @@ understood as alternative or non-standard type systems. For example, vet's printf checker infers whether a function has the "printf wrapper" type, and it applies stricter checks to calls of such functions. In addition, it records which functions are printf wrappers for use by -later analysis units to identify other printf wrappers by induction. +later analysis passes to identify other printf wrappers by induction. A result such as “f is a printf wrapper” that is not interesting by itself but serves as a stepping stone to an interesting result (such as a diagnostic) is called a "fact". @@ -252,9 +252,9 @@ An Analyzer that uses facts must declare their types: type isWrapper struct{} // => *types.Func f “is a printf wrapper” -A driver program ensures that facts for a pass’s dependencies are -generated before analyzing the pass and are responsible for propagating -facts between from one pass to another, possibly across address spaces. +The driver program ensures that facts for a pass’s dependencies are +generated before analyzing the package and is responsible for propagating +facts from one package to another, possibly across address spaces. Consequently, Facts must be serializable. The API requires that drivers use the gob encoding, an efficient, robust, self-describing binary protocol. A fact type may implement the GobEncoder/GobDecoder interfaces @@ -288,10 +288,10 @@ not currently apply analyzers to packages of the standard library. Therefore, for best results, analyzer authors should not rely on analysis facts being available for standard packages. For example, although the printf checker is capable of deducing during -analysis of the log package that log.Printf is a printf-wrapper, +analysis of the log package that log.Printf is a printf wrapper, this fact is built in to the analyzer so that it correctly checks calls to log.Printf even when run in a driver that does not apply -it to standard packages. We plan to remove this limitation in future. +it to standard packages. We would like to remove this limitation in future. Testing an Analyzer diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/analysisflags/flags.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/analysisflags/flags.go index a3c2f09630..0778f42207 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/analysisflags/flags.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/analysisflags/flags.go @@ -168,10 +168,10 @@ func printFlags() { var flags []jsonFlag = nil flag.VisitAll(func(f *flag.Flag) { // Don't report {single,multi}checker debugging - // flags as these have no effect on unitchecker + // flags or fix as these have no effect on unitchecker // (as invoked by 'go vet'). switch f.Name { - case "debug", "cpuprofile", "memprofile", "trace": + case "debug", "cpuprofile", "memprofile", "trace", "fix": return } @@ -209,7 +209,7 @@ func (versionFlag) Set(s string) error { log.Fatalf("unsupported flag value: -V=%s", s) } - // This replicates the miminal subset of + // This replicates the minimal subset of // cmd/internal/objabi.AddVersionFlag, which is private to the // go tool yet forms part of our command-line interface. // TODO(adonovan): clarify the contract. diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/facts/facts.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/facts/facts.go index 468f148900..07984521c3 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/facts/facts.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/internal/facts/facts.go @@ -29,7 +29,7 @@ // The notion of "exportedness" that matters here is that of the // compiler. According to the language spec, a method pkg.T.f is // unexported simply because its name starts with lowercase. But the -// compiler must nonethless export f so that downstream compilations can +// compiler must nonetheless export f so that downstream compilations can // accurately ascertain whether pkg.T implements an interface pkg.I // defined as interface{f()}. Exported thus means "described in export // data". @@ -99,6 +99,16 @@ func (s *Set) ExportObjectFact(obj types.Object, fact analysis.Fact) { s.mu.Unlock() } +func (s *Set) AllObjectFacts(filter map[reflect.Type]bool) []analysis.ObjectFact { + var facts []analysis.ObjectFact + for k, v := range s.m { + if k.obj != nil && filter[k.t] { + facts = append(facts, analysis.ObjectFact{Object: k.obj, Fact: v}) + } + } + return facts +} + // ImportPackageFact implements analysis.Pass.ImportPackageFact. func (s *Set) ImportPackageFact(pkg *types.Package, ptr analysis.Fact) bool { if pkg == nil { @@ -122,6 +132,16 @@ func (s *Set) ExportPackageFact(fact analysis.Fact) { s.mu.Unlock() } +func (s *Set) AllPackageFacts(filter map[reflect.Type]bool) []analysis.PackageFact { + var facts []analysis.PackageFact + for k, v := range s.m { + if k.obj == nil && filter[k.t] { + facts = append(facts, analysis.PackageFact{Package: k.pkg, Fact: v}) + } + } + return facts +} + // gobFact is the Gob declaration of a serialized fact. type gobFact struct { PkgPath string // path of package diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/assign/assign.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/assign/assign.go index 4dff2908c3..3586638efc 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/assign/assign.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/assign/assign.go @@ -9,6 +9,7 @@ package assign // methods that are on T instead of *T. import ( + "fmt" "go/ast" "go/token" "reflect" @@ -59,7 +60,14 @@ func run(pass *analysis.Pass) (interface{}, error) { le := analysisutil.Format(pass.Fset, lhs) re := analysisutil.Format(pass.Fset, rhs) if le == re { - pass.Reportf(stmt.Pos(), "self-assignment of %s to %s", re, le) + pass.Report(analysis.Diagnostic{ + Pos: stmt.Pos(), Message: fmt.Sprintf("self-assignment of %s to %s", re, le), + SuggestedFixes: []analysis.SuggestedFix{ + {Message: "Remove", TextEdits: []analysis.TextEdit{ + {Pos: stmt.Pos(), End: stmt.End(), NewText: []byte{}}, + }}, + }, + }) } } }) diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/cgocall/cgocall.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/cgocall/cgocall.go index 1e4fac8595..d499f3c329 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/cgocall/cgocall.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/cgocall/cgocall.go @@ -107,7 +107,7 @@ func checkCgo(fset *token.FileSet, f *ast.File, info *types.Info, reportf func(t // cgo files of a package (those that import "C"). Such files are not // Go, so there may be gaps in type information around C.f references. // -// This checker was initially written in vet to inpect raw cgo source +// This checker was initially written in vet to inspect raw cgo source // files using partial type information. However, Analyzers in the new // analysis API are presented with the type-checked, "cooked" Go ASTs // resulting from cgo-processing files, so we must choose between @@ -133,7 +133,7 @@ func checkCgo(fset *token.FileSet, f *ast.File, info *types.Info, reportf func(t // func (T) f(int) string { ... } // // we synthesize a new ast.File, shown below, that dot-imports the -// orginal "cooked" package using a special name ("·this·"), so that all +// original "cooked" package using a special name ("·this·"), so that all // references to package members resolve correctly. (References to // unexported names cause an "unexported" error, which we ignore.) // diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/composite/whitelist.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/composite/whitelist.go index ab609f279b..1e5f5fd20b 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/composite/whitelist.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/composite/whitelist.go @@ -24,6 +24,7 @@ var unkeyedLiteral = map[string]bool{ "image.Uniform": true, "unicode.Range16": true, + "unicode.Range32": true, // These three structs are used in generated test main files, // but the generator can be trusted. diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/ctrlflow/ctrlflow.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/ctrlflow/ctrlflow.go index 75655c5bad..51600ffc7e 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/ctrlflow/ctrlflow.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/ctrlflow/ctrlflow.go @@ -102,10 +102,11 @@ func run(pass *analysis.Pass) (interface{}, error) { inspect.Preorder(nodeFilter, func(n ast.Node) { switch n := n.(type) { case *ast.FuncDecl: - fn := pass.TypesInfo.Defs[n.Name].(*types.Func) - funcDecls[fn] = &declInfo{decl: n} - decls = append(decls, fn) - + // Type information may be incomplete. + if fn, ok := pass.TypesInfo.Defs[n.Name].(*types.Func); ok { + funcDecls[fn] = &declInfo{decl: n} + decls = append(decls, fn) + } case *ast.FuncLit: funcLits[n] = new(litInfo) lits = append(lits, n) diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/errorsas/errorsas.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/errorsas/errorsas.go index c411466c28..01abc70017 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/errorsas/errorsas.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/errorsas/errorsas.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// The errorsas package defines an Analyzer that checks that the second arugment to +// The errorsas package defines an Analyzer that checks that the second argument to // errors.As is a pointer to a type implementing error. package errorsas diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/printf.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/printf.go index f59e95dc21..f0d7e44c65 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/printf.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/printf.go @@ -67,15 +67,20 @@ of arguments with no format string. ` // isWrapper is a fact indicating that a function is a print or printf wrapper. -type isWrapper struct{ Printf bool } +type isWrapper struct{ Kind funcKind } func (f *isWrapper) AFact() {} func (f *isWrapper) String() string { - if f.Printf { + switch f.Kind { + case kindPrintf: return "printfWrapper" - } else { + case kindPrint: return "printWrapper" + case kindErrorf: + return "errorfWrapper" + default: + return "unknownWrapper" } } @@ -112,7 +117,11 @@ func maybePrintfWrapper(info *types.Info, decl ast.Decl) *printfWrapper { if !ok || fdecl.Body == nil { return nil } - fn := info.Defs[fdecl.Name].(*types.Func) + fn, ok := info.Defs[fdecl.Name].(*types.Func) + // Type information may be incomplete. + if !ok { + return nil + } sig := fn.Type().(*types.Signature) if !sig.Variadic() { @@ -223,16 +232,20 @@ func match(info *types.Info, arg ast.Expr, param *types.Var) bool { return ok && info.ObjectOf(id) == param } +type funcKind int + const ( - kindPrintf = 1 - kindPrint = 2 + kindUnknown funcKind = iota + kindPrintf = iota + kindPrint + kindErrorf ) // checkPrintfFwd checks that a printf-forwarding wrapper is forwarding correctly. // It diagnoses writing fmt.Printf(format, args) instead of fmt.Printf(format, args...). -func checkPrintfFwd(pass *analysis.Pass, w *printfWrapper, call *ast.CallExpr, kind int) { +func checkPrintfFwd(pass *analysis.Pass, w *printfWrapper, call *ast.CallExpr, kind funcKind) { matched := kind == kindPrint || - kind == kindPrintf && len(call.Args) >= 2 && match(pass.TypesInfo, call.Args[len(call.Args)-2], w.format) + kind != kindUnknown && len(call.Args) >= 2 && match(pass.TypesInfo, call.Args[len(call.Args)-2], w.format) if !matched { return } @@ -262,7 +275,7 @@ func checkPrintfFwd(pass *analysis.Pass, w *printfWrapper, call *ast.CallExpr, k fn := w.obj var fact isWrapper if !pass.ImportObjectFact(fn, &fact) { - fact.Printf = kind == kindPrintf + fact.Kind = kind pass.ExportObjectFact(fn, &fact) for _, caller := range w.callers { checkPrintfFwd(pass, caller.w, caller.call, kind) @@ -414,42 +427,42 @@ func checkCall(pass *analysis.Pass) { call := n.(*ast.CallExpr) fn, kind := printfNameAndKind(pass, call) switch kind { - case kindPrintf: - checkPrintf(pass, call, fn) + case kindPrintf, kindErrorf: + checkPrintf(pass, kind, call, fn) case kindPrint: checkPrint(pass, call, fn) } }) } -func printfNameAndKind(pass *analysis.Pass, call *ast.CallExpr) (fn *types.Func, kind int) { +func printfNameAndKind(pass *analysis.Pass, call *ast.CallExpr) (fn *types.Func, kind funcKind) { fn, _ = typeutil.Callee(pass.TypesInfo, call).(*types.Func) if fn == nil { return nil, 0 } - var fact isWrapper - if pass.ImportObjectFact(fn, &fact) { - if fact.Printf { - return fn, kindPrintf - } else { - return fn, kindPrint - } - } - _, ok := isPrint[fn.FullName()] if !ok { // Next look up just "printf", for use with -printf.funcs. _, ok = isPrint[strings.ToLower(fn.Name())] } if ok { - if strings.HasSuffix(fn.Name(), "f") { + if fn.Name() == "Errorf" { + kind = kindErrorf + } else if strings.HasSuffix(fn.Name(), "f") { kind = kindPrintf } else { kind = kindPrint } + return fn, kind + } + + var fact isWrapper + if pass.ImportObjectFact(fn, &fact) { + return fn, fact.Kind } - return fn, kind + + return fn, kindUnknown } // isFormatter reports whether t satisfies fmt.Formatter. @@ -491,7 +504,7 @@ type formatState struct { } // checkPrintf checks a call to a formatted print routine such as Printf. -func checkPrintf(pass *analysis.Pass, call *ast.CallExpr, fn *types.Func) { +func checkPrintf(pass *analysis.Pass, kind funcKind, call *ast.CallExpr, fn *types.Func) { format, idx := formatString(pass, call) if idx < 0 { if false { @@ -511,6 +524,7 @@ func checkPrintf(pass *analysis.Pass, call *ast.CallExpr, fn *types.Func) { argNum := firstArg maxArgNum := firstArg anyIndex := false + anyW := false for i, w := 0, 0; i < len(format); i += w { w = 1 if format[i] != '%' { @@ -527,6 +541,17 @@ func checkPrintf(pass *analysis.Pass, call *ast.CallExpr, fn *types.Func) { if state.hasIndex { anyIndex = true } + if state.verb == 'w' { + if kind != kindErrorf { + pass.Reportf(call.Pos(), "%s call has error-wrapping directive %%w", state.name) + return + } + if anyW { + pass.Reportf(call.Pos(), "%s call has more than one error-wrapping directive %%w", state.name) + return + } + anyW = true + } if len(state.argNums) > 0 { // Continue with the next sequential argument. argNum = state.argNums[len(state.argNums)-1] + 1 @@ -697,6 +722,7 @@ const ( argFloat argComplex argPointer + argError anyType printfArgType = ^0 ) @@ -739,7 +765,7 @@ var printVerbs = []printVerb{ {'T', "-", anyType}, {'U', "-#", argRune | argInt}, {'v', allFlags, anyType}, - {'w', noFlag, anyType}, + {'w', allFlags, argError}, {'x', sharpNumFlag, argRune | argInt | argString | argPointer}, {'X', sharpNumFlag, argRune | argInt | argString | argPointer}, } diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/types.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/types.go index 12286fd5df..bd8a594ef5 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/types.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/printf/types.go @@ -37,6 +37,12 @@ func matchArgTypeInternal(pass *analysis.Pass, t printfArgType, typ types.Type, return true // probably a type check problem } } + + // %w accepts only errors. + if t == argError { + return types.ConvertibleTo(typ, errorType) + } + // If the type implements fmt.Formatter, we have nothing to check. if isFormatter(typ) { return true @@ -228,7 +234,7 @@ func matchStructArgType(pass *analysis.Pass, t printfArgType, typ *types.Struct, return false } if t&argString != 0 && !typf.Exported() && isConvertibleToString(pass, typf.Type()) { - // Issue #17798: unexported Stringer or error cannot be properly fomatted. + // Issue #17798: unexported Stringer or error cannot be properly formatted. return false } } diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/structtag/structtag.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/structtag/structtag.go index acc6e6c770..e09160379f 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/structtag/structtag.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/passes/structtag/structtag.go @@ -40,7 +40,11 @@ func run(pass *analysis.Pass) (interface{}, error) { (*ast.StructType)(nil), } inspect.Preorder(nodeFilter, func(n ast.Node) { - styp := pass.TypesInfo.Types[n.(*ast.StructType)].Type.(*types.Struct) + styp, ok := pass.TypesInfo.Types[n.(*ast.StructType)].Type.(*types.Struct) + // Type information may be incomplete. + if !ok { + return + } var seen namesSeen for i := 0; i < styp.NumFields(); i++ { field := styp.Field(i) diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/unitchecker/unitchecker.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/unitchecker/unitchecker.go index ba2e66fed2..2ed274949b 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/unitchecker/unitchecker.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/unitchecker/unitchecker.go @@ -42,6 +42,7 @@ import ( "log" "os" "path/filepath" + "reflect" "sort" "strings" "sync" @@ -322,6 +323,11 @@ func run(fset *token.FileSet, cfg *Config, analyzers []*analysis.Analyzer) ([]re return } + factFilter := make(map[reflect.Type]bool) + for _, f := range a.FactTypes { + factFilter[reflect.TypeOf(f)] = true + } + pass := &analysis.Pass{ Analyzer: a, Fset: fset, @@ -334,8 +340,10 @@ func run(fset *token.FileSet, cfg *Config, analyzers []*analysis.Analyzer) ([]re Report: func(d analysis.Diagnostic) { act.diagnostics = append(act.diagnostics, d) }, ImportObjectFact: facts.ImportObjectFact, ExportObjectFact: facts.ExportObjectFact, + AllObjectFacts: func() []analysis.ObjectFact { return facts.AllObjectFacts(factFilter) }, ImportPackageFact: facts.ImportPackageFact, ExportPackageFact: facts.ExportPackageFact, + AllPackageFacts: func() []analysis.PackageFact { return facts.AllPackageFacts(factFilter) }, } t0 := time.Now() diff --git a/src/cmd/vendor/golang.org/x/tools/go/analysis/validate.go b/src/cmd/vendor/golang.org/x/tools/go/analysis/validate.go index 6e6cf4984f..b984ab6c2d 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/analysis/validate.go +++ b/src/cmd/vendor/golang.org/x/tools/go/analysis/validate.go @@ -10,7 +10,7 @@ import ( // Checks include: // that the name is a valid identifier; // that analyzer names are unique; -// that the Requires graph is acylic; +// that the Requires graph is acyclic; // that analyzer fact types are unique; // that each fact type is a pointer. func Validate(analyzers []*Analyzer) error { diff --git a/src/cmd/vendor/golang.org/x/tools/go/cfg/builder.go b/src/cmd/vendor/golang.org/x/tools/go/cfg/builder.go index 24e1aba033..7f95a2961a 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/cfg/builder.go +++ b/src/cmd/vendor/golang.org/x/tools/go/cfg/builder.go @@ -149,7 +149,7 @@ func (b *builder) branchStmt(s *ast.BranchStmt) { } case token.FALLTHROUGH: - for t := b.targets; t != nil; t = t.tail { + for t := b.targets; t != nil && block == nil; t = t.tail { block = t._fallthrough } diff --git a/src/cmd/vendor/golang.org/x/tools/go/types/objectpath/objectpath.go b/src/cmd/vendor/golang.org/x/tools/go/types/objectpath/objectpath.go index 0d85488efb..882e3b3d8a 100644 --- a/src/cmd/vendor/golang.org/x/tools/go/types/objectpath/objectpath.go +++ b/src/cmd/vendor/golang.org/x/tools/go/types/objectpath/objectpath.go @@ -376,7 +376,7 @@ func Object(pkg *types.Package, p Path) (types.Object, error) { return nil, fmt.Errorf("package %s does not contain %q", pkg.Path(), pkgobj) } - // abtraction of *types.{Pointer,Slice,Array,Chan,Map} + // abstraction of *types.{Pointer,Slice,Array,Chan,Map} type hasElem interface { Elem() types.Type } diff --git a/src/cmd/vendor/modules.txt b/src/cmd/vendor/modules.txt index e873ad4455..43f539fd81 100644 --- a/src/cmd/vendor/modules.txt +++ b/src/cmd/vendor/modules.txt @@ -26,7 +26,7 @@ golang.org/x/crypto/ssh/terminal # golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82 golang.org/x/sys/unix golang.org/x/sys/windows -# golang.org/x/tools v0.0.0-20190611154301-25a4f137592f +# golang.org/x/tools v0.0.0-20190925211824-e4ea94538f5b golang.org/x/tools/go/analysis golang.org/x/tools/go/analysis/internal/analysisflags golang.org/x/tools/go/analysis/internal/facts diff --git a/src/fmt/errors_test.go b/src/fmt/errors_test.go index 0c774bc28b..481a7b8403 100644 --- a/src/fmt/errors_test.go +++ b/src/fmt/errors_test.go @@ -11,6 +11,10 @@ import ( ) func TestErrorf(t *testing.T) { + // noVetErrorf is an alias for fmt.Errorf that does not trigger vet warnings for + // %w format strings. + noVetErrorf := fmt.Errorf + wrapped := errors.New("inner error") for _, test := range []struct { err error @@ -46,13 +50,13 @@ func TestErrorf(t *testing.T) { err: fmt.Errorf("%v with added context", wrapped), wantText: "inner error with added context", }, { - err: fmt.Errorf("%w is not an error", "not-an-error"), + err: noVetErrorf("%w is not an error", "not-an-error"), wantText: "%!w(string=not-an-error) is not an error", }, { - err: fmt.Errorf("wrapped two errors: %w %w", errString("1"), errString("2")), + err: noVetErrorf("wrapped two errors: %w %w", errString("1"), errString("2")), wantText: "wrapped two errors: 1 %!w(fmt_test.errString=2)", }, { - err: fmt.Errorf("wrapped three errors: %w %w %w", errString("1"), errString("2"), errString("3")), + err: noVetErrorf("wrapped three errors: %w %w %w", errString("1"), errString("2"), errString("3")), wantText: "wrapped three errors: 1 %!w(fmt_test.errString=2) %!w(fmt_test.errString=3)", }, { err: fmt.Errorf("%w", nil), -- cgit v1.3 From 2d1c0332598c77097d53a1c2d564b12dcd644810 Mon Sep 17 00:00:00 2001 From: David Crawshaw Date: Tue, 2 Jan 2018 09:43:41 -0800 Subject: reflect: let StructOf define unexported fields This was missing from the original StructOf CL because I couldn't think of a use for it. Now I can: even with types used entirely by reflect, unexported fields can be set using UnsafeAddr. Change-Id: I5e7e3d81d16e8817cdd69d85796ce33930ef523b Reviewed-on: https://go-review.googlesource.com/c/go/+/85661 Run-TryBot: Ian Lance Taylor TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- doc/go1.14.html | 13 +++++++++++++ src/reflect/all_test.go | 23 ++++++++--------------- src/reflect/type.go | 19 +++++++++++-------- 3 files changed, 32 insertions(+), 23 deletions(-) (limited to 'src') diff --git a/doc/go1.14.html b/doc/go1.14.html index 525a1421f7..e68cca56df 100644 --- a/doc/go1.14.html +++ b/doc/go1.14.html @@ -115,6 +115,19 @@ TODO +
+ +
reflect
+
+

+ StructOf now + supports creating struct types with unexported fields, by + setting the PkgPath field in + a StructField element. +

+ +
+
runtime

diff --git a/src/reflect/all_test.go b/src/reflect/all_test.go index fbb6feb0d9..7c5dd59aa7 100644 --- a/src/reflect/all_test.go +++ b/src/reflect/all_test.go @@ -4733,17 +4733,14 @@ func TestStructOfExportRules(t *testing.T) { mustPanic: true, }, { - field: StructField{Name: "s2", Type: TypeOf(int(0)), PkgPath: "other/pkg"}, - mustPanic: true, + field: StructField{Name: "s2", Type: TypeOf(int(0)), PkgPath: "other/pkg"}, }, { - field: StructField{Name: "s2", Type: TypeOf(int(0)), PkgPath: "other/pkg"}, - mustPanic: true, + field: StructField{Name: "s2", Type: TypeOf(int(0)), PkgPath: "other/pkg"}, }, { - field: StructField{Name: "S", Type: TypeOf(S1{})}, - mustPanic: false, - exported: true, + field: StructField{Name: "S", Type: TypeOf(S1{})}, + exported: true, }, { field: StructField{Name: "S", Type: TypeOf((*S1)(nil))}, @@ -4774,20 +4771,16 @@ func TestStructOfExportRules(t *testing.T) { mustPanic: true, }, { - field: StructField{Name: "s", Type: TypeOf(S1{}), PkgPath: "other/pkg"}, - mustPanic: true, // TODO(sbinet): creating a name with a package path + field: StructField{Name: "s", Type: TypeOf(S1{}), PkgPath: "other/pkg"}, }, { - field: StructField{Name: "s", Type: TypeOf((*S1)(nil)), PkgPath: "other/pkg"}, - mustPanic: true, // TODO(sbinet): creating a name with a package path + field: StructField{Name: "s", Type: TypeOf((*S1)(nil)), PkgPath: "other/pkg"}, }, { - field: StructField{Name: "s", Type: TypeOf(s2{}), PkgPath: "other/pkg"}, - mustPanic: true, // TODO(sbinet): creating a name with a package path + field: StructField{Name: "s", Type: TypeOf(s2{}), PkgPath: "other/pkg"}, }, { - field: StructField{Name: "s", Type: TypeOf((*s2)(nil)), PkgPath: "other/pkg"}, - mustPanic: true, // TODO(sbinet): creating a name with a package path + field: StructField{Name: "s", Type: TypeOf((*s2)(nil)), PkgPath: "other/pkg"}, }, { field: StructField{Name: "", Type: TypeOf(ΦType{})}, diff --git a/src/reflect/type.go b/src/reflect/type.go index 2cf912cf54..f1f8ba93a4 100644 --- a/src/reflect/type.go +++ b/src/reflect/type.go @@ -2731,15 +2731,18 @@ func StructOf(fields []StructField) Type { } func runtimeStructField(field StructField) structField { - if field.PkgPath != "" { - panic("reflect.StructOf: StructOf does not allow unexported fields") + if field.Anonymous && field.PkgPath != "" { + panic("reflect.StructOf: field \"" + field.Name + "\" is anonymous but has PkgPath set") } - // Best-effort check for misuse. - // Since PkgPath is empty, not much harm done if Unicode lowercase slips through. - c := field.Name[0] - if 'a' <= c && c <= 'z' || c == '_' { - panic("reflect.StructOf: field \"" + field.Name + "\" is unexported but missing PkgPath") + exported := field.PkgPath == "" + if exported { + // Best-effort check for misuse. + // Since this field will be treated as exported, not much harm done if Unicode lowercase slips through. + c := field.Name[0] + if 'a' <= c && c <= 'z' || c == '_' { + panic("reflect.StructOf: field \"" + field.Name + "\" is unexported but missing PkgPath") + } } offsetEmbed := uintptr(0) @@ -2749,7 +2752,7 @@ func runtimeStructField(field StructField) structField { resolveReflectType(field.Type.common()) // install in runtime return structField{ - name: newName(field.Name, string(field.Tag), true), + name: newName(field.Name, string(field.Tag), exported), typ: field.Type.common(), offsetEmbed: offsetEmbed, } -- cgit v1.3 From 9748e64fe552f484285ea6399329e6c8e696db63 Mon Sep 17 00:00:00 2001 From: Pantelis Sampaziotis Date: Wed, 25 Sep 2019 20:20:37 +0000 Subject: regexp: add examples for FindSubmatchIndex and Longest updates #21450 Change-Id: Ibffe0dadc1e1523c55cd5f5b8a69bc1c399a255d GitHub-Last-Rev: 507f55508121a525de4d210e7ada1396ccaaf367 GitHub-Pull-Request: golang/go#33497 Reviewed-on: https://go-review.googlesource.com/c/go/+/189177 Run-TryBot: Ian Lance Taylor TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- src/regexp/example_test.go | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) (limited to 'src') diff --git a/src/regexp/example_test.go b/src/regexp/example_test.go index 10eb736c7c..ea35a2e591 100644 --- a/src/regexp/example_test.go +++ b/src/regexp/example_test.go @@ -172,6 +172,34 @@ func ExampleRegexp_FindAllStringSubmatchIndex() { // [] } +func ExampleRegexp_FindSubmatchIndex() { + re := regexp.MustCompile(`a(x*)b`) + // Indices: + // 01234567 012345678 + // -ab-axb- -axxb-ab- + fmt.Println(re.FindSubmatchIndex([]byte("-ab-"))) + fmt.Println(re.FindSubmatchIndex([]byte("-axxb-"))) + fmt.Println(re.FindSubmatchIndex([]byte("-ab-axb-"))) + fmt.Println(re.FindSubmatchIndex([]byte("-axxb-ab-"))) + fmt.Println(re.FindSubmatchIndex([]byte("-foo-"))) + // Output: + // [1 3 2 2] + // [1 5 2 4] + // [1 3 2 2] + // [1 5 2 4] + // [] +} + +func ExampleRegexp_Longest() { + re := regexp.MustCompile(`a(|b)`) + fmt.Println(re.FindString("ab")) + re.Longest() + fmt.Println(re.FindString("ab")) + // Output: + // a + // ab +} + func ExampleRegexp_MatchString() { re := regexp.MustCompile(`(gopher){2}`) fmt.Println(re.MatchString("gopher")) -- cgit v1.3 From c729116332ffb66a21dd587e3ee003cb8d0b16fe Mon Sep 17 00:00:00 2001 From: Mohit Verma Date: Fri, 27 Sep 2019 15:59:03 -0700 Subject: cmd/compile: use Node.Right for OAS2* nodes (cleanup) This CL changes cmd/compile to use Node.Right instead of Node.Rlist for OAS2FUNC/OAS2RECV/OAS2MAPR/OAS2DOTTYPE nodes. Fixes #32293 Change-Id: I4c9d9100be2d98d15e016797f934f64d385f5faa Reviewed-on: https://go-review.googlesource.com/c/go/+/197817 Run-TryBot: Matthew Dempsky TryBot-Result: Gobot Gobot Reviewed-by: Matthew Dempsky --- src/cmd/compile/internal/gc/escape.go | 10 +++++----- src/cmd/compile/internal/gc/fmt.go | 3 +-- src/cmd/compile/internal/gc/iexport.go | 8 +++++++- src/cmd/compile/internal/gc/initorder.go | 2 +- src/cmd/compile/internal/gc/inl.go | 27 +++++++++++++-------------- src/cmd/compile/internal/gc/order.go | 14 +++++++------- src/cmd/compile/internal/gc/range.go | 2 +- src/cmd/compile/internal/gc/select.go | 4 +--- src/cmd/compile/internal/gc/ssa.go | 10 +++++----- src/cmd/compile/internal/gc/syntax.go | 8 ++++---- src/cmd/compile/internal/gc/typecheck.go | 7 ++++--- src/cmd/compile/internal/gc/walk.go | 12 ++++++------ 12 files changed, 55 insertions(+), 52 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/escape.go b/src/cmd/compile/internal/gc/escape.go index d04303134a..ebe5403186 100644 --- a/src/cmd/compile/internal/gc/escape.go +++ b/src/cmd/compile/internal/gc/escape.go @@ -361,18 +361,18 @@ func (e *Escape) stmt(n *Node) { } case OAS2DOTTYPE: // v, ok = x.(type) - e.assign(n.List.First(), n.Rlist.First(), "assign-pair-dot-type", n) + e.assign(n.List.First(), n.Right, "assign-pair-dot-type", n) e.assign(n.List.Second(), nil, "assign-pair-dot-type", n) case OAS2MAPR: // v, ok = m[k] - e.assign(n.List.First(), n.Rlist.First(), "assign-pair-mapr", n) + e.assign(n.List.First(), n.Right, "assign-pair-mapr", n) e.assign(n.List.Second(), nil, "assign-pair-mapr", n) case OAS2RECV: // v, ok = <-ch - e.assign(n.List.First(), n.Rlist.First(), "assign-pair-receive", n) + e.assign(n.List.First(), n.Right, "assign-pair-receive", n) e.assign(n.List.Second(), nil, "assign-pair-receive", n) case OAS2FUNC: - e.stmts(n.Rlist.First().Ninit) - e.call(e.addrs(n.List), n.Rlist.First(), nil) + e.stmts(n.Right.Ninit) + e.call(e.addrs(n.List), n.Right, nil) case ORETURN: results := e.curfn.Type.Results().FieldSlice() for i, v := range n.List.Slice() { diff --git a/src/cmd/compile/internal/gc/fmt.go b/src/cmd/compile/internal/gc/fmt.go index 7b974cc866..b401215898 100644 --- a/src/cmd/compile/internal/gc/fmt.go +++ b/src/cmd/compile/internal/gc/fmt.go @@ -945,8 +945,7 @@ func (n *Node) stmtfmt(s fmt.State, mode fmtMode) { fallthrough case OAS2DOTTYPE, OAS2FUNC, OAS2MAPR, OAS2RECV: - mode.Fprintf(s, "%.v = %.v", n.List, n.Rlist) - + mode.Fprintf(s, "%.v = %.v", n.List, n.Right) case ORETURN: mode.Fprintf(s, "return %.v", n.List) diff --git a/src/cmd/compile/internal/gc/iexport.go b/src/cmd/compile/internal/gc/iexport.go index a5acd26c7f..54b87ab1e4 100644 --- a/src/cmd/compile/internal/gc/iexport.go +++ b/src/cmd/compile/internal/gc/iexport.go @@ -1044,12 +1044,18 @@ func (w *exportWriter) stmt(n *Node) { w.expr(n.Right) } - case OAS2, OAS2DOTTYPE, OAS2FUNC, OAS2MAPR, OAS2RECV: + case OAS2: w.op(OAS2) w.pos(n.Pos) w.exprList(n.List) w.exprList(n.Rlist) + case OAS2DOTTYPE, OAS2FUNC, OAS2MAPR, OAS2RECV: + w.op(OAS2) + w.pos(n.Pos) + w.exprList(n.List) + w.exprList(asNodes([]*Node{n.Right})) + case ORETURN: w.op(ORETURN) w.pos(n.Pos) diff --git a/src/cmd/compile/internal/gc/initorder.go b/src/cmd/compile/internal/gc/initorder.go index be1e671d17..41f1349bbe 100644 --- a/src/cmd/compile/internal/gc/initorder.go +++ b/src/cmd/compile/internal/gc/initorder.go @@ -254,7 +254,7 @@ func collectDeps(n *Node, transitive bool) NodeSet { case OAS: d.inspect(n.Right) case OAS2DOTTYPE, OAS2FUNC, OAS2MAPR, OAS2RECV: - d.inspect(n.Rlist.First()) + d.inspect(n.Right) case ODCLFUNC: d.inspectList(n.Nbody) default: diff --git a/src/cmd/compile/internal/gc/inl.go b/src/cmd/compile/internal/gc/inl.go index b41b8cb1a4..4a376305bb 100644 --- a/src/cmd/compile/internal/gc/inl.go +++ b/src/cmd/compile/internal/gc/inl.go @@ -580,6 +580,12 @@ func inlnode(n *Node, maxCost int32) *Node { if n.Right != nil && n.Right.Op == OINLCALL { if n.Op == OFOR || n.Op == OFORUNTIL { inlconv2stmt(n.Right) + } else if n.Op == OAS2FUNC { + n.Rlist.Set(inlconv2list(n.Right)) + n.Right = nil + n.Op = OAS2 + n.SetTypecheck(0) + n = typecheck(n, ctxStmt) } else { n.Right = inlconv2expr(n.Right) } @@ -602,20 +608,13 @@ func inlnode(n *Node, maxCost int32) *Node { } inlnodelist(n.Rlist, maxCost) - if n.Op == OAS2FUNC && n.Rlist.First().Op == OINLCALL { - n.Rlist.Set(inlconv2list(n.Rlist.First())) - n.Op = OAS2 - n.SetTypecheck(0) - n = typecheck(n, ctxStmt) - } else { - s := n.Rlist.Slice() - for i1, n1 := range s { - if n1.Op == OINLCALL { - if n.Op == OIF { - inlconv2stmt(n1) - } else { - s[i1] = inlconv2expr(s[i1]) - } + s := n.Rlist.Slice() + for i1, n1 := range s { + if n1.Op == OINLCALL { + if n.Op == OIF { + inlconv2stmt(n1) + } else { + s[i1] = inlconv2expr(s[i1]) } } } diff --git a/src/cmd/compile/internal/gc/order.go b/src/cmd/compile/internal/gc/order.go index e6350ef721..786067c49c 100644 --- a/src/cmd/compile/internal/gc/order.go +++ b/src/cmd/compile/internal/gc/order.go @@ -567,7 +567,7 @@ func (o *Order) stmt(n *Node) { case OAS2MAPR: t := o.markTemp() o.exprList(n.List) - r := n.Rlist.First() + r := n.Right r.Left = o.expr(r.Left, nil) r.Right = o.expr(r.Right, nil) @@ -582,8 +582,8 @@ func (o *Order) stmt(n *Node) { case OAS2FUNC: t := o.markTemp() o.exprList(n.List) - o.init(n.Rlist.First()) - o.call(n.Rlist.First()) + o.init(n.Right) + o.call(n.Right) o.as2(n) o.cleanTemp(t) @@ -593,7 +593,7 @@ func (o *Order) stmt(n *Node) { case OAS2DOTTYPE: t := o.markTemp() o.exprList(n.List) - n.Rlist.First().Left = o.expr(n.Rlist.First().Left, nil) // i in i.(T) + n.Right.Left = o.expr(n.Right.Left, nil) // i in i.(T) o.okAs2(n) o.cleanTemp(t) @@ -602,8 +602,8 @@ func (o *Order) stmt(n *Node) { case OAS2RECV: t := o.markTemp() o.exprList(n.List) - n.Rlist.First().Left = o.expr(n.Rlist.First().Left, nil) // arg to recv - ch := n.Rlist.First().Left.Type + n.Right.Left = o.expr(n.Right.Left, nil) // arg to recv + ch := n.Right.Left.Type tmp1 := o.newTemp(ch.Elem(), types.Haspointers(ch.Elem())) tmp2 := o.newTemp(types.Types[TBOOL], false) o.out = append(o.out, n) @@ -1343,7 +1343,7 @@ func (o *Order) as2(n *Node) { func (o *Order) okAs2(n *Node) { var tmp1, tmp2 *Node if !n.List.First().isBlank() { - typ := n.Rlist.First().Type + typ := n.Right.Type tmp1 = o.newTemp(typ, types.Haspointers(typ)) } diff --git a/src/cmd/compile/internal/gc/range.go b/src/cmd/compile/internal/gc/range.go index 4d354f23cf..4744324a7c 100644 --- a/src/cmd/compile/internal/gc/range.go +++ b/src/cmd/compile/internal/gc/range.go @@ -343,7 +343,7 @@ func walkrange(n *Node) *Node { a := nod(OAS2RECV, nil, nil) a.SetTypecheck(1) a.List.Set2(hv1, hb) - a.Rlist.Set1(nod(ORECV, ha, nil)) + a.Right = nod(ORECV, ha, nil) n.Left.Ninit.Set1(a) if v1 == nil { body = nil diff --git a/src/cmd/compile/internal/gc/select.go b/src/cmd/compile/internal/gc/select.go index 07c5c5a2a9..49cc23cd3d 100644 --- a/src/cmd/compile/internal/gc/select.go +++ b/src/cmd/compile/internal/gc/select.go @@ -60,7 +60,7 @@ func typecheckselect(sel *Node) { // convert x, ok = <-c into OSELRECV2(x, <-c) with ntest=ok case OAS2RECV: - if n.Rlist.First().Op != ORECV { + if n.Right.Op != ORECV { yyerrorl(n.Pos, "select assignment must have receive on right hand side") break } @@ -68,8 +68,6 @@ func typecheckselect(sel *Node) { n.Op = OSELRECV2 n.Left = n.List.First() n.List.Set1(n.List.Second()) - n.Right = n.Rlist.First() - n.Rlist.Set(nil) // convert <-c into OSELRECV(N, <-c) case ORECV: diff --git a/src/cmd/compile/internal/gc/ssa.go b/src/cmd/compile/internal/gc/ssa.go index 7b0c7e5c43..efc7d1eb51 100644 --- a/src/cmd/compile/internal/gc/ssa.go +++ b/src/cmd/compile/internal/gc/ssa.go @@ -874,9 +874,9 @@ func (s *state) stmt(n *Node) { s.call(n.Left, callGo) case OAS2DOTTYPE: - res, resok := s.dottype(n.Rlist.First(), true) + res, resok := s.dottype(n.Right, true) deref := false - if !canSSAType(n.Rlist.First().Type) { + if !canSSAType(n.Right.Type) { if res.Op != ssa.OpLoad { s.Fatalf("dottype of non-load") } @@ -896,10 +896,10 @@ func (s *state) stmt(n *Node) { case OAS2FUNC: // We come here only when it is an intrinsic call returning two values. - if !isIntrinsicCall(n.Rlist.First()) { - s.Fatalf("non-intrinsic AS2FUNC not expanded %v", n.Rlist.First()) + if !isIntrinsicCall(n.Right) { + s.Fatalf("non-intrinsic AS2FUNC not expanded %v", n.Right) } - v := s.intrinsicCall(n.Rlist.First()) + v := s.intrinsicCall(n.Right) v1 := s.newValue1(ssa.OpSelect0, n.List.First().Type, v) v2 := s.newValue1(ssa.OpSelect1, n.List.Second().Type, v) s.assign(n.List.First(), v1, false, 0) diff --git a/src/cmd/compile/internal/gc/syntax.go b/src/cmd/compile/internal/gc/syntax.go index c26ed6251b..c1df046654 100644 --- a/src/cmd/compile/internal/gc/syntax.go +++ b/src/cmd/compile/internal/gc/syntax.go @@ -600,10 +600,10 @@ const ( OSTR2RUNES // Type(Left) (Type is []rune, Left is a string) OAS // Left = Right or (if Colas=true) Left := Right OAS2 // List = Rlist (x, y, z = a, b, c) - OAS2DOTTYPE // List = Rlist (x, ok = I.(int)) - OAS2FUNC // List = Rlist (x, y = f()) - OAS2MAPR // List = Rlist (x, ok = m["foo"]) - OAS2RECV // List = Rlist (x, ok = <-c) + OAS2DOTTYPE // List = Right (x, ok = I.(int)) + OAS2FUNC // List = Right (x, y = f()) + OAS2MAPR // List = Right (x, ok = m["foo"]) + OAS2RECV // List = Right (x, ok = <-c) OASOP // Left Etype= Right (x += y) OCALL // Left(List) (function call, method call or type conversion) diff --git a/src/cmd/compile/internal/gc/typecheck.go b/src/cmd/compile/internal/gc/typecheck.go index ab45fb5a2d..c9b7e3b1e8 100644 --- a/src/cmd/compile/internal/gc/typecheck.go +++ b/src/cmd/compile/internal/gc/typecheck.go @@ -3275,6 +3275,8 @@ func typecheckas2(n *Node) { goto mismatch } n.Op = OAS2FUNC + n.Right = r + n.Rlist.Set(nil) for i, l := range n.List.Slice() { f := r.Type.Field(i) if f.Type != nil && l.Type != nil { @@ -3298,15 +3300,14 @@ func typecheckas2(n *Node) { switch r.Op { case OINDEXMAP: n.Op = OAS2MAPR - case ORECV: n.Op = OAS2RECV - case ODOTTYPE: n.Op = OAS2DOTTYPE r.Op = ODOTTYPE2 } - + n.Right = r + n.Rlist.Set(nil) if l.Type != nil { checkassignto(r.Type, l) } diff --git a/src/cmd/compile/internal/gc/walk.go b/src/cmd/compile/internal/gc/walk.go index ceec1b4dc1..7f73d416e8 100644 --- a/src/cmd/compile/internal/gc/walk.go +++ b/src/cmd/compile/internal/gc/walk.go @@ -691,12 +691,12 @@ opswitch: case OAS2FUNC: init.AppendNodes(&n.Ninit) - r := n.Rlist.First() + r := n.Right walkexprlistsafe(n.List.Slice(), init) r = walkexpr(r, init) if isIntrinsicCall(r) { - n.Rlist.Set1(r) + n.Right = r break } init.Append(r) @@ -709,7 +709,7 @@ opswitch: case OAS2RECV: init.AppendNodes(&n.Ninit) - r := n.Rlist.First() + r := n.Right walkexprlistsafe(n.List.Slice(), init) r.Left = walkexpr(r.Left, init) var n1 *Node @@ -728,7 +728,7 @@ opswitch: case OAS2MAPR: init.AppendNodes(&n.Ninit) - r := n.Rlist.First() + r := n.Right walkexprlistsafe(n.List.Slice(), init) r.Left = walkexpr(r.Left, init) r.Right = walkexpr(r.Right, init) @@ -767,7 +767,7 @@ opswitch: if ok := n.List.Second(); !ok.isBlank() && ok.Type.IsBoolean() { r.Type.Field(1).Type = ok.Type } - n.Rlist.Set1(r) + n.Right = r n.Op = OAS2FUNC // don't generate a = *var if a is _ @@ -801,7 +801,7 @@ opswitch: case OAS2DOTTYPE: walkexprlistsafe(n.List.Slice(), init) - n.Rlist.SetFirst(walkexpr(n.Rlist.First(), init)) + n.Right = walkexpr(n.Right, init) case OCONVIFACE: n.Left = walkexpr(n.Left, init) -- cgit v1.3 From 2c47caa900cb4aca9ab9e802289fa0671ad843a4 Mon Sep 17 00:00:00 2001 From: Alberto Donizetti Date: Sat, 28 Sep 2019 14:33:10 +0200 Subject: cmd/compile: use %v for Node formatting CL 197817 replaced a use of n.Rlist with n.Right in a Fprintf call, but it left the corresponding format as %.v, which broke the TestFormats test on the longtest builder. Since with n.Right is custom to use %v (and not %.v), replace the format with %v. Fixes the longtest builder. Change-Id: Icf5bf820a936c51e633c25ada1a71a1ffb6d28c2 Reviewed-on: https://go-review.googlesource.com/c/go/+/197837 Run-TryBot: Alberto Donizetti TryBot-Result: Gobot Gobot Reviewed-by: Matthew Dempsky --- src/cmd/compile/internal/gc/fmt.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/fmt.go b/src/cmd/compile/internal/gc/fmt.go index b401215898..3bb2df9917 100644 --- a/src/cmd/compile/internal/gc/fmt.go +++ b/src/cmd/compile/internal/gc/fmt.go @@ -945,7 +945,8 @@ func (n *Node) stmtfmt(s fmt.State, mode fmtMode) { fallthrough case OAS2DOTTYPE, OAS2FUNC, OAS2MAPR, OAS2RECV: - mode.Fprintf(s, "%.v = %.v", n.List, n.Right) + mode.Fprintf(s, "%.v = %v", n.List, n.Right) + case ORETURN: mode.Fprintf(s, "return %.v", n.List) -- cgit v1.3 From 57662b1575030aa09043cd7a48425abdc6e0e0a3 Mon Sep 17 00:00:00 2001 From: Richard Musiol Date: Tue, 24 Sep 2019 00:48:39 +0200 Subject: cmd/link: add producer section to wasm binaries This change adds an optional "producer" section that reports the source language and compiler version. See https://github.com/WebAssembly/tool-conventions/blob/master/ProducersSection.md. It also removes the now redundant "go.version" section. Fixes #33295. Change-Id: Ib4c80528728caf9e524fbd3f26822cbbc8b05a75 Reviewed-on: https://go-review.googlesource.com/c/go/+/196804 Run-TryBot: Richard Musiol TryBot-Result: Gobot Gobot Reviewed-by: Agniva De Sarker Reviewed-by: Cherry Zhang --- src/cmd/link/internal/wasm/asm.go | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-) (limited to 'src') diff --git a/src/cmd/link/internal/wasm/asm.go b/src/cmd/link/internal/wasm/asm.go index 54b265cb19..ee0a5176ac 100644 --- a/src/cmd/link/internal/wasm/asm.go +++ b/src/cmd/link/internal/wasm/asm.go @@ -11,7 +11,6 @@ import ( "cmd/link/internal/sym" "io" "regexp" - "runtime" ) const ( @@ -177,7 +176,6 @@ func asmb2(ctxt *ld.Link) { writeBuildID(ctxt, buildid) } - writeGoVersion(ctxt) writeTypeSec(ctxt, types) writeImportSec(ctxt, hostImports) writeFunctionSec(ctxt, fns) @@ -188,6 +186,7 @@ func asmb2(ctxt *ld.Link) { writeElementSec(ctxt, uint64(len(hostImports)), uint64(len(fns))) writeCodeSec(ctxt, fns) writeDataSec(ctxt) + writeProducerSec(ctxt) if !*ld.FlagS { writeNameSec(ctxt, len(hostImports), fns) } @@ -226,13 +225,6 @@ func writeBuildID(ctxt *ld.Link, buildid []byte) { writeSecSize(ctxt, sizeOffset) } -func writeGoVersion(ctxt *ld.Link) { - sizeOffset := writeSecHeader(ctxt, sectionCustom) - writeName(ctxt.Out, "go.version") - ctxt.Out.Write([]byte(runtime.Version())) - writeSecSize(ctxt, sizeOffset) -} - // writeTypeSec writes the section that declares all function types // so they can be referenced by index. func writeTypeSec(ctxt *ld.Link, types []*wasmFuncType) { @@ -488,6 +480,26 @@ func writeDataSec(ctxt *ld.Link) { writeSecSize(ctxt, sizeOffset) } +// writeProducerSec writes an optional section that reports the source language and compiler version. +func writeProducerSec(ctxt *ld.Link) { + sizeOffset := writeSecHeader(ctxt, sectionCustom) + writeName(ctxt.Out, "producers") + + writeUleb128(ctxt.Out, 2) // number of fields + + writeName(ctxt.Out, "language") // field name + writeUleb128(ctxt.Out, 1) // number of values + writeName(ctxt.Out, "Go") // value: name + writeName(ctxt.Out, objabi.Version) // value: version + + writeName(ctxt.Out, "processed-by") // field name + writeUleb128(ctxt.Out, 1) // number of values + writeName(ctxt.Out, "Go cmd/compile") // value: name + writeName(ctxt.Out, objabi.Version) // value: version + + writeSecSize(ctxt, sizeOffset) +} + var nameRegexp = regexp.MustCompile(`[^\w\.]`) // writeNameSec writes an optional section that assigns names to the functions declared by the "func" section. -- cgit v1.3 From 931365763a294950200096d071a35f799ffade2c Mon Sep 17 00:00:00 2001 From: Carlo Alberto Ferraris Date: Sat, 24 Aug 2019 08:59:01 +0900 Subject: math/rand: devirtualize interface in lockedSource MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Avoid interface calls, enable inlining, and store the rngSource close to the Mutex to exploit better memory locality. Also add a benchmark to properly measure the threadsafe nature of globalRand. On a linux/amd64 VM: name old time/op new time/op delta Int63Threadsafe-4 36.4ns ±12% 20.6ns ±11% -43.52% (p=0.000 n=30+30) Int63ThreadsafeParallel-4 79.3ns ± 5% 56.5ns ± 5% -28.69% (p=0.000 n=29+30) Change-Id: I6ab912c1a1e9afc7bacd8e72c82d4d50d546a510 Reviewed-on: https://go-review.googlesource.com/c/go/+/191538 Reviewed-by: Emmanuel Odeke Run-TryBot: Emmanuel Odeke TryBot-Result: Gobot Gobot --- src/cmd/compile/internal/gc/inl_test.go | 4 ++++ src/math/rand/rand.go | 7 +++++-- src/math/rand/rand_test.go | 8 ++++++++ 3 files changed, 17 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/inl_test.go b/src/cmd/compile/internal/gc/inl_test.go index a0f56e776b..77c398af82 100644 --- a/src/cmd/compile/internal/gc/inl_test.go +++ b/src/cmd/compile/internal/gc/inl_test.go @@ -148,6 +148,10 @@ func TestIntendedInlining(t *testing.T) { "addVW", "subVW", }, + "math/rand": { + "(*rngSource).Int63", + "(*rngSource).Uint64", + }, } if runtime.GOARCH != "386" && runtime.GOARCH != "mips64" && runtime.GOARCH != "mips64le" { diff --git a/src/math/rand/rand.go b/src/math/rand/rand.go index 04382e6208..6e5eb4ba6a 100644 --- a/src/math/rand/rand.go +++ b/src/math/rand/rand.go @@ -285,7 +285,10 @@ func read(p []byte, int63 func() int64, readVal *int64, readPos *int8) (n int, e * Top-level convenience functions */ -var globalRand = New(&lockedSource{src: NewSource(1).(Source64)}) +var globalRand = New(&lockedSource{src: NewSource(1).(*rngSource)}) + +// Type assert that globalRand's source is a lockedSource whose src is a *rngSource. +var _ *rngSource = globalRand.src.(*lockedSource).src // Seed uses the provided seed value to initialize the default Source to a // deterministic state. If Seed is not called, the generator behaves as @@ -373,7 +376,7 @@ func ExpFloat64() float64 { return globalRand.ExpFloat64() } type lockedSource struct { lk sync.Mutex - src Source64 + src *rngSource } func (r *lockedSource) Int63() (n int64) { diff --git a/src/math/rand/rand_test.go b/src/math/rand/rand_test.go index ee9c8f8e84..e037aaed0e 100644 --- a/src/math/rand/rand_test.go +++ b/src/math/rand/rand_test.go @@ -565,6 +565,14 @@ func BenchmarkInt63Threadsafe(b *testing.B) { } } +func BenchmarkInt63ThreadsafeParallel(b *testing.B) { + b.RunParallel(func(pb *testing.PB) { + for pb.Next() { + Int63() + } + }) +} + func BenchmarkInt63Unthreadsafe(b *testing.B) { r := New(NewSource(1)) for n := b.N; n > 0; n-- { -- cgit v1.3 From 843fec1c7d75cac3f76620e79f1680d8f058c501 Mon Sep 17 00:00:00 2001 From: Julien Schmidt Date: Mon, 30 Sep 2019 00:07:34 +0000 Subject: database/sql: preallocate list slice in Drivers() The required slice capacity is already known. Thus, preallocate a slice with the correct capacity before appending to it. Change-Id: I45ac2c5f1701caeb3dda20451d371713ae7e7365 GitHub-Last-Rev: 2bf575be65e9a449322540270988eaf87cec4245 GitHub-Pull-Request: golang/go#34602 Reviewed-on: https://go-review.googlesource.com/c/go/+/197917 Reviewed-by: Brad Fitzpatrick Run-TryBot: Brad Fitzpatrick TryBot-Result: Gobot Gobot --- src/database/sql/sql.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/database/sql/sql.go b/src/database/sql/sql.go index 93001635be..0f5bbc01c9 100644 --- a/src/database/sql/sql.go +++ b/src/database/sql/sql.go @@ -64,7 +64,7 @@ func unregisterAllDrivers() { func Drivers() []string { driversMu.RLock() defer driversMu.RUnlock() - var list []string + list := make([]string, 0, len(drivers)) for name := range drivers { list = append(list, name) } -- cgit v1.3 From 60f271358f07647be0de9ee8225b50a391ea5def Mon Sep 17 00:00:00 2001 From: Richard Musiol Date: Sat, 28 Sep 2019 23:47:37 +0200 Subject: syscall/js: add Value.Delete for deleting JavaScript properties This change adds the method Value.Delete, which implements JavaScript's "delete" operator for deleting properties. Fixes #33079. Change-Id: Ia5b190240bd59daca48094fcbc32f8d0a06f19d5 Reviewed-on: https://go-review.googlesource.com/c/go/+/197840 Run-TryBot: Richard Musiol TryBot-Result: Gobot Gobot Reviewed-by: Brad Fitzpatrick Reviewed-by: Cherry Zhang --- misc/wasm/wasm_exec.js | 5 +++++ src/syscall/js/js.go | 11 +++++++++++ src/syscall/js/js_js.s | 4 ++++ src/syscall/js/js_test.go | 12 ++++++++++++ 4 files changed, 32 insertions(+) (limited to 'src') diff --git a/misc/wasm/wasm_exec.js b/misc/wasm/wasm_exec.js index 9639585693..9ffa9201e8 100644 --- a/misc/wasm/wasm_exec.js +++ b/misc/wasm/wasm_exec.js @@ -308,6 +308,11 @@ Reflect.set(loadValue(sp + 8), loadString(sp + 16), loadValue(sp + 32)); }, + // func valueDelete(v ref, p string) + "syscall/js.valueDelete": (sp) => { + Reflect.deleteProperty(loadValue(sp + 8), loadString(sp + 16)); + }, + // func valueIndex(v ref, i int) ref "syscall/js.valueIndex": (sp) => { storeValue(sp + 24, Reflect.get(loadValue(sp + 8), getInt64(sp + 16))); diff --git a/src/syscall/js/js.go b/src/syscall/js/js.go index 7300d2c769..f42a16f0d0 100644 --- a/src/syscall/js/js.go +++ b/src/syscall/js/js.go @@ -267,6 +267,17 @@ func (v Value) Set(p string, x interface{}) { func valueSet(v ref, p string, x ref) +// Delete deletes the JavaScript property p of value v. +// It panics if v is not a JavaScript object. +func (v Value) Delete(p string) { + if vType := v.Type(); !vType.isObject() { + panic(&ValueError{"Value.Delete", vType}) + } + valueDelete(v.ref, p) +} + +func valueDelete(v ref, p string) + // Index returns JavaScript index i of value v. // It panics if v is not a JavaScript object. func (v Value) Index(i int) Value { diff --git a/src/syscall/js/js_js.s b/src/syscall/js/js_js.s index 5f29468237..ab56087c16 100644 --- a/src/syscall/js/js_js.s +++ b/src/syscall/js/js_js.s @@ -16,6 +16,10 @@ TEXT ·valueSet(SB), NOSPLIT, $0 CallImport RET +TEXT ·valueDelete(SB), NOSPLIT, $0 + CallImport + RET + TEXT ·valueIndex(SB), NOSPLIT, $0 CallImport RET diff --git a/src/syscall/js/js_test.go b/src/syscall/js/js_test.go index 753c2c3a0d..10d4364e4c 100644 --- a/src/syscall/js/js_test.go +++ b/src/syscall/js/js_test.go @@ -212,6 +212,18 @@ func TestSet(t *testing.T) { }) } +func TestDelete(t *testing.T) { + dummys.Set("test", 42) + dummys.Delete("test") + if dummys.Call("hasOwnProperty", "test").Bool() { + t.Errorf("property still exists") + } + + expectValueError(t, func() { + dummys.Get("zero").Delete("badField") + }) +} + func TestIndex(t *testing.T) { if got := dummys.Get("someArray").Index(1).Int(); got != 42 { t.Errorf("got %#v, want %#v", got, 42) -- cgit v1.3 From 5f1aeaeb77b36b92305b54acc4bd6a3319dce803 Mon Sep 17 00:00:00 2001 From: Carlo Alberto Ferraris Date: Sat, 24 Aug 2019 20:42:41 +0900 Subject: math/rand: devirtualize interface call in Read MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This allows to inline the common case in which the Source is a rngSource. On linux/amd64 in a VM: name old time/op new time/op delta Read3-4 33.8ns ± 8% 18.5ns ± 8% -45.38% (p=0.000 n=10+10) Read64-4 371ns ± 8% 70ns ± 7% -81.00% (p=0.000 n=10+10) Read1000-4 5.33µs ± 5% 0.86µs ± 3% -83.85% (p=0.000 n=9+9) Change-Id: Ibf47b0e9ecdfe62ffcb66d6a92f191800bdc740e Reviewed-on: https://go-review.googlesource.com/c/go/+/191539 Reviewed-by: Daniel Martí Reviewed-by: Brad Fitzpatrick Run-TryBot: Daniel Martí TryBot-Result: Gobot Gobot --- src/math/rand/rand.go | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/math/rand/rand.go b/src/math/rand/rand.go index 6e5eb4ba6a..3e44613663 100644 --- a/src/math/rand/rand.go +++ b/src/math/rand/rand.go @@ -261,15 +261,20 @@ func (r *Rand) Read(p []byte) (n int, err error) { if lk, ok := r.src.(*lockedSource); ok { return lk.read(p, &r.readVal, &r.readPos) } - return read(p, r.Int63, &r.readVal, &r.readPos) + return read(p, r.src, &r.readVal, &r.readPos) } -func read(p []byte, int63 func() int64, readVal *int64, readPos *int8) (n int, err error) { +func read(p []byte, src Source, readVal *int64, readPos *int8) (n int, err error) { pos := *readPos val := *readVal + rng, _ := src.(*rngSource) for n = 0; n < len(p); n++ { if pos == 0 { - val = int63() + if rng != nil { + val = rng.Int63() + } else { + val = src.Int63() + } pos = 7 } p[n] = byte(val) @@ -410,7 +415,7 @@ func (r *lockedSource) seedPos(seed int64, readPos *int8) { // read implements Read for a lockedSource without a race condition. func (r *lockedSource) read(p []byte, readVal *int64, readPos *int8) (n int, err error) { r.lk.Lock() - n, err = read(p, r.src.Int63, readVal, readPos) + n, err = read(p, r.src, readVal, readPos) r.lk.Unlock() return } -- cgit v1.3 From ba18c7c42d4fa70e81b2304ccc3b2c01675a3af0 Mon Sep 17 00:00:00 2001 From: Tobias Klauser Date: Mon, 30 Sep 2019 11:47:04 +0200 Subject: syscall: fix TestGroupCleanupUserNamespace on CentOS Update the list of expected "id" outputs in TestGroupCleanupUserNamespace with SELinux context information as used on CentOS. Fixes #34547 Change-Id: I426bbe2d04e2039c87490362a1891ec3de6e36e0 Reviewed-on: https://go-review.googlesource.com/c/go/+/197841 Run-TryBot: Tobias Klauser TryBot-Result: Gobot Gobot Reviewed-by: Brad Fitzpatrick --- src/syscall/exec_linux_test.go | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/syscall/exec_linux_test.go b/src/syscall/exec_linux_test.go index f7fab7b659..acf84128ef 100644 --- a/src/syscall/exec_linux_test.go +++ b/src/syscall/exec_linux_test.go @@ -309,6 +309,7 @@ func TestGroupCleanupUserNamespace(t *testing.T) { "uid=0(root) gid=0(root) groups=0(root),65534(nogroup)", "uid=0(root) gid=0(root) groups=0(root),65534", "uid=0(root) gid=0(root) groups=0(root),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody),65534(nobody)", // Alpine; see https://golang.org/issue/19938 + "uid=0(root) gid=0(root) groups=0(root) context=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023", // CentOS with SELinux context, see https://golang.org/issue/34547 } for _, e := range expected { if strOut == e { -- cgit v1.3 From 0adc89aa962aa116da5540c3248977318d360738 Mon Sep 17 00:00:00 2001 From: Pantelis Sampaziotis Date: Tue, 10 Sep 2019 18:43:15 +0000 Subject: strconv: add Unwrap to custom error types Updates #30322 This change adds the Unwrap method to NumError. NumError is the only custom error type of the strconv that has a nested exported error. Change-Id: I8774886348880365a83f72a1d106276def27dffe GitHub-Last-Rev: 712f3df8842f48f988cebfc527476781a7cf7140 GitHub-Pull-Request: golang/go#34213 Reviewed-on: https://go-review.googlesource.com/c/go/+/194563 Run-TryBot: Bryan C. Mills TryBot-Result: Gobot Gobot Reviewed-by: Bryan C. Mills --- src/strconv/atoi.go | 2 ++ src/strconv/atoi_test.go | 7 +++++++ 2 files changed, 9 insertions(+) (limited to 'src') diff --git a/src/strconv/atoi.go b/src/strconv/atoi.go index 131b088e31..a4a8a37fb4 100644 --- a/src/strconv/atoi.go +++ b/src/strconv/atoi.go @@ -31,6 +31,8 @@ func (e *NumError) Error() string { return "strconv." + e.Func + ": " + "parsing " + Quote(e.Num) + ": " + e.Err.Error() } +func (e *NumError) Unwrap() error { return e.Err } + func syntaxError(fn, str string) *NumError { return &NumError{fn, str, ErrSyntax} } diff --git a/src/strconv/atoi_test.go b/src/strconv/atoi_test.go index b167c96833..178fb01ea7 100644 --- a/src/strconv/atoi_test.go +++ b/src/strconv/atoi_test.go @@ -592,6 +592,13 @@ func TestNumError(t *testing.T) { } } +func TestNumErrorUnwrap(t *testing.T) { + err := &NumError{Err: ErrSyntax} + if !errors.Is(err, ErrSyntax) { + t.Error("errors.Is failed, wanted success") + } +} + func BenchmarkParseInt(b *testing.B) { b.Run("Pos", func(b *testing.B) { benchmarkParseInt(b, 1) -- cgit v1.3 From cde282dbdd8c1d4c7127dc63ef0743bad23fc068 Mon Sep 17 00:00:00 2001 From: chauncyc Date: Mon, 30 Sep 2019 21:07:46 +0000 Subject: crypto/x509: add IPAddresses to list of template fields used by CreateCertificate Change-Id: Ifbdf33ee4e413c3edba59b7dbed00ab90698cd35 GitHub-Last-Rev: c3bd33c4cf9c4f4a1e6724c93b865fc5bbb4ca9d GitHub-Pull-Request: golang/go#34277 Reviewed-on: https://go-review.googlesource.com/c/go/+/195157 Run-TryBot: Andrew Bonventre TryBot-Result: Gobot Gobot Reviewed-by: Andrew Bonventre Reviewed-by: Filippo Valsorda --- src/crypto/x509/x509.go | 1 + 1 file changed, 1 insertion(+) (limited to 'src') diff --git a/src/crypto/x509/x509.go b/src/crypto/x509/x509.go index d959d0ba3f..9b47033947 100644 --- a/src/crypto/x509/x509.go +++ b/src/crypto/x509/x509.go @@ -2052,6 +2052,7 @@ var emptyASN1Subject = []byte{0x30, 0} // - ExcludedURIDomains // - ExtKeyUsage // - ExtraExtensions +// - IPAddresses // - IsCA // - IssuingCertificateURL // - KeyUsage -- cgit v1.3 From 8e032b917ac6b54c86dbf6f8fc110d82d3ecbea9 Mon Sep 17 00:00:00 2001 From: An Xiao Date: Mon, 30 Sep 2019 21:46:32 +0000 Subject: net: update quotation marks in comment This change updates the use of quotation marks by replacing `ones' with 'ones'. Quotation like `this' should not be used any more according to https://www.cl.cam.ac.uk/~mgk25/ucs/quotes.html Change-Id: I58470cdcc207864fbc8ca68ec0e77329bd81dc19 GitHub-Last-Rev: d03c81ebfba19a98a8dcc99451db60d129b43784 GitHub-Pull-Request: golang/go#33719 Reviewed-on: https://go-review.googlesource.com/c/go/+/190817 Reviewed-by: Andrew Bonventre --- src/net/ip.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/net/ip.go b/src/net/ip.go index 1a1d0e7dba..7a55486933 100644 --- a/src/net/ip.go +++ b/src/net/ip.go @@ -65,8 +65,8 @@ func IPv4Mask(a, b, c, d byte) IPMask { return p } -// CIDRMask returns an IPMask consisting of `ones' 1 bits -// followed by 0s up to a total length of `bits' bits. +// CIDRMask returns an IPMask consisting of 'ones' 1 bits +// followed by 0s up to a total length of 'bits' bits. // For a mask of this form, CIDRMask is the inverse of IPMask.Size. func CIDRMask(ones, bits int) IPMask { if bits != 8*IPv4len && bits != 8*IPv6len { -- cgit v1.3 From f91c850be62416d0aaa70e77831c8ba3e1ee2b1e Mon Sep 17 00:00:00 2001 From: Pantelis Sampaziotis Date: Mon, 30 Sep 2019 21:37:40 +0000 Subject: text/template/parse: specify slice capacity in Pipenode.CopyPipe() The required vars slice capacity is known so it can be specified before appending. Change-Id: Ifa2fe97602e84198c4d01e5a1b0529f3f65f2df1 GitHub-Last-Rev: a0580df208a1d498968138d63508ae4e30df2ec5 GitHub-Pull-Request: golang/go#34613 Reviewed-on: https://go-review.googlesource.com/c/go/+/197997 Reviewed-by: Andrew Bonventre --- src/text/template/parse/node.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/text/template/parse/node.go b/src/text/template/parse/node.go index 1174a4b970..74552c293f 100644 --- a/src/text/template/parse/node.go +++ b/src/text/template/parse/node.go @@ -187,7 +187,7 @@ func (p *PipeNode) CopyPipe() *PipeNode { if p == nil { return p } - var vars []*VariableNode + vars := make([]*VariableNode, 0, len(p.Decl)) for _, d := range p.Decl { vars = append(vars, d.Copy().(*VariableNode)) } -- cgit v1.3 From ecc2d6179898a3d24a8bb0a91aca6ff84ca843d8 Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Thu, 26 Sep 2019 10:59:11 -0700 Subject: cmd/compile: remove redundant anylit calls in walkcompare walkcompare already called walkexpr on n.Left and n.Right, which in turn calls anylit when appropriate. Passes toolstash-check. Change-Id: I6912ac5a42b977c04db9d85cb2e7295e275e083d Reviewed-on: https://go-review.googlesource.com/c/go/+/197600 Run-TryBot: Matthew Dempsky TryBot-Result: Gobot Gobot Reviewed-by: Keith Randall --- src/cmd/compile/internal/gc/walk.go | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/walk.go b/src/cmd/compile/internal/gc/walk.go index 7f73d416e8..e19b6329ba 100644 --- a/src/cmd/compile/internal/gc/walk.go +++ b/src/cmd/compile/internal/gc/walk.go @@ -3125,21 +3125,11 @@ func walkcompare(n *Node, init *Nodes) *Node { // Chose not to inline. Call equality function directly. if !inline { - if isvaluelit(cmpl) { - var_ := temp(cmpl.Type) - anylit(cmpl, var_, init) - cmpl = var_ - } - if isvaluelit(cmpr) { - var_ := temp(cmpr.Type) - anylit(cmpr, var_, init) - cmpr = var_ - } + // eq algs take pointers; cmpl and cmpr must be addressable if !islvalue(cmpl) || !islvalue(cmpr) { Fatalf("arguments of comparison must be lvalues - %v %v", cmpl, cmpr) } - // eq algs take pointers pl := temp(types.NewPtr(t)) al := nod(OAS, pl, nod(OADDR, cmpl, nil)) al = typecheck(al, ctxStmt) -- cgit v1.3 From e76b9e8908bdcdb4363d6bd23aa7ff3120237426 Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Thu, 26 Sep 2019 11:00:13 -0700 Subject: cmd/compile: remove pointer temporaries in walkcompare When comparing two T-typed values t1 and t2 using the T_eq function, we used to generate: pl := &t1 pr := &t2 return T_eq(pl, pr, unsafe.Sizeof(T{})) This CL changes it to simply generate: return T_eq(&t1, &t2, unsafe.Sizeof(T{})) Surprisingly, this does not pass toolstash. For some reason, it seems like SSA wasn't able to SSA-ify the pl and pr variables in all cases. Change-Id: I111fbb068a1741fa169c9922cb8cdb6e21579aa4 Reviewed-on: https://go-review.googlesource.com/c/go/+/197601 Run-TryBot: Matthew Dempsky TryBot-Result: Gobot Gobot Reviewed-by: Keith Randall --- src/cmd/compile/internal/gc/walk.go | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/walk.go b/src/cmd/compile/internal/gc/walk.go index e19b6329ba..727c8102ae 100644 --- a/src/cmd/compile/internal/gc/walk.go +++ b/src/cmd/compile/internal/gc/walk.go @@ -3130,20 +3130,10 @@ func walkcompare(n *Node, init *Nodes) *Node { Fatalf("arguments of comparison must be lvalues - %v %v", cmpl, cmpr) } - pl := temp(types.NewPtr(t)) - al := nod(OAS, pl, nod(OADDR, cmpl, nil)) - al = typecheck(al, ctxStmt) - init.Append(al) - - pr := temp(types.NewPtr(t)) - ar := nod(OAS, pr, nod(OADDR, cmpr, nil)) - ar = typecheck(ar, ctxStmt) - init.Append(ar) - fn, needsize := eqfor(t) call := nod(OCALL, fn, nil) - call.List.Append(pl) - call.List.Append(pr) + call.List.Append(nod(OADDR, cmpl, nil)) + call.List.Append(nod(OADDR, cmpr, nil)) if needsize { call.List.Append(nodintconst(t.Width)) } -- cgit v1.3 From 27cf81e1b48efe6a6387f34c7114766c7b0d4d73 Mon Sep 17 00:00:00 2001 From: Rob Pike Date: Tue, 1 Oct 2019 09:54:30 +1000 Subject: text/template: further simplify building the vars list Followup to https://golang.org/cl/197997 If you know the number of elements, you don't need append at all. Either use append to grow, or allocate and index. Here we choose number 2. Change-Id: Ic58637231789640ff7b293ece04a95a8de7ccf8f Reviewed-on: https://go-review.googlesource.com/c/go/+/198097 Reviewed-by: Ian Lance Taylor --- src/text/template/parse/node.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/text/template/parse/node.go b/src/text/template/parse/node.go index 74552c293f..2f921be2ec 100644 --- a/src/text/template/parse/node.go +++ b/src/text/template/parse/node.go @@ -187,9 +187,9 @@ func (p *PipeNode) CopyPipe() *PipeNode { if p == nil { return p } - vars := make([]*VariableNode, 0, len(p.Decl)) - for _, d := range p.Decl { - vars = append(vars, d.Copy().(*VariableNode)) + vars := make([]*VariableNode, len(p.Decl)) + for i, d := range p.Decl { + vars[i] = d.Copy().(*VariableNode) } n := p.tr.newPipeline(p.Pos, p.Line, vars) n.IsAssign = p.IsAssign -- cgit v1.3 From 5e514b76e2e55efbca917c686c93b2299d57386c Mon Sep 17 00:00:00 2001 From: John Papandriopoulos Date: Sun, 29 Sep 2019 16:59:56 -0700 Subject: cmd/link: load symbols from .syso in external link mode Fix linking with a package having a .syso file in external link mode, that would otherwise cause an error before executing the external linker because it can't find symbols that are exported in the said .syso file. Fixes #33139 Change-Id: Id3ee737fba1c6f1e37910593dfedf9c84486d398 Reviewed-on: https://go-review.googlesource.com/c/go/+/186417 Reviewed-by: Ian Lance Taylor --- .../go/testdata/script/link_syso_issue33139.txt | 29 ++++++++++++++++++++++ src/cmd/link/internal/arm/asm.go | 2 +- src/cmd/link/internal/ld/data.go | 13 +++++++++- src/cmd/link/internal/ld/go.go | 18 ++++++++++++++ src/cmd/link/internal/ld/lib.go | 2 +- src/cmd/link/internal/ld/macho.go | 4 +-- src/cmd/link/internal/ld/pe.go | 2 +- src/cmd/link/internal/ld/symtab.go | 2 +- src/cmd/link/internal/sym/symkind.go | 1 + src/cmd/link/internal/sym/symkind_string.go | 19 +++++++------- 10 files changed, 76 insertions(+), 16 deletions(-) create mode 100644 src/cmd/go/testdata/script/link_syso_issue33139.txt (limited to 'src') diff --git a/src/cmd/go/testdata/script/link_syso_issue33139.txt b/src/cmd/go/testdata/script/link_syso_issue33139.txt new file mode 100644 index 0000000000..53587e6823 --- /dev/null +++ b/src/cmd/go/testdata/script/link_syso_issue33139.txt @@ -0,0 +1,29 @@ +# Test that we can use the external linker with a host syso file that is +# embedded in a package, that is referenced by a Go assembly stub. +# See issue 33139. +[!gc] stop +cc -c -o syso/objTestImpl.syso syso/src/objTestImpl.c +go build -ldflags='-linkmode=external' ./cmd/main.go + +-- syso/objTest.s -- +#include "textflag.h" + +TEXT ·ObjTest(SB), NOSPLIT, $0 + JMP objTestImpl(SB) + +-- syso/pkg.go -- +package syso + +func ObjTest() + +-- syso/src/objTestImpl.c -- +void objTestImpl() { /* Empty */ } + +-- cmd/main.go -- +package main + +import "syso" + +func main() { + syso.ObjTest() +} diff --git a/src/cmd/link/internal/arm/asm.go b/src/cmd/link/internal/arm/asm.go index 43d387c862..41efd935ee 100644 --- a/src/cmd/link/internal/arm/asm.go +++ b/src/cmd/link/internal/arm/asm.go @@ -613,7 +613,7 @@ func archreloc(ctxt *ld.Link, r *sym.Reloc, s *sym.Symbol, val int64) (int64, bo rs = rs.Outer } - if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Sect == nil { + if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Type != sym.SUNDEFEXT && rs.Sect == nil { ld.Errorf(s, "missing section for %s", rs.Name) } r.Xsym = rs diff --git a/src/cmd/link/internal/ld/data.go b/src/cmd/link/internal/ld/data.go index 2266d301dd..ea674832a9 100644 --- a/src/cmd/link/internal/ld/data.go +++ b/src/cmd/link/internal/ld/data.go @@ -96,7 +96,7 @@ func trampoline(ctxt *Link, s *sym.Symbol) { if !r.Type.IsDirectJump() { continue } - if Symaddr(r.Sym) == 0 && r.Sym.Type != sym.SDYNIMPORT { + if Symaddr(r.Sym) == 0 && (r.Sym.Type != sym.SDYNIMPORT && r.Sym.Type != sym.SUNDEFEXT) { if r.Sym.File != s.File { if !isRuntimeDepPkg(s.File) || !isRuntimeDepPkg(r.Sym.File) { ctxt.ErrorUnresolved(s, r) @@ -418,6 +418,17 @@ func relocsym(ctxt *Link, s *sym.Symbol) { } fallthrough case objabi.R_CALL, objabi.R_PCREL: + if ctxt.LinkMode == LinkExternal && r.Sym != nil && r.Sym.Type == sym.SUNDEFEXT { + // pass through to the external linker. + r.Done = false + r.Xadd = 0 + if ctxt.IsELF { + r.Xadd -= int64(r.Siz) + } + r.Xsym = r.Sym + o = 0 + break + } if ctxt.LinkMode == LinkExternal && r.Sym != nil && r.Sym.Type != sym.SCONST && (r.Sym.Sect != s.Sect || r.Type == objabi.R_GOTPCREL) { r.Done = false diff --git a/src/cmd/link/internal/ld/go.go b/src/cmd/link/internal/ld/go.go index 80d7ac32f5..37adeb7701 100644 --- a/src/cmd/link/internal/ld/go.go +++ b/src/cmd/link/internal/ld/go.go @@ -334,6 +334,24 @@ func fieldtrack(ctxt *Link) { } func (ctxt *Link) addexport() { + // Track undefined external symbols during external link. + if ctxt.LinkMode == LinkExternal { + for _, s := range ctxt.Syms.Allsym { + if !s.Attr.Reachable() || s.Attr.Special() || s.Attr.SubSymbol() { + continue + } + if s.Type != sym.STEXT { + continue + } + for i := range s.R { + r := &s.R[i] + if r.Sym != nil && r.Sym.Type == sym.Sxxx { + r.Sym.Type = sym.SUNDEFEXT + } + } + } + } + // TODO(aix) if ctxt.HeadType == objabi.Hdarwin || ctxt.HeadType == objabi.Haix { return diff --git a/src/cmd/link/internal/ld/lib.go b/src/cmd/link/internal/ld/lib.go index 182e5b0769..98c5e6ca6d 100644 --- a/src/cmd/link/internal/ld/lib.go +++ b/src/cmd/link/internal/ld/lib.go @@ -2348,7 +2348,7 @@ func genasmsym(ctxt *Link, put func(*Link, *sym.Symbol, string, SymbolType, int6 } put(ctxt, s, s.Name, BSSSym, Symaddr(s), s.Gotype) - case sym.SHOSTOBJ: + case sym.SHOSTOBJ, sym.SUNDEFEXT: if ctxt.HeadType == objabi.Hwindows || ctxt.IsELF { put(ctxt, s, s.Name, UndefinedSym, s.Value, nil) } diff --git a/src/cmd/link/internal/ld/macho.go b/src/cmd/link/internal/ld/macho.go index 7453f37c62..e9e48768c1 100644 --- a/src/cmd/link/internal/ld/macho.go +++ b/src/cmd/link/internal/ld/macho.go @@ -809,7 +809,7 @@ func machogenasmsym(ctxt *Link) { } } - if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ { + if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT { if s.Attr.Reachable() { addsym(ctxt, s, "", DataSym, 0, nil) } @@ -886,7 +886,7 @@ func machosymtab(ctxt *Link) { // replace "·" as ".", because DTrace cannot handle it. Addstring(symstr, strings.Replace(s.Extname(), "·", ".", -1)) - if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ { + if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT { symtab.AddUint8(0x01) // type N_EXT, external symbol symtab.AddUint8(0) // no section symtab.AddUint16(ctxt.Arch, 0) // desc diff --git a/src/cmd/link/internal/ld/pe.go b/src/cmd/link/internal/ld/pe.go index 12363626ae..6d4674dbfd 100644 --- a/src/cmd/link/internal/ld/pe.go +++ b/src/cmd/link/internal/ld/pe.go @@ -685,7 +685,7 @@ func (f *peFile) writeSymbols(ctxt *Link) { // Only windows/386 requires underscore prefix on external symbols. if ctxt.Arch.Family == sys.I386 && ctxt.LinkMode == LinkExternal && - (s.Type == sym.SHOSTOBJ || s.Attr.CgoExport()) { + (s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT || s.Attr.CgoExport()) { s.Name = "_" + s.Name } diff --git a/src/cmd/link/internal/ld/symtab.go b/src/cmd/link/internal/ld/symtab.go index d686a8a476..4925eda0e6 100644 --- a/src/cmd/link/internal/ld/symtab.go +++ b/src/cmd/link/internal/ld/symtab.go @@ -110,7 +110,7 @@ func putelfsym(ctxt *Link, x *sym.Symbol, s string, t SymbolType, addr int64, go } var elfshnum int - if xo.Type == sym.SDYNIMPORT || xo.Type == sym.SHOSTOBJ { + if xo.Type == sym.SDYNIMPORT || xo.Type == sym.SHOSTOBJ || xo.Type == sym.SUNDEFEXT { elfshnum = SHN_UNDEF } else { if xo.Sect == nil { diff --git a/src/cmd/link/internal/sym/symkind.go b/src/cmd/link/internal/sym/symkind.go index 4e44d3fce1..5309e07ecf 100644 --- a/src/cmd/link/internal/sym/symkind.go +++ b/src/cmd/link/internal/sym/symkind.go @@ -104,6 +104,7 @@ const ( SCONST SDYNIMPORT SHOSTOBJ + SUNDEFEXT // Undefined symbol for resolution by external linker // Sections for debugging information SDWARFSECT diff --git a/src/cmd/link/internal/sym/symkind_string.go b/src/cmd/link/internal/sym/symkind_string.go index 2732ec7654..e48d90c511 100644 --- a/src/cmd/link/internal/sym/symkind_string.go +++ b/src/cmd/link/internal/sym/symkind_string.go @@ -1,4 +1,4 @@ -// Code generated by "stringer -type=SymKind"; DO NOT EDIT. +// Code generated by "stringer -type=SymKind symkind.go"; DO NOT EDIT. package sym @@ -54,17 +54,18 @@ func _() { _ = x[SCONST-43] _ = x[SDYNIMPORT-44] _ = x[SHOSTOBJ-45] - _ = x[SDWARFSECT-46] - _ = x[SDWARFINFO-47] - _ = x[SDWARFRANGE-48] - _ = x[SDWARFLOC-49] - _ = x[SDWARFLINES-50] - _ = x[SABIALIAS-51] + _ = x[SUNDEFEXT-46] + _ = x[SDWARFSECT-47] + _ = x[SDWARFINFO-48] + _ = x[SDWARFRANGE-49] + _ = x[SDWARFLOC-50] + _ = x[SDWARFLINES-51] + _ = x[SABIALIAS-52] } -const _SymKind_name = "SxxxSTEXTSELFRXSECTSTYPESSTRINGSGOSTRINGSGOFUNCSGCBITSSRODATASFUNCTABSELFROSECTSMACHOPLTSTYPERELROSSTRINGRELROSGOSTRINGRELROSGOFUNCRELROSGCBITSRELROSRODATARELROSFUNCTABRELROSTYPELINKSITABLINKSSYMTABSPCLNTABSFirstWritableSBUILDINFOSELFSECTSMACHOSMACHOGOTSWINDOWSSELFGOTSNOPTRDATASINITARRSDATASXCOFFTOCSBSSSNOPTRBSSSTLSBSSSXREFSMACHOSYMSTRSMACHOSYMTABSMACHOINDIRECTPLTSMACHOINDIRECTGOTSFILEPATHSCONSTSDYNIMPORTSHOSTOBJSDWARFSECTSDWARFINFOSDWARFRANGESDWARFLOCSDWARFLINESSABIALIAS" +const _SymKind_name = "SxxxSTEXTSELFRXSECTSTYPESSTRINGSGOSTRINGSGOFUNCSGCBITSSRODATASFUNCTABSELFROSECTSMACHOPLTSTYPERELROSSTRINGRELROSGOSTRINGRELROSGOFUNCRELROSGCBITSRELROSRODATARELROSFUNCTABRELROSTYPELINKSITABLINKSSYMTABSPCLNTABSFirstWritableSBUILDINFOSELFSECTSMACHOSMACHOGOTSWINDOWSSELFGOTSNOPTRDATASINITARRSDATASXCOFFTOCSBSSSNOPTRBSSSTLSBSSSXREFSMACHOSYMSTRSMACHOSYMTABSMACHOINDIRECTPLTSMACHOINDIRECTGOTSFILEPATHSCONSTSDYNIMPORTSHOSTOBJSUNDEFEXTSDWARFSECTSDWARFINFOSDWARFRANGESDWARFLOCSDWARFLINESSABIALIAS" -var _SymKind_index = [...]uint16{0, 4, 9, 19, 24, 31, 40, 47, 54, 61, 69, 79, 88, 98, 110, 124, 136, 148, 160, 173, 182, 191, 198, 206, 220, 230, 238, 244, 253, 261, 268, 278, 286, 291, 300, 304, 313, 320, 325, 337, 349, 366, 383, 392, 398, 408, 416, 426, 436, 447, 456, 467, 476} +var _SymKind_index = [...]uint16{0, 4, 9, 19, 24, 31, 40, 47, 54, 61, 69, 79, 88, 98, 110, 124, 136, 148, 160, 173, 182, 191, 198, 206, 220, 230, 238, 244, 253, 261, 268, 278, 286, 291, 300, 304, 313, 320, 325, 337, 349, 366, 383, 392, 398, 408, 416, 425, 435, 445, 456, 465, 476, 485} func (i SymKind) String() string { if i >= SymKind(len(_SymKind_index)-1) { -- cgit v1.3 From e617141b0b35f14f5fe9113febcc84a2b0ecb642 Mon Sep 17 00:00:00 2001 From: Andrew Bonventre Date: Mon, 30 Sep 2019 21:41:01 -0400 Subject: cmd/go/internal/modfetch: update TestCodeRepo for gopkg.in/yaml.v2 The new yaml.v2 release broke the longtest builder. Update the expected data. Updates #28856 Change-Id: I98ec9e32e55bdb6b26b67e46dc16f34f77c2d40f Reviewed-on: https://go-review.googlesource.com/c/go/+/198117 Reviewed-by: Dmitri Shuralyov --- src/cmd/go/internal/modfetch/coderepo_test.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/cmd/go/internal/modfetch/coderepo_test.go b/src/cmd/go/internal/modfetch/coderepo_test.go index 1f2b95bd23..4977814c5f 100644 --- a/src/cmd/go/internal/modfetch/coderepo_test.go +++ b/src/cmd/go/internal/modfetch/coderepo_test.go @@ -338,10 +338,10 @@ var codeRepoTests = []codeRepoTest{ vcs: "git", path: "gopkg.in/yaml.v2", rev: "v2", - version: "v2.2.3-0.20190319135612-7b8349ac747c", - name: "7b8349ac747c6a24702b762d2c4fd9266cf4f1d6", - short: "7b8349ac747c", - time: time.Date(2019, 03, 19, 13, 56, 12, 0, time.UTC), + version: "v2.2.3", + name: "bb4e33bf68bf89cad44d386192cbed201f35b241", + short: "bb4e33bf68bf", + time: time.Date(2019, 9, 30, 19, 9, 21, 0, time.UTC), gomod: "module \"gopkg.in/yaml.v2\"\n\nrequire (\n\t\"gopkg.in/check.v1\" v0.0.0-20161208181325-20d25e280405\n)\n", }, { -- cgit v1.3 From c1635ad8f0bb9fbe5bfbf0a633c78a03930758c4 Mon Sep 17 00:00:00 2001 From: Shenghou Ma Date: Mon, 30 Sep 2019 09:44:37 -0400 Subject: runtime: fix darwin syscall performance regression While understanding why syscall.Read is 2x slower on darwin/amd64, I found out that, contrary to popular belief, the slowdown is not due to the migration to use libSystem.dylib instead of direct SYSCALLs, i.e., CL 141639 (and #17490), but due to a subtle change introduced in CL 141639. Previously, syscall.Read used syscall.Syscall(SYS_READ), whose preamble called runtime.entersyscall, but after CL 141639, syscall.Read changes to call runtime.syscall_syscall instead, which in turn calls runtime.entersyscallblock instead of runtime.entersyscall. And the entire 2x slow down can be attributed to this change. I think this is unnecessary as even though syscalls like Read might block, it does not always block, so there is no need to handoff P proactively for each Read. Additionally, we have been fine with not handing off P for each Read prior to Go 1.12, so we probably don't need to change it. This changes restores the pre-Go 1.12 behavior, where syscall preamble uses runtime.entersyscall, and we rely on sysmon to take P back from g blocked in syscalls. Change-Id: If76e97b5a7040cf1c10380a567c4f5baec3121ba Reviewed-on: https://go-review.googlesource.com/c/go/+/197938 Run-TryBot: Minux Ma TryBot-Result: Gobot Gobot Reviewed-by: Keith Randall Reviewed-by: Ian Lance Taylor --- src/runtime/sys_darwin.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/runtime/sys_darwin.go b/src/runtime/sys_darwin.go index 932a2a7757..46825d5937 100644 --- a/src/runtime/sys_darwin.go +++ b/src/runtime/sys_darwin.go @@ -60,7 +60,7 @@ func libcCall(fn, arg unsafe.Pointer) int32 { //go:nosplit //go:cgo_unsafe_args func syscall_syscall(fn, a1, a2, a3 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall)), unsafe.Pointer(&fn)) exitsyscall() return @@ -71,7 +71,7 @@ func syscall() //go:nosplit //go:cgo_unsafe_args func syscall_syscall6(fn, a1, a2, a3, a4, a5, a6 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall6)), unsafe.Pointer(&fn)) exitsyscall() return @@ -82,7 +82,7 @@ func syscall6() //go:nosplit //go:cgo_unsafe_args func syscall_syscall6X(fn, a1, a2, a3, a4, a5, a6 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall6X)), unsafe.Pointer(&fn)) exitsyscall() return @@ -93,7 +93,7 @@ func syscall6X() //go:nosplit //go:cgo_unsafe_args func syscall_syscallPtr(fn, a1, a2, a3 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscallPtr)), unsafe.Pointer(&fn)) exitsyscall() return -- cgit v1.3 From 4f13a9c5b1bfc9ec2213d9ee7d9df49661b119dd Mon Sep 17 00:00:00 2001 From: Ariel Mashraki Date: Tue, 1 Oct 2019 01:10:44 +0300 Subject: text/template/parse: use strings.Builder in String methods As mentioned in godoc, strings.Builder is more efficient for concatenating and building strings. Running a simple bench test on VariableNode.String() gives: benchmark old ns/op new ns/op delta BenchmarkParseLarge-8 25676831 24453285 -4.77% BenchmarkVariableString-8 296 115 -61.15% benchmark old allocs new allocs delta BenchmarkVariableString-8 8 3 -62.50% benchmark old bytes new bytes delta BenchmarkVariableString-8 112 72 -35.71% Change-Id: I13c9340080738fcad1edeed859d33ba608e4b05a Reviewed-on: https://go-review.googlesource.com/c/go/+/198078 Reviewed-by: Emmanuel Odeke Run-TryBot: Emmanuel Odeke TryBot-Result: Gobot Gobot --- src/text/template/parse/node.go | 41 +++++++++++++++++++---------------- src/text/template/parse/parse_test.go | 16 ++++++++++++++ 2 files changed, 38 insertions(+), 19 deletions(-) (limited to 'src') diff --git a/src/text/template/parse/node.go b/src/text/template/parse/node.go index 2f921be2ec..2eb1af0a95 100644 --- a/src/text/template/parse/node.go +++ b/src/text/template/parse/node.go @@ -160,23 +160,23 @@ func (p *PipeNode) append(command *CommandNode) { } func (p *PipeNode) String() string { - s := "" + var sb strings.Builder if len(p.Decl) > 0 { for i, v := range p.Decl { if i > 0 { - s += ", " + sb.WriteString(", ") } - s += v.String() + sb.WriteString(v.String()) } - s += " := " + sb.WriteString(" := ") } for i, c := range p.Cmds { if i > 0 { - s += " | " + sb.WriteString(" | ") } - s += c.String() + sb.WriteString(c.String()) } - return s + return sb.String() } func (p *PipeNode) tree() *Tree { @@ -249,18 +249,20 @@ func (c *CommandNode) append(arg Node) { } func (c *CommandNode) String() string { - s := "" + var sb strings.Builder for i, arg := range c.Args { if i > 0 { - s += " " + sb.WriteByte(' ') } if arg, ok := arg.(*PipeNode); ok { - s += "(" + arg.String() + ")" + sb.WriteByte('(') + sb.WriteString(arg.String()) + sb.WriteByte(')') continue } - s += arg.String() + sb.WriteString(arg.String()) } - return s + return sb.String() } func (c *CommandNode) tree() *Tree { @@ -333,14 +335,14 @@ func (t *Tree) newVariable(pos Pos, ident string) *VariableNode { } func (v *VariableNode) String() string { - s := "" + var sb strings.Builder for i, id := range v.Ident { if i > 0 { - s += "." + sb.WriteByte('.') } - s += id + sb.WriteString(id) } - return s + return sb.String() } func (v *VariableNode) tree() *Tree { @@ -426,11 +428,12 @@ func (t *Tree) newField(pos Pos, ident string) *FieldNode { } func (f *FieldNode) String() string { - s := "" + var sb strings.Builder for _, id := range f.Ident { - s += "." + id + sb.WriteByte('.') + sb.WriteString(id) } - return s + return sb.String() } func (f *FieldNode) tree() *Tree { diff --git a/src/text/template/parse/parse_test.go b/src/text/template/parse/parse_test.go index 6932cf232e..371de5d67c 100644 --- a/src/text/template/parse/parse_test.go +++ b/src/text/template/parse/parse_test.go @@ -553,3 +553,19 @@ func BenchmarkParseLarge(b *testing.B) { } } } + +var sink string + +func BenchmarkVariableString(b *testing.B) { + v := &VariableNode{ + Ident: []string{"$", "A", "BB", "CCC", "THIS_IS_THE_VARIABLE_BEING_PROCESSED"}, + } + b.ResetTimer() + b.ReportAllocs() + for i := 0; i < b.N; i++ { + sink = v.String() + } + if sink == "" { + b.Fatal("Benchmark was not run") + } +} -- cgit v1.3 From af880809d8c3896a7d37d7547c290cd9bc34530f Mon Sep 17 00:00:00 2001 From: Alex Brainman Date: Thu, 26 Sep 2019 16:37:02 +1000 Subject: cmd/link: MapViewOfFile output file MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit CL 170738 used mmap for writing most of the output file content. This change implements similar functionality for Windows. The output of compilebench -count=5 command before and after this change name old time/op new time/op delta Template 254ms ±14% 239ms ±10% ~ (p=0.222 n=5+5) Unicode 119ms ±14% 113ms ±12% ~ (p=0.421 n=5+5) GoTypes 892ms ±23% 850ms ± 1% ~ (p=0.841 n=5+5) Compiler 3.86s ± 2% 3.82s ± 1% ~ (p=0.222 n=5+5) SSA 12.6s ± 1% 12.6s ± 1% ~ (p=0.095 n=5+5) Flate 162ms ±18% 149ms ± 1% -7.91% (p=0.016 n=5+5) GoParser 199ms ±12% 184ms ± 1% ~ (p=0.056 n=5+5) Reflect 524ms ±13% 507ms ± 3% ~ (p=0.421 n=5+5) Tar 207ms ± 7% 198ms ± 0% -4.58% (p=0.016 n=5+4) XML 305ms ± 6% 299ms ± 5% ~ (p=0.690 n=5+5) LinkCompiler 1.14s ±11% 1.14s ± 3% ~ (p=0.222 n=5+5) ExternalLinkCompiler 2.80s ± 5% 2.92s ±13% ~ (p=0.222 n=5+5) LinkWithoutDebugCompiler 727ms ± 2% 750ms ± 7% ~ (p=0.151 n=5+5) StdCmd 44.0s ± 8% 43.3s ± 2% ~ (p=1.000 n=5+5) name old user-time/op new user-time/op delta Template 300ms ±27% 259ms ±34% ~ (p=0.341 n=5+5) Unicode 134ms ±51% 144ms ±67% ~ (p=0.548 n=5+5) GoTypes 1.05s ±10% 1.03s ± 6% ~ (p=0.968 n=5+5) Compiler 5.01s ± 3% 4.88s ± 3% ~ (p=0.286 n=5+5) SSA 16.8s ± 1% 16.7s ± 1% -0.95% (p=0.008 n=5+5) Flate 178ms ±67% 181ms ±38% ~ (p=0.849 n=5+5) GoParser 231ms ±32% 219ms ±21% ~ (p=0.810 n=5+5) Reflect 634ms ±33% 650ms ± 6% ~ (p=0.135 n=5+5) Tar 219ms ±36% 231ms ±19% ~ (p=0.905 n=5+5) XML 378ms ±20% 366ms ±23% ~ (p=0.913 n=5+5) LinkCompiler 1.34s ±15% 1.32s ±10% ~ (p=0.730 n=5+5) ExternalLinkCompiler 1.22s ±13% 1.18s ±15% ~ (p=0.873 n=5+5) LinkWithoutDebugCompiler 847ms ±13% 841ms ±21% ~ (p=0.667 n=5+5) name old text-bytes new text-bytes delta HelloSize 767kB ± 0% 767kB ± 0% ~ (all equal) CmdGoSize 10.6MB ± 0% 10.6MB ± 0% ~ (all equal) name old data-bytes new data-bytes delta HelloSize 10.1kB ± 0% 10.1kB ± 0% ~ (all equal) CmdGoSize 310kB ± 0% 310kB ± 0% ~ (all equal) name old bss-bytes new bss-bytes delta HelloSize 0.00B 0.00B ~ (all equal) CmdGoSize 0.00B 0.00B ~ (all equal) name old exe-bytes new exe-bytes delta HelloSize 1.10MB ± 0% 1.10MB ± 0% ~ (all equal) CmdGoSize 14.7MB ± 0% 14.7MB ± 0% ~ (all equal) Change-Id: I653f63213b9cc8a4b05f71938e34b5d53b05e3f5 Reviewed-on: https://go-review.googlesource.com/c/go/+/196846 Run-TryBot: Alex Brainman TryBot-Result: Gobot Gobot Reviewed-by: Austin Clements --- src/cmd/link/internal/ld/outbuf_nommap.go | 2 +- src/cmd/link/internal/ld/outbuf_windows.go | 47 ++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+), 1 deletion(-) create mode 100644 src/cmd/link/internal/ld/outbuf_windows.go (limited to 'src') diff --git a/src/cmd/link/internal/ld/outbuf_nommap.go b/src/cmd/link/internal/ld/outbuf_nommap.go index 36a3286099..fba8cd8bc4 100644 --- a/src/cmd/link/internal/ld/outbuf_nommap.go +++ b/src/cmd/link/internal/ld/outbuf_nommap.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// +build !darwin,!dragonfly,!freebsd,!linux,!openbsd +// +build !darwin,!dragonfly,!freebsd,!linux,!openbsd,!windows package ld diff --git a/src/cmd/link/internal/ld/outbuf_windows.go b/src/cmd/link/internal/ld/outbuf_windows.go new file mode 100644 index 0000000000..4366a83c33 --- /dev/null +++ b/src/cmd/link/internal/ld/outbuf_windows.go @@ -0,0 +1,47 @@ +// Copyright 2019 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package ld + +import ( + "reflect" + "syscall" + "unsafe" +) + +func (out *OutBuf) Mmap(filesize uint64) error { + err := out.f.Truncate(int64(filesize)) + if err != nil { + Exitf("resize output file failed: %v", err) + } + + low, high := uint32(filesize), uint32(filesize>>32) + fmap, err := syscall.CreateFileMapping(syscall.Handle(out.f.Fd()), nil, syscall.PAGE_READONLY, high, low, nil) + if err != nil { + return err + } + defer syscall.CloseHandle(fmap) + + ptr, err := syscall.MapViewOfFile(fmap, syscall.FILE_MAP_READ|syscall.FILE_MAP_WRITE, 0, 0, uintptr(filesize)) + if err != nil { + return err + } + *(*reflect.SliceHeader)(unsafe.Pointer(&out.buf)) = reflect.SliceHeader{Data: ptr, Len: int(filesize), Cap: int(filesize)} + return nil +} + +func (out *OutBuf) Munmap() { + if out.buf == nil { + return + } + err := syscall.UnmapViewOfFile(uintptr(unsafe.Pointer(&out.buf[0]))) + if err != nil { + Exitf("UnmapViewOfFile failed: %v", err) + } +} + +func (out *OutBuf) Msync() error { + // does nothing on windows + return nil +} -- cgit v1.3 From 1820cca7d735574b4ac9647d3a8b996b5f97f3cc Mon Sep 17 00:00:00 2001 From: Andrew Bonventre Date: Tue, 1 Oct 2019 13:01:44 +0000 Subject: Revert "cmd/link: load symbols from .syso in external link mode" This reverts CL 186417. Reason for revert: Broke darwin (10_14), linux (ppc), aix (ppc) Updates #33139 Change-Id: I8bf3c817a96a0e57e45754a097cea7062b2fcdfd Reviewed-on: https://go-review.googlesource.com/c/go/+/198177 Run-TryBot: Andrew Bonventre TryBot-Result: Gobot Gobot Reviewed-by: Bryan C. Mills --- .../go/testdata/script/link_syso_issue33139.txt | 29 ---------------------- src/cmd/link/internal/arm/asm.go | 2 +- src/cmd/link/internal/ld/data.go | 13 +--------- src/cmd/link/internal/ld/go.go | 18 -------------- src/cmd/link/internal/ld/lib.go | 2 +- src/cmd/link/internal/ld/macho.go | 4 +-- src/cmd/link/internal/ld/pe.go | 2 +- src/cmd/link/internal/ld/symtab.go | 2 +- src/cmd/link/internal/sym/symkind.go | 1 - src/cmd/link/internal/sym/symkind_string.go | 19 +++++++------- 10 files changed, 16 insertions(+), 76 deletions(-) delete mode 100644 src/cmd/go/testdata/script/link_syso_issue33139.txt (limited to 'src') diff --git a/src/cmd/go/testdata/script/link_syso_issue33139.txt b/src/cmd/go/testdata/script/link_syso_issue33139.txt deleted file mode 100644 index 53587e6823..0000000000 --- a/src/cmd/go/testdata/script/link_syso_issue33139.txt +++ /dev/null @@ -1,29 +0,0 @@ -# Test that we can use the external linker with a host syso file that is -# embedded in a package, that is referenced by a Go assembly stub. -# See issue 33139. -[!gc] stop -cc -c -o syso/objTestImpl.syso syso/src/objTestImpl.c -go build -ldflags='-linkmode=external' ./cmd/main.go - --- syso/objTest.s -- -#include "textflag.h" - -TEXT ·ObjTest(SB), NOSPLIT, $0 - JMP objTestImpl(SB) - --- syso/pkg.go -- -package syso - -func ObjTest() - --- syso/src/objTestImpl.c -- -void objTestImpl() { /* Empty */ } - --- cmd/main.go -- -package main - -import "syso" - -func main() { - syso.ObjTest() -} diff --git a/src/cmd/link/internal/arm/asm.go b/src/cmd/link/internal/arm/asm.go index 41efd935ee..43d387c862 100644 --- a/src/cmd/link/internal/arm/asm.go +++ b/src/cmd/link/internal/arm/asm.go @@ -613,7 +613,7 @@ func archreloc(ctxt *ld.Link, r *sym.Reloc, s *sym.Symbol, val int64) (int64, bo rs = rs.Outer } - if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Type != sym.SUNDEFEXT && rs.Sect == nil { + if rs.Type != sym.SHOSTOBJ && rs.Type != sym.SDYNIMPORT && rs.Sect == nil { ld.Errorf(s, "missing section for %s", rs.Name) } r.Xsym = rs diff --git a/src/cmd/link/internal/ld/data.go b/src/cmd/link/internal/ld/data.go index ea674832a9..2266d301dd 100644 --- a/src/cmd/link/internal/ld/data.go +++ b/src/cmd/link/internal/ld/data.go @@ -96,7 +96,7 @@ func trampoline(ctxt *Link, s *sym.Symbol) { if !r.Type.IsDirectJump() { continue } - if Symaddr(r.Sym) == 0 && (r.Sym.Type != sym.SDYNIMPORT && r.Sym.Type != sym.SUNDEFEXT) { + if Symaddr(r.Sym) == 0 && r.Sym.Type != sym.SDYNIMPORT { if r.Sym.File != s.File { if !isRuntimeDepPkg(s.File) || !isRuntimeDepPkg(r.Sym.File) { ctxt.ErrorUnresolved(s, r) @@ -418,17 +418,6 @@ func relocsym(ctxt *Link, s *sym.Symbol) { } fallthrough case objabi.R_CALL, objabi.R_PCREL: - if ctxt.LinkMode == LinkExternal && r.Sym != nil && r.Sym.Type == sym.SUNDEFEXT { - // pass through to the external linker. - r.Done = false - r.Xadd = 0 - if ctxt.IsELF { - r.Xadd -= int64(r.Siz) - } - r.Xsym = r.Sym - o = 0 - break - } if ctxt.LinkMode == LinkExternal && r.Sym != nil && r.Sym.Type != sym.SCONST && (r.Sym.Sect != s.Sect || r.Type == objabi.R_GOTPCREL) { r.Done = false diff --git a/src/cmd/link/internal/ld/go.go b/src/cmd/link/internal/ld/go.go index 37adeb7701..80d7ac32f5 100644 --- a/src/cmd/link/internal/ld/go.go +++ b/src/cmd/link/internal/ld/go.go @@ -334,24 +334,6 @@ func fieldtrack(ctxt *Link) { } func (ctxt *Link) addexport() { - // Track undefined external symbols during external link. - if ctxt.LinkMode == LinkExternal { - for _, s := range ctxt.Syms.Allsym { - if !s.Attr.Reachable() || s.Attr.Special() || s.Attr.SubSymbol() { - continue - } - if s.Type != sym.STEXT { - continue - } - for i := range s.R { - r := &s.R[i] - if r.Sym != nil && r.Sym.Type == sym.Sxxx { - r.Sym.Type = sym.SUNDEFEXT - } - } - } - } - // TODO(aix) if ctxt.HeadType == objabi.Hdarwin || ctxt.HeadType == objabi.Haix { return diff --git a/src/cmd/link/internal/ld/lib.go b/src/cmd/link/internal/ld/lib.go index 98c5e6ca6d..182e5b0769 100644 --- a/src/cmd/link/internal/ld/lib.go +++ b/src/cmd/link/internal/ld/lib.go @@ -2348,7 +2348,7 @@ func genasmsym(ctxt *Link, put func(*Link, *sym.Symbol, string, SymbolType, int6 } put(ctxt, s, s.Name, BSSSym, Symaddr(s), s.Gotype) - case sym.SHOSTOBJ, sym.SUNDEFEXT: + case sym.SHOSTOBJ: if ctxt.HeadType == objabi.Hwindows || ctxt.IsELF { put(ctxt, s, s.Name, UndefinedSym, s.Value, nil) } diff --git a/src/cmd/link/internal/ld/macho.go b/src/cmd/link/internal/ld/macho.go index e9e48768c1..7453f37c62 100644 --- a/src/cmd/link/internal/ld/macho.go +++ b/src/cmd/link/internal/ld/macho.go @@ -809,7 +809,7 @@ func machogenasmsym(ctxt *Link) { } } - if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT { + if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ { if s.Attr.Reachable() { addsym(ctxt, s, "", DataSym, 0, nil) } @@ -886,7 +886,7 @@ func machosymtab(ctxt *Link) { // replace "·" as ".", because DTrace cannot handle it. Addstring(symstr, strings.Replace(s.Extname(), "·", ".", -1)) - if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT { + if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ { symtab.AddUint8(0x01) // type N_EXT, external symbol symtab.AddUint8(0) // no section symtab.AddUint16(ctxt.Arch, 0) // desc diff --git a/src/cmd/link/internal/ld/pe.go b/src/cmd/link/internal/ld/pe.go index 6d4674dbfd..12363626ae 100644 --- a/src/cmd/link/internal/ld/pe.go +++ b/src/cmd/link/internal/ld/pe.go @@ -685,7 +685,7 @@ func (f *peFile) writeSymbols(ctxt *Link) { // Only windows/386 requires underscore prefix on external symbols. if ctxt.Arch.Family == sys.I386 && ctxt.LinkMode == LinkExternal && - (s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT || s.Attr.CgoExport()) { + (s.Type == sym.SHOSTOBJ || s.Attr.CgoExport()) { s.Name = "_" + s.Name } diff --git a/src/cmd/link/internal/ld/symtab.go b/src/cmd/link/internal/ld/symtab.go index 4925eda0e6..d686a8a476 100644 --- a/src/cmd/link/internal/ld/symtab.go +++ b/src/cmd/link/internal/ld/symtab.go @@ -110,7 +110,7 @@ func putelfsym(ctxt *Link, x *sym.Symbol, s string, t SymbolType, addr int64, go } var elfshnum int - if xo.Type == sym.SDYNIMPORT || xo.Type == sym.SHOSTOBJ || xo.Type == sym.SUNDEFEXT { + if xo.Type == sym.SDYNIMPORT || xo.Type == sym.SHOSTOBJ { elfshnum = SHN_UNDEF } else { if xo.Sect == nil { diff --git a/src/cmd/link/internal/sym/symkind.go b/src/cmd/link/internal/sym/symkind.go index 5309e07ecf..4e44d3fce1 100644 --- a/src/cmd/link/internal/sym/symkind.go +++ b/src/cmd/link/internal/sym/symkind.go @@ -104,7 +104,6 @@ const ( SCONST SDYNIMPORT SHOSTOBJ - SUNDEFEXT // Undefined symbol for resolution by external linker // Sections for debugging information SDWARFSECT diff --git a/src/cmd/link/internal/sym/symkind_string.go b/src/cmd/link/internal/sym/symkind_string.go index e48d90c511..2732ec7654 100644 --- a/src/cmd/link/internal/sym/symkind_string.go +++ b/src/cmd/link/internal/sym/symkind_string.go @@ -1,4 +1,4 @@ -// Code generated by "stringer -type=SymKind symkind.go"; DO NOT EDIT. +// Code generated by "stringer -type=SymKind"; DO NOT EDIT. package sym @@ -54,18 +54,17 @@ func _() { _ = x[SCONST-43] _ = x[SDYNIMPORT-44] _ = x[SHOSTOBJ-45] - _ = x[SUNDEFEXT-46] - _ = x[SDWARFSECT-47] - _ = x[SDWARFINFO-48] - _ = x[SDWARFRANGE-49] - _ = x[SDWARFLOC-50] - _ = x[SDWARFLINES-51] - _ = x[SABIALIAS-52] + _ = x[SDWARFSECT-46] + _ = x[SDWARFINFO-47] + _ = x[SDWARFRANGE-48] + _ = x[SDWARFLOC-49] + _ = x[SDWARFLINES-50] + _ = x[SABIALIAS-51] } -const _SymKind_name = "SxxxSTEXTSELFRXSECTSTYPESSTRINGSGOSTRINGSGOFUNCSGCBITSSRODATASFUNCTABSELFROSECTSMACHOPLTSTYPERELROSSTRINGRELROSGOSTRINGRELROSGOFUNCRELROSGCBITSRELROSRODATARELROSFUNCTABRELROSTYPELINKSITABLINKSSYMTABSPCLNTABSFirstWritableSBUILDINFOSELFSECTSMACHOSMACHOGOTSWINDOWSSELFGOTSNOPTRDATASINITARRSDATASXCOFFTOCSBSSSNOPTRBSSSTLSBSSSXREFSMACHOSYMSTRSMACHOSYMTABSMACHOINDIRECTPLTSMACHOINDIRECTGOTSFILEPATHSCONSTSDYNIMPORTSHOSTOBJSUNDEFEXTSDWARFSECTSDWARFINFOSDWARFRANGESDWARFLOCSDWARFLINESSABIALIAS" +const _SymKind_name = "SxxxSTEXTSELFRXSECTSTYPESSTRINGSGOSTRINGSGOFUNCSGCBITSSRODATASFUNCTABSELFROSECTSMACHOPLTSTYPERELROSSTRINGRELROSGOSTRINGRELROSGOFUNCRELROSGCBITSRELROSRODATARELROSFUNCTABRELROSTYPELINKSITABLINKSSYMTABSPCLNTABSFirstWritableSBUILDINFOSELFSECTSMACHOSMACHOGOTSWINDOWSSELFGOTSNOPTRDATASINITARRSDATASXCOFFTOCSBSSSNOPTRBSSSTLSBSSSXREFSMACHOSYMSTRSMACHOSYMTABSMACHOINDIRECTPLTSMACHOINDIRECTGOTSFILEPATHSCONSTSDYNIMPORTSHOSTOBJSDWARFSECTSDWARFINFOSDWARFRANGESDWARFLOCSDWARFLINESSABIALIAS" -var _SymKind_index = [...]uint16{0, 4, 9, 19, 24, 31, 40, 47, 54, 61, 69, 79, 88, 98, 110, 124, 136, 148, 160, 173, 182, 191, 198, 206, 220, 230, 238, 244, 253, 261, 268, 278, 286, 291, 300, 304, 313, 320, 325, 337, 349, 366, 383, 392, 398, 408, 416, 425, 435, 445, 456, 465, 476, 485} +var _SymKind_index = [...]uint16{0, 4, 9, 19, 24, 31, 40, 47, 54, 61, 69, 79, 88, 98, 110, 124, 136, 148, 160, 173, 182, 191, 198, 206, 220, 230, 238, 244, 253, 261, 268, 278, 286, 291, 300, 304, 313, 320, 325, 337, 349, 366, 383, 392, 398, 408, 416, 426, 436, 447, 456, 467, 476} func (i SymKind) String() string { if i >= SymKind(len(_SymKind_index)-1) { -- cgit v1.3 From a49067aab6eeff36d7219142ed52cc3db4d6c1d8 Mon Sep 17 00:00:00 2001 From: Nuno Cruces Date: Tue, 1 Oct 2019 09:31:50 +0000 Subject: net/http: avoid sending unspecified time for directories Change applies to sendFile. This is already done for sendContent. Change-Id: If43d9ab99e6e66a1363b08e0bdcceb57df1f855c GitHub-Last-Rev: 1c47620a09a6f5e2b3d777fadaad6e0189de4af5 GitHub-Pull-Request: golang/go#34631 Reviewed-on: https://go-review.googlesource.com/c/go/+/198139 Reviewed-by: Brad Fitzpatrick Run-TryBot: Brad Fitzpatrick TryBot-Result: Gobot Gobot --- src/net/http/fs.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/net/http/fs.go b/src/net/http/fs.go index 27512411de..80c391d1c3 100644 --- a/src/net/http/fs.go +++ b/src/net/http/fs.go @@ -610,7 +610,7 @@ func serveFile(w ResponseWriter, r *Request, fs FileSystem, name string, redirec writeNotModified(w) return } - w.Header().Set("Last-Modified", d.ModTime().UTC().Format(TimeFormat)) + setLastModified(w, d.ModTime()) dirList(w, r, f) return } -- cgit v1.3 From 09c9bced825593aedfd79af5c35916392f43113c Mon Sep 17 00:00:00 2001 From: Clément Chigot Date: Mon, 30 Sep 2019 11:24:19 +0200 Subject: cmd/internal/obj/ppc64: Fix ADUFFxxxx generation on aix/ppc64 ADUFFCOPY and ADUFFZERO instructions weren't handled by rewriteToUseTOC. These instructions are considered as a simple branch except with -dynlink where they become an indirect call. Fixes #34604 Change-Id: I16ca6a152164966fb9cbf792219a8a39aad2b53b Reviewed-on: https://go-review.googlesource.com/c/go/+/197842 Reviewed-by: Cherry Zhang Run-TryBot: Cherry Zhang TryBot-Result: Gobot Gobot --- src/cmd/internal/obj/ppc64/obj9.go | 62 ++++++++++++++++++++++++++++++++++++-- 1 file changed, 59 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/cmd/internal/obj/ppc64/obj9.go b/src/cmd/internal/obj/ppc64/obj9.go index 30a8414d4a..916116d1a3 100644 --- a/src/cmd/internal/obj/ppc64/obj9.go +++ b/src/cmd/internal/obj/ppc64/obj9.go @@ -106,10 +106,10 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) { p.As = AADD } } - if c.ctxt.Flag_dynlink { - c.rewriteToUseGot(p) - } else if c.ctxt.Headtype == objabi.Haix { + if c.ctxt.Headtype == objabi.Haix { c.rewriteToUseTOC(p) + } else if c.ctxt.Flag_dynlink { + c.rewriteToUseGot(p) } } @@ -120,6 +120,62 @@ func (c *ctxt9) rewriteToUseTOC(p *obj.Prog) { return } + if p.As == obj.ADUFFCOPY || p.As == obj.ADUFFZERO { + // ADUFFZERO/ADUFFCOPY is considered as an ABL except in dynamic + // link where it should be an indirect call. + if !c.ctxt.Flag_dynlink { + return + } + // ADUFFxxx $offset + // becomes + // MOVD runtime.duffxxx@TOC, R12 + // ADD $offset, R12 + // MOVD R12, CTR + // BL (CTR) + var sym *obj.LSym + if p.As == obj.ADUFFZERO { + sym = c.ctxt.Lookup("runtime.duffzero") + } else { + sym = c.ctxt.Lookup("runtime.duffcopy") + } + // Retrieve or create the TOC anchor. + symtoc := c.ctxt.LookupInit("TOC."+sym.Name, func(s *obj.LSym) { + s.Type = objabi.SDATA + s.Set(obj.AttrDuplicateOK, true) + c.ctxt.Data = append(c.ctxt.Data, s) + s.WriteAddr(c.ctxt, 0, 8, sym, 0) + }) + + offset := p.To.Offset + p.As = AMOVD + p.From.Type = obj.TYPE_MEM + p.From.Name = obj.NAME_TOCREF + p.From.Sym = symtoc + p.To.Type = obj.TYPE_REG + p.To.Reg = REG_R12 + p.To.Name = obj.NAME_NONE + p.To.Offset = 0 + p.To.Sym = nil + p1 := obj.Appendp(p, c.newprog) + p1.As = AADD + p1.From.Type = obj.TYPE_CONST + p1.From.Offset = offset + p1.To.Type = obj.TYPE_REG + p1.To.Reg = REG_R12 + p2 := obj.Appendp(p1, c.newprog) + p2.As = AMOVD + p2.From.Type = obj.TYPE_REG + p2.From.Reg = REG_R12 + p2.To.Type = obj.TYPE_REG + p2.To.Reg = REG_CTR + p3 := obj.Appendp(p2, c.newprog) + p3.As = obj.ACALL + p3.From.Type = obj.TYPE_REG + p3.From.Reg = REG_R12 + p3.To.Type = obj.TYPE_REG + p3.To.Reg = REG_CTR + } + var source *obj.Addr if p.From.Name == obj.NAME_EXTERN || p.From.Name == obj.NAME_STATIC { if p.From.Type == obj.TYPE_ADDR { -- cgit v1.3 From 86cd6c2ee5c5e4c5b5edf4ea8d1c85f80d9706a8 Mon Sep 17 00:00:00 2001 From: Ariel Mashraki Date: Tue, 1 Oct 2019 18:39:29 +0300 Subject: text/template/parse: use strings.Builder in Chain and List nodes This CL is a continuation of 198078. Benchmark output: benchmark old ns/op new ns/op delta BenchmarkParseLarge-8 24759165 24516563 -0.98% BenchmarkVariableString-8 115 115 +0.00% BenchmarkListString-8 924 680 -26.41% benchmark old allocs new allocs delta BenchmarkVariableString-8 3 3 +0.00% BenchmarkListString-8 14 13 -7.14% benchmark old bytes new bytes delta BenchmarkVariableString-8 72 72 +0.00% BenchmarkListString-8 512 424 -17.19% Change-Id: I9ec48fe4832437c556a5fa94d4cbf6e29e28d944 Reviewed-on: https://go-review.googlesource.com/c/go/+/198080 Reviewed-by: Emmanuel Odeke Run-TryBot: Emmanuel Odeke TryBot-Result: Gobot Gobot --- src/text/template/parse/node.go | 20 ++++++++++++-------- src/text/template/parse/parse_test.go | 22 +++++++++++++++++++--- 2 files changed, 31 insertions(+), 11 deletions(-) (limited to 'src') diff --git a/src/text/template/parse/node.go b/src/text/template/parse/node.go index 2eb1af0a95..61c6853679 100644 --- a/src/text/template/parse/node.go +++ b/src/text/template/parse/node.go @@ -7,7 +7,6 @@ package parse import ( - "bytes" "fmt" "strconv" "strings" @@ -94,11 +93,11 @@ func (l *ListNode) tree() *Tree { } func (l *ListNode) String() string { - b := new(bytes.Buffer) + var sb strings.Builder for _, n := range l.Nodes { - fmt.Fprint(b, n) + sb.WriteString(n.String()) } - return b.String() + return sb.String() } func (l *ListNode) CopyList() *ListNode { @@ -472,14 +471,19 @@ func (c *ChainNode) Add(field string) { } func (c *ChainNode) String() string { - s := c.Node.String() + var sb strings.Builder if _, ok := c.Node.(*PipeNode); ok { - s = "(" + s + ")" + sb.WriteByte('(') + sb.WriteString(c.Node.String()) + sb.WriteByte(')') + } else { + sb.WriteString(c.Node.String()) } for _, field := range c.Field { - s += "." + field + sb.WriteByte('.') + sb.WriteString(field) } - return s + return sb.String() } func (c *ChainNode) tree() *Tree { diff --git a/src/text/template/parse/parse_test.go b/src/text/template/parse/parse_test.go index 371de5d67c..86a100bb5f 100644 --- a/src/text/template/parse/parse_test.go +++ b/src/text/template/parse/parse_test.go @@ -554,7 +554,7 @@ func BenchmarkParseLarge(b *testing.B) { } } -var sink string +var sinkv, sinkl string func BenchmarkVariableString(b *testing.B) { v := &VariableNode{ @@ -563,9 +563,25 @@ func BenchmarkVariableString(b *testing.B) { b.ResetTimer() b.ReportAllocs() for i := 0; i < b.N; i++ { - sink = v.String() + sinkv = v.String() } - if sink == "" { + if sinkv == "" { + b.Fatal("Benchmark was not run") + } +} + +func BenchmarkListString(b *testing.B) { + text := `{{ (printf .Field1.Field2.Field3).Value }}` + tree, err := New("bench").Parse(text, "", "", make(map[string]*Tree), builtins) + if err != nil { + b.Fatal(err) + } + b.ResetTimer() + b.ReportAllocs() + for i := 0; i < b.N; i++ { + sinkl = tree.Root.String() + } + if sinkl == "" { b.Fatal("Benchmark was not run") } } -- cgit v1.3 From 93a79bbcc0de229679ddeb2ad662ec8cea5b3de6 Mon Sep 17 00:00:00 2001 From: Ariel Mashraki Date: Tue, 1 Oct 2019 21:12:59 +0300 Subject: text/template/parse: remove duplication in peekNonSpace nextNonSpace has an identical code except the call to backup at the end. Change-Id: Iefa5b13950007da38323a800fb6b0ce3d436254b Reviewed-on: https://go-review.googlesource.com/c/go/+/198277 Run-TryBot: Rob Pike TryBot-Result: Gobot Gobot Reviewed-by: Rob Pike --- src/text/template/parse/parse.go | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) (limited to 'src') diff --git a/src/text/template/parse/parse.go b/src/text/template/parse/parse.go index 7c35b0ff3d..c9b80f4a24 100644 --- a/src/text/template/parse/parse.go +++ b/src/text/template/parse/parse.go @@ -108,13 +108,8 @@ func (t *Tree) nextNonSpace() (token item) { } // peekNonSpace returns but does not consume the next non-space token. -func (t *Tree) peekNonSpace() (token item) { - for { - token = t.next() - if token.typ != itemSpace { - break - } - } +func (t *Tree) peekNonSpace() item { + token := t.nextNonSpace() t.backup() return token } -- cgit v1.3 From a1b0af9904e3cc1cd169da7f0e5ad81420cd728e Mon Sep 17 00:00:00 2001 From: "Bryan C. Mills" Date: Tue, 1 Oct 2019 12:52:16 -0400 Subject: internal/goversion: update to 1.14 In #33848, we propose to use 'go 1.14' in the go.mod file to enable new default behavior. That means that 'go mod init' needs to start generating that directive by default, which requires the presence of the updated version tag in the build environment. Updates #33848 Change-Id: I9f3b8845fdfd843fd76de32f4b55d8f765d691de Reviewed-on: https://go-review.googlesource.com/c/go/+/198318 Run-TryBot: Bryan C. Mills TryBot-Result: Gobot Gobot Reviewed-by: Jay Conrod --- src/go/build/doc.go | 1 + src/internal/goversion/goversion.go | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/go/build/doc.go b/src/go/build/doc.go index de793efa87..47dec5a05d 100644 --- a/src/go/build/doc.go +++ b/src/go/build/doc.go @@ -111,6 +111,7 @@ // - "go1.11", from Go version 1.11 onward // - "go1.12", from Go version 1.12 onward // - "go1.13", from Go version 1.13 onward +// - "go1.14", from Go version 1.14 onward // - any additional words listed in ctxt.BuildTags // // There are no build tags for beta or minor releases. diff --git a/src/internal/goversion/goversion.go b/src/internal/goversion/goversion.go index 8f9c7c99c2..c5783337b3 100644 --- a/src/internal/goversion/goversion.go +++ b/src/internal/goversion/goversion.go @@ -10,4 +10,4 @@ package goversion // // When incrementing this, also add to the list at src/go/build/doc.go // (search for "onward"). -const Version = 13 +const Version = 14 -- cgit v1.3 From e79b57d6c40a25393b2d831b244b19548e23b8a4 Mon Sep 17 00:00:00 2001 From: Emmanuel T Odeke Date: Mon, 11 Mar 2019 10:52:00 -0700 Subject: os/signal: lazily start signal watch loop only on Notify By lazily starting the signal watch loop only on Notify, we are able to have deadlock detection even when "os/signal" is imported. Thanks to Ian Lance Taylor for the solution and discussion. With this change in, fix a runtime gorountine count test that assumed that os/signal.init would unconditionally start the signal watching goroutine, but alas no more. Fixes #21576. Change-Id: I6eecf82a887f59f2ec8897f1bcd67ca311ca42ff Reviewed-on: https://go-review.googlesource.com/c/go/+/101036 Run-TryBot: Emmanuel Odeke TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- src/os/signal/signal.go | 15 ++++++ src/os/signal/signal_plan9.go | 3 +- src/os/signal/signal_unix.go | 3 +- src/runtime/testdata/testprogcgo/numgoroutine.go | 7 --- test/fixedbugs/issue21576.go | 60 ++++++++++++++++++++++++ 5 files changed, 79 insertions(+), 9 deletions(-) create mode 100644 test/fixedbugs/issue21576.go (limited to 'src') diff --git a/src/os/signal/signal.go b/src/os/signal/signal.go index a0eba0d50f..136dd9cc97 100644 --- a/src/os/signal/signal.go +++ b/src/os/signal/signal.go @@ -92,6 +92,15 @@ func Ignored(sig os.Signal) bool { return sn >= 0 && signalIgnored(sn) } +var ( + // watchSignalLoopOnce guards calling the conditionally + // initialized watchSignalLoop. If watchSignalLoop is non-nil, + // it will be run in a goroutine lazily once Notify is invoked. + // See Issue 21576. + watchSignalLoopOnce sync.Once + watchSignalLoop func() +) + // Notify causes package signal to relay incoming signals to c. // If no signals are provided, all incoming signals will be relayed to c. // Otherwise, just the provided signals will. @@ -113,6 +122,12 @@ func Notify(c chan<- os.Signal, sig ...os.Signal) { panic("os/signal: Notify using nil channel") } + watchSignalLoopOnce.Do(func() { + if watchSignalLoop != nil { + go watchSignalLoop() + } + }) + handlers.Lock() defer handlers.Unlock() diff --git a/src/os/signal/signal_plan9.go b/src/os/signal/signal_plan9.go index a1eb68855e..8408607c7f 100644 --- a/src/os/signal/signal_plan9.go +++ b/src/os/signal/signal_plan9.go @@ -20,7 +20,8 @@ func signal_recv() string func init() { signal_enable(0) // first call - initialize - go loop() + + watchSignalLoop = loop } func loop() { diff --git a/src/os/signal/signal_unix.go b/src/os/signal/signal_unix.go index 7fa634f15a..0bbf41bfde 100644 --- a/src/os/signal/signal_unix.go +++ b/src/os/signal/signal_unix.go @@ -26,7 +26,8 @@ func loop() { func init() { signal_enable(0) // first call - initialize - go loop() + + watchSignalLoop = loop } const ( diff --git a/src/runtime/testdata/testprogcgo/numgoroutine.go b/src/runtime/testdata/testprogcgo/numgoroutine.go index 12fda49a13..5bdfe52ed4 100644 --- a/src/runtime/testdata/testprogcgo/numgoroutine.go +++ b/src/runtime/testdata/testprogcgo/numgoroutine.go @@ -41,13 +41,6 @@ func NumGoroutine() { // Test that there are just the expected number of goroutines // running. Specifically, test that the spare M's goroutine // doesn't show up. - // - // On non-Windows platforms there's a signal handling thread - // started by os/signal.init in addition to the main - // goroutine. - if runtime.GOOS != "windows" { - baseGoroutines = 1 - } if _, ok := checkNumGoroutine("first", 1+baseGoroutines); !ok { return } diff --git a/test/fixedbugs/issue21576.go b/test/fixedbugs/issue21576.go new file mode 100644 index 0000000000..79baec94e8 --- /dev/null +++ b/test/fixedbugs/issue21576.go @@ -0,0 +1,60 @@ +// +build !nacl,!js +// run + +// Copyright 2019 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. +// +// Ensure that deadlock detection can still +// run even with an import of "_ os/signal". + +package main + +import ( + "bytes" + "context" + "io/ioutil" + "log" + "os" + "os/exec" + "path/filepath" + "time" +) + +const prog = ` +package main + +import _ "os/signal" + +func main() { + c := make(chan int) + c <- 1 +} +` + +func main() { + dir, err := ioutil.TempDir("", "21576") + if err != nil { + log.Fatal(err) + } + defer os.RemoveAll(dir) + + file := filepath.Join(dir, "main.go") + if err := ioutil.WriteFile(file, []byte(prog), 0655); err != nil { + log.Fatalf("Write error %v", err) + } + + ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) + defer cancel() + + cmd := exec.CommandContext(ctx, "go", "run", file) + output, err := cmd.CombinedOutput() + if err == nil { + log.Fatalf("Passed, expected an error") + } + + want := []byte("fatal error: all goroutines are asleep - deadlock!") + if !bytes.Contains(output, want) { + log.Fatalf("Unmatched error message %q:\nin\n%s", want, output) + } +} -- cgit v1.3 From 148ec3e3bc8083ccb9ac9b7050ce540d1e0f0539 Mon Sep 17 00:00:00 2001 From: Kyohei Kadota Date: Thu, 26 Sep 2019 13:39:52 +0900 Subject: net/http/cgi: skip tests if not functional perl TestEnvOverride sets PATH to /wibble before executing a CGI. So customized Perl that is starting with '#!/usr/bin/env bash' will fail because /usr/bin/env can't lookup bash. Fixes #27790 Change-Id: I25e433061a7ff9da8c86429e934418fc15f12f90 Reviewed-on: https://go-review.googlesource.com/c/go/+/196845 Reviewed-by: Brad Fitzpatrick Run-TryBot: Brad Fitzpatrick TryBot-Result: Gobot Gobot --- src/net/http/cgi/host_test.go | 33 +++++++++++++++++++-------------- 1 file changed, 19 insertions(+), 14 deletions(-) (limited to 'src') diff --git a/src/net/http/cgi/host_test.go b/src/net/http/cgi/host_test.go index 1790d5de98..fb869a6728 100644 --- a/src/net/http/cgi/host_test.go +++ b/src/net/http/cgi/host_test.go @@ -455,6 +455,23 @@ func TestDirUnix(t *testing.T) { runCgiTest(t, h, "GET /test.cgi HTTP/1.0\nHost: example.com\n\n", expectedMap) } +func findPerl(t *testing.T) string { + t.Helper() + perl, err := exec.LookPath("perl") + if err != nil { + t.Skip("Skipping test: perl not found.") + } + perl, _ = filepath.Abs(perl) + + cmd := exec.Command(perl, "-e", "print 123") + cmd.Env = []string{"PATH=/garbage"} + out, err := cmd.Output() + if err != nil || string(out) != "123" { + t.Skipf("Skipping test: %s is not functional", perl) + } + return perl +} + func TestDirWindows(t *testing.T) { if runtime.GOOS != "windows" { t.Skip("Skipping windows specific test.") @@ -462,13 +479,7 @@ func TestDirWindows(t *testing.T) { cgifile, _ := filepath.Abs("testdata/test.cgi") - var perl string - var err error - perl, err = exec.LookPath("perl") - if err != nil { - t.Skip("Skipping test: perl not found.") - } - perl, _ = filepath.Abs(perl) + perl := findPerl(t) cwd, _ := os.Getwd() h := &Handler{ @@ -505,13 +516,7 @@ func TestEnvOverride(t *testing.T) { check(t) cgifile, _ := filepath.Abs("testdata/test.cgi") - var perl string - var err error - perl, err = exec.LookPath("perl") - if err != nil { - t.Skipf("Skipping test: perl not found.") - } - perl, _ = filepath.Abs(perl) + perl := findPerl(t) cwd, _ := os.Getwd() h := &Handler{ -- cgit v1.3 From 274f4cef9329262dcfd4a715ab6c2ebc908d6209 Mon Sep 17 00:00:00 2001 From: "Jason A. Donenfeld" Date: Wed, 2 Oct 2019 11:25:24 +0200 Subject: cmd/link: implement Msync for Windows using FlushViewOfFile CL 196846 implemented memory mapped output files but forgot to provide an implementation for Msync. This rectifies that with a simple call to FlushViewOfFile. Change-Id: I5aebef9baf3a2a6ad54ceda096952a5d7d660bfe Reviewed-on: https://go-review.googlesource.com/c/go/+/198418 Run-TryBot: Jason A. Donenfeld Reviewed-by: Alex Brainman TryBot-Result: Gobot Gobot --- src/cmd/link/internal/ld/outbuf_windows.go | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/cmd/link/internal/ld/outbuf_windows.go b/src/cmd/link/internal/ld/outbuf_windows.go index 4366a83c33..1cb05c301f 100644 --- a/src/cmd/link/internal/ld/outbuf_windows.go +++ b/src/cmd/link/internal/ld/outbuf_windows.go @@ -42,6 +42,8 @@ func (out *OutBuf) Munmap() { } func (out *OutBuf) Msync() error { - // does nothing on windows - return nil + if out.buf == nil { + return nil + } + return syscall.FlushViewOfFile(uintptr(unsafe.Pointer(&out.buf[0])), 0) } -- cgit v1.3 From 9c2e7e8bed3368fd2b3903b47d686b5a900ebe04 Mon Sep 17 00:00:00 2001 From: Michael Munday Date: Mon, 12 Aug 2019 20:19:58 +0100 Subject: cmd/compile: allow multiple SSA block control values MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Control values are used to choose which successor of a block is jumped to. Typically a control value takes the form of a 'flags' value that represents the result of a comparison. Some architectures however use a variable in a register as a control value. Up until now we have managed with a single control value per block. However some architectures (e.g. s390x and riscv64) have combined compare-and-branch instructions that take two variables in registers as parameters. To generate these instructions we need to support 2 control values per block. This CL allows up to 2 control values to be used in a block in order to support the addition of compare-and-branch instructions. I have implemented s390x compare-and-branch instructions in a different CL. Passes toolstash-check -all. Results of compilebench: name old time/op new time/op delta Template 208ms ± 1% 209ms ± 1% ~ (p=0.289 n=20+20) Unicode 83.7ms ± 1% 83.3ms ± 3% -0.49% (p=0.017 n=18+18) GoTypes 748ms ± 1% 748ms ± 0% ~ (p=0.460 n=20+18) Compiler 3.47s ± 1% 3.48s ± 1% ~ (p=0.070 n=19+18) SSA 11.5s ± 1% 11.7s ± 1% +1.64% (p=0.000 n=19+18) Flate 130ms ± 1% 130ms ± 1% ~ (p=0.588 n=19+20) GoParser 160ms ± 1% 161ms ± 1% ~ (p=0.211 n=20+20) Reflect 465ms ± 1% 467ms ± 1% +0.42% (p=0.007 n=20+20) Tar 184ms ± 1% 185ms ± 2% ~ (p=0.087 n=18+20) XML 253ms ± 1% 253ms ± 1% ~ (p=0.377 n=20+18) LinkCompiler 769ms ± 2% 774ms ± 2% ~ (p=0.070 n=19+19) ExternalLinkCompiler 3.59s ±11% 3.68s ± 6% ~ (p=0.072 n=20+20) LinkWithoutDebugCompiler 446ms ± 5% 454ms ± 3% +1.79% (p=0.002 n=19+20) StdCmd 26.0s ± 2% 26.0s ± 2% ~ (p=0.799 n=20+20) name old user-time/op new user-time/op delta Template 238ms ± 5% 240ms ± 5% ~ (p=0.142 n=20+20) Unicode 105ms ±11% 106ms ±10% ~ (p=0.512 n=20+20) GoTypes 876ms ± 2% 873ms ± 4% ~ (p=0.647 n=20+19) Compiler 4.17s ± 2% 4.19s ± 1% ~ (p=0.093 n=20+18) SSA 13.9s ± 1% 14.1s ± 1% +1.45% (p=0.000 n=18+18) Flate 145ms ±13% 146ms ± 5% ~ (p=0.851 n=20+18) GoParser 185ms ± 5% 188ms ± 7% ~ (p=0.174 n=20+20) Reflect 534ms ± 3% 538ms ± 2% ~ (p=0.105 n=20+18) Tar 215ms ± 4% 211ms ± 9% ~ (p=0.079 n=19+20) XML 295ms ± 6% 295ms ± 5% ~ (p=0.968 n=20+20) LinkCompiler 832ms ± 4% 837ms ± 7% ~ (p=0.707 n=17+20) ExternalLinkCompiler 1.58s ± 8% 1.60s ± 4% ~ (p=0.296 n=20+19) LinkWithoutDebugCompiler 478ms ±12% 489ms ±10% ~ (p=0.429 n=20+20) name old object-bytes new object-bytes delta Template 559kB ± 0% 559kB ± 0% ~ (all equal) Unicode 216kB ± 0% 216kB ± 0% ~ (all equal) GoTypes 2.03MB ± 0% 2.03MB ± 0% ~ (all equal) Compiler 8.07MB ± 0% 8.07MB ± 0% -0.06% (p=0.000 n=20+20) SSA 27.1MB ± 0% 27.3MB ± 0% +0.89% (p=0.000 n=20+20) Flate 343kB ± 0% 343kB ± 0% ~ (all equal) GoParser 441kB ± 0% 441kB ± 0% ~ (all equal) Reflect 1.36MB ± 0% 1.36MB ± 0% ~ (all equal) Tar 487kB ± 0% 487kB ± 0% ~ (all equal) XML 632kB ± 0% 632kB ± 0% ~ (all equal) name old export-bytes new export-bytes delta Template 18.5kB ± 0% 18.5kB ± 0% ~ (all equal) Unicode 7.92kB ± 0% 7.92kB ± 0% ~ (all equal) GoTypes 35.0kB ± 0% 35.0kB ± 0% ~ (all equal) Compiler 109kB ± 0% 110kB ± 0% +0.72% (p=0.000 n=20+20) SSA 137kB ± 0% 138kB ± 0% +0.58% (p=0.000 n=20+20) Flate 4.89kB ± 0% 4.89kB ± 0% ~ (all equal) GoParser 8.49kB ± 0% 8.49kB ± 0% ~ (all equal) Reflect 11.4kB ± 0% 11.4kB ± 0% ~ (all equal) Tar 10.5kB ± 0% 10.5kB ± 0% ~ (all equal) XML 16.7kB ± 0% 16.7kB ± 0% ~ (all equal) name old text-bytes new text-bytes delta HelloSize 761kB ± 0% 761kB ± 0% ~ (all equal) CmdGoSize 10.8MB ± 0% 10.8MB ± 0% ~ (all equal) name old data-bytes new data-bytes delta HelloSize 10.7kB ± 0% 10.7kB ± 0% ~ (all equal) CmdGoSize 312kB ± 0% 312kB ± 0% ~ (all equal) name old bss-bytes new bss-bytes delta HelloSize 122kB ± 0% 122kB ± 0% ~ (all equal) CmdGoSize 146kB ± 0% 146kB ± 0% ~ (all equal) name old exe-bytes new exe-bytes delta HelloSize 1.13MB ± 0% 1.13MB ± 0% ~ (all equal) CmdGoSize 15.1MB ± 0% 15.1MB ± 0% ~ (all equal) Change-Id: I3cc2f9829a109543d9a68be4a21775d2d3e9801f Reviewed-on: https://go-review.googlesource.com/c/go/+/196557 Run-TryBot: Michael Munday TryBot-Result: Gobot Gobot Reviewed-by: Daniel Martí Reviewed-by: Keith Randall --- src/cmd/compile/internal/amd64/ssa.go | 6 +- src/cmd/compile/internal/arm/ssa.go | 2 +- src/cmd/compile/internal/arm64/ssa.go | 8 +- src/cmd/compile/internal/gc/plive.go | 2 +- src/cmd/compile/internal/mips/ssa.go | 6 +- src/cmd/compile/internal/mips64/ssa.go | 6 +- src/cmd/compile/internal/ppc64/ssa.go | 2 +- src/cmd/compile/internal/s390x/ssa.go | 6 +- src/cmd/compile/internal/ssa/README.md | 8 +- src/cmd/compile/internal/ssa/block.go | 104 +- src/cmd/compile/internal/ssa/branchelim.go | 10 +- src/cmd/compile/internal/ssa/check.go | 52 +- src/cmd/compile/internal/ssa/copyelim.go | 6 +- src/cmd/compile/internal/ssa/cse.go | 4 +- src/cmd/compile/internal/ssa/deadcode.go | 14 +- src/cmd/compile/internal/ssa/deadstore.go | 11 +- src/cmd/compile/internal/ssa/flagalloc.go | 42 +- src/cmd/compile/internal/ssa/fuse.go | 2 +- src/cmd/compile/internal/ssa/gen/386.rules | 118 +- src/cmd/compile/internal/ssa/gen/386Ops.go | 32 +- src/cmd/compile/internal/ssa/gen/AMD64.rules | 20 +- src/cmd/compile/internal/ssa/gen/AMD64Ops.go | 32 +- src/cmd/compile/internal/ssa/gen/ARM.rules | 118 +- src/cmd/compile/internal/ssa/gen/ARM64.rules | 136 +- src/cmd/compile/internal/ssa/gen/ARM64Ops.go | 40 +- src/cmd/compile/internal/ssa/gen/ARMOps.go | 20 +- src/cmd/compile/internal/ssa/gen/MIPS.rules | 24 +- src/cmd/compile/internal/ssa/gen/MIPS64.rules | 24 +- src/cmd/compile/internal/ssa/gen/MIPS64Ops.go | 16 +- src/cmd/compile/internal/ssa/gen/MIPSOps.go | 16 +- src/cmd/compile/internal/ssa/gen/PPC64.rules | 36 +- src/cmd/compile/internal/ssa/gen/PPC64Ops.go | 20 +- src/cmd/compile/internal/ssa/gen/S390X.rules | 18 +- src/cmd/compile/internal/ssa/gen/S390XOps.go | 2 +- src/cmd/compile/internal/ssa/gen/generic.rules | 4 +- src/cmd/compile/internal/ssa/gen/genericOps.go | 28 +- src/cmd/compile/internal/ssa/gen/main.go | 3 +- src/cmd/compile/internal/ssa/gen/rulegen.go | 95 +- src/cmd/compile/internal/ssa/html.go | 4 +- src/cmd/compile/internal/ssa/loopbce.go | 9 +- src/cmd/compile/internal/ssa/nilcheck.go | 5 +- src/cmd/compile/internal/ssa/nilcheck_test.go | 2 +- src/cmd/compile/internal/ssa/phiopt.go | 8 +- src/cmd/compile/internal/ssa/prove.go | 21 +- src/cmd/compile/internal/ssa/regalloc.go | 47 +- src/cmd/compile/internal/ssa/rewrite.go | 7 +- src/cmd/compile/internal/ssa/rewrite386.go | 1048 ++++---- src/cmd/compile/internal/ssa/rewriteAMD64.go | 1644 +++++++------ src/cmd/compile/internal/ssa/rewriteARM.go | 3080 ++++++++++++++---------- src/cmd/compile/internal/ssa/rewriteARM64.go | 1954 ++++++++------- src/cmd/compile/internal/ssa/rewriteMIPS.go | 338 +-- src/cmd/compile/internal/ssa/rewriteMIPS64.go | 322 +-- src/cmd/compile/internal/ssa/rewritePPC64.go | 888 ++++--- src/cmd/compile/internal/ssa/rewriteS390X.go | 118 +- src/cmd/compile/internal/ssa/rewritegeneric.go | 27 +- src/cmd/compile/internal/ssa/schedule.go | 18 +- src/cmd/compile/internal/ssa/shortcircuit.go | 4 +- src/cmd/compile/internal/ssa/sizeof_test.go | 2 +- src/cmd/compile/internal/ssa/tighten.go | 2 +- src/cmd/compile/internal/ssa/value.go | 2 +- src/cmd/compile/internal/ssa/writebarrier.go | 2 +- src/cmd/compile/internal/wasm/ssa.go | 6 +- src/cmd/compile/internal/x86/ssa.go | 6 +- 63 files changed, 6052 insertions(+), 4605 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/amd64/ssa.go b/src/cmd/compile/internal/amd64/ssa.go index 9c91e05661..b52b996407 100644 --- a/src/cmd/compile/internal/amd64/ssa.go +++ b/src/cmd/compile/internal/amd64/ssa.go @@ -18,8 +18,8 @@ import ( // markMoves marks any MOVXconst ops that need to avoid clobbering flags. func ssaMarkMoves(s *gc.SSAGenState, b *ssa.Block) { flive := b.FlagsLiveAtEnd - if b.Control != nil && b.Control.Type.IsFlags() { - flive = true + for _, c := range b.ControlValues() { + flive = c.Type.IsFlags() || flive } for i := len(b.Values) - 1; i >= 0; i-- { v := b.Values[i] @@ -1245,6 +1245,6 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/arm/ssa.go b/src/cmd/compile/internal/arm/ssa.go index ab0f417117..2c77912f21 100644 --- a/src/cmd/compile/internal/arm/ssa.go +++ b/src/cmd/compile/internal/arm/ssa.go @@ -955,6 +955,6 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/arm64/ssa.go b/src/cmd/compile/internal/arm64/ssa.go index f13bd71f7a..252e875669 100644 --- a/src/cmd/compile/internal/arm64/ssa.go +++ b/src/cmd/compile/internal/arm64/ssa.go @@ -1057,9 +1057,9 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { s.Br(obj.AJMP, b.Succs[0].Block()) } } - if !b.Control.Type.IsFlags() { + if !b.Controls[0].Type.IsFlags() { p.From.Type = obj.TYPE_REG - p.From.Reg = b.Control.Reg() + p.From.Reg = b.Controls[0].Reg() } case ssa.BlockARM64TBZ, ssa.BlockARM64TBNZ: jmp := blockJump[b.Kind] @@ -1080,9 +1080,9 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { } p.From.Offset = b.Aux.(int64) p.From.Type = obj.TYPE_CONST - p.Reg = b.Control.Reg() + p.Reg = b.Controls[0].Reg() default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/gc/plive.go b/src/cmd/compile/internal/gc/plive.go index 16a752c893..8809a644d5 100644 --- a/src/cmd/compile/internal/gc/plive.go +++ b/src/cmd/compile/internal/gc/plive.go @@ -670,7 +670,7 @@ func (lv *Liveness) markUnsafePoints() { // single op that does the memory load from the flag // address, so we look for that. var load *ssa.Value - v := wbBlock.Control + v := wbBlock.Controls[0] for { if sym, ok := v.Aux.(*obj.LSym); ok && sym == writeBarrier { load = v diff --git a/src/cmd/compile/internal/mips/ssa.go b/src/cmd/compile/internal/mips/ssa.go index 19b7c95bfd..bac8574b5c 100644 --- a/src/cmd/compile/internal/mips/ssa.go +++ b/src/cmd/compile/internal/mips/ssa.go @@ -855,11 +855,11 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { s.Br(obj.AJMP, b.Succs[0].Block()) } } - if !b.Control.Type.IsFlags() { + if !b.Controls[0].Type.IsFlags() { p.From.Type = obj.TYPE_REG - p.From.Reg = b.Control.Reg() + p.From.Reg = b.Controls[0].Reg() } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/mips64/ssa.go b/src/cmd/compile/internal/mips64/ssa.go index 7eae35373d..a70db3576c 100644 --- a/src/cmd/compile/internal/mips64/ssa.go +++ b/src/cmd/compile/internal/mips64/ssa.go @@ -829,11 +829,11 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { s.Br(obj.AJMP, b.Succs[0].Block()) } } - if !b.Control.Type.IsFlags() { + if !b.Controls[0].Type.IsFlags() { p.From.Type = obj.TYPE_REG - p.From.Reg = b.Control.Reg() + p.From.Reg = b.Controls[0].Reg() } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/ppc64/ssa.go b/src/cmd/compile/internal/ppc64/ssa.go index a12b256680..69847c38d2 100644 --- a/src/cmd/compile/internal/ppc64/ssa.go +++ b/src/cmd/compile/internal/ppc64/ssa.go @@ -1337,6 +1337,6 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { } } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/s390x/ssa.go b/src/cmd/compile/internal/s390x/ssa.go index 74e63b9f42..52ba270116 100644 --- a/src/cmd/compile/internal/s390x/ssa.go +++ b/src/cmd/compile/internal/s390x/ssa.go @@ -17,8 +17,8 @@ import ( // markMoves marks any MOVXconst ops that need to avoid clobbering flags. func ssaMarkMoves(s *gc.SSAGenState, b *ssa.Block) { flive := b.FlagsLiveAtEnd - if b.Control != nil && b.Control.Type.IsFlags() { - flive = true + for _, c := range b.ControlValues() { + flive = c.Type.IsFlags() || flive } for i := len(b.Values) - 1; i >= 0; i-- { v := b.Values[i] @@ -864,6 +864,6 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { s.Br(s390x.ABR, succs[1]) } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } diff --git a/src/cmd/compile/internal/ssa/README.md b/src/cmd/compile/internal/ssa/README.md index d283118011..4483c2c85f 100644 --- a/src/cmd/compile/internal/ssa/README.md +++ b/src/cmd/compile/internal/ssa/README.md @@ -82,10 +82,10 @@ control value, which must return a memory state. This is necessary for functions to return some values, for example - the caller needs some memory state to depend on, to ensure that it receives those return values correctly. -The last important block kind we will mention is the `if` block. Its control -value must be a boolean value, and it has exactly two successor blocks. The -control flow is handed to the first successor if the bool is true, and to the -second otherwise. +The last important block kind we will mention is the `if` block. It has a single +control value that must be a boolean value, and it has exactly two successor +blocks. The control flow is handed to the first successor if the bool is true, +and to the second otherwise. Here is a sample if-else control flow represented with basic blocks: diff --git a/src/cmd/compile/internal/ssa/block.go b/src/cmd/compile/internal/ssa/block.go index 273e5f15d7..1ccea778c2 100644 --- a/src/cmd/compile/internal/ssa/block.go +++ b/src/cmd/compile/internal/ssa/block.go @@ -40,23 +40,28 @@ type Block struct { // arguments by block id and have this field computed explicitly when needed? Preds []Edge - // A value that determines how the block is exited. Its value depends on the kind - // of the block. For instance, a BlockIf has a boolean control value and BlockExit - // has a memory control value. - Control *Value + // A list of values that determine how the block is exited. The number + // and type of control values depends on the Kind of the block. For + // instance, a BlockIf has a single boolean control value and BlockExit + // has a single memory control value. + // + // The ControlValues() method may be used to get a slice with the non-nil + // control values that can be ranged over. + // + // Controls[1] must be nil if Controls[0] is nil. + Controls [2]*Value // Auxiliary info for the block. Its value depends on the Kind. Aux interface{} // The unordered set of Values that define the operation of this block. - // The list must include the control value, if any. (TODO: need this last condition?) // After the scheduling pass, this list is ordered. Values []*Value // The containing function Func *Func - // Storage for Succs, Preds, and Values + // Storage for Succs, Preds and Values. succstorage [2]Edge predstorage [4]Edge valstorage [9]*Value @@ -96,12 +101,12 @@ func (e Edge) Index() int { return e.i } -// kind control successors +// kind controls successors // ------------------------------------------ -// Exit return mem [] -// Plain nil [next] -// If a boolean Value [then, else] -// Defer mem [nopanic, panic] (control opcode should be OpStaticCall to runtime.deferproc) +// Exit [return mem] [] +// Plain [] [next] +// If [boolean Value] [then, else] +// Defer [mem] [nopanic, panic] (control opcode should be OpStaticCall to runtime.deferproc) type BlockKind int8 // short form print @@ -115,8 +120,8 @@ func (b *Block) LongString() string { if b.Aux != nil { s += fmt.Sprintf(" %s", b.Aux) } - if b.Control != nil { - s += fmt.Sprintf(" %s", b.Control) + for _, c := range b.ControlValues() { + s += fmt.Sprintf(" %s", c) } if len(b.Succs) > 0 { s += " ->" @@ -133,13 +138,76 @@ func (b *Block) LongString() string { return s } +// NumControls returns the number of non-nil control values the +// block has. +func (b *Block) NumControls() int { + if b.Controls[0] == nil { + return 0 + } + if b.Controls[1] == nil { + return 1 + } + return 2 +} + +// ControlValues returns a slice containing the non-nil control +// values of the block. The index of each control value will be +// the same as it is in the Controls property and can be used +// in ReplaceControl calls. +func (b *Block) ControlValues() []*Value { + if b.Controls[0] == nil { + return b.Controls[:0] + } + if b.Controls[1] == nil { + return b.Controls[:1] + } + return b.Controls[:2] +} + +// SetControl removes all existing control values and then adds +// the control value provided. The number of control values after +// a call to SetControl will always be 1. func (b *Block) SetControl(v *Value) { - if w := b.Control; w != nil { - w.Uses-- + b.ResetControls() + b.Controls[0] = v + v.Uses++ +} + +// ResetControls sets the number of controls for the block to 0. +func (b *Block) ResetControls() { + if b.Controls[0] != nil { + b.Controls[0].Uses-- + } + if b.Controls[1] != nil { + b.Controls[1].Uses-- + } + b.Controls = [2]*Value{} // reset both controls to nil +} + +// AddControl appends a control value to the existing list of control values. +func (b *Block) AddControl(v *Value) { + i := b.NumControls() + b.Controls[i] = v // panics if array is full + v.Uses++ +} + +// ReplaceControl exchanges the existing control value at the index provided +// for the new value. The index must refer to a valid control value. +func (b *Block) ReplaceControl(i int, v *Value) { + b.Controls[i].Uses-- + b.Controls[i] = v + v.Uses++ +} + +// CopyControls replaces the controls for this block with those from the +// provided block. The provided block is not modified. +func (b *Block) CopyControls(from *Block) { + if b == from { + return } - b.Control = v - if v != nil { - v.Uses++ + b.ResetControls() + for _, c := range from.ControlValues() { + b.AddControl(c) } } diff --git a/src/cmd/compile/internal/ssa/branchelim.go b/src/cmd/compile/internal/ssa/branchelim.go index fda0cbb9b3..c79b913d72 100644 --- a/src/cmd/compile/internal/ssa/branchelim.go +++ b/src/cmd/compile/internal/ssa/branchelim.go @@ -160,13 +160,13 @@ func elimIf(f *Func, loadAddr *sparseSet, dom *Block) bool { if swap { v.Args[0], v.Args[1] = v.Args[1], v.Args[0] } - v.AddArg(dom.Control) + v.AddArg(dom.Controls[0]) } // Put all of the instructions into 'dom' // and update the CFG appropriately. dom.Kind = post.Kind - dom.SetControl(post.Control) + dom.CopyControls(post) dom.Aux = post.Aux dom.Succs = append(dom.Succs[:0], post.Succs...) for i := range dom.Succs { @@ -201,7 +201,7 @@ func clobberBlock(b *Block) { b.Preds = nil b.Succs = nil b.Aux = nil - b.SetControl(nil) + b.ResetControls() b.Likely = BranchUnknown b.Kind = BlockInvalid } @@ -259,13 +259,13 @@ func elimIfElse(f *Func, loadAddr *sparseSet, b *Block) bool { if swap { v.Args[0], v.Args[1] = v.Args[1], v.Args[0] } - v.AddArg(b.Control) + v.AddArg(b.Controls[0]) } // Move the contents of all of these // blocks into 'b' and update CFG edges accordingly b.Kind = post.Kind - b.SetControl(post.Control) + b.CopyControls(post) b.Aux = post.Aux b.Succs = append(b.Succs[:0], post.Succs...) for i := range b.Succs { diff --git a/src/cmd/compile/internal/ssa/check.go b/src/cmd/compile/internal/ssa/check.go index 6dbe2ac0b6..e97377bf5c 100644 --- a/src/cmd/compile/internal/ssa/check.go +++ b/src/cmd/compile/internal/ssa/check.go @@ -39,31 +39,31 @@ func checkFunc(f *Func) { if len(b.Succs) != 0 { f.Fatalf("exit block %s has successors", b) } - if b.Control == nil { + if b.NumControls() != 1 { f.Fatalf("exit block %s has no control value", b) } - if !b.Control.Type.IsMemory() { - f.Fatalf("exit block %s has non-memory control value %s", b, b.Control.LongString()) + if !b.Controls[0].Type.IsMemory() { + f.Fatalf("exit block %s has non-memory control value %s", b, b.Controls[0].LongString()) } case BlockRet: if len(b.Succs) != 0 { f.Fatalf("ret block %s has successors", b) } - if b.Control == nil { + if b.NumControls() != 1 { f.Fatalf("ret block %s has nil control", b) } - if !b.Control.Type.IsMemory() { - f.Fatalf("ret block %s has non-memory control value %s", b, b.Control.LongString()) + if !b.Controls[0].Type.IsMemory() { + f.Fatalf("ret block %s has non-memory control value %s", b, b.Controls[0].LongString()) } case BlockRetJmp: if len(b.Succs) != 0 { f.Fatalf("retjmp block %s len(Succs)==%d, want 0", b, len(b.Succs)) } - if b.Control == nil { + if b.NumControls() != 1 { f.Fatalf("retjmp block %s has nil control", b) } - if !b.Control.Type.IsMemory() { - f.Fatalf("retjmp block %s has non-memory control value %s", b, b.Control.LongString()) + if !b.Controls[0].Type.IsMemory() { + f.Fatalf("retjmp block %s has non-memory control value %s", b, b.Controls[0].LongString()) } if b.Aux == nil { f.Fatalf("retjmp block %s has nil Aux field", b) @@ -72,34 +72,34 @@ func checkFunc(f *Func) { if len(b.Succs) != 1 { f.Fatalf("plain block %s len(Succs)==%d, want 1", b, len(b.Succs)) } - if b.Control != nil { - f.Fatalf("plain block %s has non-nil control %s", b, b.Control.LongString()) + if b.NumControls() != 0 { + f.Fatalf("plain block %s has non-nil control %s", b, b.Controls[0].LongString()) } case BlockIf: if len(b.Succs) != 2 { f.Fatalf("if block %s len(Succs)==%d, want 2", b, len(b.Succs)) } - if b.Control == nil { + if b.NumControls() != 1 { f.Fatalf("if block %s has no control value", b) } - if !b.Control.Type.IsBoolean() { - f.Fatalf("if block %s has non-bool control value %s", b, b.Control.LongString()) + if !b.Controls[0].Type.IsBoolean() { + f.Fatalf("if block %s has non-bool control value %s", b, b.Controls[0].LongString()) } case BlockDefer: if len(b.Succs) != 2 { f.Fatalf("defer block %s len(Succs)==%d, want 2", b, len(b.Succs)) } - if b.Control == nil { + if b.NumControls() != 1 { f.Fatalf("defer block %s has no control value", b) } - if !b.Control.Type.IsMemory() { - f.Fatalf("defer block %s has non-memory control value %s", b, b.Control.LongString()) + if !b.Controls[0].Type.IsMemory() { + f.Fatalf("defer block %s has non-memory control value %s", b, b.Controls[0].LongString()) } case BlockFirst: if len(b.Succs) != 2 { f.Fatalf("plain/dead block %s len(Succs)==%d, want 2", b, len(b.Succs)) } - if b.Control != nil { + if b.NumControls() != 0 { f.Fatalf("plain/dead block %s has a control value", b) } } @@ -263,8 +263,10 @@ func checkFunc(f *Func) { } } } - if b.Control != nil && !valueMark[b.Control.ID] { - f.Fatalf("control value for %s is missing: %v", b, b.Control) + for _, c := range b.ControlValues() { + if !valueMark[c.ID] { + f.Fatalf("control value for %s is missing: %v", b, c) + } } } for b := f.freeBlocks; b != nil; b = b.succstorage[0].b { @@ -296,8 +298,10 @@ func checkFunc(f *Func) { } } } - if b.Control != nil && !domCheck(f, sdom, b.Control.Block, b) { - f.Fatalf("control value %s for %s doesn't dominate", b.Control, b) + for _, c := range b.ControlValues() { + if !domCheck(f, sdom, c.Block, b) { + f.Fatalf("control value %s for %s doesn't dominate", c, b) + } } } } @@ -329,8 +333,8 @@ func checkFunc(f *Func) { uses[a.ID]++ } } - if b.Control != nil { - uses[b.Control.ID]++ + for _, c := range b.ControlValues() { + uses[c.ID]++ } } for _, b := range f.Blocks { diff --git a/src/cmd/compile/internal/ssa/copyelim.go b/src/cmd/compile/internal/ssa/copyelim.go index 44ccfe1bfe..5954d3bec8 100644 --- a/src/cmd/compile/internal/ssa/copyelim.go +++ b/src/cmd/compile/internal/ssa/copyelim.go @@ -17,8 +17,10 @@ func copyelim(f *Func) { // Update block control values. for _, b := range f.Blocks { - if v := b.Control; v != nil && v.Op == OpCopy { - b.SetControl(v.Args[0]) + for i, v := range b.ControlValues() { + if v.Op == OpCopy { + b.ReplaceControl(i, v.Args[0]) + } } } diff --git a/src/cmd/compile/internal/ssa/cse.go b/src/cmd/compile/internal/ssa/cse.go index 75595c3b3d..1fdcffcae8 100644 --- a/src/cmd/compile/internal/ssa/cse.go +++ b/src/cmd/compile/internal/ssa/cse.go @@ -248,14 +248,14 @@ func cse(f *Func) { } } } - if v := b.Control; v != nil { + for i, v := range b.ControlValues() { if x := rewrite[v.ID]; x != nil { if v.Op == OpNilCheck { // nilcheck pass will remove the nil checks and log // them appropriately, so don't mess with them here. continue } - b.SetControl(x) + b.ReplaceControl(i, x) } } } diff --git a/src/cmd/compile/internal/ssa/deadcode.go b/src/cmd/compile/internal/ssa/deadcode.go index 24d1d88165..b79ec7c2f6 100644 --- a/src/cmd/compile/internal/ssa/deadcode.go +++ b/src/cmd/compile/internal/ssa/deadcode.go @@ -110,11 +110,13 @@ func liveValues(f *Func, reachable []bool) (live []bool, liveOrderStmts []*Value if !reachable[b.ID] { continue } - if v := b.Control; v != nil && !live[v.ID] { - live[v.ID] = true - q = append(q, v) - if v.Pos.IsStmt() != src.PosNotStmt { - liveOrderStmts = append(liveOrderStmts, v) + for _, v := range b.ControlValues() { + if !live[v.ID] { + live[v.ID] = true + q = append(q, v) + if v.Pos.IsStmt() != src.PosNotStmt { + liveOrderStmts = append(liveOrderStmts, v) + } } } for _, v := range b.Values { @@ -252,7 +254,7 @@ func deadcode(f *Func) { for i, b := range f.Blocks { if !reachable[b.ID] { // TODO what if control is statement boundary? Too late here. - b.SetControl(nil) + b.ResetControls() } for _, v := range b.Values { if !live[v.ID] { diff --git a/src/cmd/compile/internal/ssa/deadstore.go b/src/cmd/compile/internal/ssa/deadstore.go index ebcb571e66..6b9bcedadb 100644 --- a/src/cmd/compile/internal/ssa/deadstore.go +++ b/src/cmd/compile/internal/ssa/deadstore.go @@ -264,12 +264,11 @@ func elimDeadAutosGeneric(f *Func) { changed = visit(v) || changed } // keep the auto if its address reaches a control value - if b.Control == nil { - continue - } - if n, ok := addr[b.Control]; ok && !used[n] { - used[n] = true - changed = true + for _, c := range b.ControlValues() { + if n, ok := addr[c]; ok && !used[n] { + used[n] = true + changed = true + } } } if !changed { diff --git a/src/cmd/compile/internal/ssa/flagalloc.go b/src/cmd/compile/internal/ssa/flagalloc.go index 7a2ecc22dc..7e7ce11482 100644 --- a/src/cmd/compile/internal/ssa/flagalloc.go +++ b/src/cmd/compile/internal/ssa/flagalloc.go @@ -18,9 +18,17 @@ func flagalloc(f *Func) { // Walk values backwards to figure out what flag // value we want in the flag register at the start // of the block. - flag := end[b.ID] - if b.Control != nil && b.Control.Type.IsFlags() { - flag = b.Control + var flag *Value + for _, c := range b.ControlValues() { + if c.Type.IsFlags() { + if flag != nil { + panic("cannot have multiple controls using flags") + } + flag = c + } + } + if flag == nil { + flag = end[b.ID] } for j := len(b.Values) - 1; j >= 0; j-- { v := b.Values[j] @@ -49,13 +57,15 @@ func flagalloc(f *Func) { // we can leave in the flags register at the end of the block. (There // is no place to put a flag regeneration instruction.) for _, b := range f.Blocks { - v := b.Control - if v != nil && v.Type.IsFlags() && end[b.ID] != v { - end[b.ID] = nil - } if b.Kind == BlockDefer { // Defer blocks internally use/clobber the flags value. end[b.ID] = nil + continue + } + for _, v := range b.ControlValues() { + if v.Type.IsFlags() && end[b.ID] != v { + end[b.ID] = nil + } } } @@ -85,8 +95,10 @@ func flagalloc(f *Func) { flag = v } } - if v := b.Control; v != nil && v != flag && v.Type.IsFlags() { - spill[v.ID] = true + for _, v := range b.ControlValues() { + if v != flag && v.Type.IsFlags() { + spill[v.ID] = true + } } if v := end[b.ID]; v != nil && v != flag { spill[v.ID] = true @@ -149,11 +161,13 @@ func flagalloc(f *Func) { flag = v } } - if v := b.Control; v != nil && v != flag && v.Type.IsFlags() { - // Recalculate control value. - c := copyFlags(v, b) - b.SetControl(c) - flag = v + for i, v := range b.ControlValues() { + if v != flag && v.Type.IsFlags() { + // Recalculate control value. + c := copyFlags(v, b) + b.ReplaceControl(i, c) + flag = v + } } if v := end[b.ID]; v != nil && v != flag { // Need to reissue flag generator for use by diff --git a/src/cmd/compile/internal/ssa/fuse.go b/src/cmd/compile/internal/ssa/fuse.go index 8d14b5d696..a530874b80 100644 --- a/src/cmd/compile/internal/ssa/fuse.go +++ b/src/cmd/compile/internal/ssa/fuse.go @@ -118,7 +118,7 @@ func fuseBlockIf(b *Block) bool { } b.Kind = BlockPlain b.Likely = BranchUnknown - b.SetControl(nil) + b.ResetControls() // Trash the empty blocks s0 and s1. blocks := [...]*Block{s0, s1} diff --git a/src/cmd/compile/internal/ssa/gen/386.rules b/src/cmd/compile/internal/ssa/gen/386.rules index 1cdcf4c710..94573702a5 100644 --- a/src/cmd/compile/internal/ssa/gen/386.rules +++ b/src/cmd/compile/internal/ssa/gen/386.rules @@ -899,65 +899,65 @@ (SBBLcarrymask (FlagGT_UGT)) -> (MOVLconst [0]) // Absorb flag constants into branches. -(EQ (FlagEQ) yes no) -> (First nil yes no) -(EQ (FlagLT_ULT) yes no) -> (First nil no yes) -(EQ (FlagLT_UGT) yes no) -> (First nil no yes) -(EQ (FlagGT_ULT) yes no) -> (First nil no yes) -(EQ (FlagGT_UGT) yes no) -> (First nil no yes) - -(NE (FlagEQ) yes no) -> (First nil no yes) -(NE (FlagLT_ULT) yes no) -> (First nil yes no) -(NE (FlagLT_UGT) yes no) -> (First nil yes no) -(NE (FlagGT_ULT) yes no) -> (First nil yes no) -(NE (FlagGT_UGT) yes no) -> (First nil yes no) - -(LT (FlagEQ) yes no) -> (First nil no yes) -(LT (FlagLT_ULT) yes no) -> (First nil yes no) -(LT (FlagLT_UGT) yes no) -> (First nil yes no) -(LT (FlagGT_ULT) yes no) -> (First nil no yes) -(LT (FlagGT_UGT) yes no) -> (First nil no yes) - -(LE (FlagEQ) yes no) -> (First nil yes no) -(LE (FlagLT_ULT) yes no) -> (First nil yes no) -(LE (FlagLT_UGT) yes no) -> (First nil yes no) -(LE (FlagGT_ULT) yes no) -> (First nil no yes) -(LE (FlagGT_UGT) yes no) -> (First nil no yes) - -(GT (FlagEQ) yes no) -> (First nil no yes) -(GT (FlagLT_ULT) yes no) -> (First nil no yes) -(GT (FlagLT_UGT) yes no) -> (First nil no yes) -(GT (FlagGT_ULT) yes no) -> (First nil yes no) -(GT (FlagGT_UGT) yes no) -> (First nil yes no) - -(GE (FlagEQ) yes no) -> (First nil yes no) -(GE (FlagLT_ULT) yes no) -> (First nil no yes) -(GE (FlagLT_UGT) yes no) -> (First nil no yes) -(GE (FlagGT_ULT) yes no) -> (First nil yes no) -(GE (FlagGT_UGT) yes no) -> (First nil yes no) - -(ULT (FlagEQ) yes no) -> (First nil no yes) -(ULT (FlagLT_ULT) yes no) -> (First nil yes no) -(ULT (FlagLT_UGT) yes no) -> (First nil no yes) -(ULT (FlagGT_ULT) yes no) -> (First nil yes no) -(ULT (FlagGT_UGT) yes no) -> (First nil no yes) - -(ULE (FlagEQ) yes no) -> (First nil yes no) -(ULE (FlagLT_ULT) yes no) -> (First nil yes no) -(ULE (FlagLT_UGT) yes no) -> (First nil no yes) -(ULE (FlagGT_ULT) yes no) -> (First nil yes no) -(ULE (FlagGT_UGT) yes no) -> (First nil no yes) - -(UGT (FlagEQ) yes no) -> (First nil no yes) -(UGT (FlagLT_ULT) yes no) -> (First nil no yes) -(UGT (FlagLT_UGT) yes no) -> (First nil yes no) -(UGT (FlagGT_ULT) yes no) -> (First nil no yes) -(UGT (FlagGT_UGT) yes no) -> (First nil yes no) - -(UGE (FlagEQ) yes no) -> (First nil yes no) -(UGE (FlagLT_ULT) yes no) -> (First nil no yes) -(UGE (FlagLT_UGT) yes no) -> (First nil yes no) -(UGE (FlagGT_ULT) yes no) -> (First nil no yes) -(UGE (FlagGT_UGT) yes no) -> (First nil yes no) +(EQ (FlagEQ) yes no) -> (First yes no) +(EQ (FlagLT_ULT) yes no) -> (First no yes) +(EQ (FlagLT_UGT) yes no) -> (First no yes) +(EQ (FlagGT_ULT) yes no) -> (First no yes) +(EQ (FlagGT_UGT) yes no) -> (First no yes) + +(NE (FlagEQ) yes no) -> (First no yes) +(NE (FlagLT_ULT) yes no) -> (First yes no) +(NE (FlagLT_UGT) yes no) -> (First yes no) +(NE (FlagGT_ULT) yes no) -> (First yes no) +(NE (FlagGT_UGT) yes no) -> (First yes no) + +(LT (FlagEQ) yes no) -> (First no yes) +(LT (FlagLT_ULT) yes no) -> (First yes no) +(LT (FlagLT_UGT) yes no) -> (First yes no) +(LT (FlagGT_ULT) yes no) -> (First no yes) +(LT (FlagGT_UGT) yes no) -> (First no yes) + +(LE (FlagEQ) yes no) -> (First yes no) +(LE (FlagLT_ULT) yes no) -> (First yes no) +(LE (FlagLT_UGT) yes no) -> (First yes no) +(LE (FlagGT_ULT) yes no) -> (First no yes) +(LE (FlagGT_UGT) yes no) -> (First no yes) + +(GT (FlagEQ) yes no) -> (First no yes) +(GT (FlagLT_ULT) yes no) -> (First no yes) +(GT (FlagLT_UGT) yes no) -> (First no yes) +(GT (FlagGT_ULT) yes no) -> (First yes no) +(GT (FlagGT_UGT) yes no) -> (First yes no) + +(GE (FlagEQ) yes no) -> (First yes no) +(GE (FlagLT_ULT) yes no) -> (First no yes) +(GE (FlagLT_UGT) yes no) -> (First no yes) +(GE (FlagGT_ULT) yes no) -> (First yes no) +(GE (FlagGT_UGT) yes no) -> (First yes no) + +(ULT (FlagEQ) yes no) -> (First no yes) +(ULT (FlagLT_ULT) yes no) -> (First yes no) +(ULT (FlagLT_UGT) yes no) -> (First no yes) +(ULT (FlagGT_ULT) yes no) -> (First yes no) +(ULT (FlagGT_UGT) yes no) -> (First no yes) + +(ULE (FlagEQ) yes no) -> (First yes no) +(ULE (FlagLT_ULT) yes no) -> (First yes no) +(ULE (FlagLT_UGT) yes no) -> (First no yes) +(ULE (FlagGT_ULT) yes no) -> (First yes no) +(ULE (FlagGT_UGT) yes no) -> (First no yes) + +(UGT (FlagEQ) yes no) -> (First no yes) +(UGT (FlagLT_ULT) yes no) -> (First no yes) +(UGT (FlagLT_UGT) yes no) -> (First yes no) +(UGT (FlagGT_ULT) yes no) -> (First no yes) +(UGT (FlagGT_UGT) yes no) -> (First yes no) + +(UGE (FlagEQ) yes no) -> (First yes no) +(UGE (FlagLT_ULT) yes no) -> (First no yes) +(UGE (FlagLT_UGT) yes no) -> (First yes no) +(UGE (FlagGT_ULT) yes no) -> (First no yes) +(UGE (FlagGT_UGT) yes no) -> (First yes no) // Absorb flag constants into SETxx ops. (SETEQ (FlagEQ)) -> (MOVLconst [1]) diff --git a/src/cmd/compile/internal/ssa/gen/386Ops.go b/src/cmd/compile/internal/ssa/gen/386Ops.go index 2851c4321c..4fb61adfeb 100644 --- a/src/cmd/compile/internal/ssa/gen/386Ops.go +++ b/src/cmd/compile/internal/ssa/gen/386Ops.go @@ -564,22 +564,22 @@ func init() { } var _386blocks = []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LT"}, - {name: "LE"}, - {name: "GT"}, - {name: "GE"}, - {name: "OS"}, - {name: "OC"}, - {name: "ULT"}, - {name: "ULE"}, - {name: "UGT"}, - {name: "UGE"}, - {name: "EQF"}, - {name: "NEF"}, - {name: "ORD"}, // FP, ordered comparison (parity zero) - {name: "NAN"}, // FP, unordered comparison (parity one) + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LT", controls: 1}, + {name: "LE", controls: 1}, + {name: "GT", controls: 1}, + {name: "GE", controls: 1}, + {name: "OS", controls: 1}, + {name: "OC", controls: 1}, + {name: "ULT", controls: 1}, + {name: "ULE", controls: 1}, + {name: "UGT", controls: 1}, + {name: "UGE", controls: 1}, + {name: "EQF", controls: 1}, + {name: "NEF", controls: 1}, + {name: "ORD", controls: 1}, // FP, ordered comparison (parity zero) + {name: "NAN", controls: 1}, // FP, unordered comparison (parity one) } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/AMD64.rules b/src/cmd/compile/internal/ssa/gen/AMD64.rules index 58e2d3ad18..e4b97a8763 100644 --- a/src/cmd/compile/internal/ssa/gen/AMD64.rules +++ b/src/cmd/compile/internal/ssa/gen/AMD64.rules @@ -1346,16 +1346,16 @@ (SBBLcarrymask (FlagGT_UGT)) -> (MOVLconst [0]) // Absorb flag constants into branches. -((EQ|LE|GE|ULE|UGE) (FlagEQ) yes no) -> (First nil yes no) -((NE|LT|GT|ULT|UGT) (FlagEQ) yes no) -> (First nil no yes) -((NE|LT|LE|ULT|ULE) (FlagLT_ULT) yes no) -> (First nil yes no) -((EQ|GT|GE|UGT|UGE) (FlagLT_ULT) yes no) -> (First nil no yes) -((NE|LT|LE|UGT|UGE) (FlagLT_UGT) yes no) -> (First nil yes no) -((EQ|GT|GE|ULT|ULE) (FlagLT_UGT) yes no) -> (First nil no yes) -((NE|GT|GE|ULT|ULE) (FlagGT_ULT) yes no) -> (First nil yes no) -((EQ|LT|LE|UGT|UGE) (FlagGT_ULT) yes no) -> (First nil no yes) -((NE|GT|GE|UGT|UGE) (FlagGT_UGT) yes no) -> (First nil yes no) -((EQ|LT|LE|ULT|ULE) (FlagGT_UGT) yes no) -> (First nil no yes) +((EQ|LE|GE|ULE|UGE) (FlagEQ) yes no) -> (First yes no) +((NE|LT|GT|ULT|UGT) (FlagEQ) yes no) -> (First no yes) +((NE|LT|LE|ULT|ULE) (FlagLT_ULT) yes no) -> (First yes no) +((EQ|GT|GE|UGT|UGE) (FlagLT_ULT) yes no) -> (First no yes) +((NE|LT|LE|UGT|UGE) (FlagLT_UGT) yes no) -> (First yes no) +((EQ|GT|GE|ULT|ULE) (FlagLT_UGT) yes no) -> (First no yes) +((NE|GT|GE|ULT|ULE) (FlagGT_ULT) yes no) -> (First yes no) +((EQ|LT|LE|UGT|UGE) (FlagGT_ULT) yes no) -> (First no yes) +((NE|GT|GE|UGT|UGE) (FlagGT_UGT) yes no) -> (First yes no) +((EQ|LT|LE|ULT|ULE) (FlagGT_UGT) yes no) -> (First no yes) // Absorb flag constants into SETxx ops. ((SETEQ|SETLE|SETGE|SETBE|SETAE) (FlagEQ)) -> (MOVLconst [1]) diff --git a/src/cmd/compile/internal/ssa/gen/AMD64Ops.go b/src/cmd/compile/internal/ssa/gen/AMD64Ops.go index 739733cf16..ed58db4d59 100644 --- a/src/cmd/compile/internal/ssa/gen/AMD64Ops.go +++ b/src/cmd/compile/internal/ssa/gen/AMD64Ops.go @@ -788,22 +788,22 @@ func init() { } var AMD64blocks = []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LT"}, - {name: "LE"}, - {name: "GT"}, - {name: "GE"}, - {name: "OS"}, - {name: "OC"}, - {name: "ULT"}, - {name: "ULE"}, - {name: "UGT"}, - {name: "UGE"}, - {name: "EQF"}, - {name: "NEF"}, - {name: "ORD"}, // FP, ordered comparison (parity zero) - {name: "NAN"}, // FP, unordered comparison (parity one) + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LT", controls: 1}, + {name: "LE", controls: 1}, + {name: "GT", controls: 1}, + {name: "GE", controls: 1}, + {name: "OS", controls: 1}, + {name: "OC", controls: 1}, + {name: "ULT", controls: 1}, + {name: "ULE", controls: 1}, + {name: "UGT", controls: 1}, + {name: "UGE", controls: 1}, + {name: "EQF", controls: 1}, + {name: "NEF", controls: 1}, + {name: "ORD", controls: 1}, // FP, ordered comparison (parity zero) + {name: "NAN", controls: 1}, // FP, unordered comparison (parity one) } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/ARM.rules b/src/cmd/compile/internal/ssa/gen/ARM.rules index a3ee9046c5..0858b443da 100644 --- a/src/cmd/compile/internal/ssa/gen/ARM.rules +++ b/src/cmd/compile/internal/ssa/gen/ARM.rules @@ -647,65 +647,65 @@ (CMPconst (SRLconst _ [c]) [n]) && 0 <= n && 0 < c && c <= 32 && (1< (FlagLT_ULT) // absorb flag constants into branches -(EQ (FlagEQ) yes no) -> (First nil yes no) -(EQ (FlagLT_ULT) yes no) -> (First nil no yes) -(EQ (FlagLT_UGT) yes no) -> (First nil no yes) -(EQ (FlagGT_ULT) yes no) -> (First nil no yes) -(EQ (FlagGT_UGT) yes no) -> (First nil no yes) - -(NE (FlagEQ) yes no) -> (First nil no yes) -(NE (FlagLT_ULT) yes no) -> (First nil yes no) -(NE (FlagLT_UGT) yes no) -> (First nil yes no) -(NE (FlagGT_ULT) yes no) -> (First nil yes no) -(NE (FlagGT_UGT) yes no) -> (First nil yes no) - -(LT (FlagEQ) yes no) -> (First nil no yes) -(LT (FlagLT_ULT) yes no) -> (First nil yes no) -(LT (FlagLT_UGT) yes no) -> (First nil yes no) -(LT (FlagGT_ULT) yes no) -> (First nil no yes) -(LT (FlagGT_UGT) yes no) -> (First nil no yes) - -(LE (FlagEQ) yes no) -> (First nil yes no) -(LE (FlagLT_ULT) yes no) -> (First nil yes no) -(LE (FlagLT_UGT) yes no) -> (First nil yes no) -(LE (FlagGT_ULT) yes no) -> (First nil no yes) -(LE (FlagGT_UGT) yes no) -> (First nil no yes) - -(GT (FlagEQ) yes no) -> (First nil no yes) -(GT (FlagLT_ULT) yes no) -> (First nil no yes) -(GT (FlagLT_UGT) yes no) -> (First nil no yes) -(GT (FlagGT_ULT) yes no) -> (First nil yes no) -(GT (FlagGT_UGT) yes no) -> (First nil yes no) - -(GE (FlagEQ) yes no) -> (First nil yes no) -(GE (FlagLT_ULT) yes no) -> (First nil no yes) -(GE (FlagLT_UGT) yes no) -> (First nil no yes) -(GE (FlagGT_ULT) yes no) -> (First nil yes no) -(GE (FlagGT_UGT) yes no) -> (First nil yes no) - -(ULT (FlagEQ) yes no) -> (First nil no yes) -(ULT (FlagLT_ULT) yes no) -> (First nil yes no) -(ULT (FlagLT_UGT) yes no) -> (First nil no yes) -(ULT (FlagGT_ULT) yes no) -> (First nil yes no) -(ULT (FlagGT_UGT) yes no) -> (First nil no yes) - -(ULE (FlagEQ) yes no) -> (First nil yes no) -(ULE (FlagLT_ULT) yes no) -> (First nil yes no) -(ULE (FlagLT_UGT) yes no) -> (First nil no yes) -(ULE (FlagGT_ULT) yes no) -> (First nil yes no) -(ULE (FlagGT_UGT) yes no) -> (First nil no yes) - -(UGT (FlagEQ) yes no) -> (First nil no yes) -(UGT (FlagLT_ULT) yes no) -> (First nil no yes) -(UGT (FlagLT_UGT) yes no) -> (First nil yes no) -(UGT (FlagGT_ULT) yes no) -> (First nil no yes) -(UGT (FlagGT_UGT) yes no) -> (First nil yes no) - -(UGE (FlagEQ) yes no) -> (First nil yes no) -(UGE (FlagLT_ULT) yes no) -> (First nil no yes) -(UGE (FlagLT_UGT) yes no) -> (First nil yes no) -(UGE (FlagGT_ULT) yes no) -> (First nil no yes) -(UGE (FlagGT_UGT) yes no) -> (First nil yes no) +(EQ (FlagEQ) yes no) -> (First yes no) +(EQ (FlagLT_ULT) yes no) -> (First no yes) +(EQ (FlagLT_UGT) yes no) -> (First no yes) +(EQ (FlagGT_ULT) yes no) -> (First no yes) +(EQ (FlagGT_UGT) yes no) -> (First no yes) + +(NE (FlagEQ) yes no) -> (First no yes) +(NE (FlagLT_ULT) yes no) -> (First yes no) +(NE (FlagLT_UGT) yes no) -> (First yes no) +(NE (FlagGT_ULT) yes no) -> (First yes no) +(NE (FlagGT_UGT) yes no) -> (First yes no) + +(LT (FlagEQ) yes no) -> (First no yes) +(LT (FlagLT_ULT) yes no) -> (First yes no) +(LT (FlagLT_UGT) yes no) -> (First yes no) +(LT (FlagGT_ULT) yes no) -> (First no yes) +(LT (FlagGT_UGT) yes no) -> (First no yes) + +(LE (FlagEQ) yes no) -> (First yes no) +(LE (FlagLT_ULT) yes no) -> (First yes no) +(LE (FlagLT_UGT) yes no) -> (First yes no) +(LE (FlagGT_ULT) yes no) -> (First no yes) +(LE (FlagGT_UGT) yes no) -> (First no yes) + +(GT (FlagEQ) yes no) -> (First no yes) +(GT (FlagLT_ULT) yes no) -> (First no yes) +(GT (FlagLT_UGT) yes no) -> (First no yes) +(GT (FlagGT_ULT) yes no) -> (First yes no) +(GT (FlagGT_UGT) yes no) -> (First yes no) + +(GE (FlagEQ) yes no) -> (First yes no) +(GE (FlagLT_ULT) yes no) -> (First no yes) +(GE (FlagLT_UGT) yes no) -> (First no yes) +(GE (FlagGT_ULT) yes no) -> (First yes no) +(GE (FlagGT_UGT) yes no) -> (First yes no) + +(ULT (FlagEQ) yes no) -> (First no yes) +(ULT (FlagLT_ULT) yes no) -> (First yes no) +(ULT (FlagLT_UGT) yes no) -> (First no yes) +(ULT (FlagGT_ULT) yes no) -> (First yes no) +(ULT (FlagGT_UGT) yes no) -> (First no yes) + +(ULE (FlagEQ) yes no) -> (First yes no) +(ULE (FlagLT_ULT) yes no) -> (First yes no) +(ULE (FlagLT_UGT) yes no) -> (First no yes) +(ULE (FlagGT_ULT) yes no) -> (First yes no) +(ULE (FlagGT_UGT) yes no) -> (First no yes) + +(UGT (FlagEQ) yes no) -> (First no yes) +(UGT (FlagLT_ULT) yes no) -> (First no yes) +(UGT (FlagLT_UGT) yes no) -> (First yes no) +(UGT (FlagGT_ULT) yes no) -> (First no yes) +(UGT (FlagGT_UGT) yes no) -> (First yes no) + +(UGE (FlagEQ) yes no) -> (First yes no) +(UGE (FlagLT_ULT) yes no) -> (First no yes) +(UGE (FlagLT_UGT) yes no) -> (First yes no) +(UGE (FlagGT_ULT) yes no) -> (First no yes) +(UGE (FlagGT_UGT) yes no) -> (First yes no) // absorb InvertFlags into branches (LT (InvertFlags cmp) yes no) -> (GT cmp yes no) diff --git a/src/cmd/compile/internal/ssa/gen/ARM64.rules b/src/cmd/compile/internal/ssa/gen/ARM64.rules index ddb504531c..7edd19e9cc 100644 --- a/src/cmd/compile/internal/ssa/gen/ARM64.rules +++ b/src/cmd/compile/internal/ssa/gen/ARM64.rules @@ -1481,74 +1481,74 @@ (CMPWconst (MOVHUreg _) [c]) && 0xffff < int32(c) -> (FlagLT_ULT) // absorb flag constants into branches -(EQ (FlagEQ) yes no) -> (First nil yes no) -(EQ (FlagLT_ULT) yes no) -> (First nil no yes) -(EQ (FlagLT_UGT) yes no) -> (First nil no yes) -(EQ (FlagGT_ULT) yes no) -> (First nil no yes) -(EQ (FlagGT_UGT) yes no) -> (First nil no yes) - -(NE (FlagEQ) yes no) -> (First nil no yes) -(NE (FlagLT_ULT) yes no) -> (First nil yes no) -(NE (FlagLT_UGT) yes no) -> (First nil yes no) -(NE (FlagGT_ULT) yes no) -> (First nil yes no) -(NE (FlagGT_UGT) yes no) -> (First nil yes no) - -(LT (FlagEQ) yes no) -> (First nil no yes) -(LT (FlagLT_ULT) yes no) -> (First nil yes no) -(LT (FlagLT_UGT) yes no) -> (First nil yes no) -(LT (FlagGT_ULT) yes no) -> (First nil no yes) -(LT (FlagGT_UGT) yes no) -> (First nil no yes) - -(LE (FlagEQ) yes no) -> (First nil yes no) -(LE (FlagLT_ULT) yes no) -> (First nil yes no) -(LE (FlagLT_UGT) yes no) -> (First nil yes no) -(LE (FlagGT_ULT) yes no) -> (First nil no yes) -(LE (FlagGT_UGT) yes no) -> (First nil no yes) - -(GT (FlagEQ) yes no) -> (First nil no yes) -(GT (FlagLT_ULT) yes no) -> (First nil no yes) -(GT (FlagLT_UGT) yes no) -> (First nil no yes) -(GT (FlagGT_ULT) yes no) -> (First nil yes no) -(GT (FlagGT_UGT) yes no) -> (First nil yes no) - -(GE (FlagEQ) yes no) -> (First nil yes no) -(GE (FlagLT_ULT) yes no) -> (First nil no yes) -(GE (FlagLT_UGT) yes no) -> (First nil no yes) -(GE (FlagGT_ULT) yes no) -> (First nil yes no) -(GE (FlagGT_UGT) yes no) -> (First nil yes no) - -(ULT (FlagEQ) yes no) -> (First nil no yes) -(ULT (FlagLT_ULT) yes no) -> (First nil yes no) -(ULT (FlagLT_UGT) yes no) -> (First nil no yes) -(ULT (FlagGT_ULT) yes no) -> (First nil yes no) -(ULT (FlagGT_UGT) yes no) -> (First nil no yes) - -(ULE (FlagEQ) yes no) -> (First nil yes no) -(ULE (FlagLT_ULT) yes no) -> (First nil yes no) -(ULE (FlagLT_UGT) yes no) -> (First nil no yes) -(ULE (FlagGT_ULT) yes no) -> (First nil yes no) -(ULE (FlagGT_UGT) yes no) -> (First nil no yes) - -(UGT (FlagEQ) yes no) -> (First nil no yes) -(UGT (FlagLT_ULT) yes no) -> (First nil no yes) -(UGT (FlagLT_UGT) yes no) -> (First nil yes no) -(UGT (FlagGT_ULT) yes no) -> (First nil no yes) -(UGT (FlagGT_UGT) yes no) -> (First nil yes no) - -(UGE (FlagEQ) yes no) -> (First nil yes no) -(UGE (FlagLT_ULT) yes no) -> (First nil no yes) -(UGE (FlagLT_UGT) yes no) -> (First nil yes no) -(UGE (FlagGT_ULT) yes no) -> (First nil no yes) -(UGE (FlagGT_UGT) yes no) -> (First nil yes no) - -(Z (MOVDconst [0]) yes no) -> (First nil yes no) -(Z (MOVDconst [c]) yes no) && c != 0 -> (First nil no yes) -(NZ (MOVDconst [0]) yes no) -> (First nil no yes) -(NZ (MOVDconst [c]) yes no) && c != 0 -> (First nil yes no) -(ZW (MOVDconst [c]) yes no) && int32(c) == 0 -> (First nil yes no) -(ZW (MOVDconst [c]) yes no) && int32(c) != 0 -> (First nil no yes) -(NZW (MOVDconst [c]) yes no) && int32(c) == 0 -> (First nil no yes) -(NZW (MOVDconst [c]) yes no) && int32(c) != 0 -> (First nil yes no) +(EQ (FlagEQ) yes no) -> (First yes no) +(EQ (FlagLT_ULT) yes no) -> (First no yes) +(EQ (FlagLT_UGT) yes no) -> (First no yes) +(EQ (FlagGT_ULT) yes no) -> (First no yes) +(EQ (FlagGT_UGT) yes no) -> (First no yes) + +(NE (FlagEQ) yes no) -> (First no yes) +(NE (FlagLT_ULT) yes no) -> (First yes no) +(NE (FlagLT_UGT) yes no) -> (First yes no) +(NE (FlagGT_ULT) yes no) -> (First yes no) +(NE (FlagGT_UGT) yes no) -> (First yes no) + +(LT (FlagEQ) yes no) -> (First no yes) +(LT (FlagLT_ULT) yes no) -> (First yes no) +(LT (FlagLT_UGT) yes no) -> (First yes no) +(LT (FlagGT_ULT) yes no) -> (First no yes) +(LT (FlagGT_UGT) yes no) -> (First no yes) + +(LE (FlagEQ) yes no) -> (First yes no) +(LE (FlagLT_ULT) yes no) -> (First yes no) +(LE (FlagLT_UGT) yes no) -> (First yes no) +(LE (FlagGT_ULT) yes no) -> (First no yes) +(LE (FlagGT_UGT) yes no) -> (First no yes) + +(GT (FlagEQ) yes no) -> (First no yes) +(GT (FlagLT_ULT) yes no) -> (First no yes) +(GT (FlagLT_UGT) yes no) -> (First no yes) +(GT (FlagGT_ULT) yes no) -> (First yes no) +(GT (FlagGT_UGT) yes no) -> (First yes no) + +(GE (FlagEQ) yes no) -> (First yes no) +(GE (FlagLT_ULT) yes no) -> (First no yes) +(GE (FlagLT_UGT) yes no) -> (First no yes) +(GE (FlagGT_ULT) yes no) -> (First yes no) +(GE (FlagGT_UGT) yes no) -> (First yes no) + +(ULT (FlagEQ) yes no) -> (First no yes) +(ULT (FlagLT_ULT) yes no) -> (First yes no) +(ULT (FlagLT_UGT) yes no) -> (First no yes) +(ULT (FlagGT_ULT) yes no) -> (First yes no) +(ULT (FlagGT_UGT) yes no) -> (First no yes) + +(ULE (FlagEQ) yes no) -> (First yes no) +(ULE (FlagLT_ULT) yes no) -> (First yes no) +(ULE (FlagLT_UGT) yes no) -> (First no yes) +(ULE (FlagGT_ULT) yes no) -> (First yes no) +(ULE (FlagGT_UGT) yes no) -> (First no yes) + +(UGT (FlagEQ) yes no) -> (First no yes) +(UGT (FlagLT_ULT) yes no) -> (First no yes) +(UGT (FlagLT_UGT) yes no) -> (First yes no) +(UGT (FlagGT_ULT) yes no) -> (First no yes) +(UGT (FlagGT_UGT) yes no) -> (First yes no) + +(UGE (FlagEQ) yes no) -> (First yes no) +(UGE (FlagLT_ULT) yes no) -> (First no yes) +(UGE (FlagLT_UGT) yes no) -> (First yes no) +(UGE (FlagGT_ULT) yes no) -> (First no yes) +(UGE (FlagGT_UGT) yes no) -> (First yes no) + +(Z (MOVDconst [0]) yes no) -> (First yes no) +(Z (MOVDconst [c]) yes no) && c != 0 -> (First no yes) +(NZ (MOVDconst [0]) yes no) -> (First no yes) +(NZ (MOVDconst [c]) yes no) && c != 0 -> (First yes no) +(ZW (MOVDconst [c]) yes no) && int32(c) == 0 -> (First yes no) +(ZW (MOVDconst [c]) yes no) && int32(c) != 0 -> (First no yes) +(NZW (MOVDconst [c]) yes no) && int32(c) == 0 -> (First no yes) +(NZW (MOVDconst [c]) yes no) && int32(c) != 0 -> (First yes no) // absorb InvertFlags into branches (LT (InvertFlags cmp) yes no) -> (GT cmp yes no) diff --git a/src/cmd/compile/internal/ssa/gen/ARM64Ops.go b/src/cmd/compile/internal/ssa/gen/ARM64Ops.go index d4de904a24..e1f045fcf8 100644 --- a/src/cmd/compile/internal/ssa/gen/ARM64Ops.go +++ b/src/cmd/compile/internal/ssa/gen/ARM64Ops.go @@ -678,26 +678,26 @@ func init() { } blocks := []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LT"}, - {name: "LE"}, - {name: "GT"}, - {name: "GE"}, - {name: "ULT"}, - {name: "ULE"}, - {name: "UGT"}, - {name: "UGE"}, - {name: "Z"}, // Control == 0 (take a register instead of flags) - {name: "NZ"}, // Control != 0 - {name: "ZW"}, // Control == 0, 32-bit - {name: "NZW"}, // Control != 0, 32-bit - {name: "TBZ"}, // Control & (1 << Aux.(int64)) == 0 - {name: "TBNZ"}, // Control & (1 << Aux.(int64)) != 0 - {name: "FLT"}, - {name: "FLE"}, - {name: "FGT"}, - {name: "FGE"}, + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LT", controls: 1}, + {name: "LE", controls: 1}, + {name: "GT", controls: 1}, + {name: "GE", controls: 1}, + {name: "ULT", controls: 1}, + {name: "ULE", controls: 1}, + {name: "UGT", controls: 1}, + {name: "UGE", controls: 1}, + {name: "Z", controls: 1}, // Control == 0 (take a register instead of flags) + {name: "NZ", controls: 1}, // Control != 0 + {name: "ZW", controls: 1}, // Control == 0, 32-bit + {name: "NZW", controls: 1}, // Control != 0, 32-bit + {name: "TBZ", controls: 1}, // Control & (1 << Aux.(int64)) == 0 + {name: "TBNZ", controls: 1}, // Control & (1 << Aux.(int64)) != 0 + {name: "FLT", controls: 1}, + {name: "FLE", controls: 1}, + {name: "FGT", controls: 1}, + {name: "FGE", controls: 1}, } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/ARMOps.go b/src/cmd/compile/internal/ssa/gen/ARMOps.go index eb0f671d0d..2983870486 100644 --- a/src/cmd/compile/internal/ssa/gen/ARMOps.go +++ b/src/cmd/compile/internal/ssa/gen/ARMOps.go @@ -568,16 +568,16 @@ func init() { } blocks := []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LT"}, - {name: "LE"}, - {name: "GT"}, - {name: "GE"}, - {name: "ULT"}, - {name: "ULE"}, - {name: "UGT"}, - {name: "UGE"}, + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LT", controls: 1}, + {name: "LE", controls: 1}, + {name: "GT", controls: 1}, + {name: "GE", controls: 1}, + {name: "ULT", controls: 1}, + {name: "ULE", controls: 1}, + {name: "UGT", controls: 1}, + {name: "UGE", controls: 1}, } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/MIPS.rules b/src/cmd/compile/internal/ssa/gen/MIPS.rules index 2b3ae5d93e..2932f13ac7 100644 --- a/src/cmd/compile/internal/ssa/gen/MIPS.rules +++ b/src/cmd/compile/internal/ssa/gen/MIPS.rules @@ -687,18 +687,18 @@ (SGTUconst [c] (SRLconst _ [d])) && uint32(d) <= 31 && 0xffffffff>>uint32(d) < uint32(c) -> (MOVWconst [1]) // absorb constants into branches -(EQ (MOVWconst [0]) yes no) -> (First nil yes no) -(EQ (MOVWconst [c]) yes no) && c != 0 -> (First nil no yes) -(NE (MOVWconst [0]) yes no) -> (First nil no yes) -(NE (MOVWconst [c]) yes no) && c != 0 -> (First nil yes no) -(LTZ (MOVWconst [c]) yes no) && int32(c) < 0 -> (First nil yes no) -(LTZ (MOVWconst [c]) yes no) && int32(c) >= 0 -> (First nil no yes) -(LEZ (MOVWconst [c]) yes no) && int32(c) <= 0 -> (First nil yes no) -(LEZ (MOVWconst [c]) yes no) && int32(c) > 0 -> (First nil no yes) -(GTZ (MOVWconst [c]) yes no) && int32(c) > 0 -> (First nil yes no) -(GTZ (MOVWconst [c]) yes no) && int32(c) <= 0 -> (First nil no yes) -(GEZ (MOVWconst [c]) yes no) && int32(c) >= 0 -> (First nil yes no) -(GEZ (MOVWconst [c]) yes no) && int32(c) < 0 -> (First nil no yes) +(EQ (MOVWconst [0]) yes no) -> (First yes no) +(EQ (MOVWconst [c]) yes no) && c != 0 -> (First no yes) +(NE (MOVWconst [0]) yes no) -> (First no yes) +(NE (MOVWconst [c]) yes no) && c != 0 -> (First yes no) +(LTZ (MOVWconst [c]) yes no) && int32(c) < 0 -> (First yes no) +(LTZ (MOVWconst [c]) yes no) && int32(c) >= 0 -> (First no yes) +(LEZ (MOVWconst [c]) yes no) && int32(c) <= 0 -> (First yes no) +(LEZ (MOVWconst [c]) yes no) && int32(c) > 0 -> (First no yes) +(GTZ (MOVWconst [c]) yes no) && int32(c) > 0 -> (First yes no) +(GTZ (MOVWconst [c]) yes no) && int32(c) <= 0 -> (First no yes) +(GEZ (MOVWconst [c]) yes no) && int32(c) >= 0 -> (First yes no) +(GEZ (MOVWconst [c]) yes no) && int32(c) < 0 -> (First no yes) // conditional move (CMOVZ _ f (MOVWconst [0])) -> f diff --git a/src/cmd/compile/internal/ssa/gen/MIPS64.rules b/src/cmd/compile/internal/ssa/gen/MIPS64.rules index 69fe4b721e..a39241d160 100644 --- a/src/cmd/compile/internal/ssa/gen/MIPS64.rules +++ b/src/cmd/compile/internal/ssa/gen/MIPS64.rules @@ -694,15 +694,15 @@ (SGTUconst [c] (SRLVconst _ [d])) && 0 < d && d <= 63 && 0xffffffffffffffff>>uint64(d) < uint64(c) -> (MOVVconst [1]) // absorb constants into branches -(EQ (MOVVconst [0]) yes no) -> (First nil yes no) -(EQ (MOVVconst [c]) yes no) && c != 0 -> (First nil no yes) -(NE (MOVVconst [0]) yes no) -> (First nil no yes) -(NE (MOVVconst [c]) yes no) && c != 0 -> (First nil yes no) -(LTZ (MOVVconst [c]) yes no) && c < 0 -> (First nil yes no) -(LTZ (MOVVconst [c]) yes no) && c >= 0 -> (First nil no yes) -(LEZ (MOVVconst [c]) yes no) && c <= 0 -> (First nil yes no) -(LEZ (MOVVconst [c]) yes no) && c > 0 -> (First nil no yes) -(GTZ (MOVVconst [c]) yes no) && c > 0 -> (First nil yes no) -(GTZ (MOVVconst [c]) yes no) && c <= 0 -> (First nil no yes) -(GEZ (MOVVconst [c]) yes no) && c >= 0 -> (First nil yes no) -(GEZ (MOVVconst [c]) yes no) && c < 0 -> (First nil no yes) +(EQ (MOVVconst [0]) yes no) -> (First yes no) +(EQ (MOVVconst [c]) yes no) && c != 0 -> (First no yes) +(NE (MOVVconst [0]) yes no) -> (First no yes) +(NE (MOVVconst [c]) yes no) && c != 0 -> (First yes no) +(LTZ (MOVVconst [c]) yes no) && c < 0 -> (First yes no) +(LTZ (MOVVconst [c]) yes no) && c >= 0 -> (First no yes) +(LEZ (MOVVconst [c]) yes no) && c <= 0 -> (First yes no) +(LEZ (MOVVconst [c]) yes no) && c > 0 -> (First no yes) +(GTZ (MOVVconst [c]) yes no) && c > 0 -> (First yes no) +(GTZ (MOVVconst [c]) yes no) && c <= 0 -> (First no yes) +(GEZ (MOVVconst [c]) yes no) && c >= 0 -> (First yes no) +(GEZ (MOVVconst [c]) yes no) && c < 0 -> (First no yes) diff --git a/src/cmd/compile/internal/ssa/gen/MIPS64Ops.go b/src/cmd/compile/internal/ssa/gen/MIPS64Ops.go index e0a920f23d..184b119f89 100644 --- a/src/cmd/compile/internal/ssa/gen/MIPS64Ops.go +++ b/src/cmd/compile/internal/ssa/gen/MIPS64Ops.go @@ -453,14 +453,14 @@ func init() { } blocks := []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LTZ"}, // < 0 - {name: "LEZ"}, // <= 0 - {name: "GTZ"}, // > 0 - {name: "GEZ"}, // >= 0 - {name: "FPT"}, // FP flag is true - {name: "FPF"}, // FP flag is false + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LTZ", controls: 1}, // < 0 + {name: "LEZ", controls: 1}, // <= 0 + {name: "GTZ", controls: 1}, // > 0 + {name: "GEZ", controls: 1}, // >= 0 + {name: "FPT", controls: 1}, // FP flag is true + {name: "FPF", controls: 1}, // FP flag is false } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/MIPSOps.go b/src/cmd/compile/internal/ssa/gen/MIPSOps.go index 729cc05102..0f7b985e06 100644 --- a/src/cmd/compile/internal/ssa/gen/MIPSOps.go +++ b/src/cmd/compile/internal/ssa/gen/MIPSOps.go @@ -409,14 +409,14 @@ func init() { } blocks := []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LTZ"}, // < 0 - {name: "LEZ"}, // <= 0 - {name: "GTZ"}, // > 0 - {name: "GEZ"}, // >= 0 - {name: "FPT"}, // FP flag is true - {name: "FPF"}, // FP flag is false + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LTZ", controls: 1}, // < 0 + {name: "LEZ", controls: 1}, // <= 0 + {name: "GTZ", controls: 1}, // > 0 + {name: "GEZ", controls: 1}, // >= 0 + {name: "FPT", controls: 1}, // FP flag is true + {name: "FPF", controls: 1}, // FP flag is false } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/PPC64.rules b/src/cmd/compile/internal/ssa/gen/PPC64.rules index b247a0b99e..59cce4ed57 100644 --- a/src/cmd/compile/internal/ssa/gen/PPC64.rules +++ b/src/cmd/compile/internal/ssa/gen/PPC64.rules @@ -447,29 +447,29 @@ (NE (CMPWconst [0] (ANDconst [c] x)) yes no) -> (NE (ANDCCconst [c] x) yes no) // absorb flag constants into branches -(EQ (FlagEQ) yes no) -> (First nil yes no) -(EQ (FlagLT) yes no) -> (First nil no yes) -(EQ (FlagGT) yes no) -> (First nil no yes) +(EQ (FlagEQ) yes no) -> (First yes no) +(EQ (FlagLT) yes no) -> (First no yes) +(EQ (FlagGT) yes no) -> (First no yes) -(NE (FlagEQ) yes no) -> (First nil no yes) -(NE (FlagLT) yes no) -> (First nil yes no) -(NE (FlagGT) yes no) -> (First nil yes no) +(NE (FlagEQ) yes no) -> (First no yes) +(NE (FlagLT) yes no) -> (First yes no) +(NE (FlagGT) yes no) -> (First yes no) -(LT (FlagEQ) yes no) -> (First nil no yes) -(LT (FlagLT) yes no) -> (First nil yes no) -(LT (FlagGT) yes no) -> (First nil no yes) +(LT (FlagEQ) yes no) -> (First no yes) +(LT (FlagLT) yes no) -> (First yes no) +(LT (FlagGT) yes no) -> (First no yes) -(LE (FlagEQ) yes no) -> (First nil yes no) -(LE (FlagLT) yes no) -> (First nil yes no) -(LE (FlagGT) yes no) -> (First nil no yes) +(LE (FlagEQ) yes no) -> (First yes no) +(LE (FlagLT) yes no) -> (First yes no) +(LE (FlagGT) yes no) -> (First no yes) -(GT (FlagEQ) yes no) -> (First nil no yes) -(GT (FlagLT) yes no) -> (First nil no yes) -(GT (FlagGT) yes no) -> (First nil yes no) +(GT (FlagEQ) yes no) -> (First no yes) +(GT (FlagLT) yes no) -> (First no yes) +(GT (FlagGT) yes no) -> (First yes no) -(GE (FlagEQ) yes no) -> (First nil yes no) -(GE (FlagLT) yes no) -> (First nil no yes) -(GE (FlagGT) yes no) -> (First nil yes no) +(GE (FlagEQ) yes no) -> (First yes no) +(GE (FlagLT) yes no) -> (First no yes) +(GE (FlagGT) yes no) -> (First yes no) // absorb InvertFlags into branches (LT (InvertFlags cmp) yes no) -> (GT cmp yes no) diff --git a/src/cmd/compile/internal/ssa/gen/PPC64Ops.go b/src/cmd/compile/internal/ssa/gen/PPC64Ops.go index 138fe23ca8..5505db5222 100644 --- a/src/cmd/compile/internal/ssa/gen/PPC64Ops.go +++ b/src/cmd/compile/internal/ssa/gen/PPC64Ops.go @@ -585,16 +585,16 @@ func init() { } blocks := []blockData{ - {name: "EQ"}, - {name: "NE"}, - {name: "LT"}, - {name: "LE"}, - {name: "GT"}, - {name: "GE"}, - {name: "FLT"}, - {name: "FLE"}, - {name: "FGT"}, - {name: "FGE"}, + {name: "EQ", controls: 1}, + {name: "NE", controls: 1}, + {name: "LT", controls: 1}, + {name: "LE", controls: 1}, + {name: "GT", controls: 1}, + {name: "GE", controls: 1}, + {name: "FLT", controls: 1}, + {name: "FLE", controls: 1}, + {name: "FGT", controls: 1}, + {name: "FGE", controls: 1}, } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/S390X.rules b/src/cmd/compile/internal/ssa/gen/S390X.rules index e30312e454..83c3b358b5 100644 --- a/src/cmd/compile/internal/ssa/gen/S390X.rules +++ b/src/cmd/compile/internal/ssa/gen/S390X.rules @@ -976,15 +976,15 @@ (CMP(W|W|WU|WU)const (MOV(W|WZ|W|WZ)reg x) [c]) -> (CMP(W|W|WU|WU)const x [c]) // Absorb flag constants into branches. -(BRC {c} (FlagEQ) yes no) && c.(s390x.CCMask) & s390x.Equal != 0 -> (First nil yes no) -(BRC {c} (FlagLT) yes no) && c.(s390x.CCMask) & s390x.Less != 0 -> (First nil yes no) -(BRC {c} (FlagGT) yes no) && c.(s390x.CCMask) & s390x.Greater != 0 -> (First nil yes no) -(BRC {c} (FlagOV) yes no) && c.(s390x.CCMask) & s390x.Unordered != 0 -> (First nil yes no) - -(BRC {c} (FlagEQ) yes no) && c.(s390x.CCMask) & s390x.Equal == 0 -> (First nil no yes) -(BRC {c} (FlagLT) yes no) && c.(s390x.CCMask) & s390x.Less == 0 -> (First nil no yes) -(BRC {c} (FlagGT) yes no) && c.(s390x.CCMask) & s390x.Greater == 0 -> (First nil no yes) -(BRC {c} (FlagOV) yes no) && c.(s390x.CCMask) & s390x.Unordered == 0 -> (First nil no yes) +(BRC {c} (FlagEQ) yes no) && c.(s390x.CCMask) & s390x.Equal != 0 -> (First yes no) +(BRC {c} (FlagLT) yes no) && c.(s390x.CCMask) & s390x.Less != 0 -> (First yes no) +(BRC {c} (FlagGT) yes no) && c.(s390x.CCMask) & s390x.Greater != 0 -> (First yes no) +(BRC {c} (FlagOV) yes no) && c.(s390x.CCMask) & s390x.Unordered != 0 -> (First yes no) + +(BRC {c} (FlagEQ) yes no) && c.(s390x.CCMask) & s390x.Equal == 0 -> (First no yes) +(BRC {c} (FlagLT) yes no) && c.(s390x.CCMask) & s390x.Less == 0 -> (First no yes) +(BRC {c} (FlagGT) yes no) && c.(s390x.CCMask) & s390x.Greater == 0 -> (First no yes) +(BRC {c} (FlagOV) yes no) && c.(s390x.CCMask) & s390x.Unordered == 0 -> (First no yes) // Absorb flag constants into SETxx ops. (LOCGR {c} _ x (FlagEQ)) && c.(s390x.CCMask) & s390x.Equal != 0 -> x diff --git a/src/cmd/compile/internal/ssa/gen/S390XOps.go b/src/cmd/compile/internal/ssa/gen/S390XOps.go index c8e4a22846..d34c250cf6 100644 --- a/src/cmd/compile/internal/ssa/gen/S390XOps.go +++ b/src/cmd/compile/internal/ssa/gen/S390XOps.go @@ -708,7 +708,7 @@ func init() { } var S390Xblocks = []blockData{ - {name: "BRC"}, // aux is condition code mask (s390x.CCMask) + {name: "BRC", controls: 1}, // aux is condition code mask (s390x.CCMask) } archs = append(archs, arch{ diff --git a/src/cmd/compile/internal/ssa/gen/generic.rules b/src/cmd/compile/internal/ssa/gen/generic.rules index 8696464a70..1503a5da6c 100644 --- a/src/cmd/compile/internal/ssa/gen/generic.rules +++ b/src/cmd/compile/internal/ssa/gen/generic.rules @@ -879,8 +879,8 @@ (NilCheck (GetG mem) mem) -> mem (If (Not cond) yes no) -> (If cond no yes) -(If (ConstBool [c]) yes no) && c == 1 -> (First nil yes no) -(If (ConstBool [c]) yes no) && c == 0 -> (First nil no yes) +(If (ConstBool [c]) yes no) && c == 1 -> (First yes no) +(If (ConstBool [c]) yes no) && c == 0 -> (First no yes) // Get rid of Convert ops for pointer arithmetic on unsafe.Pointer. (Convert (Add(64|32) (Convert ptr mem) off) mem) -> (Add(64|32) ptr off) diff --git a/src/cmd/compile/internal/ssa/gen/genericOps.go b/src/cmd/compile/internal/ssa/gen/genericOps.go index 3ca773b595..df0dd8cabc 100644 --- a/src/cmd/compile/internal/ssa/gen/genericOps.go +++ b/src/cmd/compile/internal/ssa/gen/genericOps.go @@ -557,24 +557,22 @@ var genericOps = []opData{ {name: "Clobber", argLength: 0, typ: "Void", aux: "SymOff", symEffect: "None"}, // write an invalid pointer value to the given pointer slot of a stack variable } -// kind control successors implicit exit +// kind controls successors implicit exit // ---------------------------------------------------------- -// Exit return mem [] yes -// Ret return mem [] yes -// RetJmp return mem [] yes -// Plain nil [next] -// If a boolean Value [then, else] -// Call mem [next] yes (control opcode should be OpCall or OpStaticCall) -// Check void [next] yes (control opcode should be Op{Lowered}NilCheck) -// First nil [always,never] +// Exit [return mem] [] yes +// Ret [return mem] [] yes +// RetJmp [return mem] [] yes +// Plain [] [next] +// If [boolean Value] [then, else] +// First [] [always, never] var genericBlocks = []blockData{ - {name: "Plain"}, // a single successor - {name: "If"}, // 2 successors, if control goto Succs[0] else goto Succs[1] - {name: "Defer"}, // 2 successors, Succs[0]=defer queued, Succs[1]=defer recovered. control is call op (of memory type) - {name: "Ret"}, // no successors, control value is memory result - {name: "RetJmp"}, // no successors, jumps to b.Aux.(*gc.Sym) - {name: "Exit"}, // no successors, control value generates a panic + {name: "Plain"}, // a single successor + {name: "If", controls: 1}, // if Controls[0] goto Succs[0] else goto Succs[1] + {name: "Defer", controls: 1}, // Succs[0]=defer queued, Succs[1]=defer recovered. Controls[0] is call op (of memory type) + {name: "Ret", controls: 1}, // no successors, Controls[0] value is memory result + {name: "RetJmp", controls: 1}, // no successors, Controls[0] value is memory result, jumps to b.Aux.(*gc.Sym) + {name: "Exit", controls: 1}, // no successors, Controls[0] value generates a panic // transient block state used for dead code removal {name: "First"}, // 2 successors, always takes the first one (second is dead) diff --git a/src/cmd/compile/internal/ssa/gen/main.go b/src/cmd/compile/internal/ssa/gen/main.go index decc583431..eef72284b9 100644 --- a/src/cmd/compile/internal/ssa/gen/main.go +++ b/src/cmd/compile/internal/ssa/gen/main.go @@ -68,7 +68,8 @@ type opData struct { } type blockData struct { - name string + name string // the suffix for this block ("EQ", "LT", etc.) + controls int // the number of control values this type of block requires } type regInfo struct { diff --git a/src/cmd/compile/internal/ssa/gen/rulegen.go b/src/cmd/compile/internal/ssa/gen/rulegen.go index 7c02778181..5c4c5ef1af 100644 --- a/src/cmd/compile/internal/ssa/gen/rulegen.go +++ b/src/cmd/compile/internal/ssa/gen/rulegen.go @@ -238,7 +238,6 @@ func genRulesSuffix(arch arch, suff string) { fn = &Func{kind: "Block"} fn.add(declf("config", "b.Func.Config")) fn.add(declf("typ", "&b.Func.Config.Types")) - fn.add(declf("v", "b.Control")) sw = &Switch{expr: exprf("b.Kind")} ops = ops[:0] @@ -247,9 +246,10 @@ func genRulesSuffix(arch arch, suff string) { } sort.Strings(ops) for _, op := range ops { - swc := &Case{expr: exprf("%s", blockName(op, arch))} + name, data := getBlockInfo(op, arch) + swc := &Case{expr: exprf("%s", name)} for _, rule := range blockrules[op] { - swc.add(genBlockRewrite(rule, arch)) + swc.add(genBlockRewrite(rule, arch, data)) } sw.add(swc) } @@ -593,11 +593,7 @@ func fprint(w io.Writer, n Node) { fmt.Fprintf(w, "// cond: %s\n", n.cond) } fmt.Fprintf(w, "// result: %s\n", n.result) - if n.checkOp != "" { - fmt.Fprintf(w, "for v.Op == %s {\n", n.checkOp) - } else { - fmt.Fprintf(w, "for {\n") - } + fmt.Fprintf(w, "for %s {\n", n.check) for _, n := range n.list { fprint(w, n) } @@ -700,7 +696,7 @@ type ( RuleRewrite struct { bodyBase match, cond, result string // top comments - checkOp string + check string // top-level boolean expression alloc int // for unique var names loc string // file name & line number of the original rule @@ -750,18 +746,39 @@ func breakf(format string, a ...interface{}) *CondBreak { return &CondBreak{exprf(format, a...)} } -func genBlockRewrite(rule Rule, arch arch) *RuleRewrite { +func genBlockRewrite(rule Rule, arch arch, data blockData) *RuleRewrite { rr := &RuleRewrite{loc: rule.loc} rr.match, rr.cond, rr.result = rule.parse() _, _, _, aux, s := extract(rr.match) // remove parens, then split - // check match of control value - pos := "" - if s[0] != "nil" { - if strings.Contains(s[0], "(") { - pos, rr.checkOp = genMatch0(rr, arch, s[0], "v") + // check match of control values + if len(s) < data.controls { + log.Fatalf("incorrect number of arguments in %s, got %v wanted at least %v", rule, len(s), data.controls) + } + controls := s[:data.controls] + pos := make([]string, data.controls) + for i, arg := range controls { + if strings.Contains(arg, "(") { + // TODO: allow custom names? + cname := fmt.Sprintf("b.Controls[%v]", i) + vname := fmt.Sprintf("v_%v", i) + rr.add(declf(vname, cname)) + p, op := genMatch0(rr, arch, arg, vname) + if op != "" { + check := fmt.Sprintf("%s.Op == %s", cname, op) + if rr.check == "" { + rr.check = check + } else { + rr.check = rr.check + " && " + check + } + } + if p == "" { + p = vname + ".Pos" + } + pos[i] = p } else { - rr.add(declf(s[0], "b.Control")) + rr.add(declf(arg, "b.Controls[%v]", i)) + pos[i] = arg + ".Pos" } } if aux != "" { @@ -773,10 +790,14 @@ func genBlockRewrite(rule Rule, arch arch) *RuleRewrite { // Rule matches. Generate result. outop, _, _, aux, t := extract(rr.result) // remove parens, then split - newsuccs := t[1:] + _, outdata := getBlockInfo(outop, arch) + if len(t) < outdata.controls { + log.Fatalf("incorrect number of output arguments in %s, got %v wanted at least %v", rule, len(s), outdata.controls) + } // Check if newsuccs is the same set as succs. - succs := s[1:] + succs := s[data.controls:] + newsuccs := t[outdata.controls:] m := map[string]bool{} for _, succ := range succs { if m[succ] { @@ -794,15 +815,23 @@ func genBlockRewrite(rule Rule, arch arch) *RuleRewrite { log.Fatalf("unmatched successors %v in %s", m, rule) } - rr.add(stmtf("b.Kind = %s", blockName(outop, arch))) - if t[0] == "nil" { - rr.add(stmtf("b.SetControl(nil)")) - } else { - if pos == "" { - pos = "v.Pos" + blockName, _ := getBlockInfo(outop, arch) + rr.add(stmtf("b.Kind = %s", blockName)) + rr.add(stmtf("b.ResetControls()")) + for i, control := range t[:outdata.controls] { + // Select a source position for any new control values. + // TODO: does it always make sense to use the source position + // of the original control values or should we be using the + // block's source position in some cases? + newpos := "b.Pos" // default to block's source position + if i < len(pos) && pos[i] != "" { + // Use the previous control value's source position. + newpos = pos[i] } - v := genResult0(rr, arch, t[0], false, false, pos) - rr.add(stmtf("b.SetControl(%s)", v)) + + // Generate a new control value (or copy an existing value). + v := genResult0(rr, arch, control, false, false, newpos) + rr.add(stmtf("b.AddControl(%s)", v)) } if aux != "" { rr.add(stmtf("b.Aux = %s", aux)) @@ -1164,13 +1193,19 @@ func parseValue(val string, arch arch, loc string) (op opData, oparch, typ, auxi return } -func blockName(name string, arch arch) string { +func getBlockInfo(op string, arch arch) (name string, data blockData) { for _, b := range genericBlocks { - if b.name == name { - return "Block" + name + if b.name == op { + return "Block" + op, b + } + } + for _, b := range arch.blocks { + if b.name == op { + return "Block" + arch.name + op, b } } - return "Block" + arch.name + name + log.Fatalf("could not find block data for %s", op) + panic("unreachable") } // typeName returns the string to use to generate a type. diff --git a/src/cmd/compile/internal/ssa/html.go b/src/cmd/compile/internal/ssa/html.go index a1b718096d..1e76a673ef 100644 --- a/src/cmd/compile/internal/ssa/html.go +++ b/src/cmd/compile/internal/ssa/html.go @@ -846,8 +846,8 @@ func (b *Block) LongHTML() string { if b.Aux != nil { s += html.EscapeString(fmt.Sprintf(" {%v}", b.Aux)) } - if b.Control != nil { - s += fmt.Sprintf(" %s", b.Control.HTML()) + for _, c := range b.ControlValues() { + s += fmt.Sprintf(" %s", c.HTML()) } if len(b.Succs) > 0 { s += " →" // right arrow diff --git a/src/cmd/compile/internal/ssa/loopbce.go b/src/cmd/compile/internal/ssa/loopbce.go index bfa2597493..d53014943d 100644 --- a/src/cmd/compile/internal/ssa/loopbce.go +++ b/src/cmd/compile/internal/ssa/loopbce.go @@ -96,17 +96,18 @@ func findIndVar(f *Func) []indVar { // Check thet the control if it either ind />= ind. // TODO: Handle 32-bit comparisons. // TODO: Handle unsigned comparisons? - switch b.Control.Op { + c := b.Controls[0] + switch c.Op { case OpLeq64: flags |= indVarMaxInc fallthrough case OpLess64: - ind, max = b.Control.Args[0], b.Control.Args[1] + ind, max = c.Args[0], c.Args[1] case OpGeq64: flags |= indVarMaxInc fallthrough case OpGreater64: - ind, max = b.Control.Args[1], b.Control.Args[0] + ind, max = c.Args[1], c.Args[0] default: continue } @@ -207,7 +208,7 @@ func findIndVar(f *Func) []indVar { } // Handle induction variables of these forms. // KNN is known-not-negative. - // SIGNED ARITHMETIC ONLY. (see switch on b.Control.Op above) + // SIGNED ARITHMETIC ONLY. (see switch on c above) // Possibilities for KNN are len and cap; perhaps we can infer others. // for i := 0; i <= KNN-k ; i += k // for i := 0; i < KNN-(k-1); i += k diff --git a/src/cmd/compile/internal/ssa/nilcheck.go b/src/cmd/compile/internal/ssa/nilcheck.go index 54c9c9d7de..009c68afa1 100644 --- a/src/cmd/compile/internal/ssa/nilcheck.go +++ b/src/cmd/compile/internal/ssa/nilcheck.go @@ -99,9 +99,8 @@ func nilcheckelim(f *Func) { // First, see if we're dominated by an explicit nil check. if len(b.Preds) == 1 { p := b.Preds[0].b - if p.Kind == BlockIf && p.Control.Op == OpIsNonNil && p.Succs[0].b == b { - ptr := p.Control.Args[0] - if !nonNilValues[ptr.ID] { + if p.Kind == BlockIf && p.Controls[0].Op == OpIsNonNil && p.Succs[0].b == b { + if ptr := p.Controls[0].Args[0]; !nonNilValues[ptr.ID] { nonNilValues[ptr.ID] = true work = append(work, bp{op: ClearPtr, ptr: ptr}) } diff --git a/src/cmd/compile/internal/ssa/nilcheck_test.go b/src/cmd/compile/internal/ssa/nilcheck_test.go index b2f5cae088..e984069022 100644 --- a/src/cmd/compile/internal/ssa/nilcheck_test.go +++ b/src/cmd/compile/internal/ssa/nilcheck_test.go @@ -59,7 +59,7 @@ func ptrn(n int) string { return "p" + strconv.Itoa(n) } func booln(n int) string { return "c" + strconv.Itoa(n) } func isNilCheck(b *Block) bool { - return b.Kind == BlockIf && b.Control.Op == OpIsNonNil + return b.Kind == BlockIf && b.Controls[0].Op == OpIsNonNil } // TestNilcheckSimple verifies that a second repeated nilcheck is removed. diff --git a/src/cmd/compile/internal/ssa/phiopt.go b/src/cmd/compile/internal/ssa/phiopt.go index 60c8e58bd2..1840d6d54e 100644 --- a/src/cmd/compile/internal/ssa/phiopt.go +++ b/src/cmd/compile/internal/ssa/phiopt.go @@ -79,7 +79,7 @@ func phiopt(f *Func) { if v.Args[reverse].AuxInt != v.Args[1-reverse].AuxInt { ops := [2]Op{OpNot, OpCopy} v.reset(ops[v.Args[reverse].AuxInt]) - v.AddArg(b0.Control) + v.AddArg(b0.Controls[0]) if f.pass.debug > 0 { f.Warnl(b.Pos, "converted OpPhi to %v", v.Op) } @@ -95,7 +95,7 @@ func phiopt(f *Func) { if v.Args[reverse].Op == OpConstBool && v.Args[reverse].AuxInt == 1 { if tmp := v.Args[1-reverse]; sdom.isAncestorEq(tmp.Block, b) { v.reset(OpOrB) - v.SetArgs2(b0.Control, tmp) + v.SetArgs2(b0.Controls[0], tmp) if f.pass.debug > 0 { f.Warnl(b.Pos, "converted OpPhi to %v", v.Op) } @@ -111,7 +111,7 @@ func phiopt(f *Func) { if v.Args[1-reverse].Op == OpConstBool && v.Args[1-reverse].AuxInt == 0 { if tmp := v.Args[reverse]; sdom.isAncestorEq(tmp.Block, b) { v.reset(OpAndB) - v.SetArgs2(b0.Control, tmp) + v.SetArgs2(b0.Controls[0], tmp) if f.pass.debug > 0 { f.Warnl(b.Pos, "converted OpPhi to %v", v.Op) } @@ -161,7 +161,7 @@ func phioptint(v *Value, b0 *Block, reverse int) { v.Fatalf("bad int size %d", v.Type.Size()) } - a := b0.Control + a := b0.Controls[0] if negate { a = v.Block.NewValue1(v.Pos, OpNot, a.Type, a) } diff --git a/src/cmd/compile/internal/ssa/prove.go b/src/cmd/compile/internal/ssa/prove.go index 014535c0a4..efa4453f75 100644 --- a/src/cmd/compile/internal/ssa/prove.go +++ b/src/cmd/compile/internal/ssa/prove.go @@ -979,7 +979,7 @@ func addIndVarRestrictions(ft *factsTable, b *Block, iv indVar) { // addBranchRestrictions updates the factsTables ft with the facts learned when // branching from Block b in direction br. func addBranchRestrictions(ft *factsTable, b *Block, br branch) { - c := b.Control + c := b.Controls[0] switch br { case negative: addRestrictions(b, ft, boolean, nil, c, eq) @@ -988,14 +988,14 @@ func addBranchRestrictions(ft *factsTable, b *Block, br branch) { default: panic("unknown branch") } - if tr, has := domainRelationTable[b.Control.Op]; has { + if tr, has := domainRelationTable[c.Op]; has { // When we branched from parent we learned a new set of // restrictions. Update the factsTable accordingly. d := tr.d if d == signed && ft.isNonNegative(c.Args[0]) && ft.isNonNegative(c.Args[1]) { d |= unsigned } - switch b.Control.Op { + switch c.Op { case OpIsInBounds, OpIsSliceInBounds: // 0 <= a0 < a1 (or 0 <= a0 <= a1) // @@ -1096,6 +1096,7 @@ func addLocalInductiveFacts(ft *factsTable, b *Block) { if pred.Kind != BlockIf { continue } + control := pred.Controls[0] br := unknown if pred.Succs[0].b == child { @@ -1108,7 +1109,7 @@ func addLocalInductiveFacts(ft *factsTable, b *Block) { br = negative } - tr, has := domainRelationTable[pred.Control.Op] + tr, has := domainRelationTable[control.Op] if !has { continue } @@ -1121,10 +1122,10 @@ func addLocalInductiveFacts(ft *factsTable, b *Block) { // Check for i2 < max or max > i2. var max *Value - if r == lt && pred.Control.Args[0] == i2 { - max = pred.Control.Args[1] - } else if r == gt && pred.Control.Args[1] == i2 { - max = pred.Control.Args[0] + if r == lt && control.Args[0] == i2 { + max = control.Args[1] + } else if r == gt && control.Args[1] == i2 { + max = control.Args[0] } else { continue } @@ -1288,7 +1289,7 @@ func removeBranch(b *Block, branch branch) { if branch == positive { verb = "Disproved" } - c := b.Control + c := b.Controls[0] if b.Func.pass.debug > 1 { b.Func.Warnl(b.Pos, "%s %s (%s)", verb, c.Op, c) } else { @@ -1296,7 +1297,7 @@ func removeBranch(b *Block, branch branch) { } } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() if branch == positive { b.swapSuccessors() } diff --git a/src/cmd/compile/internal/ssa/regalloc.go b/src/cmd/compile/internal/ssa/regalloc.go index 2590315ba1..6ffa1e3848 100644 --- a/src/cmd/compile/internal/ssa/regalloc.go +++ b/src/cmd/compile/internal/ssa/regalloc.go @@ -701,8 +701,10 @@ func (s *regAllocState) init(f *Func) { for _, b := range f.Blocks { // New block. Clear candidate set. canLiveOnStack.clear() - if b.Control != nil && b.Control.Uses == 1 && !opcodeTable[b.Control.Op].generic { - canLiveOnStack.add(b.Control.ID) + for _, c := range b.ControlValues() { + if c.Uses == 1 && !opcodeTable[c.Op].generic { + canLiveOnStack.add(c.ID) + } } // Walking backwards. for i := len(b.Values) - 1; i >= 0; i-- { @@ -856,9 +858,11 @@ func (s *regAllocState) regalloc(f *Func) { s.addUse(e.ID, int32(len(b.Values))+e.dist, e.pos) // pseudo-uses from beyond end of block regValLiveSet.add(e.ID) } - if v := b.Control; v != nil && s.values[v.ID].needReg { - s.addUse(v.ID, int32(len(b.Values)), b.Pos) // pseudo-use by control value - regValLiveSet.add(v.ID) + for _, v := range b.ControlValues() { + if s.values[v.ID].needReg { + s.addUse(v.ID, int32(len(b.Values)), b.Pos) // pseudo-use by control values + regValLiveSet.add(v.ID) + } } for i := len(b.Values) - 1; i >= 0; i-- { v := b.Values[i] @@ -1503,21 +1507,32 @@ func (s *regAllocState) regalloc(f *Func) { issueSpill: } - // Load control value into reg. - if v := b.Control; v != nil && s.values[v.ID].needReg { + // Copy the control values - we need this so we can reduce the + // uses property of these values later. + controls := append(make([]*Value, 0, 2), b.ControlValues()...) + + // Load control values into registers. + for i, v := range b.ControlValues() { + if !s.values[v.ID].needReg { + continue + } if s.f.pass.debug > regDebug { fmt.Printf(" processing control %s\n", v.LongString()) } // We assume that a control input can be passed in any // type-compatible register. If this turns out not to be true, // we'll need to introduce a regspec for a block's control value. - b.Control = s.allocValToReg(v, s.compatRegs(v.Type), false, b.Pos) - if b.Control != v { - v.Uses-- - b.Control.Uses++ + b.ReplaceControl(i, s.allocValToReg(v, s.compatRegs(v.Type), false, b.Pos)) + } + + // Reduce the uses of the control values once registers have been loaded. + // This loop is equivalent to the advanceUses method. + for _, v := range controls { + vi := &s.values[v.ID] + if !vi.needReg { + continue } // Remove this use from the uses list. - vi := &s.values[v.ID] u := vi.uses vi.uses = u.next if u.next == nil { @@ -2355,9 +2370,11 @@ func (s *regAllocState) computeLive() { live.set(e.ID, e.dist+int32(len(b.Values)), e.pos) } - // Mark control value as live - if b.Control != nil && s.values[b.Control.ID].needReg { - live.set(b.Control.ID, int32(len(b.Values)), b.Pos) + // Mark control values as live + for _, c := range b.ControlValues() { + if s.values[c.ID].needReg { + live.set(c.ID, int32(len(b.Values)), b.Pos) + } } // Propagate backwards to the start of the block diff --git a/src/cmd/compile/internal/ssa/rewrite.go b/src/cmd/compile/internal/ssa/rewrite.go index 22e17cb5da..59d7601567 100644 --- a/src/cmd/compile/internal/ssa/rewrite.go +++ b/src/cmd/compile/internal/ssa/rewrite.go @@ -25,9 +25,10 @@ func applyRewrite(f *Func, rb blockRewriter, rv valueRewriter) { for { change := false for _, b := range f.Blocks { - if b.Control != nil && b.Control.Op == OpCopy { - for b.Control.Op == OpCopy { - b.SetControl(b.Control.Args[0]) + for i, c := range b.ControlValues() { + for c.Op == OpCopy { + c = c.Args[0] + b.ReplaceControl(i, c) } } if rb(b) { diff --git a/src/cmd/compile/internal/ssa/rewrite386.go b/src/cmd/compile/internal/ssa/rewrite386.go index 08139d6ae4..bde41059f8 100644 --- a/src/cmd/compile/internal/ssa/rewrite386.go +++ b/src/cmd/compile/internal/ssa/rewrite386.go @@ -21975,58 +21975,59 @@ func rewriteValue386_OpZeromask_0(v *Value) bool { } } func rewriteBlock386(b *Block) bool { - v := b.Control switch b.Kind { case Block386EQ: // match: (EQ (InvertFlags cmp) yes no) // result: (EQ cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -22034,304 +22035,341 @@ func rewriteBlock386(b *Block) bool { case Block386GE: // match: (GE (InvertFlags cmp) yes no) // result: (LE cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case Block386GT: // match: (GT (InvertFlags cmp) yes no) // result: (LT cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockIf: // match: (If (SETL cmp) yes no) // result: (LT cmp yes no) - for v.Op == Op386SETL { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETL { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETLE cmp) yes no) // result: (LE cmp yes no) - for v.Op == Op386SETLE { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETLE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETG cmp) yes no) // result: (GT cmp yes no) - for v.Op == Op386SETG { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETG { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGE cmp) yes no) // result: (GE cmp yes no) - for v.Op == Op386SETGE { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETGE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETEQ cmp) yes no) // result: (EQ cmp yes no) - for v.Op == Op386SETEQ { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETEQ { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETNE cmp) yes no) // result: (NE cmp yes no) - for v.Op == Op386SETNE { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETNE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETB cmp) yes no) // result: (ULT cmp yes no) - for v.Op == Op386SETB { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETB { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETBE cmp) yes no) // result: (ULE cmp yes no) - for v.Op == Op386SETBE { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETBE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETA cmp) yes no) // result: (UGT cmp yes no) - for v.Op == Op386SETA { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETA { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETAE cmp) yes no) // result: (UGE cmp yes no) - for v.Op == Op386SETAE { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETAE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETO cmp) yes no) // result: (OS cmp yes no) - for v.Op == Op386SETO { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETO { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGF cmp) yes no) // result: (UGT cmp yes no) - for v.Op == Op386SETGF { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETGF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGEF cmp) yes no) // result: (UGE cmp yes no) - for v.Op == Op386SETGEF { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETGEF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETEQF cmp) yes no) // result: (EQF cmp yes no) - for v.Op == Op386SETEQF { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETEQF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETNEF cmp) yes no) // result: (NEF cmp yes no) - for v.Op == Op386SETNEF { - cmp := v.Args[0] + for b.Controls[0].Op == Op386SETNEF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If cond yes no) // result: (NE (TESTB cond cond) yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = Block386NE - v0 := b.NewValue0(v.Pos, Op386TESTB, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(cond.Pos, Op386TESTB, types.TypeFlags) v0.AddArg(cond) v0.AddArg(cond) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case Block386LE: // match: (LE (InvertFlags cmp) yes no) // result: (GE cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -22339,52 +22377,54 @@ func rewriteBlock386(b *Block) bool { case Block386LT: // match: (LT (InvertFlags cmp) yes no) // result: (GT cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -22392,747 +22432,815 @@ func rewriteBlock386(b *Block) bool { case Block386NE: // match: (NE (TESTB (SETL cmp) (SETL cmp)) yes no) // result: (LT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETL { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETL { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETL || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETL || cmp != v_0_1.Args[0] { break } b.Kind = Block386LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETL cmp) (SETL cmp)) yes no) // result: (LT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETL { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETL { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETL || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETL || cmp != v_0_1.Args[0] { break } b.Kind = Block386LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETLE cmp) (SETLE cmp)) yes no) // result: (LE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETLE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETLE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETLE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETLE || cmp != v_0_1.Args[0] { break } b.Kind = Block386LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETLE cmp) (SETLE cmp)) yes no) // result: (LE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETLE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETLE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETLE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETLE || cmp != v_0_1.Args[0] { break } b.Kind = Block386LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETG cmp) (SETG cmp)) yes no) // result: (GT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETG { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETG { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETG || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETG || cmp != v_0_1.Args[0] { break } b.Kind = Block386GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETG cmp) (SETG cmp)) yes no) // result: (GT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETG { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETG { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETG || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETG || cmp != v_0_1.Args[0] { break } b.Kind = Block386GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGE cmp) (SETGE cmp)) yes no) // result: (GE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGE || cmp != v_0_1.Args[0] { break } b.Kind = Block386GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGE cmp) (SETGE cmp)) yes no) // result: (GE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGE || cmp != v_0_1.Args[0] { break } b.Kind = Block386GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQ cmp) (SETEQ cmp)) yes no) // result: (EQ cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETEQ { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETEQ { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETEQ || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETEQ || cmp != v_0_1.Args[0] { break } b.Kind = Block386EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQ cmp) (SETEQ cmp)) yes no) // result: (EQ cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETEQ { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETEQ { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETEQ || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETEQ || cmp != v_0_1.Args[0] { break } b.Kind = Block386EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNE cmp) (SETNE cmp)) yes no) // result: (NE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETNE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETNE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETNE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETNE || cmp != v_0_1.Args[0] { break } b.Kind = Block386NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNE cmp) (SETNE cmp)) yes no) // result: (NE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETNE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETNE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETNE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETNE || cmp != v_0_1.Args[0] { break } b.Kind = Block386NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETB cmp) (SETB cmp)) yes no) // result: (ULT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETB { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETB { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETB || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETB || cmp != v_0_1.Args[0] { break } b.Kind = Block386ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETB cmp) (SETB cmp)) yes no) // result: (ULT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETB { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETB { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETB || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETB || cmp != v_0_1.Args[0] { break } b.Kind = Block386ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETBE cmp) (SETBE cmp)) yes no) // result: (ULE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETBE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETBE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETBE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETBE || cmp != v_0_1.Args[0] { break } b.Kind = Block386ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETBE cmp) (SETBE cmp)) yes no) // result: (ULE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETBE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETBE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETBE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETBE || cmp != v_0_1.Args[0] { break } b.Kind = Block386ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETA cmp) (SETA cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETA { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETA { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETA || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETA || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETA cmp) (SETA cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETA { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETA { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETA || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETA || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETAE cmp) (SETAE cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETAE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETAE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETAE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETAE || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETAE cmp) (SETAE cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETAE { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETAE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETAE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETAE || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETO cmp) (SETO cmp)) yes no) // result: (OS cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETO { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETO { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETO || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETO || cmp != v_0_1.Args[0] { break } b.Kind = Block386OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETO cmp) (SETO cmp)) yes no) // result: (OS cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETO { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETO { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETO || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETO || cmp != v_0_1.Args[0] { break } b.Kind = Block386OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGF cmp) (SETGF cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGF || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGF cmp) (SETGF cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGF || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGEF cmp) (SETGEF cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGEF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGEF || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGEF cmp) (SETGEF cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETGEF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETGEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETGEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETGEF || cmp != v_0_1.Args[0] { break } b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQF cmp) (SETEQF cmp)) yes no) // result: (EQF cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETEQF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETEQF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETEQF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETEQF || cmp != v_0_1.Args[0] { break } b.Kind = Block386EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQF cmp) (SETEQF cmp)) yes no) // result: (EQF cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETEQF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETEQF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETEQF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETEQF || cmp != v_0_1.Args[0] { break } b.Kind = Block386EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNEF cmp) (SETNEF cmp)) yes no) // result: (NEF cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETNEF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETNEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETNEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETNEF || cmp != v_0_1.Args[0] { break } b.Kind = Block386NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNEF cmp) (SETNEF cmp)) yes no) // result: (NEF cmp yes no) - for v.Op == Op386TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != Op386SETNEF { + for b.Controls[0].Op == Op386TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != Op386SETNEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != Op386SETNEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != Op386SETNEF || cmp != v_0_1.Args[0] { break } b.Kind = Block386NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (InvertFlags cmp) yes no) // result: (NE cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case Block386UGE: // match: (UGE (InvertFlags cmp) yes no) // result: (ULE cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (UGE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case Block386UGT: // match: (UGT (InvertFlags cmp) yes no) // result: (ULT cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (UGT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case Block386ULE: // match: (ULE (InvertFlags cmp) yes no) // result: (UGE cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (ULE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -23140,52 +23248,54 @@ func rewriteBlock386(b *Block) bool { case Block386ULT: // match: (ULT (InvertFlags cmp) yes no) // result: (UGT cmp yes no) - for v.Op == Op386InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == Op386InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = Block386UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (ULT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == Op386FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == Op386FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == Op386FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == Op386FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true diff --git a/src/cmd/compile/internal/ssa/rewriteAMD64.go b/src/cmd/compile/internal/ssa/rewriteAMD64.go index 055ab73b83..20443d2f48 100644 --- a/src/cmd/compile/internal/ssa/rewriteAMD64.go +++ b/src/cmd/compile/internal/ssa/rewriteAMD64.go @@ -58100,182 +58100,198 @@ func rewriteValueAMD64_OpZeroExt8to64_0(v *Value) bool { } func rewriteBlockAMD64(b *Block) bool { config := b.Func.Config - v := b.Control switch b.Kind { case BlockAMD64EQ: // match: (EQ (TESTL (SHLL (MOVLconst [1]) x) y)) // cond: !config.nacl // result: (UGE (BTL x y)) - for v.Op == OpAMD64TESTL { - y := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SHLL { + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + y := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SHLL { break } - x := v_0.Args[1] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpAMD64MOVLconst || v_0_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_0.Args[1] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpAMD64MOVLconst || v_0_0_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTL, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL y (SHLL (MOVLconst [1]) x))) // cond: !config.nacl // result: (UGE (BTL x y)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - y := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SHLL { + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + y := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SHLL { break } - x := v_1.Args[1] - v_1_0 := v_1.Args[0] - if v_1_0.Op != OpAMD64MOVLconst || v_1_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_1.Args[1] + v_0_1_0 := v_0_1.Args[0] + if v_0_1_0.Op != OpAMD64MOVLconst || v_0_1_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTL, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ (SHLQ (MOVQconst [1]) x) y)) // cond: !config.nacl // result: (UGE (BTQ x y)) - for v.Op == OpAMD64TESTQ { - y := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SHLQ { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + y := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SHLQ { break } - x := v_0.Args[1] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpAMD64MOVQconst || v_0_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_0.Args[1] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpAMD64MOVQconst || v_0_0_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ y (SHLQ (MOVQconst [1]) x))) // cond: !config.nacl // result: (UGE (BTQ x y)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - y := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SHLQ { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + y := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SHLQ { break } - x := v_1.Args[1] - v_1_0 := v_1.Args[0] - if v_1_0.Op != OpAMD64MOVQconst || v_1_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_1.Args[1] + v_0_1_0 := v_0_1.Args[0] + if v_0_1_0.Op != OpAMD64MOVQconst || v_0_1_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTLconst [c] x)) // cond: isUint32PowerOfTwo(c) && !config.nacl // result: (UGE (BTLconst [log2uint32(c)] x)) - for v.Op == OpAMD64TESTLconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTLconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(isUint32PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = log2uint32(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQconst [c] x)) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (UGE (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ (MOVQconst [c]) x)) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (UGE (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQ { - x := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64MOVQconst { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + x := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64MOVQconst { break } - c := v_0.AuxInt + c := v_0_0.AuxInt if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ x (MOVQconst [c]))) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (UGE (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64MOVQconst { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64MOVQconst { break } - c := v_1.AuxInt + c := v_0_1.AuxInt if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z1:(SHLQconst [63] (SHRQconst [63] x)) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHLQconst || z1.AuxInt != 63 { break } @@ -58288,20 +58304,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z2 z1:(SHLQconst [63] (SHRQconst [63] x)))) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHLQconst || z1.AuxInt != 63 { break } @@ -58314,19 +58332,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z1:(SHLLconst [31] (SHRQconst [31] x)) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [31] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHLLconst || z1.AuxInt != 31 { break } @@ -58339,20 +58359,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z2 z1:(SHLLconst [31] (SHRQconst [31] x)))) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [31] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHLLconst || z1.AuxInt != 31 { break } @@ -58365,19 +58387,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z1:(SHRQconst [63] (SHLQconst [63] x)) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [0] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -58390,20 +58414,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z2 z1:(SHRQconst [63] (SHLQconst [63] x)))) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [0] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -58416,19 +58442,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z1:(SHRLconst [31] (SHLLconst [31] x)) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTLconst [0] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -58441,20 +58469,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z2 z1:(SHRLconst [31] (SHLLconst [31] x)))) // cond: z1==z2 && !config.nacl // result: (UGE (BTLconst [0] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -58467,19 +58497,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z1:(SHRQconst [63] x) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -58488,20 +58520,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTQ z2 z1:(SHRQconst [63] x))) // cond: z1==z2 && !config.nacl // result: (UGE (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -58510,19 +58544,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z1:(SHRLconst [31] x) z2)) // cond: z1==z2 && !config.nacl // result: (UGE (BTLconst [31] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -58531,20 +58567,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TESTL z2 z1:(SHRLconst [31] x))) // cond: z1==z2 && !config.nacl // result: (UGE (BTLconst [31] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -58553,62 +58591,65 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64UGE - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (InvertFlags cmp) yes no) // result: (EQ cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -58616,304 +58657,341 @@ func rewriteBlockAMD64(b *Block) bool { case BlockAMD64GE: // match: (GE (InvertFlags cmp) yes no) // result: (LE cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockAMD64GT: // match: (GT (InvertFlags cmp) yes no) // result: (LT cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockIf: // match: (If (SETL cmp) yes no) // result: (LT cmp yes no) - for v.Op == OpAMD64SETL { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETL { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETLE cmp) yes no) // result: (LE cmp yes no) - for v.Op == OpAMD64SETLE { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETLE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETG cmp) yes no) // result: (GT cmp yes no) - for v.Op == OpAMD64SETG { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETG { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGE cmp) yes no) // result: (GE cmp yes no) - for v.Op == OpAMD64SETGE { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETGE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETEQ cmp) yes no) // result: (EQ cmp yes no) - for v.Op == OpAMD64SETEQ { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETEQ { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETNE cmp) yes no) // result: (NE cmp yes no) - for v.Op == OpAMD64SETNE { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETNE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETB cmp) yes no) // result: (ULT cmp yes no) - for v.Op == OpAMD64SETB { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETB { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETBE cmp) yes no) // result: (ULE cmp yes no) - for v.Op == OpAMD64SETBE { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETBE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETA cmp) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64SETA { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETA { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETAE cmp) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64SETAE { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETAE { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETO cmp) yes no) // result: (OS cmp yes no) - for v.Op == OpAMD64SETO { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETO { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGF cmp) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64SETGF { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETGF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETGEF cmp) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64SETGEF { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETGEF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETEQF cmp) yes no) // result: (EQF cmp yes no) - for v.Op == OpAMD64SETEQF { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETEQF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If (SETNEF cmp) yes no) // result: (NEF cmp yes no) - for v.Op == OpAMD64SETNEF { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64SETNEF { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (If cond yes no) // result: (NE (TESTB cond cond) yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockAMD64NE - v0 := b.NewValue0(v.Pos, OpAMD64TESTB, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(cond.Pos, OpAMD64TESTB, types.TypeFlags) v0.AddArg(cond) v0.AddArg(cond) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockAMD64LE: // match: (LE (InvertFlags cmp) yes no) // result: (GE cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -58921,52 +58999,54 @@ func rewriteBlockAMD64(b *Block) bool { case BlockAMD64LT: // match: (LT (InvertFlags cmp) yes no) // result: (GT cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -58974,573 +59054,634 @@ func rewriteBlockAMD64(b *Block) bool { case BlockAMD64NE: // match: (NE (TESTB (SETL cmp) (SETL cmp)) yes no) // result: (LT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETL { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETL { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETL || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETL || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETL cmp) (SETL cmp)) yes no) // result: (LT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETL { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETL { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETL || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETL || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETLE cmp) (SETLE cmp)) yes no) // result: (LE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETLE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETLE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETLE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETLE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETLE cmp) (SETLE cmp)) yes no) // result: (LE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETLE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETLE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETLE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETLE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETG cmp) (SETG cmp)) yes no) // result: (GT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETG { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETG { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETG || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETG || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETG cmp) (SETG cmp)) yes no) // result: (GT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETG { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETG { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETG || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETG || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGE cmp) (SETGE cmp)) yes no) // result: (GE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGE cmp) (SETGE cmp)) yes no) // result: (GE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQ cmp) (SETEQ cmp)) yes no) // result: (EQ cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETEQ { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETEQ { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETEQ || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETEQ || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQ cmp) (SETEQ cmp)) yes no) // result: (EQ cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETEQ { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETEQ { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETEQ || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETEQ || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNE cmp) (SETNE cmp)) yes no) // result: (NE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETNE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETNE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETNE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETNE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNE cmp) (SETNE cmp)) yes no) // result: (NE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETNE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETNE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETNE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETNE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETB cmp) (SETB cmp)) yes no) // result: (ULT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETB { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETB { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETB || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETB || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETB cmp) (SETB cmp)) yes no) // result: (ULT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETB { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETB { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETB || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETB || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETBE cmp) (SETBE cmp)) yes no) // result: (ULE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETBE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETBE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETBE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETBE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETBE cmp) (SETBE cmp)) yes no) // result: (ULE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETBE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETBE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETBE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETBE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETA cmp) (SETA cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETA { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETA { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETA || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETA || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETA cmp) (SETA cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETA { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETA { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETA || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETA || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETAE cmp) (SETAE cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETAE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETAE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETAE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETAE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETAE cmp) (SETAE cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETAE { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETAE { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETAE || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETAE || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETO cmp) (SETO cmp)) yes no) // result: (OS cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETO { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETO { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETO || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETO || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETO cmp) (SETO cmp)) yes no) // result: (OS cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETO { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETO { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETO || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETO || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64OS - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTL (SHLL (MOVLconst [1]) x) y)) // cond: !config.nacl // result: (ULT (BTL x y)) - for v.Op == OpAMD64TESTL { - y := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SHLL { + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + y := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SHLL { break } - x := v_0.Args[1] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpAMD64MOVLconst || v_0_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_0.Args[1] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpAMD64MOVLconst || v_0_0_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTL, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL y (SHLL (MOVLconst [1]) x))) // cond: !config.nacl // result: (ULT (BTL x y)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - y := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SHLL { + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + y := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SHLL { break } - x := v_1.Args[1] - v_1_0 := v_1.Args[0] - if v_1_0.Op != OpAMD64MOVLconst || v_1_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_1.Args[1] + v_0_1_0 := v_0_1.Args[0] + if v_0_1_0.Op != OpAMD64MOVLconst || v_0_1_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTL, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ (SHLQ (MOVQconst [1]) x) y)) // cond: !config.nacl // result: (ULT (BTQ x y)) - for v.Op == OpAMD64TESTQ { - y := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SHLQ { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + y := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SHLQ { break } - x := v_0.Args[1] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpAMD64MOVQconst || v_0_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_0.Args[1] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpAMD64MOVQconst || v_0_0_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ y (SHLQ (MOVQconst [1]) x))) // cond: !config.nacl // result: (ULT (BTQ x y)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - y := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SHLQ { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + y := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SHLQ { break } - x := v_1.Args[1] - v_1_0 := v_1.Args[0] - if v_1_0.Op != OpAMD64MOVQconst || v_1_0.AuxInt != 1 || !(!config.nacl) { + x := v_0_1.Args[1] + v_0_1_0 := v_0_1.Args[0] + if v_0_1_0.Op != OpAMD64MOVQconst || v_0_1_0.AuxInt != 1 || !(!config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTLconst [c] x)) // cond: isUint32PowerOfTwo(c) && !config.nacl // result: (ULT (BTLconst [log2uint32(c)] x)) - for v.Op == OpAMD64TESTLconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTLconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(isUint32PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = log2uint32(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQconst [c] x)) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (ULT (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ (MOVQconst [c]) x)) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (ULT (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQ { - x := v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64MOVQconst { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + x := v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64MOVQconst { break } - c := v_0.AuxInt + c := v_0_0.AuxInt if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ x (MOVQconst [c]))) // cond: isUint64PowerOfTwo(c) && !config.nacl // result: (ULT (BTQconst [log2(c)] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64MOVQconst { + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64MOVQconst { break } - c := v_1.AuxInt + c := v_0_1.AuxInt if !(isUint64PowerOfTwo(c) && !config.nacl) { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = log2(c) v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z1:(SHLQconst [63] (SHRQconst [63] x)) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHLQconst || z1.AuxInt != 63 { break } @@ -59553,20 +59694,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z2 z1:(SHLQconst [63] (SHRQconst [63] x)))) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHLQconst || z1.AuxInt != 63 { break } @@ -59579,19 +59722,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z1:(SHLLconst [31] (SHRQconst [31] x)) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [31] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHLLconst || z1.AuxInt != 31 { break } @@ -59604,20 +59749,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z2 z1:(SHLLconst [31] (SHRQconst [31] x)))) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [31] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHLLconst || z1.AuxInt != 31 { break } @@ -59630,19 +59777,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z1:(SHRQconst [63] (SHLQconst [63] x)) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [0] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -59655,20 +59804,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z2 z1:(SHRQconst [63] (SHLQconst [63] x)))) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [0] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -59681,19 +59832,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z1:(SHRLconst [31] (SHLLconst [31] x)) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTLconst [0] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -59706,20 +59859,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z2 z1:(SHRLconst [31] (SHLLconst [31] x)))) // cond: z1==z2 && !config.nacl // result: (ULT (BTLconst [0] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -59732,19 +59887,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z1:(SHRQconst [63] x) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -59753,20 +59910,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTQ z2 z1:(SHRQconst [63] x))) // cond: z1==z2 && !config.nacl // result: (ULT (BTQconst [63] x)) - for v.Op == OpAMD64TESTQ { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTQ { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRQconst || z1.AuxInt != 63 { break } @@ -59775,19 +59934,21 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTQconst, types.TypeFlags) v0.AuxInt = 63 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z1:(SHRLconst [31] x) z2)) // cond: z1==z2 && !config.nacl // result: (ULT (BTLconst [31] x)) - for v.Op == OpAMD64TESTL { - z2 := v.Args[1] - z1 := v.Args[0] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + z2 := v_0.Args[1] + z1 := v_0.Args[0] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -59796,20 +59957,22 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTL z2 z1:(SHRLconst [31] x))) // cond: z1==z2 && !config.nacl // result: (ULT (BTLconst [31] x)) - for v.Op == OpAMD64TESTL { - _ = v.Args[1] - z2 := v.Args[0] - z1 := v.Args[1] + for b.Controls[0].Op == OpAMD64TESTL { + v_0 := b.Controls[0] + _ = v_0.Args[1] + z2 := v_0.Args[0] + z1 := v_0.Args[1] if z1.Op != OpAMD64SHRLconst || z1.AuxInt != 31 { break } @@ -59818,360 +59981,385 @@ func rewriteBlockAMD64(b *Block) bool { break } b.Kind = BlockAMD64ULT - v0 := b.NewValue0(v.Pos, OpAMD64BTLconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpAMD64BTLconst, types.TypeFlags) v0.AuxInt = 31 v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TESTB (SETGF cmp) (SETGF cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGF cmp) (SETGF cmp)) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGEF cmp) (SETGEF cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGEF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGEF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETGEF cmp) (SETGEF cmp)) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETGEF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETGEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETGEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETGEF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQF cmp) (SETEQF cmp)) yes no) // result: (EQF cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETEQF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETEQF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETEQF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETEQF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETEQF cmp) (SETEQF cmp)) yes no) // result: (EQF cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETEQF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETEQF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETEQF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETEQF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64EQF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNEF cmp) (SETNEF cmp)) yes no) // result: (NEF cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETNEF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETNEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETNEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETNEF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (TESTB (SETNEF cmp) (SETNEF cmp)) yes no) // result: (NEF cmp yes no) - for v.Op == OpAMD64TESTB { - _ = v.Args[1] - v_0 := v.Args[0] - if v_0.Op != OpAMD64SETNEF { + for b.Controls[0].Op == OpAMD64TESTB { + v_0 := b.Controls[0] + _ = v_0.Args[1] + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpAMD64SETNEF { break } - cmp := v_0.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpAMD64SETNEF || cmp != v_1.Args[0] { + cmp := v_0_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpAMD64SETNEF || cmp != v_0_1.Args[0] { break } b.Kind = BlockAMD64NEF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (InvertFlags cmp) yes no) // result: (NE cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockAMD64UGE: // match: (UGE (InvertFlags cmp) yes no) // result: (ULE cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (UGE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockAMD64UGT: // match: (UGT (InvertFlags cmp) yes no) // result: (ULT cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (UGT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockAMD64ULE: // match: (ULE (InvertFlags cmp) yes no) // result: (UGE cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (ULE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -60179,52 +60367,54 @@ func rewriteBlockAMD64(b *Block) bool { case BlockAMD64ULT: // match: (ULT (InvertFlags cmp) yes no) // result: (UGT cmp yes no) - for v.Op == OpAMD64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpAMD64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockAMD64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (ULT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpAMD64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpAMD64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpAMD64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpAMD64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true diff --git a/src/cmd/compile/internal/ssa/rewriteARM.go b/src/cmd/compile/internal/ssa/rewriteARM.go index a192556059..b51799743b 100644 --- a/src/cmd/compile/internal/ssa/rewriteARM.go +++ b/src/cmd/compile/internal/ssa/rewriteARM.go @@ -20654,70 +20654,72 @@ func rewriteValueARM_OpZeromask_0(v *Value) bool { } } func rewriteBlockARM(b *Block) bool { - v := b.Control switch b.Kind { case BlockARMEQ: // match: (EQ (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (InvertFlags cmp) yes no) // result: (EQ cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (EQ (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -20727,21 +20729,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (EQ (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -20752,24 +20756,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (EQ (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -20779,21 +20785,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -20804,22 +20812,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -20830,22 +20840,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -20856,22 +20868,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -20882,22 +20896,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -20908,22 +20924,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -20934,22 +20952,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (EQ (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -20959,21 +20979,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (EQ (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -20984,24 +21006,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (EQ (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -21011,21 +21035,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -21036,22 +21062,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -21062,22 +21090,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -21088,22 +21118,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -21114,22 +21146,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -21140,22 +21174,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -21166,22 +21202,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (EQ (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -21191,21 +21229,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (EQ (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -21215,21 +21255,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -21240,22 +21282,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -21266,22 +21310,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -21292,22 +21338,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -21318,22 +21366,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -21344,22 +21394,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -21370,22 +21422,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (EQ (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -21395,21 +21449,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (EQ (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -21419,21 +21475,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -21444,22 +21502,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -21470,22 +21530,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -21496,22 +21558,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -21522,22 +21586,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -21548,22 +21614,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (EQ (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -21574,74 +21642,78 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMEQ - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMGE: // match: (GE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (InvertFlags cmp) yes no) // result: (LE cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMLE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (GE (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -21651,21 +21723,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (GE (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -21676,24 +21750,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (GE (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -21703,21 +21779,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -21728,22 +21806,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -21754,22 +21834,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -21780,22 +21862,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -21806,22 +21890,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -21832,22 +21918,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -21858,22 +21946,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (GE (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -21883,21 +21973,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (GE (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -21908,24 +22000,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (GE (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -21935,21 +22029,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -21960,22 +22056,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -21986,22 +22084,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -22012,22 +22112,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -22038,22 +22140,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -22064,22 +22168,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -22090,22 +22196,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (GE (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -22115,21 +22223,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (GE (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -22139,21 +22249,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -22164,22 +22276,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -22190,22 +22304,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -22216,22 +22332,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -22242,22 +22360,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -22268,22 +22388,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -22294,22 +22416,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (GE (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -22319,21 +22443,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (GE (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -22343,21 +22469,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -22368,22 +22496,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -22394,22 +22524,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -22420,22 +22552,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -22446,22 +22580,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -22472,22 +22608,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GE (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -22498,75 +22636,79 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMGT: // match: (GT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (InvertFlags cmp) yes no) // result: (LT cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMLT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (GT (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -22576,21 +22718,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (GT (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -22601,24 +22745,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (GT (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -22628,21 +22774,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -22653,22 +22801,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -22679,22 +22829,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -22705,22 +22857,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -22731,22 +22885,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -22757,22 +22913,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -22783,22 +22941,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (GT (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -22808,21 +22968,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (GT (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -22832,21 +22994,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -22857,22 +23021,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -22883,22 +23049,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -22909,22 +23077,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -22935,22 +23105,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -22961,22 +23133,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -22987,22 +23161,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (GT (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -23012,21 +23188,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (GT (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -23037,24 +23215,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (GT (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -23064,21 +23244,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -23089,22 +23271,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -23115,22 +23299,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -23141,22 +23327,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -23167,22 +23355,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -23193,22 +23383,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -23219,22 +23411,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (GT (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -23244,21 +23438,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (GT (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -23268,21 +23464,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -23293,22 +23491,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -23319,22 +23519,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -23345,22 +23547,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -23371,22 +23575,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -23397,22 +23603,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (GT (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -23423,177 +23631,202 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMGT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockIf: // match: (If (Equal cc) yes no) // result: (EQ cc yes no) - for v.Op == OpARMEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARMEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMEQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (NotEqual cc) yes no) // result: (NE cc yes no) - for v.Op == OpARMNotEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARMNotEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMNE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThan cc) yes no) // result: (LT cc yes no) - for v.Op == OpARMLessThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARMLessThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThanU cc) yes no) // result: (ULT cc yes no) - for v.Op == OpARMLessThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARMLessThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMULT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqual cc) yes no) // result: (LE cc yes no) - for v.Op == OpARMLessEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARMLessEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqualU cc) yes no) // result: (ULE cc yes no) - for v.Op == OpARMLessEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARMLessEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMULE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThan cc) yes no) // result: (GT cc yes no) - for v.Op == OpARMGreaterThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARMGreaterThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThanU cc) yes no) // result: (UGT cc yes no) - for v.Op == OpARMGreaterThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARMGreaterThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMUGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqual cc) yes no) // result: (GE cc yes no) - for v.Op == OpARMGreaterEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARMGreaterEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqualU cc) yes no) // result: (UGE cc yes no) - for v.Op == OpARMGreaterEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARMGreaterEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARMUGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If cond yes no) // result: (NE (CMPconst [0] cond) yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(cond.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(cond) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMLE: // match: (LE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (InvertFlags cmp) yes no) // result: (GE cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (LE (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -23603,21 +23836,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (LE (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -23628,24 +23863,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (LE (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -23655,21 +23892,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -23680,22 +23919,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -23706,22 +23947,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -23732,22 +23975,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -23758,22 +24003,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -23784,22 +24031,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -23810,22 +24059,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (LE (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -23835,21 +24086,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (LE (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -23860,24 +24113,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (LE (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -23887,21 +24142,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -23912,22 +24169,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -23938,22 +24197,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -23964,22 +24225,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -23990,22 +24253,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -24016,22 +24281,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -24042,22 +24309,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (LE (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -24067,21 +24336,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (LE (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -24091,21 +24362,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -24116,22 +24389,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -24142,22 +24417,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -24168,22 +24445,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -24194,22 +24473,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -24220,22 +24501,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -24246,22 +24529,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (LE (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -24271,21 +24556,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (LE (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -24295,21 +24582,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -24320,22 +24609,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -24346,22 +24637,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -24372,22 +24665,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -24398,22 +24693,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -24424,22 +24721,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LE (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -24450,75 +24749,79 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMLT: // match: (LT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (InvertFlags cmp) yes no) // result: (GT cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (LT (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -24528,21 +24831,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (LT (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -24553,24 +24858,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (LT (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -24580,21 +24887,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -24605,22 +24914,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -24631,22 +24942,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -24657,22 +24970,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -24683,22 +24998,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -24709,22 +25026,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -24735,22 +25054,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (LT (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -24760,21 +25081,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (LT (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -24785,24 +25108,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (LT (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -24812,21 +25137,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -24837,22 +25164,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -24863,22 +25192,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -24889,22 +25220,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -24915,22 +25248,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -24941,22 +25276,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -24967,22 +25304,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (LT (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -24992,21 +25331,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (LT (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -25016,21 +25357,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -25041,22 +25384,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -25067,22 +25412,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -25093,22 +25440,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -25119,22 +25468,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -25145,22 +25496,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -25171,22 +25524,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (LT (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -25196,21 +25551,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (LT (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -25220,21 +25577,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -25245,22 +25604,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -25271,22 +25632,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -25297,22 +25660,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -25323,22 +25688,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -25349,22 +25716,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (LT (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -25375,233 +25744,257 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMLT - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMNE: // match: (NE (CMPconst [0] (Equal cc)) yes no) // result: (EQ cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMEQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (NotEqual cc)) yes no) // result: (NE cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMNotEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMNotEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMNE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (LessThan cc)) yes no) // result: (LT cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMLessThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMLessThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (LessThanU cc)) yes no) // result: (ULT cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMLessThanU { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMLessThanU { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMULT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (LessEqual cc)) yes no) // result: (LE cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMLessEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMLessEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (LessEqualU cc)) yes no) // result: (ULE cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMLessEqualU { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMLessEqualU { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMULE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (GreaterThan cc)) yes no) // result: (GT cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMGreaterThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMGreaterThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (GreaterThanU cc)) yes no) // result: (UGT cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMGreaterThanU { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMGreaterThanU { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMUGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (GreaterEqual cc)) yes no) // result: (GE cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMGreaterEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMGreaterEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (GreaterEqualU cc)) yes no) // result: (UGE cc yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpARMGreaterEqualU { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpARMGreaterEqualU { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockARMUGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (InvertFlags cmp) yes no) // result: (NE cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUB x y)) yes no) // cond: l.Uses==1 // result: (NE (CMP x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUB { break } @@ -25611,21 +26004,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(MULS x y a)) yes no) // cond: l.Uses==1 // result: (NE (CMP a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULS { break } @@ -25636,24 +26031,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBconst [c] x)) yes no) // cond: l.Uses==1 // result: (NE (CMPconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBconst { break } @@ -25663,21 +26060,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLL { break } @@ -25688,22 +26087,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRL { break } @@ -25714,22 +26115,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRA { break } @@ -25740,22 +26143,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftLLreg { break } @@ -25766,22 +26171,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRLreg { break } @@ -25792,22 +26199,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(SUBshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMPshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMSUBshiftRAreg { break } @@ -25818,22 +26227,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMPshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMPshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADD x y)) yes no) // cond: l.Uses==1 // result: (NE (CMN x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADD { break } @@ -25843,21 +26254,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(MULA x y a)) yes no) // cond: l.Uses==1 // result: (NE (CMN a (MUL x y)) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMMULA { break } @@ -25868,24 +26281,26 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARMMUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARMMUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDconst [c] x)) yes no) // cond: l.Uses==1 // result: (NE (CMNconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDconst { break } @@ -25895,21 +26310,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLL { break } @@ -25920,22 +26337,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRL { break } @@ -25946,22 +26365,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRA { break } @@ -25972,22 +26393,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftLLreg { break } @@ -25998,22 +26421,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRLreg { break } @@ -26024,22 +26449,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ADDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (CMNshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMADDshiftRAreg { break } @@ -26050,22 +26477,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMCMNshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMCMNshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(AND x y)) yes no) // cond: l.Uses==1 // result: (NE (TST x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMAND { break } @@ -26075,21 +26504,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDconst [c] x)) yes no) // cond: l.Uses==1 // result: (NE (TSTconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDconst { break } @@ -26099,21 +26530,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLL { break } @@ -26124,22 +26557,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRL { break } @@ -26150,22 +26585,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRA { break } @@ -26176,22 +26613,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftLLreg { break } @@ -26202,22 +26641,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRLreg { break } @@ -26228,22 +26669,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(ANDshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TSTshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMANDshiftRAreg { break } @@ -26254,22 +26697,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTSTshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTSTshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XOR x y)) yes no) // cond: l.Uses==1 // result: (NE (TEQ x y) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXOR { break } @@ -26279,21 +26724,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQ, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQ, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORconst [c] x)) yes no) // cond: l.Uses==1 // result: (NE (TEQconst [c] x) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORconst { break } @@ -26303,21 +26750,23 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftLL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftLL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLL { break } @@ -26328,22 +26777,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftRL x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftRL x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRL { break } @@ -26354,22 +26805,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRL, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRL, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftRA x y [c])) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftRA x y [c]) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRA { break } @@ -26380,22 +26833,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRA, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRA, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftLLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftLLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftLLreg { break } @@ -26406,22 +26861,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftLLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftLLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftRLreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftRLreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRLreg { break } @@ -26432,22 +26889,24 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRLreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRLreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] l:(XORshiftRAreg x y z)) yes no) // cond: l.Uses==1 // result: (NE (TEQshiftRAreg x y z) yes no) - for v.Op == OpARMCMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARMCMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - l := v.Args[0] + l := v_0.Args[0] if l.Op != OpARMXORshiftRAreg { break } @@ -26458,221 +26917,230 @@ func rewriteBlockARM(b *Block) bool { break } b.Kind = BlockARMNE - v0 := b.NewValue0(v.Pos, OpARMTEQshiftRAreg, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARMTEQshiftRAreg, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) v0.AddArg(z) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockARMUGE: // match: (UGE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (InvertFlags cmp) yes no) // result: (ULE cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARMUGT: // match: (UGT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (InvertFlags cmp) yes no) // result: (ULT cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARMULE: // match: (ULE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (InvertFlags cmp) yes no) // result: (UGE cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMUGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARMULT: // match: (ULT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARMFlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARMFlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARMFlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARMFlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (InvertFlags cmp) yes no) // result: (UGT cmp yes no) - for v.Op == OpARMInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARMInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARMUGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } diff --git a/src/cmd/compile/internal/ssa/rewriteARM64.go b/src/cmd/compile/internal/ssa/rewriteARM64.go index f6f8301853..66db390e59 100644 --- a/src/cmd/compile/internal/ssa/rewriteARM64.go +++ b/src/cmd/compile/internal/ssa/rewriteARM64.go @@ -33280,17 +33280,17 @@ func rewriteValueARM64_OpZeroExt8to64_0(v *Value) bool { } } func rewriteBlockARM64(b *Block) bool { - v := b.Control switch b.Kind { case BlockARM64EQ: // match: (EQ (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (EQ (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -33300,21 +33300,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (EQ (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -33324,21 +33326,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (EQ (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -33348,21 +33352,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (EQ (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -33372,21 +33378,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (EQ (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -33396,21 +33404,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (EQ (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -33420,21 +33430,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (EQ (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -33444,21 +33456,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (EQ (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -33468,20 +33482,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (EQ (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -33490,20 +33506,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (EQ (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -33512,45 +33530,51 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] x) yes no) // result: (Z x yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64Z - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (CMPWconst [0] x) yes no) // result: (ZW x yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64ZW - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (EQ (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -33561,24 +33585,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (EQ (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -33589,24 +33615,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (EQ (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -33617,24 +33645,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (EQ (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -33645,134 +33675,149 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64EQ - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (TSTconst [c] x) yes no) // cond: oneBit(c) // result: (TBZ {ntz(c)} x yes no) - for v.Op == OpARM64TSTconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64TSTconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(c)) { break } b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(c) return true } // match: (EQ (TSTWconst [c] x) yes no) // cond: oneBit(int64(uint32(c))) // result: (TBZ {ntz(int64(uint32(c)))} x yes no) - for v.Op == OpARM64TSTWconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64TSTWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(int64(uint32(c)))) { break } b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(int64(uint32(c))) return true } // match: (EQ (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (InvertFlags cmp) yes no) // result: (EQ cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64FGE: // match: (FGE (InvertFlags cmp) yes no) // result: (FLE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64FLE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64FGT: // match: (FGT (InvertFlags cmp) yes no) // result: (FLT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64FLT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64FLE: // match: (FLE (InvertFlags cmp) yes no) // result: (FGE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64FGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64FLT: // match: (FLT (InvertFlags cmp) yes no) // result: (FGT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64FGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } @@ -33780,11 +33825,12 @@ func rewriteBlockARM64(b *Block) bool { // match: (GE (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GE (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -33794,21 +33840,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GE (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -33818,21 +33866,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GE (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -33842,21 +33892,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GE (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -33866,21 +33918,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GE (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -33890,21 +33944,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GE (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -33914,21 +33970,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (GE (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -33938,21 +33996,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (GE (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -33962,20 +34022,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (GE (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -33984,20 +34046,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (GE (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -34006,21 +34070,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (GE (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -34031,24 +34097,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (GE (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -34059,24 +34127,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (GE (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -34087,24 +34157,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (GE (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -34115,88 +34187,95 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GE - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] x) yes no) // result: (TBZ {int64(31)} x yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = int64(31) return true } // match: (GE (CMPconst [0] x) yes no) // result: (TBZ {int64(63)} x yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = int64(63) return true } // match: (GE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (InvertFlags cmp) yes no) // result: (LE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } @@ -34204,11 +34283,12 @@ func rewriteBlockARM64(b *Block) bool { // match: (GT (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GT (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -34218,21 +34298,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GT (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -34242,21 +34324,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GT (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -34266,21 +34350,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GT (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -34290,21 +34376,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GT (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -34314,21 +34402,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (GT (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -34338,21 +34428,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (GT (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -34362,21 +34454,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (GT (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -34386,20 +34480,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (GT (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -34408,20 +34504,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (GT (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -34430,21 +34528,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (GT (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -34455,24 +34555,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (GT (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -34483,24 +34585,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (GT (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -34511,24 +34615,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (GT (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -34539,201 +34645,233 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64GT - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (InvertFlags cmp) yes no) // result: (LT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockIf: // match: (If (Equal cc) yes no) // result: (EQ cc yes no) - for v.Op == OpARM64Equal { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64Equal { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64EQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (NotEqual cc) yes no) // result: (NE cc yes no) - for v.Op == OpARM64NotEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64NotEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64NE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThan cc) yes no) // result: (LT cc yes no) - for v.Op == OpARM64LessThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64LT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThanU cc) yes no) // result: (ULT cc yes no) - for v.Op == OpARM64LessThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64ULT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqual cc) yes no) // result: (LE cc yes no) - for v.Op == OpARM64LessEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64LE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqualU cc) yes no) // result: (ULE cc yes no) - for v.Op == OpARM64LessEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64ULE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThan cc) yes no) // result: (GT cc yes no) - for v.Op == OpARM64GreaterThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64GT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThanU cc) yes no) // result: (UGT cc yes no) - for v.Op == OpARM64GreaterThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64UGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqual cc) yes no) // result: (GE cc yes no) - for v.Op == OpARM64GreaterEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64GE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqualU cc) yes no) // result: (UGE cc yes no) - for v.Op == OpARM64GreaterEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64UGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThanF cc) yes no) // result: (FLT cc yes no) - for v.Op == OpARM64LessThanF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThanF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqualF cc) yes no) // result: (FLE cc yes no) - for v.Op == OpARM64LessEqualF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqualF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThanF cc) yes no) // result: (FGT cc yes no) - for v.Op == OpARM64GreaterThanF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThanF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqualF cc) yes no) // result: (FGE cc yes no) - for v.Op == OpARM64GreaterEqualF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqualF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If cond yes no) // result: (NZ cond yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockARM64NZ - b.SetControl(cond) + b.ResetControls() + b.AddControl(cond) b.Aux = nil return true } @@ -34741,11 +34879,12 @@ func rewriteBlockARM64(b *Block) bool { // match: (LE (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LE (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -34755,21 +34894,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LE (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -34779,21 +34920,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LE (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -34803,21 +34946,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LE (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -34827,21 +34972,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LE (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -34851,21 +34998,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LE (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -34875,21 +35024,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (LE (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -34899,21 +35050,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (LE (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -34923,20 +35076,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (LE (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -34945,20 +35100,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (LE (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -34967,21 +35124,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (LE (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -34992,24 +35151,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (LE (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -35020,24 +35181,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (LE (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -35048,24 +35211,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (LE (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -35076,64 +35241,67 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LE - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (InvertFlags cmp) yes no) // result: (GE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } @@ -35141,11 +35309,12 @@ func rewriteBlockARM64(b *Block) bool { // match: (LT (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LT (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -35155,21 +35324,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LT (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -35179,21 +35350,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LT (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -35203,21 +35376,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LT (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -35227,21 +35402,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LT (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -35251,21 +35428,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (LT (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -35275,21 +35454,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (LT (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -35299,21 +35480,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (LT (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -35323,20 +35506,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (LT (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -35345,20 +35530,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (LT (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -35367,21 +35554,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (LT (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -35392,24 +35581,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (LT (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -35420,24 +35611,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (LT (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -35448,24 +35641,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (LT (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -35476,89 +35671,96 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64LT - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] x) yes no) // result: (TBNZ {int64(31)} x yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = int64(31) return true } // match: (LT (CMPconst [0] x) yes no) // result: (TBNZ {int64(63)} x yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = int64(63) return true } // match: (LT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (InvertFlags cmp) yes no) // result: (GT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } @@ -35566,11 +35768,12 @@ func rewriteBlockARM64(b *Block) bool { // match: (NE (CMPWconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (NE (TSTWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -35580,21 +35783,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64TSTWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (NE (TST x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -35604,21 +35809,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64TST, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TST, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (NE (TSTW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64AND { break } @@ -35628,21 +35835,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64TSTW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] x:(ANDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (NE (TSTconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ANDconst { break } @@ -35652,21 +35861,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64TSTconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64TSTconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (NE (CMNconst [c] y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -35676,21 +35887,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMNconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] x:(ADDconst [c] y)) yes no) // cond: x.Uses == 1 // result: (NE (CMNWconst [c] y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] if x.Op != OpARM64ADDconst { break } @@ -35700,21 +35913,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMNWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNWconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (NE (CMN x y) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -35724,21 +35939,23 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] z:(ADD x y)) yes no) // cond: z.Uses == 1 // result: (NE (CMNW x y) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64ADD { break } @@ -35748,20 +35965,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMP x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (NE (CMN x y) yes no) - for v.Op == OpARM64CMP { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMP { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -35770,20 +35989,22 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPW x z:(NEG y)) yes no) // cond: z.Uses == 1 // result: (NE (CMNW x y) yes no) - for v.Op == OpARM64CMPW { - _ = v.Args[1] - x := v.Args[0] - z := v.Args[1] + for b.Controls[0].Op == OpARM64CMPW { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + z := v_0.Args[1] if z.Op != OpARM64NEG { break } @@ -35792,45 +36013,51 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] x) yes no) // result: (NZ x yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64NZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (CMPWconst [0] x) yes no) // result: (NZW x yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockARM64NZW - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(MADD a x y)) yes no) // cond: z.Uses==1 // result: (NE (CMN a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADD { break } @@ -35841,24 +36068,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMN, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMN, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(MSUB a x y)) yes no) // cond: z.Uses==1 // result: (NE (CMP a (MUL x y)) yes no) - for v.Op == OpARM64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUB { break } @@ -35869,24 +36098,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMP, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMP, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MUL, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MUL, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] z:(MADDW a x y)) yes no) // cond: z.Uses==1 // result: (NE (CMNW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MADDW { break } @@ -35897,24 +36128,26 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMNW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMNW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] z:(MSUBW a x y)) yes no) // cond: z.Uses==1 // result: (NE (CMPW a (MULW x y)) yes no) - for v.Op == OpARM64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpARM64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpARM64MSUBW { break } @@ -35925,257 +36158,296 @@ func rewriteBlockARM64(b *Block) bool { break } b.Kind = BlockARM64NE - v0 := b.NewValue0(v.Pos, OpARM64CMPW, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpARM64CMPW, types.TypeFlags) v0.AddArg(a) - v1 := b.NewValue0(v.Pos, OpARM64MULW, x.Type) + v1 := b.NewValue0(v_0.Pos, OpARM64MULW, x.Type) v1.AddArg(x) v1.AddArg(y) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (TSTconst [c] x) yes no) // cond: oneBit(c) // result: (TBNZ {ntz(c)} x yes no) - for v.Op == OpARM64TSTconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64TSTconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(c)) { break } b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(c) return true } // match: (NE (TSTWconst [c] x) yes no) // cond: oneBit(int64(uint32(c))) // result: (TBNZ {ntz(int64(uint32(c)))} x yes no) - for v.Op == OpARM64TSTWconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64TSTWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(int64(uint32(c)))) { break } b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(int64(uint32(c))) return true } // match: (NE (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (InvertFlags cmp) yes no) // result: (NE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64NZ: // match: (NZ (Equal cc) yes no) // result: (EQ cc yes no) - for v.Op == OpARM64Equal { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64Equal { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64EQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (NotEqual cc) yes no) // result: (NE cc yes no) - for v.Op == OpARM64NotEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64NotEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64NE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessThan cc) yes no) // result: (LT cc yes no) - for v.Op == OpARM64LessThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64LT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessThanU cc) yes no) // result: (ULT cc yes no) - for v.Op == OpARM64LessThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64ULT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessEqual cc) yes no) // result: (LE cc yes no) - for v.Op == OpARM64LessEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64LE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessEqualU cc) yes no) // result: (ULE cc yes no) - for v.Op == OpARM64LessEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64ULE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterThan cc) yes no) // result: (GT cc yes no) - for v.Op == OpARM64GreaterThan { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64GT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterThanU cc) yes no) // result: (UGT cc yes no) - for v.Op == OpARM64GreaterThanU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThanU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64UGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterEqual cc) yes no) // result: (GE cc yes no) - for v.Op == OpARM64GreaterEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64GE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterEqualU cc) yes no) // result: (UGE cc yes no) - for v.Op == OpARM64GreaterEqualU { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqualU { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64UGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessThanF cc) yes no) // result: (FLT cc yes no) - for v.Op == OpARM64LessThanF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessThanF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (LessEqualF cc) yes no) // result: (FLE cc yes no) - for v.Op == OpARM64LessEqualF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64LessEqualF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterThanF cc) yes no) // result: (FGT cc yes no) - for v.Op == OpARM64GreaterThanF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterThanF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (GreaterEqualF cc) yes no) // result: (FGE cc yes no) - for v.Op == OpARM64GreaterEqualF { - cc := v.Args[0] + for b.Controls[0].Op == OpARM64GreaterEqualF { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockARM64FGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NZ (ANDconst [c] x) yes no) // cond: oneBit(c) // result: (TBNZ {ntz(c)} x yes no) - for v.Op == OpARM64ANDconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64ANDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(c)) { break } b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(c) return true } // match: (NZ (MOVDconst [0]) yes no) - // result: (First nil no yes) - for v.Op == OpARM64MOVDconst { - if v.AuxInt != 0 { + // result: (First no yes) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NZ (MOVDconst [c]) yes no) // cond: c != 0 - // result: (First nil yes no) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } @@ -36183,251 +36455,263 @@ func rewriteBlockARM64(b *Block) bool { // match: (NZW (ANDconst [c] x) yes no) // cond: oneBit(int64(uint32(c))) // result: (TBNZ {ntz(int64(uint32(c)))} x yes no) - for v.Op == OpARM64ANDconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64ANDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(int64(uint32(c)))) { break } b.Kind = BlockARM64TBNZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(int64(uint32(c))) return true } // match: (NZW (MOVDconst [c]) yes no) // cond: int32(c) == 0 - // result: (First nil no yes) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NZW (MOVDconst [c]) yes no) // cond: int32(c) != 0 - // result: (First nil yes no) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } case BlockARM64UGE: // match: (UGE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGE (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGE (InvertFlags cmp) yes no) // result: (ULE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64ULE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64UGT: // match: (UGT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagLT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (FlagGT_ULT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_ULT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (UGT (FlagGT_UGT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_UGT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (UGT (InvertFlags cmp) yes no) // result: (ULT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64ULT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64ULE: // match: (ULE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULE (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULE (InvertFlags cmp) yes no) // result: (UGE cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64UGE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } case BlockARM64ULT: // match: (ULT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagLT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagLT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagLT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagLT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagLT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagLT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (FlagGT_ULT) yes no) - // result: (First nil yes no) - for v.Op == OpARM64FlagGT_ULT { + // result: (First yes no) + for b.Controls[0].Op == OpARM64FlagGT_ULT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ULT (FlagGT_UGT) yes no) - // result: (First nil no yes) - for v.Op == OpARM64FlagGT_UGT { + // result: (First no yes) + for b.Controls[0].Op == OpARM64FlagGT_UGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (ULT (InvertFlags cmp) yes no) // result: (UGT cmp yes no) - for v.Op == OpARM64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpARM64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockARM64UGT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } @@ -36435,38 +36719,42 @@ func rewriteBlockARM64(b *Block) bool { // match: (Z (ANDconst [c] x) yes no) // cond: oneBit(c) // result: (TBZ {ntz(c)} x yes no) - for v.Op == OpARM64ANDconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64ANDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(c)) { break } b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(c) return true } // match: (Z (MOVDconst [0]) yes no) - // result: (First nil yes no) - for v.Op == OpARM64MOVDconst { - if v.AuxInt != 0 { + // result: (First yes no) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (Z (MOVDconst [c]) yes no) // cond: c != 0 - // result: (First nil no yes) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -36475,40 +36763,44 @@ func rewriteBlockARM64(b *Block) bool { // match: (ZW (ANDconst [c] x) yes no) // cond: oneBit(int64(uint32(c))) // result: (TBZ {ntz(int64(uint32(c)))} x yes no) - for v.Op == OpARM64ANDconst { - c := v.AuxInt - x := v.Args[0] + for b.Controls[0].Op == OpARM64ANDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt + x := v_0.Args[0] if !(oneBit(int64(uint32(c)))) { break } b.Kind = BlockARM64TBZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = ntz(int64(uint32(c))) return true } // match: (ZW (MOVDconst [c]) yes no) // cond: int32(c) == 0 - // result: (First nil yes no) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (ZW (MOVDconst [c]) yes no) // cond: int32(c) != 0 - // result: (First nil no yes) - for v.Op == OpARM64MOVDconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpARM64MOVDconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true diff --git a/src/cmd/compile/internal/ssa/rewriteMIPS.go b/src/cmd/compile/internal/ssa/rewriteMIPS.go index 98bb5f3168..3ae2a72457 100644 --- a/src/cmd/compile/internal/ssa/rewriteMIPS.go +++ b/src/cmd/compile/internal/ssa/rewriteMIPS.go @@ -8995,182 +8995,207 @@ func rewriteValueMIPS_OpZeromask_0(v *Value) bool { } } func rewriteBlockMIPS(b *Block) bool { - v := b.Control switch b.Kind { case BlockMIPSEQ: // match: (EQ (FPFlagTrue cmp) yes no) // result: (FPF cmp yes no) - for v.Op == OpMIPSFPFlagTrue { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPSFPFlagTrue { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPSFPF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (FPFlagFalse cmp) yes no) // result: (FPT cmp yes no) - for v.Op == OpMIPSFPFlagFalse { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPSFPFlagFalse { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPSFPT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGT _ _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGT { break } _ = cmp.Args[1] b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTU _ _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTU { break } _ = cmp.Args[1] b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTconst _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTconst { break } b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTUconst _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTUconst { break } b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTzero _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTzero { break } b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTUzero _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTUzero { break } b.Kind = BlockMIPSNE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (SGTUconst [1] x) yes no) // result: (NE x yes no) - for v.Op == OpMIPSSGTUconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSSGTUconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPSNE - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGTUzero x) yes no) // result: (EQ x yes no) - for v.Op == OpMIPSSGTUzero { - x := v.Args[0] + for b.Controls[0].Op == OpMIPSSGTUzero { + v_0 := b.Controls[0] + x := v_0.Args[0] b.Kind = BlockMIPSEQ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGTconst [0] x) yes no) // result: (GEZ x yes no) - for v.Op == OpMIPSSGTconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpMIPSSGTconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPSGEZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGTzero x) yes no) // result: (LEZ x yes no) - for v.Op == OpMIPSSGTzero { - x := v.Args[0] + for b.Controls[0].Op == OpMIPSSGTzero { + v_0 := b.Controls[0] + x := v_0.Args[0] b.Kind = BlockMIPSLEZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (MOVWconst [0]) yes no) - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - if v.AuxInt != 0 { + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (MOVWconst [c]) yes no) // cond: c != 0 - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9178,27 +9203,29 @@ func rewriteBlockMIPS(b *Block) bool { case BlockMIPSGEZ: // match: (GEZ (MOVWconst [c]) yes no) // cond: int32(c) >= 0 - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) >= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GEZ (MOVWconst [c]) yes no) // cond: int32(c) < 0 - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) < 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9206,27 +9233,29 @@ func rewriteBlockMIPS(b *Block) bool { case BlockMIPSGTZ: // match: (GTZ (MOVWconst [c]) yes no) // cond: int32(c) > 0 - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) > 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GTZ (MOVWconst [c]) yes no) // cond: int32(c) <= 0 - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) <= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9235,36 +9264,39 @@ func rewriteBlockMIPS(b *Block) bool { // match: (If cond yes no) // result: (NE cond yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockMIPSNE - b.SetControl(cond) + b.ResetControls() + b.AddControl(cond) b.Aux = nil return true } case BlockMIPSLEZ: // match: (LEZ (MOVWconst [c]) yes no) // cond: int32(c) <= 0 - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) <= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LEZ (MOVWconst [c]) yes no) // cond: int32(c) > 0 - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) > 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9272,27 +9304,29 @@ func rewriteBlockMIPS(b *Block) bool { case BlockMIPSLTZ: // match: (LTZ (MOVWconst [c]) yes no) // cond: int32(c) < 0 - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) < 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LTZ (MOVWconst [c]) yes no) // cond: int32(c) >= 0 - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(int32(c) >= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9300,178 +9334,204 @@ func rewriteBlockMIPS(b *Block) bool { case BlockMIPSNE: // match: (NE (FPFlagTrue cmp) yes no) // result: (FPT cmp yes no) - for v.Op == OpMIPSFPFlagTrue { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPSFPFlagTrue { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPSFPT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (FPFlagFalse cmp) yes no) // result: (FPF cmp yes no) - for v.Op == OpMIPSFPFlagFalse { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPSFPFlagFalse { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPSFPF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGT _ _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGT { break } _ = cmp.Args[1] b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTU _ _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTU { break } _ = cmp.Args[1] b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTconst _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTconst { break } b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTUconst _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTUconst { break } b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTzero _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTzero { break } b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTUzero _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPSXORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSXORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPSSGTUzero { break } b.Kind = BlockMIPSEQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (SGTUconst [1] x) yes no) // result: (EQ x yes no) - for v.Op == OpMIPSSGTUconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPSSGTUconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPSEQ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGTUzero x) yes no) // result: (NE x yes no) - for v.Op == OpMIPSSGTUzero { - x := v.Args[0] + for b.Controls[0].Op == OpMIPSSGTUzero { + v_0 := b.Controls[0] + x := v_0.Args[0] b.Kind = BlockMIPSNE - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGTconst [0] x) yes no) // result: (LTZ x yes no) - for v.Op == OpMIPSSGTconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpMIPSSGTconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPSLTZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGTzero x) yes no) // result: (GTZ x yes no) - for v.Op == OpMIPSSGTzero { - x := v.Args[0] + for b.Controls[0].Op == OpMIPSSGTzero { + v_0 := b.Controls[0] + x := v_0.Args[0] b.Kind = BlockMIPSGTZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (MOVWconst [0]) yes no) - // result: (First nil no yes) - for v.Op == OpMIPSMOVWconst { - if v.AuxInt != 0 { + // result: (First no yes) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (MOVWconst [c]) yes no) // cond: c != 0 - // result: (First nil yes no) - for v.Op == OpMIPSMOVWconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPSMOVWconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } diff --git a/src/cmd/compile/internal/ssa/rewriteMIPS64.go b/src/cmd/compile/internal/ssa/rewriteMIPS64.go index 1be27697aa..226dc00952 100644 --- a/src/cmd/compile/internal/ssa/rewriteMIPS64.go +++ b/src/cmd/compile/internal/ssa/rewriteMIPS64.go @@ -9740,162 +9740,183 @@ func rewriteValueMIPS64_OpZeroExt8to64_0(v *Value) bool { } } func rewriteBlockMIPS64(b *Block) bool { - v := b.Control switch b.Kind { case BlockMIPS64EQ: // match: (EQ (FPFlagTrue cmp) yes no) // result: (FPF cmp yes no) - for v.Op == OpMIPS64FPFlagTrue { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPS64FPFlagTrue { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPS64FPF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (FPFlagFalse cmp) yes no) // result: (FPT cmp yes no) - for v.Op == OpMIPS64FPFlagFalse { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPS64FPFlagFalse { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPS64FPT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGT _ _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGT { break } _ = cmp.Args[1] b.Kind = BlockMIPS64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTU _ _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTU { break } _ = cmp.Args[1] b.Kind = BlockMIPS64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTconst _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTconst { break } b.Kind = BlockMIPS64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (XORconst [1] cmp:(SGTUconst _)) yes no) // result: (NE cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTUconst { break } b.Kind = BlockMIPS64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (SGTUconst [1] x) yes no) // result: (NE x yes no) - for v.Op == OpMIPS64SGTUconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64SGTUconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPS64NE - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGTU x (MOVVconst [0])) yes no) // result: (EQ x yes no) - for v.Op == OpMIPS64SGTU { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpMIPS64MOVVconst || v_1.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGTU { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpMIPS64MOVVconst || v_0_1.AuxInt != 0 { break } b.Kind = BlockMIPS64EQ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGTconst [0] x) yes no) // result: (GEZ x yes no) - for v.Op == OpMIPS64SGTconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGTconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPS64GEZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (SGT x (MOVVconst [0])) yes no) // result: (LEZ x yes no) - for v.Op == OpMIPS64SGT { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpMIPS64MOVVconst || v_1.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGT { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpMIPS64MOVVconst || v_0_1.AuxInt != 0 { break } b.Kind = BlockMIPS64LEZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (EQ (MOVVconst [0]) yes no) - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - if v.AuxInt != 0 { + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (MOVVconst [c]) yes no) // cond: c != 0 - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9903,27 +9924,29 @@ func rewriteBlockMIPS64(b *Block) bool { case BlockMIPS64GEZ: // match: (GEZ (MOVVconst [c]) yes no) // cond: c >= 0 - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c >= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GEZ (MOVVconst [c]) yes no) // cond: c < 0 - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c < 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9931,27 +9954,29 @@ func rewriteBlockMIPS64(b *Block) bool { case BlockMIPS64GTZ: // match: (GTZ (MOVVconst [c]) yes no) // cond: c > 0 - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c > 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GTZ (MOVVconst [c]) yes no) // cond: c <= 0 - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c <= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9960,36 +9985,39 @@ func rewriteBlockMIPS64(b *Block) bool { // match: (If cond yes no) // result: (NE cond yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockMIPS64NE - b.SetControl(cond) + b.ResetControls() + b.AddControl(cond) b.Aux = nil return true } case BlockMIPS64LEZ: // match: (LEZ (MOVVconst [c]) yes no) // cond: c <= 0 - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c <= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LEZ (MOVVconst [c]) yes no) // cond: c > 0 - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c > 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -9997,27 +10025,29 @@ func rewriteBlockMIPS64(b *Block) bool { case BlockMIPS64LTZ: // match: (LTZ (MOVVconst [c]) yes no) // cond: c < 0 - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c < 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LTZ (MOVVconst [c]) yes no) // cond: c >= 0 - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c >= 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -10025,158 +10055,180 @@ func rewriteBlockMIPS64(b *Block) bool { case BlockMIPS64NE: // match: (NE (FPFlagTrue cmp) yes no) // result: (FPT cmp yes no) - for v.Op == OpMIPS64FPFlagTrue { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPS64FPFlagTrue { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPS64FPT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (FPFlagFalse cmp) yes no) // result: (FPF cmp yes no) - for v.Op == OpMIPS64FPFlagFalse { - cmp := v.Args[0] + for b.Controls[0].Op == OpMIPS64FPFlagFalse { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockMIPS64FPF - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGT _ _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGT { break } _ = cmp.Args[1] b.Kind = BlockMIPS64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTU _ _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTU { break } _ = cmp.Args[1] b.Kind = BlockMIPS64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTconst _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTconst { break } b.Kind = BlockMIPS64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (XORconst [1] cmp:(SGTUconst _)) yes no) // result: (EQ cmp yes no) - for v.Op == OpMIPS64XORconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64XORconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - cmp := v.Args[0] + cmp := v_0.Args[0] if cmp.Op != OpMIPS64SGTUconst { break } b.Kind = BlockMIPS64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (SGTUconst [1] x) yes no) // result: (EQ x yes no) - for v.Op == OpMIPS64SGTUconst { - if v.AuxInt != 1 { + for b.Controls[0].Op == OpMIPS64SGTUconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 1 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPS64EQ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGTU x (MOVVconst [0])) yes no) // result: (NE x yes no) - for v.Op == OpMIPS64SGTU { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpMIPS64MOVVconst || v_1.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGTU { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpMIPS64MOVVconst || v_0_1.AuxInt != 0 { break } b.Kind = BlockMIPS64NE - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGTconst [0] x) yes no) // result: (LTZ x yes no) - for v.Op == OpMIPS64SGTconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGTconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - x := v.Args[0] + x := v_0.Args[0] b.Kind = BlockMIPS64LTZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (SGT x (MOVVconst [0])) yes no) // result: (GTZ x yes no) - for v.Op == OpMIPS64SGT { - _ = v.Args[1] - x := v.Args[0] - v_1 := v.Args[1] - if v_1.Op != OpMIPS64MOVVconst || v_1.AuxInt != 0 { + for b.Controls[0].Op == OpMIPS64SGT { + v_0 := b.Controls[0] + _ = v_0.Args[1] + x := v_0.Args[0] + v_0_1 := v_0.Args[1] + if v_0_1.Op != OpMIPS64MOVVconst || v_0_1.AuxInt != 0 { break } b.Kind = BlockMIPS64GTZ - b.SetControl(x) + b.ResetControls() + b.AddControl(x) b.Aux = nil return true } // match: (NE (MOVVconst [0]) yes no) - // result: (First nil no yes) - for v.Op == OpMIPS64MOVVconst { - if v.AuxInt != 0 { + // result: (First no yes) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (MOVVconst [c]) yes no) // cond: c != 0 - // result: (First nil yes no) - for v.Op == OpMIPS64MOVVconst { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpMIPS64MOVVconst { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } diff --git a/src/cmd/compile/internal/ssa/rewritePPC64.go b/src/cmd/compile/internal/ssa/rewritePPC64.go index 4d2dfc1074..7743a2855e 100644 --- a/src/cmd/compile/internal/ssa/rewritePPC64.go +++ b/src/cmd/compile/internal/ssa/rewritePPC64.go @@ -26466,132 +26466,142 @@ func rewriteValuePPC64_OpZeroExt8to64_0(v *Value) bool { } } func rewriteBlockPPC64(b *Block) bool { - v := b.Control switch b.Kind { case BlockPPC64EQ: // match: (EQ (CMPconst [0] (ANDconst [c] x)) yes no) // result: (EQ (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (EQ (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (EQ (FlagLT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagLT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (FlagGT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagGT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (EQ (InvertFlags cmp) yes no) // result: (EQ cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64EQ - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (EQ (CMPconst [0] (ANDconst [c] x)) yes no) // result: (EQ (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (EQ (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (EQ (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -26601,21 +26611,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (EQ (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -26625,21 +26637,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (EQ (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (EQ (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -26649,96 +26663,104 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64EQ - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockPPC64GE: // match: (GE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (FlagLT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagLT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GE (FlagGT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagGT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GE (InvertFlags cmp) yes no) // result: (LE cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64LE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GE (CMPconst [0] (ANDconst [c] x)) yes no) // result: (GE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64GE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (GE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64GE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GE (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -26748,21 +26770,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (GE (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -26772,21 +26796,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GE - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GE (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (GE (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -26796,97 +26822,105 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GE - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockPPC64GT: // match: (GT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagLT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagLT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (GT (FlagGT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagGT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (GT (InvertFlags cmp) yes no) // result: (LT cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64LT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (GT (CMPconst [0] (ANDconst [c] x)) yes no) // result: (GT (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64GT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (GT (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64GT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (GT (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -26896,21 +26930,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (GT (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -26920,21 +26956,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GT - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (GT (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (GT (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -26944,199 +26982,228 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64GT - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockIf: // match: (If (Equal cc) yes no) // result: (EQ cc yes no) - for v.Op == OpPPC64Equal { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64Equal { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64EQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (NotEqual cc) yes no) // result: (NE cc yes no) - for v.Op == OpPPC64NotEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64NotEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64NE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessThan cc) yes no) // result: (LT cc yes no) - for v.Op == OpPPC64LessThan { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64LessThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64LT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (LessEqual cc) yes no) // result: (LE cc yes no) - for v.Op == OpPPC64LessEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64LessEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64LE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterThan cc) yes no) // result: (GT cc yes no) - for v.Op == OpPPC64GreaterThan { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64GreaterThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64GT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (GreaterEqual cc) yes no) // result: (GE cc yes no) - for v.Op == OpPPC64GreaterEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64GreaterEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64GE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (FLessThan cc) yes no) // result: (FLT cc yes no) - for v.Op == OpPPC64FLessThan { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64FLessThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64FLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (FLessEqual cc) yes no) // result: (FLE cc yes no) - for v.Op == OpPPC64FLessEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64FLessEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64FLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (FGreaterThan cc) yes no) // result: (FGT cc yes no) - for v.Op == OpPPC64FGreaterThan { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64FGreaterThan { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64FGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If (FGreaterEqual cc) yes no) // result: (FGE cc yes no) - for v.Op == OpPPC64FGreaterEqual { - cc := v.Args[0] + for b.Controls[0].Op == OpPPC64FGreaterEqual { + v_0 := b.Controls[0] + cc := v_0.Args[0] b.Kind = BlockPPC64FGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (If cond yes no) // result: (NE (CMPWconst [0] cond) yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64CMPWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(cond.Pos, OpPPC64CMPWconst, types.TypeFlags) v0.AuxInt = 0 v0.AddArg(cond) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockPPC64LE: // match: (LE (FlagEQ) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagLT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagLT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LE (FlagGT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagGT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LE (InvertFlags cmp) yes no) // result: (GE cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64GE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LE (CMPconst [0] (ANDconst [c] x)) yes no) // result: (LE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64LE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (LE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64LE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LE (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -27146,21 +27213,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (LE (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -27170,21 +27239,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LE - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LE (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (LE (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -27194,97 +27265,105 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LE - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockPPC64LT: // match: (LT (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (FlagLT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagLT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (LT (FlagGT) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagGT { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (LT (InvertFlags cmp) yes no) // result: (GT cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64GT - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (LT (CMPconst [0] (ANDconst [c] x)) yes no) // result: (LT (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64LT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (LT (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64LT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (LT (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -27294,21 +27373,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LT - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (LT (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -27318,21 +27399,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LT - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (LT (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (LT (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -27342,296 +27425,328 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64LT - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } case BlockPPC64NE: // match: (NE (CMPWconst [0] (Equal cc)) yes no) // result: (EQ cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64Equal { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64Equal { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64EQ - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (NotEqual cc)) yes no) // result: (NE cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64NotEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64NotEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64NE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (LessThan cc)) yes no) // result: (LT cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64LessThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64LessThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64LT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (LessEqual cc)) yes no) // result: (LE cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64LessEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64LessEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64LE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (GreaterThan cc)) yes no) // result: (GT cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64GreaterThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64GreaterThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64GT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (GreaterEqual cc)) yes no) // result: (GE cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64GreaterEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64GreaterEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64GE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (FLessThan cc)) yes no) // result: (FLT cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64FLessThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64FLessThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64FLT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (FLessEqual cc)) yes no) // result: (FLE cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64FLessEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64FLessEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64FLE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (FGreaterThan cc)) yes no) // result: (FGT cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64FGreaterThan { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64FGreaterThan { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64FGT - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPWconst [0] (FGreaterEqual cc)) yes no) // result: (FGE cc yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64FGreaterEqual { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64FGreaterEqual { break } - cc := v_0.Args[0] + cc := v_0_0.Args[0] b.Kind = BlockPPC64FGE - b.SetControl(cc) + b.ResetControls() + b.AddControl(cc) b.Aux = nil return true } // match: (NE (CMPconst [0] (ANDconst [c] x)) yes no) // result: (NE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (NE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (FlagEQ) yes no) - // result: (First nil no yes) - for v.Op == OpPPC64FlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpPPC64FlagEQ { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (NE (FlagLT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagLT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagLT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (FlagGT) yes no) - // result: (First nil yes no) - for v.Op == OpPPC64FlagGT { + // result: (First yes no) + for b.Controls[0].Op == OpPPC64FlagGT { b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (NE (InvertFlags cmp) yes no) // result: (NE cmp yes no) - for v.Op == OpPPC64InvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpPPC64InvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] b.Kind = BlockPPC64NE - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = nil return true } // match: (NE (CMPconst [0] (ANDconst [c] x)) yes no) // result: (NE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPWconst [0] (ANDconst [c] x)) yes no) // result: (NE (ANDCCconst [c] x) yes no) - for v.Op == OpPPC64CMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpPPC64ANDconst { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpPPC64ANDconst { break } - c := v_0.AuxInt - x := v_0.Args[0] + c := v_0_0.AuxInt + x := v_0_0.Args[0] b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCCconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCCconst, types.TypeFlags) v0.AuxInt = c v0.AddArg(x) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(AND x y)) yes no) // cond: z.Uses == 1 // result: (NE (ANDCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64AND { break } @@ -27641,21 +27756,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ANDCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ANDCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(OR x y)) yes no) // cond: z.Uses == 1 // result: (NE (ORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64OR { break } @@ -27665,21 +27782,23 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64ORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64ORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } // match: (NE (CMPconst [0] z:(XOR x y)) yes no) // cond: z.Uses == 1 // result: (NE (XORCC x y) yes no) - for v.Op == OpPPC64CMPconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpPPC64CMPconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - z := v.Args[0] + z := v_0.Args[0] if z.Op != OpPPC64XOR { break } @@ -27689,10 +27808,11 @@ func rewriteBlockPPC64(b *Block) bool { break } b.Kind = BlockPPC64NE - v0 := b.NewValue0(v.Pos, OpPPC64XORCC, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(v_0.Pos, OpPPC64XORCC, types.TypeFlags) v0.AddArg(x) v0.AddArg(y) - b.SetControl(v0) + b.AddControl(v0) b.Aux = nil return true } diff --git a/src/cmd/compile/internal/ssa/rewriteS390X.go b/src/cmd/compile/internal/ssa/rewriteS390X.go index 84fe1473c0..9db0cc42e9 100644 --- a/src/cmd/compile/internal/ssa/rewriteS390X.go +++ b/src/cmd/compile/internal/ssa/rewriteS390X.go @@ -36449,37 +36449,38 @@ func rewriteValueS390X_OpZeroExt8to64_0(v *Value) bool { } func rewriteBlockS390X(b *Block) bool { typ := &b.Func.Config.Types - v := b.Control switch b.Kind { case BlockS390XBRC: // match: (BRC {c} (CMPWconst [0] (LOCGR {d} (MOVDconst [0]) (MOVDconst [x]) cmp)) yes no) // cond: x != 0 && c.(s390x.CCMask) == s390x.Equal // result: (BRC {d} cmp no yes) - for v.Op == OpS390XCMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpS390XCMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpS390XLOCGR { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpS390XLOCGR { break } - d := v_0.Aux - cmp := v_0.Args[2] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpS390XMOVDconst || v_0_0.AuxInt != 0 { + d := v_0_0.Aux + cmp := v_0_0.Args[2] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpS390XMOVDconst || v_0_0_0.AuxInt != 0 { break } - v_0_1 := v_0.Args[1] - if v_0_1.Op != OpS390XMOVDconst { + v_0_0_1 := v_0_0.Args[1] + if v_0_0_1.Op != OpS390XMOVDconst { break } - x := v_0_1.AuxInt + x := v_0_0_1.AuxInt c := b.Aux if !(x != 0 && c.(s390x.CCMask) == s390x.Equal) { break } b.Kind = BlockS390XBRC - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = d b.swapSuccessors() return true @@ -36487,148 +36488,152 @@ func rewriteBlockS390X(b *Block) bool { // match: (BRC {c} (CMPWconst [0] (LOCGR {d} (MOVDconst [0]) (MOVDconst [x]) cmp)) yes no) // cond: x != 0 && c.(s390x.CCMask) == s390x.NotEqual // result: (BRC {d} cmp yes no) - for v.Op == OpS390XCMPWconst { - if v.AuxInt != 0 { + for b.Controls[0].Op == OpS390XCMPWconst { + v_0 := b.Controls[0] + if v_0.AuxInt != 0 { break } - v_0 := v.Args[0] - if v_0.Op != OpS390XLOCGR { + v_0_0 := v_0.Args[0] + if v_0_0.Op != OpS390XLOCGR { break } - d := v_0.Aux - cmp := v_0.Args[2] - v_0_0 := v_0.Args[0] - if v_0_0.Op != OpS390XMOVDconst || v_0_0.AuxInt != 0 { + d := v_0_0.Aux + cmp := v_0_0.Args[2] + v_0_0_0 := v_0_0.Args[0] + if v_0_0_0.Op != OpS390XMOVDconst || v_0_0_0.AuxInt != 0 { break } - v_0_1 := v_0.Args[1] - if v_0_1.Op != OpS390XMOVDconst { + v_0_0_1 := v_0_0.Args[1] + if v_0_0_1.Op != OpS390XMOVDconst { break } - x := v_0_1.AuxInt + x := v_0_0_1.AuxInt c := b.Aux if !(x != 0 && c.(s390x.CCMask) == s390x.NotEqual) { break } b.Kind = BlockS390XBRC - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = d return true } // match: (BRC {c} (InvertFlags cmp) yes no) // result: (BRC {c.(s390x.CCMask).ReverseComparison()} cmp yes no) - for v.Op == OpS390XInvertFlags { - cmp := v.Args[0] + for b.Controls[0].Op == OpS390XInvertFlags { + v_0 := b.Controls[0] + cmp := v_0.Args[0] c := b.Aux b.Kind = BlockS390XBRC - b.SetControl(cmp) + b.ResetControls() + b.AddControl(cmp) b.Aux = c.(s390x.CCMask).ReverseComparison() return true } // match: (BRC {c} (FlagEQ) yes no) // cond: c.(s390x.CCMask) & s390x.Equal != 0 - // result: (First nil yes no) - for v.Op == OpS390XFlagEQ { + // result: (First yes no) + for b.Controls[0].Op == OpS390XFlagEQ { c := b.Aux if !(c.(s390x.CCMask)&s390x.Equal != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (BRC {c} (FlagLT) yes no) // cond: c.(s390x.CCMask) & s390x.Less != 0 - // result: (First nil yes no) - for v.Op == OpS390XFlagLT { + // result: (First yes no) + for b.Controls[0].Op == OpS390XFlagLT { c := b.Aux if !(c.(s390x.CCMask)&s390x.Less != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (BRC {c} (FlagGT) yes no) // cond: c.(s390x.CCMask) & s390x.Greater != 0 - // result: (First nil yes no) - for v.Op == OpS390XFlagGT { + // result: (First yes no) + for b.Controls[0].Op == OpS390XFlagGT { c := b.Aux if !(c.(s390x.CCMask)&s390x.Greater != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (BRC {c} (FlagOV) yes no) // cond: c.(s390x.CCMask) & s390x.Unordered != 0 - // result: (First nil yes no) - for v.Op == OpS390XFlagOV { + // result: (First yes no) + for b.Controls[0].Op == OpS390XFlagOV { c := b.Aux if !(c.(s390x.CCMask)&s390x.Unordered != 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (BRC {c} (FlagEQ) yes no) // cond: c.(s390x.CCMask) & s390x.Equal == 0 - // result: (First nil no yes) - for v.Op == OpS390XFlagEQ { + // result: (First no yes) + for b.Controls[0].Op == OpS390XFlagEQ { c := b.Aux if !(c.(s390x.CCMask)&s390x.Equal == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (BRC {c} (FlagLT) yes no) // cond: c.(s390x.CCMask) & s390x.Less == 0 - // result: (First nil no yes) - for v.Op == OpS390XFlagLT { + // result: (First no yes) + for b.Controls[0].Op == OpS390XFlagLT { c := b.Aux if !(c.(s390x.CCMask)&s390x.Less == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (BRC {c} (FlagGT) yes no) // cond: c.(s390x.CCMask) & s390x.Greater == 0 - // result: (First nil no yes) - for v.Op == OpS390XFlagGT { + // result: (First no yes) + for b.Controls[0].Op == OpS390XFlagGT { c := b.Aux if !(c.(s390x.CCMask)&s390x.Greater == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true } // match: (BRC {c} (FlagOV) yes no) // cond: c.(s390x.CCMask) & s390x.Unordered == 0 - // result: (First nil no yes) - for v.Op == OpS390XFlagOV { + // result: (First no yes) + for b.Controls[0].Op == OpS390XFlagOV { c := b.Aux if !(c.(s390x.CCMask)&s390x.Unordered == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true @@ -36637,14 +36642,15 @@ func rewriteBlockS390X(b *Block) bool { // match: (If cond yes no) // result: (BRC {s390x.NotEqual} (CMPWconst [0] (MOVBZreg cond)) yes no) for { - cond := b.Control + cond := b.Controls[0] b.Kind = BlockS390XBRC - v0 := b.NewValue0(v.Pos, OpS390XCMPWconst, types.TypeFlags) + b.ResetControls() + v0 := b.NewValue0(cond.Pos, OpS390XCMPWconst, types.TypeFlags) v0.AuxInt = 0 - v1 := b.NewValue0(v.Pos, OpS390XMOVBZreg, typ.Bool) + v1 := b.NewValue0(cond.Pos, OpS390XMOVBZreg, typ.Bool) v1.AddArg(cond) v0.AddArg(v1) - b.SetControl(v0) + b.AddControl(v0) b.Aux = s390x.NotEqual return true } diff --git a/src/cmd/compile/internal/ssa/rewritegeneric.go b/src/cmd/compile/internal/ssa/rewritegeneric.go index be1aefbfdc..091dff60be 100644 --- a/src/cmd/compile/internal/ssa/rewritegeneric.go +++ b/src/cmd/compile/internal/ssa/rewritegeneric.go @@ -47407,42 +47407,45 @@ func rewriteValuegeneric_OpZeroExt8to64_0(v *Value) bool { return false } func rewriteBlockgeneric(b *Block) bool { - v := b.Control switch b.Kind { case BlockIf: // match: (If (Not cond) yes no) // result: (If cond no yes) - for v.Op == OpNot { - cond := v.Args[0] + for b.Controls[0].Op == OpNot { + v_0 := b.Controls[0] + cond := v_0.Args[0] b.Kind = BlockIf - b.SetControl(cond) + b.ResetControls() + b.AddControl(cond) b.Aux = nil b.swapSuccessors() return true } // match: (If (ConstBool [c]) yes no) // cond: c == 1 - // result: (First nil yes no) - for v.Op == OpConstBool { - c := v.AuxInt + // result: (First yes no) + for b.Controls[0].Op == OpConstBool { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c == 1) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil return true } // match: (If (ConstBool [c]) yes no) // cond: c == 0 - // result: (First nil no yes) - for v.Op == OpConstBool { - c := v.AuxInt + // result: (First no yes) + for b.Controls[0].Op == OpConstBool { + v_0 := b.Controls[0] + c := v_0.AuxInt if !(c == 0) { break } b.Kind = BlockFirst - b.SetControl(nil) + b.ResetControls() b.Aux = nil b.swapSuccessors() return true diff --git a/src/cmd/compile/internal/ssa/schedule.go b/src/cmd/compile/internal/ssa/schedule.go index ca0e82953e..ff0ef25e90 100644 --- a/src/cmd/compile/internal/ssa/schedule.go +++ b/src/cmd/compile/internal/ssa/schedule.go @@ -195,27 +195,31 @@ func schedule(f *Func) { } } - if b.Control != nil && b.Control.Op != OpPhi && b.Control.Op != OpArg { - // Force the control value to be scheduled at the end, - // unless it is a phi value (which must be first). + for _, c := range b.ControlValues() { + // Force the control values to be scheduled at the end, + // unless they are phi values (which must be first). // OpArg also goes first -- if it is stack it register allocates // to a LoadReg, if it is register it is from the beginning anyway. - score[b.Control.ID] = ScoreControl + if c.Op == OpPhi || c.Op == OpArg { + continue + } + score[c.ID] = ScoreControl - // Schedule values dependent on the control value at the end. + // Schedule values dependent on the control values at the end. // This reduces the number of register spills. We don't find - // all values that depend on the control, just values with a + // all values that depend on the controls, just values with a // direct dependency. This is cheaper and in testing there // was no difference in the number of spills. for _, v := range b.Values { if v.Op != OpPhi { for _, a := range v.Args { - if a == b.Control { + if a == c { score[v.ID] = ScoreControl } } } } + } // To put things into a priority queue diff --git a/src/cmd/compile/internal/ssa/shortcircuit.go b/src/cmd/compile/internal/ssa/shortcircuit.go index 5bf0888043..bb2322e28a 100644 --- a/src/cmd/compile/internal/ssa/shortcircuit.go +++ b/src/cmd/compile/internal/ssa/shortcircuit.go @@ -32,7 +32,7 @@ func shortcircuit(f *Func) { if p.Kind != BlockIf { continue } - if p.Control != a { + if p.Controls[0] != a { continue } if e.i == 0 { @@ -103,7 +103,7 @@ func shortcircuitBlock(b *Block) bool { // Look for control values of the form Copy(Not(Copy(Phi(const, ...)))). // Those must be the only values in the b, and they each must be used only by b. // Track the negations so that we can swap successors as needed later. - v := b.Control + v := b.Controls[0] nval := 1 // the control value swap := false for v.Uses == 1 && v.Block == b && (v.Op == OpCopy || v.Op == OpNot) { diff --git a/src/cmd/compile/internal/ssa/sizeof_test.go b/src/cmd/compile/internal/ssa/sizeof_test.go index 449788d32a..8ba6a88b66 100644 --- a/src/cmd/compile/internal/ssa/sizeof_test.go +++ b/src/cmd/compile/internal/ssa/sizeof_test.go @@ -23,7 +23,7 @@ func TestSizeof(t *testing.T) { _64bit uintptr // size on 64bit platforms }{ {Value{}, 72, 112}, - {Block{}, 152, 288}, + {Block{}, 156, 296}, {LocalSlot{}, 32, 48}, {valState{}, 28, 40}, } diff --git a/src/cmd/compile/internal/ssa/tighten.go b/src/cmd/compile/internal/ssa/tighten.go index 580a06dfde..5dfc453649 100644 --- a/src/cmd/compile/internal/ssa/tighten.go +++ b/src/cmd/compile/internal/ssa/tighten.go @@ -87,7 +87,7 @@ func tighten(f *Func) { } } } - if c := b.Control; c != nil { + for _, c := range b.ControlValues() { if !canMove[c.ID] { continue } diff --git a/src/cmd/compile/internal/ssa/value.go b/src/cmd/compile/internal/ssa/value.go index a0905eab1e..d2038fcfa5 100644 --- a/src/cmd/compile/internal/ssa/value.go +++ b/src/cmd/compile/internal/ssa/value.go @@ -47,7 +47,7 @@ type Value struct { // Source position Pos src.XPos - // Use count. Each appearance in Value.Args and Block.Control counts once. + // Use count. Each appearance in Value.Args and Block.Controls counts once. Uses int32 // wasm: Value stays on the WebAssembly stack. This value will not get a "register" (WebAssembly variable) diff --git a/src/cmd/compile/internal/ssa/writebarrier.go b/src/cmd/compile/internal/ssa/writebarrier.go index 5fc0ec19f7..4c51f9c788 100644 --- a/src/cmd/compile/internal/ssa/writebarrier.go +++ b/src/cmd/compile/internal/ssa/writebarrier.go @@ -182,7 +182,7 @@ func writebarrier(f *Func) { b.Pos = pos // set up control flow for end block - bEnd.SetControl(b.Control) + bEnd.CopyControls(b) bEnd.Likely = b.Likely for _, e := range b.Succs { bEnd.Succs = append(bEnd.Succs, e) diff --git a/src/cmd/compile/internal/wasm/ssa.go b/src/cmd/compile/internal/wasm/ssa.go index 8584fca9be..75b306e168 100644 --- a/src/cmd/compile/internal/wasm/ssa.go +++ b/src/cmd/compile/internal/wasm/ssa.go @@ -78,20 +78,20 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { switch next { case b.Succs[0].Block(): // if false, jump to b.Succs[1] - getValue32(s, b.Control) + getValue32(s, b.Controls[0]) s.Prog(wasm.AI32Eqz) s.Prog(wasm.AIf) s.Br(obj.AJMP, b.Succs[1].Block()) s.Prog(wasm.AEnd) case b.Succs[1].Block(): // if true, jump to b.Succs[0] - getValue32(s, b.Control) + getValue32(s, b.Controls[0]) s.Prog(wasm.AIf) s.Br(obj.AJMP, b.Succs[0].Block()) s.Prog(wasm.AEnd) default: // if true, jump to b.Succs[0], else jump to b.Succs[1] - getValue32(s, b.Control) + getValue32(s, b.Controls[0]) s.Prog(wasm.AIf) s.Br(obj.AJMP, b.Succs[0].Block()) s.Prog(wasm.AEnd) diff --git a/src/cmd/compile/internal/x86/ssa.go b/src/cmd/compile/internal/x86/ssa.go index 66c7b753c6..603903ba48 100644 --- a/src/cmd/compile/internal/x86/ssa.go +++ b/src/cmd/compile/internal/x86/ssa.go @@ -18,8 +18,8 @@ import ( // markMoves marks any MOVXconst ops that need to avoid clobbering flags. func ssaMarkMoves(s *gc.SSAGenState, b *ssa.Block) { flive := b.FlagsLiveAtEnd - if b.Control != nil && b.Control.Type.IsFlags() { - flive = true + for _, c := range b.ControlValues() { + flive = c.Type.IsFlags() || flive } for i := len(b.Values) - 1; i >= 0; i-- { v := b.Values[i] @@ -952,6 +952,6 @@ func ssaGenBlock(s *gc.SSAGenState, b, next *ssa.Block) { } } default: - b.Fatalf("branch not implemented: %s. Control: %s", b.LongString(), b.Control.LongString()) + b.Fatalf("branch not implemented: %s", b.LongString()) } } -- cgit v1.3 From ac2ceba01a503ca0b4fee2de915dad8e97e75f3f Mon Sep 17 00:00:00 2001 From: "Ruixin(Peter) Bao" Date: Tue, 24 Sep 2019 10:42:32 -0400 Subject: cmd/compile/internal/gc: intrinsify mulWW on s390x MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit SSA rule have already been added previously to intrisinfy Mul/Mul64 on s390x. In this CL, we want to let mulWW use that SSA rule as well. Also removed an extra line for formatting. Benchmarks: QuoRem-18 3.59µs ±15% 2.94µs ± 3% -18.06% (p=0.000 n=8+8) ModSqrt225_Tonelli-18 806µs ± 0% 800µs ± 0% -0.85% (p=0.000 n=7+8) ModSqrt225_3Mod4-18 245µs ± 1% 243µs ± 0% -0.81% (p=0.001 n=8+8) ModSqrt231_Tonelli-18 837µs ± 0% 834µs ± 1% -0.36% (p=0.028 n=8+8) ModSqrt231_5Mod8-18 282µs ± 0% 280µs ± 0% -0.76% (p=0.000 n=8+8) Sqrt-18 45.8µs ± 2% 38.6µs ± 0% -15.63% (p=0.000 n=8+8) IntSqr/1-18 19.1ns ± 0% 13.1ns ± 0% -31.41% (p=0.000 n=8+8) IntSqr/2-18 48.3ns ± 2% 48.2ns ± 0% ~ (p=0.094 n=8+8) IntSqr/3-18 70.5ns ± 1% 70.7ns ± 0% ~ (p=0.428 n=8+8) IntSqr/5-18 119ns ± 1% 118ns ± 0% -1.02% (p=0.000 n=7+8) IntSqr/8-18 215ns ± 1% 215ns ± 0% ~ (p=0.320 n=8+7) IntSqr/10-18 302ns ± 1% 301ns ± 0% ~ (p=0.148 n=8+7) IntSqr/20-18 952ns ± 1% 807ns ± 0% -15.28% (p=0.000 n=8+8) IntSqr/30-18 1.74µs ± 0% 1.53µs ± 0% -11.93% (p=0.000 n=8+8) IntSqr/50-18 3.91µs ± 0% 3.57µs ± 0% -8.64% (p=0.000 n=7+8) IntSqr/80-18 8.66µs ± 1% 8.11µs ± 0% -6.39% (p=0.000 n=8+8) IntSqr/100-18 12.8µs ± 0% 12.2µs ± 0% -5.19% (p=0.000 n=8+8) IntSqr/200-18 46.0µs ± 0% 44.5µs ± 0% -3.06% (p=0.000 n=8+8) IntSqr/300-18 81.4µs ± 0% 78.4µs ± 0% -3.71% (p=0.000 n=7+8) IntSqr/500-18 212µs ± 1% 206µs ± 0% -2.66% (p=0.000 n=8+8) IntSqr/800-18 419µs ± 1% 406µs ± 0% -3.07% (p=0.000 n=8+8) IntSqr/1000-18 635µs ± 0% 621µs ± 0% -2.13% (p=0.000 n=8+8) Change-Id: Ib097857186932b902601ab087cbeff3fc9555c3e Reviewed-on: https://go-review.googlesource.com/c/go/+/197639 Run-TryBot: Emmanuel Odeke TryBot-Result: Gobot Gobot Reviewed-by: Keith Randall --- src/cmd/compile/internal/gc/ssa.go | 2 +- src/cmd/compile/internal/s390x/ssa.go | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/ssa.go b/src/cmd/compile/internal/gc/ssa.go index efc7d1eb51..ed1cccc6b0 100644 --- a/src/cmd/compile/internal/gc/ssa.go +++ b/src/cmd/compile/internal/gc/ssa.go @@ -3671,7 +3671,7 @@ func init() { func(s *state, n *Node, args []*ssa.Value) *ssa.Value { return s.newValue2(ssa.OpMul64uhilo, types.NewTuple(types.Types[TUINT64], types.Types[TUINT64]), args[0], args[1]) }, - sys.ArchAMD64, sys.ArchARM64, sys.ArchPPC64LE, sys.ArchPPC64) + sys.ArchAMD64, sys.ArchARM64, sys.ArchPPC64LE, sys.ArchPPC64, sys.ArchS390X) add("math/big", "divWW", func(s *state, n *Node, args []*ssa.Value) *ssa.Value { return s.newValue3(ssa.OpDiv128u, types.NewTuple(types.Types[TUINT64], types.Types[TUINT64]), args[0], args[1], args[2]) diff --git a/src/cmd/compile/internal/s390x/ssa.go b/src/cmd/compile/internal/s390x/ssa.go index 52ba270116..15cb553eff 100644 --- a/src/cmd/compile/internal/s390x/ssa.go +++ b/src/cmd/compile/internal/s390x/ssa.go @@ -237,7 +237,6 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) { p.From.Reg = r0 p.To.Reg = s390x.REG_R2 p.To.Type = obj.TYPE_REG - case ssa.OpS390XFMADD, ssa.OpS390XFMADDS, ssa.OpS390XFMSUB, ssa.OpS390XFMSUBS: r := v.Reg() -- cgit v1.3 From 0ba0ea172d12901cba79314e26d5713b857c29c4 Mon Sep 17 00:00:00 2001 From: Brad Fitzpatrick Date: Wed, 2 Oct 2019 16:34:03 +0000 Subject: net/http: document that Request.Host includes HTTP/2 :authority Fixes #34640 Change-Id: I4a6c9414fe369cd5e9915472331c4bd8a21d8b0e Reviewed-on: https://go-review.googlesource.com/c/go/+/198457 Reviewed-by: Filippo Valsorda --- src/net/http/request.go | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/net/http/request.go b/src/net/http/request.go index 0b195a89a6..1fdd8a4fc7 100644 --- a/src/net/http/request.go +++ b/src/net/http/request.go @@ -217,9 +217,11 @@ type Request struct { // Transport.DisableKeepAlives were set. Close bool - // For server requests, Host specifies the host on which the URL - // is sought. Per RFC 7230, section 5.4, this is either the value - // of the "Host" header or the host name given in the URL itself. + // For server requests, Host specifies the host on which the + // URL is sought. For HTTP/1 (per RFC 7230, section 5.4), this + // is either the value of the "Host" header or the host name + // given in the URL itself. For HTTP/2, it is the value of the + // ":authority" pseudo-header field. // It may be of the form "host:port". For international domain // names, Host may be in Punycode or Unicode form. Use // golang.org/x/net/idna to convert it to either format if -- cgit v1.3 From 0000f0be0a3d357de56839330b5ccf04f4d593fe Mon Sep 17 00:00:00 2001 From: Dan Scales Date: Tue, 1 Oct 2019 13:36:07 -0700 Subject: cmd/compile: add an explicit test for compile of arch.ZeroRange Add a test that causes generation of arch.ZeroRange calls of various sizes 8-136 bytes in the compiler. This is to test that ZeroRanges of various sizes actually compile on different architectures, but is not testing runtime correctness (which is hard to do). Updates #34604 Change-Id: I4131eb86669bdfe8d4e36f4ae5c2a7b069abd6c4 Reviewed-on: https://go-review.googlesource.com/c/go/+/198045 Run-TryBot: Dan Scales TryBot-Result: Gobot Gobot Reviewed-by: Cherry Zhang --- src/cmd/compile/internal/gc/zerorange_test.go | 98 +++++++++++++++++++++++++++ 1 file changed, 98 insertions(+) create mode 100644 src/cmd/compile/internal/gc/zerorange_test.go (limited to 'src') diff --git a/src/cmd/compile/internal/gc/zerorange_test.go b/src/cmd/compile/internal/gc/zerorange_test.go new file mode 100644 index 0000000000..89f4cb9bcf --- /dev/null +++ b/src/cmd/compile/internal/gc/zerorange_test.go @@ -0,0 +1,98 @@ +// Copyright 2019 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package gc + +import ( + "testing" +) + +var glob = 3 +var globp *int64 + +// Testing compilation of arch.ZeroRange of various sizes. + +// By storing a pointer to an int64 output param in a global, the compiler must +// ensure that output param is allocated on the heap. Also, since there is a +// defer, the pointer to each output param must be zeroed in the prologue (see +// plive.go:epilogue()). So, we will get a block of one or more stack slots that +// need to be zeroed. Hence, we are testing compilation completes successfully when +// zerorange calls of various sizes (8-136 bytes) are generated. We are not +// testing runtime correctness (which is hard to do for the current uses of +// ZeroRange). + +func TestZeroRange(t *testing.T) { + testZeroRange8(t) + testZeroRange16(t) + testZeroRange32(t) + testZeroRange64(t) + testZeroRange136(t) +} + +func testZeroRange8(t *testing.T) (r int64) { + defer func() { + glob = 4 + }() + globp = &r + return +} + +func testZeroRange16(t *testing.T) (r, s int64) { + defer func() { + glob = 4 + }() + globp = &r + globp = &s + return +} + +func testZeroRange32(t *testing.T) (r, s, t2, u int64) { + defer func() { + glob = 4 + }() + globp = &r + globp = &s + globp = &t2 + globp = &u + return +} + +func testZeroRange64(t *testing.T) (r, s, t2, u, v, w, x, y int64) { + defer func() { + glob = 4 + }() + globp = &r + globp = &s + globp = &t2 + globp = &u + globp = &v + globp = &w + globp = &x + globp = &y + return +} + +func testZeroRange136(t *testing.T) (r, s, t2, u, v, w, x, y, r1, s1, t1, u1, v1, w1, x1, y1, z1 int64) { + defer func() { + glob = 4 + }() + globp = &r + globp = &s + globp = &t2 + globp = &u + globp = &v + globp = &w + globp = &x + globp = &y + globp = &r1 + globp = &s1 + globp = &t1 + globp = &u1 + globp = &v1 + globp = &w1 + globp = &x1 + globp = &y1 + globp = &z1 + return +} -- cgit v1.3 From 30d7b6400860d87d810a0db3593b28dfb72879f2 Mon Sep 17 00:00:00 2001 From: "W. Trevor King" Date: Wed, 2 Oct 2019 17:49:49 +0000 Subject: crypto/x509: add Detail to Expired errors Because errors like: certificate has expired or is not yet valid make it difficult to distinguish between "certificate has expired" and "my local clock is skewed". Including our idea of the local time makes it easier to identify the clock-skew case, and including the violated certificate constraint saves folks the trouble of looking it up in the target certificate. Change-Id: I52e0e71705ee36f6afde1bb5a47b9b42ed5ead5b GitHub-Last-Rev: db2ca4029c1e0b17363772d9824e3042d5501d48 GitHub-Pull-Request: golang/go#34646 Reviewed-on: https://go-review.googlesource.com/c/go/+/198046 Reviewed-by: Filippo Valsorda Run-TryBot: Filippo Valsorda TryBot-Result: Gobot Gobot --- src/crypto/x509/verify.go | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/crypto/x509/verify.go b/src/crypto/x509/verify.go index 3b5b3576bd..c8bad642f0 100644 --- a/src/crypto/x509/verify.go +++ b/src/crypto/x509/verify.go @@ -80,7 +80,7 @@ func (e CertificateInvalidError) Error() string { case NotAuthorizedToSign: return "x509: certificate is not authorized to sign other certificates" case Expired: - return "x509: certificate has expired or is not yet valid" + return "x509: certificate has expired or is not yet valid: " + e.Detail case CANotAuthorizedForThisName: return "x509: a root or intermediate certificate is not authorized to sign for this name: " + e.Detail case CANotAuthorizedForExtKeyUsage: @@ -576,8 +576,18 @@ func (c *Certificate) isValid(certType int, currentChain []*Certificate, opts *V if now.IsZero() { now = time.Now() } - if now.Before(c.NotBefore) || now.After(c.NotAfter) { - return CertificateInvalidError{c, Expired, ""} + if now.Before(c.NotBefore) { + return CertificateInvalidError{ + Cert: c, + Reason: Expired, + Detail: fmt.Sprintf("current time %s is before %s", now.Format(time.RFC3339), c.NotBefore.Format(time.RFC3339)), + } + } else if now.After(c.NotAfter) { + return CertificateInvalidError{ + Cert: c, + Reason: Expired, + Detail: fmt.Sprintf("current time %s is after %s", now.Format(time.RFC3339), c.NotAfter.Format(time.RFC3339)), + } } maxConstraintComparisons := opts.MaxConstraintComparisions -- cgit v1.3 From e85ffec784b867f016805873eec5dc91eec1c99a Mon Sep 17 00:00:00 2001 From: Egon Elbre Date: Tue, 1 Oct 2019 18:12:55 +0300 Subject: cmd/cgo: optimize cgoCheckPointer call MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Currently cgoCheckPointer is only used with one optional argument. Using a slice for the optional arguments is quite expensive, hence replace it with a single interface{}. This results in ~30% improvement. When checking struct fields, they quite often end up being without pointers. Check this before calling cgoCheckPointer, which results in additional ~20% improvement. Inline some p == nil checks from cgoIsGoPointer which gives additional ~15% improvement. All of this translates to: name old time/op new time/op delta CgoCall/add-int-32 46.9ns ± 1% 46.6ns ± 1% -0.75% (p=0.000 n=18+20) CgoCall/one-pointer-32 143ns ± 1% 87ns ± 1% -38.96% (p=0.000 n=20+20) CgoCall/eight-pointers-32 767ns ± 0% 327ns ± 1% -57.30% (p=0.000 n=18+16) CgoCall/eight-pointers-nil-32 110ns ± 1% 89ns ± 2% -19.10% (p=0.000 n=19+19) CgoCall/eight-pointers-array-32 5.09µs ± 1% 3.56µs ± 2% -30.09% (p=0.000 n=19+19) CgoCall/eight-pointers-slice-32 3.92µs ± 0% 2.57µs ± 2% -34.48% (p=0.000 n=20+20) Change-Id: I2aa9f5ae8962a9a41a7fb1db0c300893109d0d75 Reviewed-on: https://go-review.googlesource.com/c/go/+/198081 Run-TryBot: Ian Lance Taylor TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- misc/cgo/test/test.go | 82 +++++++++++++++++++++++++++++++++++++++++++++++--- src/cmd/cgo/gcc.go | 6 ++-- src/cmd/cgo/out.go | 12 ++++---- src/runtime/cgocall.go | 18 +++++++---- 4 files changed, 98 insertions(+), 20 deletions(-) (limited to 'src') diff --git a/misc/cgo/test/test.go b/misc/cgo/test/test.go index 0aa80ebc82..68bfa90825 100644 --- a/misc/cgo/test/test.go +++ b/misc/cgo/test/test.go @@ -115,6 +115,44 @@ int add(int x, int y) { return x+y; }; +// Following mimicks vulkan complex definitions for benchmarking cgocheck overhead. + +typedef uint32_t VkFlags; +typedef VkFlags VkDeviceQueueCreateFlags; +typedef uint32_t VkStructureType; + +typedef struct VkDeviceQueueCreateInfo { + VkStructureType sType; + const void* pNext; + VkDeviceQueueCreateFlags flags; + uint32_t queueFamilyIndex; + uint32_t queueCount; + const float* pQueuePriorities; +} VkDeviceQueueCreateInfo; + +typedef struct VkPhysicalDeviceFeatures { + uint32_t bools[56]; +} VkPhysicalDeviceFeatures; + +typedef struct VkDeviceCreateInfo { + VkStructureType sType; + const void* pNext; + VkFlags flags; + uint32_t queueCreateInfoCount; + const VkDeviceQueueCreateInfo* pQueueCreateInfos; + uint32_t enabledLayerCount; + const char* const* ppEnabledLayerNames; + uint32_t enabledExtensionCount; + const char* const* ppEnabledExtensionNames; + const VkPhysicalDeviceFeatures* pEnabledFeatures; +} VkDeviceCreateInfo; + +void handleComplexPointer(VkDeviceCreateInfo *a0) {} +void handleComplexPointer8( + VkDeviceCreateInfo *a0, VkDeviceCreateInfo *a1, VkDeviceCreateInfo *a2, VkDeviceCreateInfo *a3, + VkDeviceCreateInfo *a4, VkDeviceCreateInfo *a5, VkDeviceCreateInfo *a6, VkDeviceCreateInfo *a7 +) {} + // complex alignment struct { @@ -993,11 +1031,45 @@ type Context struct { } func benchCgoCall(b *testing.B) { - const x = C.int(2) - const y = C.int(3) - for i := 0; i < b.N; i++ { - C.add(x, y) - } + b.Run("add-int", func(b *testing.B) { + const x = C.int(2) + const y = C.int(3) + + for i := 0; i < b.N; i++ { + C.add(x, y) + } + }) + + b.Run("one-pointer", func(b *testing.B) { + var a0 C.VkDeviceCreateInfo + for i := 0; i < b.N; i++ { + C.handleComplexPointer(&a0) + } + }) + b.Run("eight-pointers", func(b *testing.B) { + var a0, a1, a2, a3, a4, a5, a6, a7 C.VkDeviceCreateInfo + for i := 0; i < b.N; i++ { + C.handleComplexPointer8(&a0, &a1, &a2, &a3, &a4, &a5, &a6, &a7) + } + }) + b.Run("eight-pointers-nil", func(b *testing.B) { + var a0, a1, a2, a3, a4, a5, a6, a7 *C.VkDeviceCreateInfo + for i := 0; i < b.N; i++ { + C.handleComplexPointer8(a0, a1, a2, a3, a4, a5, a6, a7) + } + }) + b.Run("eight-pointers-array", func(b *testing.B) { + var a [8]C.VkDeviceCreateInfo + for i := 0; i < b.N; i++ { + C.handleComplexPointer8(&a[0], &a[1], &a[2], &a[3], &a[4], &a[5], &a[6], &a[7]) + } + }) + b.Run("eight-pointers-slice", func(b *testing.B) { + a := make([]C.VkDeviceCreateInfo, 8) + for i := 0; i < b.N; i++ { + C.handleComplexPointer8(&a[0], &a[1], &a[2], &a[3], &a[4], &a[5], &a[6], &a[7]) + } + }) } // Benchmark measuring overhead from Go to C and back to Go (via a callback) diff --git a/src/cmd/cgo/gcc.go b/src/cmd/cgo/gcc.go index 01b86adadb..12d4749677 100644 --- a/src/cmd/cgo/gcc.go +++ b/src/cmd/cgo/gcc.go @@ -816,7 +816,7 @@ func (p *Package) rewriteCall(f *File, call *Call) (string, bool) { // Rewrite C.f(p) to // func() { // _cgo0 := p - // _cgoCheckPointer(_cgo0) + // _cgoCheckPointer(_cgo0, nil) // C.f(_cgo0) // }() // Using a function literal like this lets us evaluate the @@ -834,7 +834,7 @@ func (p *Package) rewriteCall(f *File, call *Call) (string, bool) { // defer func() func() { // _cgo0 := p // return func() { - // _cgoCheckPointer(_cgo0) + // _cgoCheckPointer(_cgo0, nil) // C.f(_cgo0) // } // }()() @@ -921,7 +921,7 @@ func (p *Package) rewriteCall(f *File, call *Call) (string, bool) { } fmt.Fprintf(&sb, "_cgo%d := %s; ", i, gofmtPos(arg, origArg.Pos())) - fmt.Fprintf(&sbCheck, "_cgoCheckPointer(_cgo%d); ", i) + fmt.Fprintf(&sbCheck, "_cgoCheckPointer(_cgo%d, nil); ", i) } if call.Deferred { diff --git a/src/cmd/cgo/out.go b/src/cmd/cgo/out.go index 1fddbb6b54..6bee9b1909 100644 --- a/src/cmd/cgo/out.go +++ b/src/cmd/cgo/out.go @@ -1631,14 +1631,14 @@ func _cgo_runtime_cgocall(unsafe.Pointer, uintptr) int32 func _cgo_runtime_cgocallback(unsafe.Pointer, unsafe.Pointer, uintptr, uintptr) //go:linkname _cgoCheckPointer runtime.cgoCheckPointer -func _cgoCheckPointer(interface{}, ...interface{}) +func _cgoCheckPointer(interface{}, interface{}) //go:linkname _cgoCheckResult runtime.cgoCheckResult func _cgoCheckResult(interface{}) ` const gccgoGoProlog = ` -func _cgoCheckPointer(interface{}, ...interface{}) +func _cgoCheckPointer(interface{}, interface{}) func _cgoCheckResult(interface{}) ` @@ -1825,16 +1825,16 @@ typedef struct __go_empty_interface { void *__object; } Eface; -extern void runtimeCgoCheckPointer(Eface, Slice) +extern void runtimeCgoCheckPointer(Eface, Eface) __asm__("runtime.cgoCheckPointer") __attribute__((weak)); -extern void localCgoCheckPointer(Eface, Slice) +extern void localCgoCheckPointer(Eface, Eface) __asm__("GCCGOSYMBOLPREF._cgoCheckPointer"); -void localCgoCheckPointer(Eface ptr, Slice args) { +void localCgoCheckPointer(Eface ptr, Eface arg) { if(runtimeCgoCheckPointer) { - runtimeCgoCheckPointer(ptr, args); + runtimeCgoCheckPointer(ptr, arg); } } diff --git a/src/runtime/cgocall.go b/src/runtime/cgocall.go index a881ae1489..3595e49ed5 100644 --- a/src/runtime/cgocall.go +++ b/src/runtime/cgocall.go @@ -406,7 +406,7 @@ var racecgosync uint64 // represents possible synchronization in C code // cgoCheckPointer checks if the argument contains a Go pointer that // points to a Go pointer, and panics if it does. -func cgoCheckPointer(ptr interface{}, args ...interface{}) { +func cgoCheckPointer(ptr interface{}, arg interface{}) { if debug.cgocheck == 0 { return } @@ -415,15 +415,15 @@ func cgoCheckPointer(ptr interface{}, args ...interface{}) { t := ep._type top := true - if len(args) > 0 && (t.kind&kindMask == kindPtr || t.kind&kindMask == kindUnsafePointer) { + if arg != nil && (t.kind&kindMask == kindPtr || t.kind&kindMask == kindUnsafePointer) { p := ep.data if t.kind&kindDirectIface == 0 { p = *(*unsafe.Pointer)(p) } - if !cgoIsGoPointer(p) { + if p == nil || !cgoIsGoPointer(p) { return } - aep := (*eface)(unsafe.Pointer(&args[0])) + aep := (*eface)(unsafe.Pointer(&arg)) switch aep._type.kind & kindMask { case kindBool: if t.kind&kindMask == kindUnsafePointer { @@ -460,7 +460,7 @@ const cgoResultFail = "cgo result has Go pointer" // depending on indir. The top parameter is whether we are at the top // level, where Go pointers are allowed. func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { - if t.ptrdata == 0 { + if t.ptrdata == 0 || p == nil { // If the type has no pointers there is nothing to do. return } @@ -517,7 +517,7 @@ func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { st := (*slicetype)(unsafe.Pointer(t)) s := (*slice)(p) p = s.array - if !cgoIsGoPointer(p) { + if p == nil || !cgoIsGoPointer(p) { return } if !top { @@ -548,11 +548,17 @@ func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { return } for _, f := range st.fields { + if f.typ.ptrdata == 0 { + continue + } cgoCheckArg(f.typ, add(p, f.offset()), true, top, msg) } case kindPtr, kindUnsafePointer: if indir { p = *(*unsafe.Pointer)(p) + if p == nil { + return + } } if !cgoIsGoPointer(p) { -- cgit v1.3 From f0e940ebc985661f54d31c8d9ba31a553b87041b Mon Sep 17 00:00:00 2001 From: Michael Hendricks Date: Wed, 2 Oct 2019 09:30:51 -0600 Subject: net: avoid an infinite loop in LookupAddr If a request for a PTR record returned a response with a non-PTR answer, goLookupPTR would loop forever. Skipping non-PTR answers guarantees progress through the DNS response. Fixes #34660 Change-Id: I56f9d21e5342d07e7d843d253267e93a29707904 Reviewed-on: https://go-review.googlesource.com/c/go/+/198460 Run-TryBot: Brad Fitzpatrick TryBot-Result: Gobot Gobot Reviewed-by: Brad Fitzpatrick --- src/net/dnsclient_unix.go | 8 +++++++ src/net/dnsclient_unix_test.go | 47 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 55 insertions(+) (limited to 'src') diff --git a/src/net/dnsclient_unix.go b/src/net/dnsclient_unix.go index e0a7ef8552..c90892b833 100644 --- a/src/net/dnsclient_unix.go +++ b/src/net/dnsclient_unix.go @@ -765,6 +765,14 @@ func (r *Resolver) goLookupPTR(ctx context.Context, addr string) ([]string, erro } } if h.Type != dnsmessage.TypePTR { + err := p.SkipAnswer() + if err != nil { + return nil, &DNSError{ + Err: "cannot marshal DNS message", + Name: addr, + Server: server, + } + } continue } ptr, err := p.PTRResource() diff --git a/src/net/dnsclient_unix_test.go b/src/net/dnsclient_unix_test.go index 98304d36ea..31cb6f721a 100644 --- a/src/net/dnsclient_unix_test.go +++ b/src/net/dnsclient_unix_test.go @@ -1753,3 +1753,50 @@ func TestDNSUseTCP(t *testing.T) { t.Fatal("exchange failed:", err) } } + +// Issue 34660: PTR response with non-PTR answers should ignore non-PTR +func TestPTRandNonPTR(t *testing.T) { + fake := fakeDNSServer{ + rh: func(n, _ string, q dnsmessage.Message, _ time.Time) (dnsmessage.Message, error) { + r := dnsmessage.Message{ + Header: dnsmessage.Header{ + ID: q.Header.ID, + Response: true, + RCode: dnsmessage.RCodeSuccess, + }, + Questions: q.Questions, + Answers: []dnsmessage.Resource{ + { + Header: dnsmessage.ResourceHeader{ + Name: q.Questions[0].Name, + Type: dnsmessage.TypePTR, + Class: dnsmessage.ClassINET, + }, + Body: &dnsmessage.PTRResource{ + PTR: dnsmessage.MustNewName("golang.org."), + }, + }, + { + Header: dnsmessage.ResourceHeader{ + Name: q.Questions[0].Name, + Type: dnsmessage.TypeTXT, + Class: dnsmessage.ClassINET, + }, + Body: &dnsmessage.TXTResource{ + TXT: []string{"PTR 8 6 60 ..."}, // fake RRSIG + }, + }, + }, + } + return r, nil + }, + } + r := Resolver{PreferGo: true, Dial: fake.DialContext} + names, err := r.lookupAddr(context.Background(), "192.0.2.123") + if err != nil { + t.Fatalf("LookupAddr: %v", err) + } + if want := []string{"golang.org."}; !reflect.DeepEqual(names, want) { + t.Errorf("names = %q; want %q", names, want) + } +} -- cgit v1.3 From debbb1e78d08b201313c83f2d236de90d8444c8e Mon Sep 17 00:00:00 2001 From: Ariel Mashraki Date: Tue, 1 Oct 2019 22:40:20 +0300 Subject: text/template/parse: speed up nodes printing This CL is a follow up for 198080. Added a private writeTo method to the Node interface, in order to use the same builder for printing all nodes in the tree. Benchmark output against master: benchmark old ns/op new ns/op delta BenchmarkParseLarge-8 24594994 25292054 +2.83% BenchmarkVariableString-8 117 118 +0.85% BenchmarkListString-8 10475 3353 -67.99% benchmark old allocs new allocs delta BenchmarkVariableString-8 3 3 +0.00% BenchmarkListString-8 149 31 -79.19% benchmark old bytes new bytes delta BenchmarkVariableString-8 72 72 +0.00% BenchmarkListString-8 5698 1608 -71.78% Change-Id: I2b1cf07cda65c1b80083fb99671289423700feba Reviewed-on: https://go-review.googlesource.com/c/go/+/198278 Reviewed-by: Rob Pike Run-TryBot: Rob Pike TryBot-Result: Gobot Gobot --- src/text/template/parse/node.go | 129 +++++++++++++++++++++++++++++----- src/text/template/parse/parse_test.go | 22 +++++- 2 files changed, 130 insertions(+), 21 deletions(-) (limited to 'src') diff --git a/src/text/template/parse/node.go b/src/text/template/parse/node.go index 61c6853679..1c116ea6fa 100644 --- a/src/text/template/parse/node.go +++ b/src/text/template/parse/node.go @@ -28,6 +28,8 @@ type Node interface { // tree returns the containing *Tree. // It is unexported so all implementations of Node are in this package. tree() *Tree + // writeTo writes the String output to the builder. + writeTo(*strings.Builder) } // NodeType identifies the type of a parse tree node. @@ -94,10 +96,14 @@ func (l *ListNode) tree() *Tree { func (l *ListNode) String() string { var sb strings.Builder + l.writeTo(&sb) + return sb.String() +} + +func (l *ListNode) writeTo(sb *strings.Builder) { for _, n := range l.Nodes { - sb.WriteString(n.String()) + n.writeTo(sb) } - return sb.String() } func (l *ListNode) CopyList() *ListNode { @@ -131,6 +137,10 @@ func (t *TextNode) String() string { return fmt.Sprintf(textFormat, t.Text) } +func (t *TextNode) writeTo(sb *strings.Builder) { + sb.WriteString(t.String()) +} + func (t *TextNode) tree() *Tree { return t.tr } @@ -160,12 +170,17 @@ func (p *PipeNode) append(command *CommandNode) { func (p *PipeNode) String() string { var sb strings.Builder + p.writeTo(&sb) + return sb.String() +} + +func (p *PipeNode) writeTo(sb *strings.Builder) { if len(p.Decl) > 0 { for i, v := range p.Decl { if i > 0 { sb.WriteString(", ") } - sb.WriteString(v.String()) + v.writeTo(sb) } sb.WriteString(" := ") } @@ -173,9 +188,8 @@ func (p *PipeNode) String() string { if i > 0 { sb.WriteString(" | ") } - sb.WriteString(c.String()) + c.writeTo(sb) } - return sb.String() } func (p *PipeNode) tree() *Tree { @@ -218,8 +232,15 @@ func (t *Tree) newAction(pos Pos, line int, pipe *PipeNode) *ActionNode { } func (a *ActionNode) String() string { - return fmt.Sprintf("{{%s}}", a.Pipe) + var sb strings.Builder + a.writeTo(&sb) + return sb.String() +} +func (a *ActionNode) writeTo(sb *strings.Builder) { + sb.WriteString("{{") + a.Pipe.writeTo(sb) + sb.WriteString("}}") } func (a *ActionNode) tree() *Tree { @@ -249,19 +270,23 @@ func (c *CommandNode) append(arg Node) { func (c *CommandNode) String() string { var sb strings.Builder + c.writeTo(&sb) + return sb.String() +} + +func (c *CommandNode) writeTo(sb *strings.Builder) { for i, arg := range c.Args { if i > 0 { sb.WriteByte(' ') } if arg, ok := arg.(*PipeNode); ok { sb.WriteByte('(') - sb.WriteString(arg.String()) + arg.writeTo(sb) sb.WriteByte(')') continue } - sb.WriteString(arg.String()) + arg.writeTo(sb) } - return sb.String() } func (c *CommandNode) tree() *Tree { @@ -312,6 +337,10 @@ func (i *IdentifierNode) String() string { return i.Ident } +func (i *IdentifierNode) writeTo(sb *strings.Builder) { + sb.WriteString(i.String()) +} + func (i *IdentifierNode) tree() *Tree { return i.tr } @@ -335,13 +364,17 @@ func (t *Tree) newVariable(pos Pos, ident string) *VariableNode { func (v *VariableNode) String() string { var sb strings.Builder + v.writeTo(&sb) + return sb.String() +} + +func (v *VariableNode) writeTo(sb *strings.Builder) { for i, id := range v.Ident { if i > 0 { sb.WriteByte('.') } sb.WriteString(id) } - return sb.String() } func (v *VariableNode) tree() *Tree { @@ -374,6 +407,10 @@ func (d *DotNode) String() string { return "." } +func (d *DotNode) writeTo(sb *strings.Builder) { + sb.WriteString(d.String()) +} + func (d *DotNode) tree() *Tree { return d.tr } @@ -404,6 +441,10 @@ func (n *NilNode) String() string { return "nil" } +func (n *NilNode) writeTo(sb *strings.Builder) { + sb.WriteString(n.String()) +} + func (n *NilNode) tree() *Tree { return n.tr } @@ -428,11 +469,15 @@ func (t *Tree) newField(pos Pos, ident string) *FieldNode { func (f *FieldNode) String() string { var sb strings.Builder + f.writeTo(&sb) + return sb.String() +} + +func (f *FieldNode) writeTo(sb *strings.Builder) { for _, id := range f.Ident { sb.WriteByte('.') sb.WriteString(id) } - return sb.String() } func (f *FieldNode) tree() *Tree { @@ -472,18 +517,22 @@ func (c *ChainNode) Add(field string) { func (c *ChainNode) String() string { var sb strings.Builder + c.writeTo(&sb) + return sb.String() +} + +func (c *ChainNode) writeTo(sb *strings.Builder) { if _, ok := c.Node.(*PipeNode); ok { sb.WriteByte('(') - sb.WriteString(c.Node.String()) + c.Node.writeTo(sb) sb.WriteByte(')') } else { - sb.WriteString(c.Node.String()) + c.Node.writeTo(sb) } for _, field := range c.Field { sb.WriteByte('.') sb.WriteString(field) } - return sb.String() } func (c *ChainNode) tree() *Tree { @@ -513,6 +562,10 @@ func (b *BoolNode) String() string { return "false" } +func (b *BoolNode) writeTo(sb *strings.Builder) { + sb.WriteString(b.String()) +} + func (b *BoolNode) tree() *Tree { return b.tr } @@ -646,6 +699,10 @@ func (n *NumberNode) String() string { return n.Text } +func (n *NumberNode) writeTo(sb *strings.Builder) { + sb.WriteString(n.String()) +} + func (n *NumberNode) tree() *Tree { return n.tr } @@ -673,6 +730,10 @@ func (s *StringNode) String() string { return s.Quoted } +func (s *StringNode) writeTo(sb *strings.Builder) { + sb.WriteString(s.String()) +} + func (s *StringNode) tree() *Tree { return s.tr } @@ -697,6 +758,10 @@ func (e *endNode) String() string { return "{{end}}" } +func (e *endNode) writeTo(sb *strings.Builder) { + sb.WriteString(e.String()) +} + func (e *endNode) tree() *Tree { return e.tr } @@ -725,6 +790,10 @@ func (e *elseNode) String() string { return "{{else}}" } +func (e *elseNode) writeTo(sb *strings.Builder) { + sb.WriteString(e.String()) +} + func (e *elseNode) tree() *Tree { return e.tr } @@ -745,6 +814,12 @@ type BranchNode struct { } func (b *BranchNode) String() string { + var sb strings.Builder + b.writeTo(&sb) + return sb.String() +} + +func (b *BranchNode) writeTo(sb *strings.Builder) { name := "" switch b.NodeType { case NodeIf: @@ -756,10 +831,17 @@ func (b *BranchNode) String() string { default: panic("unknown branch type") } + sb.WriteString("{{") + sb.WriteString(name) + sb.WriteByte(' ') + b.Pipe.writeTo(sb) + sb.WriteString("}}") + b.List.writeTo(sb) if b.ElseList != nil { - return fmt.Sprintf("{{%s %s}}%s{{else}}%s{{end}}", name, b.Pipe, b.List, b.ElseList) + sb.WriteString("{{else}}") + b.ElseList.writeTo(sb) } - return fmt.Sprintf("{{%s %s}}%s{{end}}", name, b.Pipe, b.List) + sb.WriteString("{{end}}") } func (b *BranchNode) tree() *Tree { @@ -833,10 +915,19 @@ func (t *Tree) newTemplate(pos Pos, line int, name string, pipe *PipeNode) *Temp } func (t *TemplateNode) String() string { - if t.Pipe == nil { - return fmt.Sprintf("{{template %q}}", t.Name) + var sb strings.Builder + t.writeTo(&sb) + return sb.String() +} + +func (t *TemplateNode) writeTo(sb *strings.Builder) { + sb.WriteString("{{template ") + sb.WriteString(strconv.Quote(t.Name)) + if t.Pipe != nil { + sb.WriteByte(' ') + t.Pipe.writeTo(sb) } - return fmt.Sprintf("{{template %q %s}}", t.Name, t.Pipe) + sb.WriteString("}}") } func (t *TemplateNode) tree() *Tree { diff --git a/src/text/template/parse/parse_test.go b/src/text/template/parse/parse_test.go index 86a100bb5f..4e09a7852c 100644 --- a/src/text/template/parse/parse_test.go +++ b/src/text/template/parse/parse_test.go @@ -304,7 +304,8 @@ var parseTests = []parseTest{ } var builtins = map[string]interface{}{ - "printf": fmt.Sprintf, + "printf": fmt.Sprintf, + "contains": strings.Contains, } func testParse(doCopy bool, t *testing.T) { @@ -571,7 +572,24 @@ func BenchmarkVariableString(b *testing.B) { } func BenchmarkListString(b *testing.B) { - text := `{{ (printf .Field1.Field2.Field3).Value }}` + text := ` +{{(printf .Field1.Field2.Field3).Value}} +{{$x := (printf .Field1.Field2.Field3).Value}} +{{$y := (printf $x.Field1.Field2.Field3).Value}} +{{$z := $y.Field1.Field2.Field3}} +{{if contains $y $z}} + {{printf "%q" $y}} +{{else}} + {{printf "%q" $x}} +{{end}} +{{with $z.Field1 | contains "boring"}} + {{printf "%q" . | printf "%s"}} +{{else}} + {{printf "%d %d %d" 11 11 11}} + {{printf "%d %d %s" 22 22 $x.Field1.Field2.Field3 | printf "%s"}} + {{printf "%v" (contains $z.Field1.Field2 $y)}} +{{end}} +` tree, err := New("bench").Parse(text, "", "", make(map[string]*Tree), builtins) if err != nil { b.Fatal(err) -- cgit v1.3 From 64e598f7837566802085ba9bb684e82ccbcf7ca6 Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Wed, 2 Oct 2019 15:41:13 -0700 Subject: runtime: use efaceOf where applicable Prepared with gofmt -r. Change-Id: Ifea325c209d800b5692d318955930b10debb548b Reviewed-on: https://go-review.googlesource.com/c/go/+/198494 Run-TryBot: Matthew Dempsky TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- src/runtime/cgocall.go | 6 +++--- src/runtime/iface.go | 10 +++++----- 2 files changed, 8 insertions(+), 8 deletions(-) (limited to 'src') diff --git a/src/runtime/cgocall.go b/src/runtime/cgocall.go index 3595e49ed5..5f8ff8139a 100644 --- a/src/runtime/cgocall.go +++ b/src/runtime/cgocall.go @@ -411,7 +411,7 @@ func cgoCheckPointer(ptr interface{}, arg interface{}) { return } - ep := (*eface)(unsafe.Pointer(&ptr)) + ep := efaceOf(&ptr) t := ep._type top := true @@ -423,7 +423,7 @@ func cgoCheckPointer(ptr interface{}, arg interface{}) { if p == nil || !cgoIsGoPointer(p) { return } - aep := (*eface)(unsafe.Pointer(&arg)) + aep := efaceOf(&arg) switch aep._type.kind & kindMask { case kindBool: if t.kind&kindMask == kindUnsafePointer { @@ -650,7 +650,7 @@ func cgoCheckResult(val interface{}) { return } - ep := (*eface)(unsafe.Pointer(&val)) + ep := efaceOf(&val) t := ep._type cgoCheckArg(t, ep.data, t.kind&kindDirectIface == 0, false, cgoResultFail) } diff --git a/src/runtime/iface.go b/src/runtime/iface.go index bb4eccc9bd..243e51fc48 100644 --- a/src/runtime/iface.go +++ b/src/runtime/iface.go @@ -295,11 +295,11 @@ var ( stringEface interface{} = stringInterfacePtr("") sliceEface interface{} = sliceInterfacePtr(nil) - uint16Type *_type = (*eface)(unsafe.Pointer(&uint16Eface))._type - uint32Type *_type = (*eface)(unsafe.Pointer(&uint32Eface))._type - uint64Type *_type = (*eface)(unsafe.Pointer(&uint64Eface))._type - stringType *_type = (*eface)(unsafe.Pointer(&stringEface))._type - sliceType *_type = (*eface)(unsafe.Pointer(&sliceEface))._type + uint16Type *_type = efaceOf(&uint16Eface)._type + uint32Type *_type = efaceOf(&uint32Eface)._type + uint64Type *_type = efaceOf(&uint64Eface)._type + stringType *_type = efaceOf(&stringEface)._type + sliceType *_type = efaceOf(&sliceEface)._type ) // The conv and assert functions below do very similar things. -- cgit v1.3 From 27fc32ff01cc699e160890546816bd99d6c57823 Mon Sep 17 00:00:00 2001 From: Robert Griesemer Date: Wed, 2 Oct 2019 14:42:46 -0700 Subject: cmd/compile: better error message for language version errors Fixes #33753. Updates #31747. Change-Id: Icc42b23405ead4f7f17b0ffa3611405454b6b271 Reviewed-on: https://go-review.googlesource.com/c/go/+/198491 Run-TryBot: Robert Griesemer TryBot-Result: Gobot Gobot Reviewed-by: Ian Lance Taylor --- src/cmd/compile/internal/gc/noder.go | 8 ++++---- src/cmd/compile/internal/gc/subr.go | 5 +++++ src/cmd/compile/internal/gc/typecheck.go | 2 +- test/fixedbugs/issue31747.go | 10 +++++----- 4 files changed, 15 insertions(+), 10 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/noder.go b/src/cmd/compile/internal/gc/noder.go index 2922f9a872..a4f834b5ab 100644 --- a/src/cmd/compile/internal/gc/noder.go +++ b/src/cmd/compile/internal/gc/noder.go @@ -1327,7 +1327,7 @@ func checkLangCompat(lit *syntax.BasicLit) { } // len(s) > 2 if strings.Contains(s, "_") { - yyerror("underscores in numeric literals only supported as of -lang=go1.13") + yyerrorv("go1.13", "underscores in numeric literals") return } if s[0] != '0' { @@ -1335,15 +1335,15 @@ func checkLangCompat(lit *syntax.BasicLit) { } base := s[1] if base == 'b' || base == 'B' { - yyerror("binary literals only supported as of -lang=go1.13") + yyerrorv("go1.13", "binary literals") return } if base == 'o' || base == 'O' { - yyerror("0o/0O-style octal literals only supported as of -lang=go1.13") + yyerrorv("go1.13", "0o/0O-style octal literals") return } if lit.Kind != syntax.IntLit && (base == 'x' || base == 'X') { - yyerror("hexadecimal floating-point literals only supported as of -lang=go1.13") + yyerrorv("go1.13", "hexadecimal floating-point literals") } } diff --git a/src/cmd/compile/internal/gc/subr.go b/src/cmd/compile/internal/gc/subr.go index b4be5dcbfb..3fc59194e4 100644 --- a/src/cmd/compile/internal/gc/subr.go +++ b/src/cmd/compile/internal/gc/subr.go @@ -154,6 +154,11 @@ func yyerrorl(pos src.XPos, format string, args ...interface{}) { } } +func yyerrorv(lang string, format string, args ...interface{}) { + what := fmt.Sprintf(format, args...) + yyerrorl(lineno, "%s requires %s or later (-lang was set to %s; check go.mod)", what, lang, flag_lang) +} + func yyerror(format string, args ...interface{}) { yyerrorl(lineno, format, args...) } diff --git a/src/cmd/compile/internal/gc/typecheck.go b/src/cmd/compile/internal/gc/typecheck.go index c9b7e3b1e8..d5483c9ce5 100644 --- a/src/cmd/compile/internal/gc/typecheck.go +++ b/src/cmd/compile/internal/gc/typecheck.go @@ -604,7 +604,7 @@ func typecheck1(n *Node, top int) (res *Node) { return n } if t.IsSigned() && !langSupported(1, 13) { - yyerror("invalid operation: %v (signed shift count type %v, only supported as of -lang=go1.13)", n, r.Type) + yyerrorv("go1.13", "invalid operation: %v (signed shift count type %v)", n, r.Type) n.Type = nil return n } diff --git a/test/fixedbugs/issue31747.go b/test/fixedbugs/issue31747.go index dfb585c613..420fe30735 100644 --- a/test/fixedbugs/issue31747.go +++ b/test/fixedbugs/issue31747.go @@ -8,11 +8,11 @@ package p // numeric literals const ( - _ = 1_000 // ERROR "underscores in numeric literals only supported as of -lang=go1.13" - _ = 0b111 // ERROR "binary literals only supported as of -lang=go1.13" - _ = 0o567 // ERROR "0o/0O-style octal literals only supported as of -lang=go1.13" + _ = 1_000 // ERROR "underscores in numeric literals requires go1.13 or later \(-lang was set to go1.12; check go.mod\)" + _ = 0b111 // ERROR "binary literals requires go1.13 or later" + _ = 0o567 // ERROR "0o/0O-style octal literals requires go1.13 or later" _ = 0xabc // ok - _ = 0x0p1 // ERROR "hexadecimal floating-point literals only supported as of -lang=go1.13" + _ = 0x0p1 // ERROR "hexadecimal floating-point literals requires go1.13 or later" _ = 0B111 // ERROR "binary" _ = 0O567 // ERROR "octal" @@ -29,6 +29,6 @@ const ( // signed shift counts var ( s int - _ = 1 << s // ERROR "signed shift count type int, only supported as of -lang=go1.13" + _ = 1 << s // ERROR "invalid operation: 1 << s \(signed shift count type int\) requires go1.13 or later" _ = 1 >> s // ERROR "signed shift count" ) -- cgit v1.3 From 64785bf96c5942e5e2a3d326b48eae4e7b189e03 Mon Sep 17 00:00:00 2001 From: Tobias Klauser Date: Thu, 3 Oct 2019 10:06:08 +0200 Subject: cmd/go/internal/modfetch: update TestCodeRepo for gopkg.in/yaml.v2 again Update the expected data to fix the longtest builder. Updates #28856 Change-Id: I7fb6ee72e8469d974561b4b4057f40142f5b3654 Reviewed-on: https://go-review.googlesource.com/c/go/+/198557 Run-TryBot: Tobias Klauser TryBot-Result: Gobot Gobot Reviewed-by: Dmitri Shuralyov --- src/cmd/go/internal/modfetch/coderepo_test.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/cmd/go/internal/modfetch/coderepo_test.go b/src/cmd/go/internal/modfetch/coderepo_test.go index 4977814c5f..663324b3dd 100644 --- a/src/cmd/go/internal/modfetch/coderepo_test.go +++ b/src/cmd/go/internal/modfetch/coderepo_test.go @@ -338,10 +338,10 @@ var codeRepoTests = []codeRepoTest{ vcs: "git", path: "gopkg.in/yaml.v2", rev: "v2", - version: "v2.2.3", - name: "bb4e33bf68bf89cad44d386192cbed201f35b241", - short: "bb4e33bf68bf", - time: time.Date(2019, 9, 30, 19, 9, 21, 0, time.UTC), + version: "v2.2.5-0.20191002202810-970885f01c8b", + name: "970885f01c8bc1fecb7ab1c8ce8e7609bda45530", + short: "970885f01c8b", + time: time.Date(2019, 10, 2, 20, 28, 10, 0, time.UTC), gomod: "module \"gopkg.in/yaml.v2\"\n\nrequire (\n\t\"gopkg.in/check.v1\" v0.0.0-20161208181325-20d25e280405\n)\n", }, { -- cgit v1.3 From 9e6a84f2b126cfe15eaa57b86b0d074a018dbef4 Mon Sep 17 00:00:00 2001 From: Jeremy Faller Date: Fri, 20 Sep 2019 14:02:24 -0400 Subject: cmd/compile: walk the progs to generate debug_lines MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Rather than use the pcln tables, walk progs while generating debug_lines. This code slightly increases the number of is_stmt toggles in the debug information due to a previous bug in how the pcline walking worked. (Previous versions of the line walking code wouldn't return the old_value, instead returning 0. This behavior might lose is_stmt toggles in the line table.) We suspected there would be a speedup with this change, but benchmarking hasn't shown this to be true (but has been noisy enough to not really show any large differences either way). These benchmarks are comparing non-prog walking code with this prog-walking code: name old time/op new time/op delta Template 321ms ± 4% 316ms ± 3% ~ (p=0.165 n=10+10) Unicode 146ms ± 5% 142ms ± 4% ~ (p=0.063 n=10+10) GoTypes 1.06s ± 2% 1.07s ± 2% ~ (p=0.280 n=10+10) Compiler 4.07s ± 1% 4.06s ± 1% ~ (p=0.549 n=10+9) SSA 12.6s ± 2% 12.7s ± 2% +1.27% (p=0.019 n=10+10) Flate 201ms ± 7% 202ms ± 4% ~ (p=0.436 n=10+10) GoParser 248ms ± 4% 250ms ± 2% ~ (p=0.356 n=9+10) Reflect 679ms ± 5% 678ms ± 4% ~ (p=0.971 n=10+10) Tar 281ms ± 2% 283ms ± 3% ~ (p=0.222 n=9+9) XML 381ms ± 3% 384ms ± 5% ~ (p=0.393 n=10+10) LinkCompiler 1.08s ± 2% 1.10s ± 2% +1.89% (p=0.009 n=10+10) ExternalLinkCompiler 2.23s ± 4% 2.23s ± 1% ~ (p=1.000 n=10+8) LinkWithoutDebugCompiler 654ms ± 4% 673ms ± 4% +2.94% (p=0.019 n=10+10) StdCmd 13.6s ± 2% 13.9s ± 1% +2.00% (p=0.000 n=10+10) name old user-time/op new user-time/op delta Template 582ms ±11% 575ms ±14% ~ (p=0.631 n=10+10) Unicode 431ms ±24% 390ms ±38% ~ (p=0.315 n=10+10) GoTypes 2.47s ±11% 2.51s ± 4% ~ (p=0.280 n=10+10) Compiler 9.09s ± 3% 9.04s ± 5% ~ (p=0.684 n=10+10) SSA 25.8s ± 4% 26.0s ± 3% ~ (p=0.529 n=10+10) Flate 318ms ±14% 322ms ±13% ~ (p=0.912 n=10+10) GoParser 386ms ± 6% 386ms ± 5% ~ (p=0.888 n=9+8) Reflect 1.42s ±20% 1.32s ±24% ~ (p=0.393 n=10+10) Tar 476ms ±19% 471ms ±25% ~ (p=1.000 n=10+10) XML 681ms ±25% 745ms ±21% ~ (p=0.143 n=10+10) LinkCompiler 1.75s ±13% 1.86s ±12% ~ (p=0.075 n=10+10) ExternalLinkCompiler 2.98s ±18% 3.41s ±13% +14.48% (p=0.003 n=10+10) LinkWithoutDebugCompiler 1.05s ±12% 1.08s ±16% ~ (p=0.739 n=10+10) name old alloc/op new alloc/op delta Template 36.4MB ± 0% 36.4MB ± 0% -0.11% (p=0.000 n=10+10) Unicode 28.6MB ± 0% 28.5MB ± 0% -0.06% (p=0.029 n=10+10) GoTypes 121MB ± 0% 121MB ± 0% -0.09% (p=0.000 n=9+9) Compiler 548MB ± 0% 547MB ± 0% -0.10% (p=0.000 n=10+10) SSA 1.87GB ± 0% 1.87GB ± 0% -0.13% (p=0.000 n=10+10) Flate 23.0MB ± 0% 22.9MB ± 0% -0.09% (p=0.000 n=9+10) GoParser 27.9MB ± 0% 27.8MB ± 0% -0.12% (p=0.000 n=10+10) Reflect 77.7MB ± 0% 77.6MB ± 0% -0.12% (p=0.000 n=8+10) Tar 34.5MB ± 0% 34.5MB ± 0% -0.07% (p=0.003 n=10+10) XML 44.4MB ± 0% 44.4MB ± 0% -0.07% (p=0.000 n=10+10) LinkCompiler 236MB ± 0% 240MB ± 0% +1.72% (p=0.000 n=10+10) ExternalLinkCompiler 246MB ± 0% 254MB ± 0% +3.02% (p=0.000 n=10+10) LinkWithoutDebugCompiler 159MB ± 0% 164MB ± 0% +3.35% (p=0.000 n=10+10) name old allocs/op new allocs/op delta Template 372k ± 0% 371k ± 0% -0.23% (p=0.000 n=10+10) Unicode 340k ± 0% 340k ± 0% -0.05% (p=0.000 n=10+10) GoTypes 1.33M ± 0% 1.32M ± 0% -0.20% (p=0.000 n=9+10) Compiler 5.37M ± 0% 5.36M ± 0% -0.17% (p=0.000 n=10+10) SSA 17.9M ± 0% 17.9M ± 0% -0.15% (p=0.000 n=10+10) Flate 234k ± 0% 233k ± 0% -0.24% (p=0.000 n=9+10) GoParser 309k ± 0% 309k ± 0% -0.21% (p=0.000 n=10+10) Reflect 969k ± 0% 966k ± 0% -0.30% (p=0.000 n=9+10) Tar 348k ± 0% 347k ± 0% -0.22% (p=0.000 n=10+9) XML 426k ± 0% 425k ± 0% -0.15% (p=0.000 n=9+10) LinkCompiler 638k ± 0% 637k ± 0% -0.07% (p=0.000 n=10+10) ExternalLinkCompiler 1.69M ± 0% 1.69M ± 0% -0.05% (p=0.000 n=10+10) LinkWithoutDebugCompiler 222k ± 0% 221k ± 0% -0.03% (p=0.007 n=10+9) name old object-bytes new object-bytes delta Template 559kB ± 0% 560kB ± 0% +0.23% (p=0.000 n=10+10) Unicode 216kB ± 0% 216kB ± 0% +0.01% (p=0.000 n=10+10) GoTypes 2.03MB ± 0% 2.04MB ± 0% +0.31% (p=0.000 n=10+10) Compiler 8.07MB ± 0% 8.10MB ± 0% +0.35% (p=0.000 n=10+10) SSA 27.1MB ± 0% 27.3MB ± 0% +0.72% (p=0.000 n=10+10) Flate 343kB ± 0% 344kB ± 0% +0.22% (p=0.000 n=10+10) GoParser 441kB ± 0% 442kB ± 0% +0.34% (p=0.000 n=10+10) Reflect 1.36MB ± 0% 1.36MB ± 0% +0.23% (p=0.000 n=10+10) Tar 487kB ± 0% 488kB ± 0% +0.21% (p=0.000 n=10+10) XML 632kB ± 0% 634kB ± 0% +0.35% (p=0.000 n=10+10) name old export-bytes new export-bytes delta Template 18.5kB ± 0% 18.5kB ± 0% ~ (all equal) Unicode 7.92kB ± 0% 7.92kB ± 0% ~ (all equal) GoTypes 35.0kB ± 0% 35.0kB ± 0% ~ (all equal) Compiler 109kB ± 0% 109kB ± 0% +0.00% (p=0.000 n=10+10) SSA 137kB ± 0% 137kB ± 0% +0.00% (p=0.000 n=10+10) Flate 4.89kB ± 0% 4.89kB ± 0% ~ (all equal) GoParser 8.49kB ± 0% 8.49kB ± 0% ~ (all equal) Reflect 11.4kB ± 0% 11.4kB ± 0% ~ (all equal) Tar 10.5kB ± 0% 10.5kB ± 0% ~ (all equal) XML 16.7kB ± 0% 16.7kB ± 0% ~ (all equal) name old text-bytes new text-bytes delta HelloSize 760kB ± 0% 760kB ± 0% ~ (all equal) CmdGoSize 10.8MB ± 0% 10.8MB ± 0% ~ (all equal) name old data-bytes new data-bytes delta HelloSize 10.7kB ± 0% 10.7kB ± 0% ~ (all equal) CmdGoSize 312kB ± 0% 312kB ± 0% ~ (all equal) name old bss-bytes new bss-bytes delta HelloSize 122kB ± 0% 122kB ± 0% ~ (all equal) CmdGoSize 146kB ± 0% 146kB ± 0% ~ (all equal) name old exe-bytes new exe-bytes delta HelloSize 1.13MB ± 0% 1.13MB ± 0% ~ (all equal) CmdGoSize 15.0MB ± 0% 15.1MB ± 0% +0.22% (p=0.000 n=10+10) Change-Id: If6e0982cd1398062a88e6c0c7513e141f9503531 Reviewed-on: https://go-review.googlesource.com/c/go/+/196661 Run-TryBot: Jeremy Faller TryBot-Result: Gobot Gobot Reviewed-by: David Chase --- src/cmd/internal/obj/dwarf.go | 117 +++++++++++++----------------------------- src/cmd/internal/obj/pcln.go | 29 ----------- 2 files changed, 37 insertions(+), 109 deletions(-) (limited to 'src') diff --git a/src/cmd/internal/obj/dwarf.go b/src/cmd/internal/obj/dwarf.go index d8f3de3b69..5efafe11b8 100644 --- a/src/cmd/internal/obj/dwarf.go +++ b/src/cmd/internal/obj/dwarf.go @@ -8,6 +8,7 @@ package obj import ( "cmd/internal/dwarf" + "cmd/internal/src" "fmt" ) @@ -31,95 +32,51 @@ const ( func (ctxt *Link) generateDebugLinesSymbol(s, lines *LSym) { dctxt := dwCtxt{ctxt} - // The Pcfile table is used to generate the debug_lines section, and the file - // indices for that data could differ from the files we write out for the - // debug_lines section. Here we generate a LUT between those two indices. - fileNums := make(map[int32]int64) - for i, filename := range s.Func.Pcln.File { - if symbolIndex := ctxt.PosTable.FileIndex(filename); symbolIndex >= 0 { - fileNums[int32(i)] = int64(symbolIndex) + 1 - } else { - panic(fmt.Sprintf("First time we've seen filename: %q", filename)) - } - } - // Set up the debug_lines state machine. // NB: This state machine is reset to this state when we've finished // generating the line table. See below. // TODO: Once delve can support multiple DW_LNS_end_statements, we don't have // to do this. - is_stmt := uint8(1) + stmt := true + line := int64(1) pc := s.Func.Text.Pc - line := 1 - file := 1 - - // The linker will insert the DW_LNE_set_address once determined; therefore, - // it's omitted here. - - // Generate the actual line information. - // We use the pcline and pcfile to generate this section, and it's suboptimal. - // Likely better would be to generate this dirrectly from the progs and not - // parse those tables. - // TODO: Generate from the progs if it's faster. - pcfile := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) - pcline := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) - pcstmt := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) - pcfile.Init(s.Func.Pcln.Pcfile.P) - pcline.Init(s.Func.Pcln.Pcline.P) - var pctostmtData Pcdata - funcpctab(ctxt, &pctostmtData, s, "pctostmt", pctostmt, nil) - pcstmt.Init(pctostmtData.P) - var thispc uint32 - - for !pcfile.Done && !pcline.Done { - // Only changed if it advanced - if int32(file) != pcfile.Value { - dctxt.AddUint8(lines, dwarf.DW_LNS_set_file) - dwarf.Uleb128put(dctxt, lines, fileNums[pcfile.Value]) - file = int(pcfile.Value) + name := "" + prologue, wrotePrologue := false, false + + // Walk the progs, generating the DWARF table. + for p := s.Func.Text; p != nil; p = p.Link { + prologue = prologue || (p.Pos.Xlogue() == src.PosPrologueEnd) + // If we're not at a real instruction, keep looping! + if p.Pos.Line() == 0 || (p.Link != nil && p.Link.Pc == pc) { + continue } + newStmt := p.Pos.IsStmt() != src.PosNotStmt + newName, newLine := linkgetlineFromPos(ctxt, p.Pos) - // Only changed if it advanced - if is_stmt != uint8(pcstmt.Value) { - new_stmt := uint8(pcstmt.Value) - switch new_stmt &^ 1 { - case PrologueEnd: - dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_set_prologue_end)) - case EpilogueBegin: - // TODO if there is a use for this, add it. - // Don't forget to increase OPCODE_BASE by 1 and add entry for standard_opcode_lengths[11] - panic("unsupported EpilogueBegin") - } - new_stmt &= 1 - if is_stmt != new_stmt { - is_stmt = new_stmt - dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_negate_stmt)) - } + // Output debug info. + wrote := false + if name != newName { + newFile := ctxt.PosTable.FileIndex(newName) + 1 // 1 indexing for the table. + dctxt.AddUint8(lines, dwarf.DW_LNS_set_file) + dwarf.Uleb128put(dctxt, lines, int64(newFile)) + name = newName + wrote = true } - - // putpcldelta makes a row in the DWARF matrix, always, even if line is unchanged. - putpclcdelta(ctxt, dctxt, lines, uint64(s.Func.Text.Pc+int64(thispc)-pc), int64(pcline.Value)-int64(line)) - - pc = s.Func.Text.Pc + int64(thispc) - line = int(pcline.Value) - - // Take the minimum step forward for the three iterators - thispc = pcfile.NextPC - if pcline.NextPC < thispc { - thispc = pcline.NextPC + if prologue && !wrotePrologue { + dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_set_prologue_end)) + wrotePrologue = true + wrote = true } - if !pcstmt.Done && pcstmt.NextPC < thispc { - thispc = pcstmt.NextPC + if stmt != newStmt { + dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_negate_stmt)) + stmt = newStmt + wrote = true } - if pcfile.NextPC == thispc { - pcfile.Next() - } - if !pcstmt.Done && pcstmt.NextPC == thispc { - pcstmt.Next() - } - if pcline.NextPC == thispc { - pcline.Next() + if line != int64(newLine) || wrote { + pcdelta := (p.Pc - pc) / int64(ctxt.Arch.MinLC) + putpclcdelta(ctxt, dctxt, lines, uint64(pcdelta), int64(newLine)-line) + line, pc = int64(newLine), p.Pc } } @@ -129,16 +86,16 @@ func (ctxt *Link) generateDebugLinesSymbol(s, lines *LSym) { // file = 1 // line = 1 // column = 0 - // is_stmt = set in header, we assume true + // stmt = set in header, we assume true // basic_block = false // Careful readers of the DWARF specification will note that we don't reset // the address of the state machine -- but this will happen at the beginning - // of the NEXT block of opcodes. (See the SetAddress call above.) + // of the NEXT block of opcodes. dctxt.AddUint8(lines, dwarf.DW_LNS_set_file) dwarf.Uleb128put(dctxt, lines, 1) dctxt.AddUint8(lines, dwarf.DW_LNS_advance_line) dwarf.Sleb128put(dctxt, lines, int64(1-line)) - if is_stmt != 1 { + if !stmt { dctxt.AddUint8(lines, dwarf.DW_LNS_negate_stmt) } dctxt.AddUint8(lines, dwarf.DW_LNS_copy) diff --git a/src/cmd/internal/obj/pcln.go b/src/cmd/internal/obj/pcln.go index ca1eda8d1e..c47897a263 100644 --- a/src/cmd/internal/obj/pcln.go +++ b/src/cmd/internal/obj/pcln.go @@ -5,7 +5,6 @@ package obj import ( - "cmd/internal/src" "encoding/binary" "log" ) @@ -249,34 +248,6 @@ func pctospadj(ctxt *Link, sym *LSym, oldval int32, p *Prog, phase int32, arg in return oldval + p.Spadj } -// pctostmt returns either, -// if phase==0, then whether the current instruction is a step-target (Dwarf is_stmt) -// bit-or'd with whether the current statement is a prologue end or epilogue begin -// else (phase == 1), zero. -// -func pctostmt(ctxt *Link, sym *LSym, oldval int32, p *Prog, phase int32, arg interface{}) int32 { - if phase == 1 { - return 0 // Ignored; also different from initial value of -1, if that ever matters. - } - s := p.Pos.IsStmt() - l := p.Pos.Xlogue() - - var is_stmt int32 - - // PrologueEnd, at least, is passed to the next instruction - switch l { - case src.PosPrologueEnd: - is_stmt = PrologueEnd - case src.PosEpilogueBegin: - is_stmt = EpilogueBegin - } - - if s != src.PosNotStmt { - is_stmt |= 1 // either PosDefaultStmt from asm, or PosIsStmt from go - } - return is_stmt -} - // pctopcdata computes the pcdata value in effect at p. // A PCDATA instruction sets the value in effect at future // non-PCDATA instructions. -- cgit v1.3 From 6b85fa80519615ae5fd58154277b47d77e5cf08b Mon Sep 17 00:00:00 2001 From: "Jason A. Donenfeld" Date: Wed, 2 Oct 2019 10:05:46 +0200 Subject: runtime: iterate ms via allm linked list to avoid race It's pointless to reach all ms via allgs, and doing so introduces a race, since the m member of a g can change underneath it. Instead iterate directly through the allm linked list. Updates: #31528 Updates: #34130 Change-Id: I34b88402b44339b0a5b4cd76eafd0ce6e43e2be1 Reviewed-on: https://go-review.googlesource.com/c/go/+/198417 Run-TryBot: Jason A. Donenfeld Reviewed-by: Alex Brainman Reviewed-by: Austin Clements TryBot-Result: Gobot Gobot --- src/runtime/os_windows.go | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/runtime/os_windows.go b/src/runtime/os_windows.go index 567c567000..34d0627fcb 100644 --- a/src/runtime/os_windows.go +++ b/src/runtime/os_windows.go @@ -277,13 +277,11 @@ func monitorSuspendResume() { return // Running on Windows 7, where we don't need it anyway. } var fn interface{} = func(context uintptr, changeType uint32, setting uintptr) uintptr { - lock(&allglock) - for _, gp := range allgs { - if gp.m != nil && gp.m.resumesema != 0 { - stdcall1(_SetEvent, gp.m.resumesema) + for mp := (*m)(atomic.Loadp(unsafe.Pointer(&allm))); mp != nil; mp = mp.alllink { + if mp.resumesema != 0 { + stdcall1(_SetEvent, mp.resumesema) } } - unlock(&allglock) return 0 } params := _DEVICE_NOTIFY_SUBSCRIBE_PARAMETERS{ -- cgit v1.3 From c33d45a898ab1d966faba33d18acdffefb0fae0d Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Thu, 3 Oct 2019 10:49:28 -0700 Subject: cmd/compile: don't statically copy string-typed variables During package initialization, the compiler tries to optimize: var A = "foo" var B = A into var A = "foo" var B = "foo" so that we can statically initialize both A and B and skip emitting dynamic initialization code to assign "B = A". However, this isn't safe in the presence of cmd/link's -X flag, which might overwrite an initialized string-typed variable at link time. In particular, if cmd/link changes A's static initialization, it won't know it also needs to change B's static initialization. To address this, this CL disables this optimization for string-typed variables. Fixes #34675. Change-Id: I1c18f3b855f6d7114aeb39f96aaaf1b452b88236 Reviewed-on: https://go-review.googlesource.com/c/go/+/198657 Run-TryBot: Matthew Dempsky Reviewed-by: Cuong Manh Le Reviewed-by: Brad Fitzpatrick TryBot-Result: Gobot Gobot --- src/cmd/compile/internal/gc/sinit.go | 3 +++ test/linkx.go | 9 +++++++++ test/linkx_run.go | 2 +- 3 files changed, 13 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/sinit.go b/src/cmd/compile/internal/gc/sinit.go index ae16d41b1c..a6d13d1ac5 100644 --- a/src/cmd/compile/internal/gc/sinit.go +++ b/src/cmd/compile/internal/gc/sinit.go @@ -83,6 +83,9 @@ func (s *InitSchedule) staticcopy(l *Node, r *Node) bool { if r.Name.Defn.Op != OAS { return false } + if r.Type.IsString() { // perhaps overwritten by cmd/link -X (#34675) + return false + } orig := r r = r.Name.Defn.Right diff --git a/test/linkx.go b/test/linkx.go index 20b8c773d8..520a065182 100644 --- a/test/linkx.go +++ b/test/linkx.go @@ -14,10 +14,19 @@ import "fmt" var tbd string var overwrite string = "dibs" +var tbdcopy = tbd +var overwritecopy = overwrite +var arraycopy = [2]string{tbd, overwrite} + var b bool var x int func main() { fmt.Println(tbd) + fmt.Println(tbdcopy) + fmt.Println(arraycopy[0]) + fmt.Println(overwrite) + fmt.Println(overwritecopy) + fmt.Println(arraycopy[1]) } diff --git a/test/linkx_run.go b/test/linkx_run.go index ca9d31612a..f25053bf28 100644 --- a/test/linkx_run.go +++ b/test/linkx_run.go @@ -36,7 +36,7 @@ func test(sep string) { os.Exit(1) } - want := "hello\ntrumped\n" + want := "hello\nhello\nhello\ntrumped\ntrumped\ntrumped\n" got := out.String() if got != want { fmt.Printf("got %q want %q\n", got, want) -- cgit v1.3 From 5fe3b49a0540aacf685273a43b0fb31b44cf5dd6 Mon Sep 17 00:00:00 2001 From: "Bryan C. Mills" Date: Thu, 3 Oct 2019 18:07:53 +0000 Subject: Revert "cmd/compile: walk the progs to generate debug_lines" This reverts CL 196661. Reason for revert: broke TestGdb* tests on mips64le, ppc64le, and s390x builders. Change-Id: I3b5c97c840819a0d407b943f7cf7e2d97f06042d Reviewed-on: https://go-review.googlesource.com/c/go/+/198697 Run-TryBot: Bryan C. Mills Reviewed-by: Brad Fitzpatrick TryBot-Result: Gobot Gobot --- src/cmd/internal/obj/dwarf.go | 117 +++++++++++++++++++++++++++++------------- src/cmd/internal/obj/pcln.go | 29 +++++++++++ 2 files changed, 109 insertions(+), 37 deletions(-) (limited to 'src') diff --git a/src/cmd/internal/obj/dwarf.go b/src/cmd/internal/obj/dwarf.go index 5efafe11b8..d8f3de3b69 100644 --- a/src/cmd/internal/obj/dwarf.go +++ b/src/cmd/internal/obj/dwarf.go @@ -8,7 +8,6 @@ package obj import ( "cmd/internal/dwarf" - "cmd/internal/src" "fmt" ) @@ -32,51 +31,95 @@ const ( func (ctxt *Link) generateDebugLinesSymbol(s, lines *LSym) { dctxt := dwCtxt{ctxt} + // The Pcfile table is used to generate the debug_lines section, and the file + // indices for that data could differ from the files we write out for the + // debug_lines section. Here we generate a LUT between those two indices. + fileNums := make(map[int32]int64) + for i, filename := range s.Func.Pcln.File { + if symbolIndex := ctxt.PosTable.FileIndex(filename); symbolIndex >= 0 { + fileNums[int32(i)] = int64(symbolIndex) + 1 + } else { + panic(fmt.Sprintf("First time we've seen filename: %q", filename)) + } + } + // Set up the debug_lines state machine. // NB: This state machine is reset to this state when we've finished // generating the line table. See below. // TODO: Once delve can support multiple DW_LNS_end_statements, we don't have // to do this. - stmt := true - line := int64(1) + is_stmt := uint8(1) pc := s.Func.Text.Pc - name := "" - prologue, wrotePrologue := false, false - - // Walk the progs, generating the DWARF table. - for p := s.Func.Text; p != nil; p = p.Link { - prologue = prologue || (p.Pos.Xlogue() == src.PosPrologueEnd) - // If we're not at a real instruction, keep looping! - if p.Pos.Line() == 0 || (p.Link != nil && p.Link.Pc == pc) { - continue - } - newStmt := p.Pos.IsStmt() != src.PosNotStmt - newName, newLine := linkgetlineFromPos(ctxt, p.Pos) + line := 1 + file := 1 + + // The linker will insert the DW_LNE_set_address once determined; therefore, + // it's omitted here. - // Output debug info. - wrote := false - if name != newName { - newFile := ctxt.PosTable.FileIndex(newName) + 1 // 1 indexing for the table. + // Generate the actual line information. + // We use the pcline and pcfile to generate this section, and it's suboptimal. + // Likely better would be to generate this dirrectly from the progs and not + // parse those tables. + // TODO: Generate from the progs if it's faster. + pcfile := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) + pcline := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) + pcstmt := NewPCIter(uint32(ctxt.Arch.Arch.MinLC)) + pcfile.Init(s.Func.Pcln.Pcfile.P) + pcline.Init(s.Func.Pcln.Pcline.P) + var pctostmtData Pcdata + funcpctab(ctxt, &pctostmtData, s, "pctostmt", pctostmt, nil) + pcstmt.Init(pctostmtData.P) + var thispc uint32 + + for !pcfile.Done && !pcline.Done { + // Only changed if it advanced + if int32(file) != pcfile.Value { dctxt.AddUint8(lines, dwarf.DW_LNS_set_file) - dwarf.Uleb128put(dctxt, lines, int64(newFile)) - name = newName - wrote = true + dwarf.Uleb128put(dctxt, lines, fileNums[pcfile.Value]) + file = int(pcfile.Value) + } + + // Only changed if it advanced + if is_stmt != uint8(pcstmt.Value) { + new_stmt := uint8(pcstmt.Value) + switch new_stmt &^ 1 { + case PrologueEnd: + dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_set_prologue_end)) + case EpilogueBegin: + // TODO if there is a use for this, add it. + // Don't forget to increase OPCODE_BASE by 1 and add entry for standard_opcode_lengths[11] + panic("unsupported EpilogueBegin") + } + new_stmt &= 1 + if is_stmt != new_stmt { + is_stmt = new_stmt + dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_negate_stmt)) + } } - if prologue && !wrotePrologue { - dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_set_prologue_end)) - wrotePrologue = true - wrote = true + + // putpcldelta makes a row in the DWARF matrix, always, even if line is unchanged. + putpclcdelta(ctxt, dctxt, lines, uint64(s.Func.Text.Pc+int64(thispc)-pc), int64(pcline.Value)-int64(line)) + + pc = s.Func.Text.Pc + int64(thispc) + line = int(pcline.Value) + + // Take the minimum step forward for the three iterators + thispc = pcfile.NextPC + if pcline.NextPC < thispc { + thispc = pcline.NextPC } - if stmt != newStmt { - dctxt.AddUint8(lines, uint8(dwarf.DW_LNS_negate_stmt)) - stmt = newStmt - wrote = true + if !pcstmt.Done && pcstmt.NextPC < thispc { + thispc = pcstmt.NextPC } - if line != int64(newLine) || wrote { - pcdelta := (p.Pc - pc) / int64(ctxt.Arch.MinLC) - putpclcdelta(ctxt, dctxt, lines, uint64(pcdelta), int64(newLine)-line) - line, pc = int64(newLine), p.Pc + if pcfile.NextPC == thispc { + pcfile.Next() + } + if !pcstmt.Done && pcstmt.NextPC == thispc { + pcstmt.Next() + } + if pcline.NextPC == thispc { + pcline.Next() } } @@ -86,16 +129,16 @@ func (ctxt *Link) generateDebugLinesSymbol(s, lines *LSym) { // file = 1 // line = 1 // column = 0 - // stmt = set in header, we assume true + // is_stmt = set in header, we assume true // basic_block = false // Careful readers of the DWARF specification will note that we don't reset // the address of the state machine -- but this will happen at the beginning - // of the NEXT block of opcodes. + // of the NEXT block of opcodes. (See the SetAddress call above.) dctxt.AddUint8(lines, dwarf.DW_LNS_set_file) dwarf.Uleb128put(dctxt, lines, 1) dctxt.AddUint8(lines, dwarf.DW_LNS_advance_line) dwarf.Sleb128put(dctxt, lines, int64(1-line)) - if !stmt { + if is_stmt != 1 { dctxt.AddUint8(lines, dwarf.DW_LNS_negate_stmt) } dctxt.AddUint8(lines, dwarf.DW_LNS_copy) diff --git a/src/cmd/internal/obj/pcln.go b/src/cmd/internal/obj/pcln.go index c47897a263..ca1eda8d1e 100644 --- a/src/cmd/internal/obj/pcln.go +++ b/src/cmd/internal/obj/pcln.go @@ -5,6 +5,7 @@ package obj import ( + "cmd/internal/src" "encoding/binary" "log" ) @@ -248,6 +249,34 @@ func pctospadj(ctxt *Link, sym *LSym, oldval int32, p *Prog, phase int32, arg in return oldval + p.Spadj } +// pctostmt returns either, +// if phase==0, then whether the current instruction is a step-target (Dwarf is_stmt) +// bit-or'd with whether the current statement is a prologue end or epilogue begin +// else (phase == 1), zero. +// +func pctostmt(ctxt *Link, sym *LSym, oldval int32, p *Prog, phase int32, arg interface{}) int32 { + if phase == 1 { + return 0 // Ignored; also different from initial value of -1, if that ever matters. + } + s := p.Pos.IsStmt() + l := p.Pos.Xlogue() + + var is_stmt int32 + + // PrologueEnd, at least, is passed to the next instruction + switch l { + case src.PosPrologueEnd: + is_stmt = PrologueEnd + case src.PosEpilogueBegin: + is_stmt = EpilogueBegin + } + + if s != src.PosNotStmt { + is_stmt |= 1 // either PosDefaultStmt from asm, or PosIsStmt from go + } + return is_stmt +} + // pctopcdata computes the pcdata value in effect at p. // A PCDATA instruction sets the value in effect at future // non-PCDATA instructions. -- cgit v1.3 From 2bf7a925712dca5646f9215cda17c5b61eea14ce Mon Sep 17 00:00:00 2001 From: Meng Zhuo Date: Wed, 2 Oct 2019 11:50:34 +0800 Subject: cmd/asm: add VLD[1-4]R vector instructions on arm64 This change adds VLD1R, VLD2R, VLD3R, VLD4R Change-Id: Ie19e9ae02fdfc94b9344acde8c9938849efb0bf0 Reviewed-on: https://go-review.googlesource.com/c/go/+/181697 Run-TryBot: Cherry Zhang TryBot-Result: Gobot Gobot Reviewed-by: Cherry Zhang --- src/cmd/asm/internal/asm/testdata/arm64.s | 12 +++++++ src/cmd/internal/obj/arm64/a.out.go | 4 +++ src/cmd/internal/obj/arm64/anames.go | 4 +++ src/cmd/internal/obj/arm64/asm7.go | 52 ++++++++++++++++++++----------- 4 files changed, 53 insertions(+), 19 deletions(-) (limited to 'src') diff --git a/src/cmd/asm/internal/asm/testdata/arm64.s b/src/cmd/asm/internal/asm/testdata/arm64.s index 9f19ff1e8d..93f70045b7 100644 --- a/src/cmd/asm/internal/asm/testdata/arm64.s +++ b/src/cmd/asm/internal/asm/testdata/arm64.s @@ -352,6 +352,18 @@ TEXT foo(SB), DUPOK|NOSPLIT, $-8 VLD4 (R15), [V10.H4, V11.H4, V12.H4, V13.H4] // ea05400c VLD4.P 32(R24), [V31.B8, V0.B8, V1.B8, V2.B8] // 1f03df0c VLD4.P (R13)(R9), [V14.S2, V15.S2, V16.S2, V17.S2] // VLD4.P (R13)(R9*1), [V14.S2,V15.S2,V16.S2,V17.S2] // ae09c90c + VLD1R (R0), [V0.B16] // 00c0404d + VLD1R.P 16(R0), [V0.B16] // 00c0df4d + VLD1R.P (R15)(R1), [V15.H4] // VLD1R.P (R15)(R1*1), [V15.H4] // efc5c10d + VLD2R (R15), [V15.H4, V16.H4] // efc5600d + VLD2R.P 32(R0), [V0.D2, V1.D2] // 00ccff4d + VLD2R.P (R0)(R5), [V31.D1, V0.D1] // VLD2R.P (R0)(R5*1), [V31.D1, V0.D1] // 1fcce50d + VLD3R (RSP), [V31.S2, V0.S2, V1.S2] // ffeb400d + VLD3R.P 24(R15), [V15.H4, V16.H4, V17.H4] // efe5df0d + VLD3R.P (R15)(R6), [V15.H8, V16.H8, V17.H8] // VLD3R.P (R15)(R6*1), [V15.H8, V16.H8, V17.H8] // efe5c64d + VLD4R (R0), [V0.B8, V1.B8, V2.B8, V3.B8] // 00e0600d + VLD4R.P 64(RSP), [V31.S4, V0.S4, V1.S4, V2.S4] // ffebff4d + VLD4R.P (R15)(R9), [V15.H4, V16.H4, V17.H4, V18.H4] // VLD4R.P (R15)(R9*1), [V15.H4, V16.H4, V17.H4, V18.H4] // efe5e90d VST1.P [V24.S2], 8(R2) // 58789f0c VST1 [V29.S2, V30.S2], (R29) // bdab000c VST1 [V14.H4, V15.H4, V16.H4], (R27) // 6e67000c diff --git a/src/cmd/internal/obj/arm64/a.out.go b/src/cmd/internal/obj/arm64/a.out.go index f793cdc4f9..4e5eb75a22 100644 --- a/src/cmd/internal/obj/arm64/a.out.go +++ b/src/cmd/internal/obj/arm64/a.out.go @@ -956,6 +956,10 @@ const ( AVLD2 AVLD3 AVLD4 + AVLD1R + AVLD2R + AVLD3R + AVLD4R AVORR AVREV32 AVREV64 diff --git a/src/cmd/internal/obj/arm64/anames.go b/src/cmd/internal/obj/arm64/anames.go index 621af6c195..2c277dfb95 100644 --- a/src/cmd/internal/obj/arm64/anames.go +++ b/src/cmd/internal/obj/arm64/anames.go @@ -463,6 +463,10 @@ var Anames = []string{ "VLD2", "VLD3", "VLD4", + "VLD1R", + "VLD2R", + "VLD3R", + "VLD4R", "VORR", "VREV32", "VREV64", diff --git a/src/cmd/internal/obj/arm64/asm7.go b/src/cmd/internal/obj/arm64/asm7.go index 47586ba262..c7fa943e7e 100644 --- a/src/cmd/internal/obj/arm64/asm7.go +++ b/src/cmd/internal/obj/arm64/asm7.go @@ -784,15 +784,9 @@ var optab = []Optab{ {AVLD1, C_ZOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, 0}, {AVLD1, C_LOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, {AVLD1, C_ROFF, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD2, C_ZOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, 0}, - {AVLD2, C_LOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD2, C_ROFF, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD3, C_ZOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, 0}, - {AVLD3, C_LOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD3, C_ROFF, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD4, C_ZOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, 0}, - {AVLD4, C_LOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, - {AVLD4, C_ROFF, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, + {AVLD1R, C_ZOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, 0}, + {AVLD1R, C_LOREG, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, + {AVLD1R, C_ROFF, C_NONE, C_NONE, C_LIST, 81, 4, 0, 0, C_XPOST}, {AVLD1, C_LOREG, C_NONE, C_NONE, C_ELEM, 97, 4, 0, 0, C_XPOST}, {AVLD1, C_ROFF, C_NONE, C_NONE, C_ELEM, 97, 4, 0, 0, C_XPOST}, {AVLD1, C_LOREG, C_NONE, C_NONE, C_ELEM, 97, 4, 0, 0, 0}, @@ -2709,13 +2703,18 @@ func buildop(ctxt *obj.Link) { case AVZIP1: oprangeset(AVZIP2, t) + case AVLD1R: + oprangeset(AVLD2, t) + oprangeset(AVLD2R, t) + oprangeset(AVLD3, t) + oprangeset(AVLD3R, t) + oprangeset(AVLD4, t) + oprangeset(AVLD4R, t) + case ASHA1H, AVCNT, AVMOV, AVLD1, - AVLD2, - AVLD3, - AVLD4, AVST1, AVST2, AVST3, @@ -2803,7 +2802,7 @@ func (c *ctxt7) checkindex(p *obj.Prog, index, maxindex int) { func (c *ctxt7) checkoffset(p *obj.Prog, as obj.As) { var offset, list, n, expect int64 switch as { - case AVLD1, AVLD2, AVLD3, AVLD4: + case AVLD1, AVLD2, AVLD3, AVLD4, AVLD1R, AVLD2R, AVLD3R, AVLD4R: offset = p.From.Offset list = p.To.Offset case AVST1, AVST2, AVST3, AVST4: @@ -2836,11 +2835,13 @@ func (c *ctxt7) checkoffset(p *obj.Prog, as obj.As) { switch as { case AVLD1, AVST1: return - case AVLD2, AVST2: + case AVLD1R: + expect = 1 + case AVLD2, AVST2, AVLD2R: expect = 2 - case AVLD3, AVST3: + case AVLD3, AVST3, AVLD3R: expect = 3 - case AVLD4, AVST4: + case AVLD4, AVST4, AVLD4R: expect = 4 } @@ -4344,10 +4345,10 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) { } o1 |= (uint32(imm5&0x1f) << 16) | (uint32(rf&31) << 5) | uint32(rt&31) - case 81: /* vld[1-4] (Rn), [Vt1., Vt2., ...] */ + case 81: /* vld[1-4]|vld[1-4]r (Rn), [Vt1., Vt2., ...] */ c.checkoffset(p, p.As) r := int(p.From.Reg) - o1 = 3<<26 | 1<<22 + o1 = c.oprrr(p, p.As) if o.scond == C_XPOST { o1 |= 1 << 23 if p.From.Index == 0 { @@ -4358,7 +4359,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) { if isRegShiftOrExt(&p.From) { c.ctxt.Diag("invalid extended register op: %v\n", p) } - o1 |= uint32(p.From.Index&31) << 16 + o1 |= uint32(p.From.Index&0x1f) << 16 } } o1 |= uint32(p.To.Offset) @@ -5591,6 +5592,15 @@ func (c *ctxt7) oprrr(p *obj.Prog, a obj.As) uint32 { case AVRBIT: return 0x2E<<24 | 1<<22 | 0x10<<17 | 5<<12 | 2<<10 + + case AVLD1, AVLD2, AVLD3, AVLD4: + return 3<<26 | 1<<22 + + case AVLD1R, AVLD3R: + return 0xD<<24 | 1<<22 + + case AVLD2R, AVLD4R: + return 0xD<<24 | 3<<21 } c.ctxt.Diag("%v: bad rrr %d %v", p, a, a) @@ -6779,6 +6789,10 @@ func (c *ctxt7) maskOpvldvst(p *obj.Prog, o1 uint32) uint32 { o1 &^= 0xf000 // mask out "opcode" field (bit 12-15) switch p.As { + case AVLD1R, AVLD2R: + o1 |= 0xC << 12 + case AVLD3R, AVLD4R: + o1 |= 0xE << 12 case AVLD2, AVST2: o1 |= 8 << 12 case AVLD3, AVST3: -- cgit v1.3 From a1b1ba7daf4d612cb08e98567d809a6f202498ce Mon Sep 17 00:00:00 2001 From: Meng Zhuo Date: Wed, 2 Oct 2019 16:06:25 +0800 Subject: internal/bytealg: (re)adding mips64x compare implementation MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The original CL of mips64x compare function has been reverted due to wrong implement for little endian. Original CL: https://go-review.googlesource.com/c/go/+/196837 name old time/op new time/op delta BytesCompare/1 28.9ns ± 4% 22.1ns ± 0% -23.60% (p=0.000 n=9+8) BytesCompare/2 34.6ns ± 0% 23.1ns ± 0% -33.25% (p=0.000 n=8+10) BytesCompare/4 54.6ns ± 0% 40.8ns ± 0% -25.27% (p=0.000 n=8+8) BytesCompare/8 73.9ns ± 0% 49.1ns ± 0% -33.56% (p=0.000 n=8+8) BytesCompare/16 113ns ± 0% 24ns ± 0% -79.20% (p=0.000 n=9+9) BytesCompare/32 190ns ± 0% 26ns ± 0% -86.53% (p=0.000 n=10+10) BytesCompare/64 345ns ± 0% 44ns ± 0% -87.19% (p=0.000 n=10+8) BytesCompare/128 654ns ± 0% 52ns ± 0% -91.97% (p=0.000 n=9+8) BytesCompare/256 1.27µs ± 0% 0.07µs ± 0% -94.14% (p=0.001 n=8+9) BytesCompare/512 2.51µs ± 0% 0.12µs ± 0% -95.26% (p=0.000 n=9+10) BytesCompare/1024 4.99µs ± 0% 0.21µs ± 0% -95.85% (p=0.000 n=8+10) BytesCompare/2048 9.94µs ± 0% 0.38µs ± 0% -96.14% (p=0.000 n=8+8) CompareBytesEqual 105ns ± 0% 64ns ± 0% -39.43% (p=0.000 n=10+9) CompareBytesToNil 34.8ns ± 1% 38.6ns ± 3% +11.01% (p=0.000 n=10+10) CompareBytesEmpty 33.6ns ± 3% 36.6ns ± 0% +8.77% (p=0.000 n=10+8) CompareBytesIdentical 29.7ns ± 0% 40.5ns ± 1% +36.45% (p=0.000 n=10+8) CompareBytesSameLength 69.1ns ± 0% 51.8ns ± 0% -25.04% (p=0.000 n=10+9) CompareBytesDifferentLength 69.8ns ± 0% 52.5ns ± 0% -24.79% (p=0.000 n=10+8) CompareBytesBigUnaligned 5.15ms ± 0% 2.19ms ± 0% -57.59% (p=0.000 n=9+9) CompareBytesBig 5.28ms ± 0% 0.28ms ± 0% -94.64% (p=0.000 n=8+8) CompareBytesBigIdentical 29.7ns ± 0% 36.9ns ± 2% +24.11% (p=0.000 n=8+10) name old speed new speed delta CompareBytesBigUnaligned 204MB/s ± 0% 480MB/s ± 0% +135.77% (p=0.000 n=9+9) CompareBytesBig 198MB/s ± 0% 3704MB/s ± 0% +1765.97% (p=0.000 n=8+8) CompareBytesBigIdentical 35.3TB/s ± 0% 28.4TB/s ± 2% -19.44% (p=0.000 n=8+10) Fixes #34549 Change-Id: I2ef29f13cdd4229745ac2d018bb53c76f2ff1209 Reviewed-on: https://go-review.googlesource.com/c/go/+/197557 Reviewed-by: Cherry Zhang Run-TryBot: Cherry Zhang TryBot-Result: Gobot Gobot --- src/internal/bytealg/compare_generic.go | 2 +- src/internal/bytealg/compare_mips64x.s | 88 +++++++++++++++++++++++++++++++++ src/internal/bytealg/compare_native.go | 2 +- 3 files changed, 90 insertions(+), 2 deletions(-) create mode 100644 src/internal/bytealg/compare_mips64x.s (limited to 'src') diff --git a/src/internal/bytealg/compare_generic.go b/src/internal/bytealg/compare_generic.go index 2ac60f3df9..4839df9528 100644 --- a/src/internal/bytealg/compare_generic.go +++ b/src/internal/bytealg/compare_generic.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// +build !386,!amd64,!amd64p32,!s390x,!arm,!arm64,!ppc64,!ppc64le,!mips,!mipsle,!wasm +// +build !386,!amd64,!amd64p32,!s390x,!arm,!arm64,!ppc64,!ppc64le,!mips,!mipsle,!wasm,!mips64,!mips64le package bytealg diff --git a/src/internal/bytealg/compare_mips64x.s b/src/internal/bytealg/compare_mips64x.s new file mode 100644 index 0000000000..4f05fceaca --- /dev/null +++ b/src/internal/bytealg/compare_mips64x.s @@ -0,0 +1,88 @@ +// Copyright 2019 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +// +build mips64 mips64le + +#include "go_asm.h" +#include "textflag.h" + +TEXT ·Compare(SB),NOSPLIT,$0-56 + MOVV a_base+0(FP), R3 + MOVV b_base+24(FP), R4 + MOVV a_len+8(FP), R1 + MOVV b_len+32(FP), R2 + MOVV $ret+48(FP), R9 + JMP cmpbody<>(SB) + +TEXT runtime·cmpstring(SB),NOSPLIT,$0-40 + MOVV a_base+0(FP), R3 + MOVV b_base+16(FP), R4 + MOVV a_len+8(FP), R1 + MOVV b_len+24(FP), R2 + MOVV $ret+32(FP), R9 + JMP cmpbody<>(SB) + +// On entry: +// R1 length of a +// R2 length of b +// R3 points to the start of a +// R4 points to the start of b +// R9 points to the return value (-1/0/1) +TEXT cmpbody<>(SB),NOSPLIT|NOFRAME,$0 + BEQ R3, R4, samebytes // same start of a and b + + SGTU R1, R2, R7 + BNE R0, R7, r2_lt_r1 + MOVV R1, R10 + JMP entry +r2_lt_r1: + MOVV R2, R10 // R10 is min(R1, R2) +entry: + ADDV R3, R10, R8 // R3 start of a, R8 end of a + BEQ R3, R8, samebytes // length is 0 + + SRLV $4, R10 // R10 is number of chunks + BEQ R0, R10, byte_loop + + // make sure both a and b are aligned. + OR R3, R4, R11 + AND $7, R11 + BNE R0, R11, byte_loop + +chunk16_loop: + BEQ R0, R10, byte_loop + MOVV (R3), R6 + MOVV (R4), R7 + BNE R6, R7, byte_loop + MOVV 8(R3), R13 + MOVV 8(R4), R14 + ADDV $16, R3 + ADDV $16, R4 + SUBVU $1, R10 + BEQ R13, R14, chunk16_loop + SUBV $8, R3 + SUBV $8, R4 + +byte_loop: + BEQ R3, R8, samebytes + MOVBU (R3), R6 + ADDVU $1, R3 + MOVBU (R4), R7 + ADDVU $1, R4 + BEQ R6, R7, byte_loop + +byte_cmp: + SGTU R6, R7, R8 // R8 = 1 if (R6 > R7) + BNE R0, R8, ret + MOVV $-1, R8 + JMP ret + +samebytes: + SGTU R1, R2, R6 + SGTU R2, R1, R7 + SUBV R7, R6, R8 + +ret: + MOVV R8, (R9) + RET diff --git a/src/internal/bytealg/compare_native.go b/src/internal/bytealg/compare_native.go index b14aa8c72c..95486e8542 100644 --- a/src/internal/bytealg/compare_native.go +++ b/src/internal/bytealg/compare_native.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// +build 386 amd64 amd64p32 s390x arm arm64 ppc64 ppc64le mips mipsle wasm +// +build 386 amd64 amd64p32 s390x arm arm64 ppc64 ppc64le mips mipsle wasm mips64 mips64le package bytealg -- cgit v1.3 From 3ad350820df8217b4d05c56923e533a196bace27 Mon Sep 17 00:00:00 2001 From: Matthew Dempsky Date: Thu, 3 Oct 2019 11:48:34 -0700 Subject: cmd/compile: change size diagnostic to use benchmark format Makes it easier to run go build -a -gcflags=-d=export std |& grep ^BenchmarkExportSize and get useful output for feeding into benchstat. Change-Id: I2b52e8f5ff33b7ccb6c25b18e464513344bd9ad9 Reviewed-on: https://go-review.googlesource.com/c/go/+/198698 Reviewed-by: Robert Griesemer --- src/cmd/compile/internal/gc/export.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/export.go b/src/cmd/compile/internal/gc/export.go index 31e6ab5b6d..44bea2b1fd 100644 --- a/src/cmd/compile/internal/gc/export.go +++ b/src/cmd/compile/internal/gc/export.go @@ -71,7 +71,7 @@ func dumpexport(bout *bio.Writer) { exportf(bout, "\n$$\n") if Debug_export != 0 { - fmt.Printf("export data size = %d bytes\n", size) + fmt.Printf("BenchmarkExportSize:%s 1 %d bytes\n", myimportpath, size) } } -- cgit v1.3 From f7f85bdc2c4a8a472a271a7d2333557ad6143eeb Mon Sep 17 00:00:00 2001 From: David Chase Date: Tue, 30 Jul 2019 16:23:55 -0400 Subject: cmd/compile: refine statement marking in numberlines 1) An empty block is treated as not-a-statement unless its line differs from at least one of its predecessors (it might make sense to rearrange branches in predecessors, but that is a different issue). 2) When iterating forward to choose a "good" place for a statement, actually check that the chosen place is in fact good. 3) Refactor same line and same file into methods on XPos and Pos. This reduces the failure rate of ssa/stmtlines_test by 7-ish lines. (And interacts favorably with later debugging CLs.) Change-Id: Idb7cca7068f6fc9fbfdbe25bc0da15bcfc7b9d4a Reviewed-on: https://go-review.googlesource.com/c/go/+/188217 Run-TryBot: David Chase Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/numberlines.go | 41 ++++++++++++++++++----------- src/cmd/internal/src/pos.go | 5 ++-- src/cmd/internal/src/xpos.go | 5 ++++ 3 files changed, 33 insertions(+), 18 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/numberlines.go b/src/cmd/compile/internal/ssa/numberlines.go index 4807da731c..a39e597d59 100644 --- a/src/cmd/compile/internal/ssa/numberlines.go +++ b/src/cmd/compile/internal/ssa/numberlines.go @@ -43,16 +43,20 @@ func nextGoodStatementIndex(v *Value, i int, b *Block) int { if i >= len(b.Values)-1 { return i } - // Only consider the likely-ephemeral/fragile opcodes expected to vanish in a rewrite. + // Skip the likely-ephemeral/fragile opcodes expected to vanish in a rewrite. if !isPoorStatementOp(v.Op) { return i } // Look ahead to see what the line number is on the next thing that could be a boundary. for j := i + 1; j < len(b.Values); j++ { - if b.Values[j].Pos.IsStmt() == src.PosNotStmt { // ignore non-statements + u := b.Values[j] + if u.Pos.IsStmt() == src.PosNotStmt { // ignore non-statements continue } - if b.Values[j].Pos.Line() == v.Pos.Line() && v.Pos.SameFile(b.Values[j].Pos) { + if u.Pos.SameFileAndLine(v.Pos) { + if isPoorStatementOp(u.Op) { + continue // Keep looking, this is also not a good statement op + } return j } return i @@ -156,18 +160,10 @@ func numberLines(f *Func) { } if firstPosIndex == -1 { // Effectively empty block, check block's own Pos, consider preds. - if b.Pos.IsStmt() != src.PosNotStmt { - b.Pos = b.Pos.WithIsStmt() - endlines[b.ID] = b.Pos - if f.pass.debug > 0 { - fmt.Printf("Mark stmt effectively-empty-block %s %s %s\n", f.Name, b, flc(b.Pos)) - } - continue - } line := src.NoXPos for _, p := range b.Preds { pbi := p.Block().ID - if endlines[pbi] != line { + if !endlines[pbi].SameFileAndLine(line) { if line == src.NoXPos { line = endlines[pbi] continue @@ -178,7 +174,20 @@ func numberLines(f *Func) { } } - endlines[b.ID] = line + // If the block has no statement itself and is effectively empty, tag it w/ predecessor(s) but not as a statement + if b.Pos.IsStmt() == src.PosNotStmt { + b.Pos = line + endlines[b.ID] = line + continue + } + // If the block differs from its predecessors, mark it as a statement + if line == src.NoXPos || !line.SameFileAndLine(b.Pos) { + b.Pos = b.Pos.WithIsStmt() + if f.pass.debug > 0 { + fmt.Printf("Mark stmt effectively-empty-block %s %s %s\n", f.Name, b, flc(b.Pos)) + } + } + endlines[b.ID] = b.Pos continue } // check predecessors for any difference; if firstPos differs, then it is a boundary. @@ -190,7 +199,7 @@ func numberLines(f *Func) { } else { // differing pred for _, p := range b.Preds { pbi := p.Block().ID - if endlines[pbi].Line() != firstPos.Line() || !endlines[pbi].SameFile(firstPos) { + if !endlines[pbi].SameFileAndLine(firstPos) { b.Values[firstPosIndex].Pos = firstPos.WithIsStmt() if f.pass.debug > 0 { fmt.Printf("Mark stmt differing-pred %s %s %s %s, different=%s ending %s\n", @@ -210,7 +219,7 @@ func numberLines(f *Func) { // skip ahead if possible i = nextGoodStatementIndex(v, i, b) v = b.Values[i] - if v.Pos.Line() != firstPos.Line() || !v.Pos.SameFile(firstPos) { + if !v.Pos.SameFileAndLine(firstPos) { if f.pass.debug > 0 { fmt.Printf("Mark stmt new line %s %s %s %s prev pos = %s\n", f.Name, b, v, flc(v.Pos), flc(firstPos)) } @@ -220,7 +229,7 @@ func numberLines(f *Func) { v.Pos = v.Pos.WithDefaultStmt() } } - if b.Pos.IsStmt() != src.PosNotStmt && (b.Pos.Line() != firstPos.Line() || !b.Pos.SameFile(firstPos)) { + if b.Pos.IsStmt() != src.PosNotStmt && !b.Pos.SameFileAndLine(firstPos) { if f.pass.debug > 0 { fmt.Printf("Mark stmt end of block differs %s %s %s prev pos = %s\n", f.Name, b, flc(b.Pos), flc(firstPos)) } diff --git a/src/cmd/internal/src/pos.go b/src/cmd/internal/src/pos.go index c9d3d347db..8c0b6d277b 100644 --- a/src/cmd/internal/src/pos.go +++ b/src/cmd/internal/src/pos.go @@ -381,8 +381,9 @@ func makeLico(line, col uint) lico { return makeLicoRaw(line, col) } -func (x lico) Line() uint { return uint(x) >> lineShift } -func (x lico) Col() uint { return uint(x) >> colShift & colMax } +func (x lico) Line() uint { return uint(x) >> lineShift } +func (x lico) SameLine(y lico) bool { return 0 == (x^y)&^lico(1 << lineShift-1) } +func (x lico) Col() uint { return uint(x) >> colShift & colMax } func (x lico) IsStmt() uint { if x == 0 { return PosNotStmt diff --git a/src/cmd/internal/src/xpos.go b/src/cmd/internal/src/xpos.go index da90ccdb78..54fe64cf86 100644 --- a/src/cmd/internal/src/xpos.go +++ b/src/cmd/internal/src/xpos.go @@ -35,6 +35,11 @@ func (p XPos) SameFile(q XPos) bool { return p.index == q.index } +// SameFileAndLine reports whether p and q are positions on the same line in the same file. +func (p XPos) SameFileAndLine(q XPos) bool { + return p.index == q.index && p.lico.SameLine(q.lico) +} + // After reports whether the position p comes after q in the source. // For positions with different bases, ordering is by base index. func (p XPos) After(q XPos) bool { -- cgit v1.3 From 6139019efaa3faa9ec94a57ab8c15b726d516664 Mon Sep 17 00:00:00 2001 From: David Chase Date: Wed, 25 Sep 2019 15:20:10 -0400 Subject: cmd/compile: pick position of implicit break statements more carefully The previous version used the position of the switch statement, which makes for potentially jumpy stepping and introduces a large number of statements repeating the line (tricky for inserting breaks). It also shared a single OBREAK node and this was not really a syntax "tree". This improves both the nostmt test (by 6 lines) and reduces the total badness score from dwarf-goodness (by about 200). Change-Id: I1f71b231a26f152bdb6ce9bc8f95828bb222f665 Reviewed-on: https://go-review.googlesource.com/c/go/+/188218 Run-TryBot: David Chase Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/gc/swt.go | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/swt.go b/src/cmd/compile/internal/gc/swt.go index a97e9735da..1381cdacba 100644 --- a/src/cmd/compile/internal/gc/swt.go +++ b/src/cmd/compile/internal/gc/swt.go @@ -268,7 +268,6 @@ func walkExprSwitch(sw *Node) { exprname: cond, } - br := nod(OBREAK, nil, nil) var defaultGoto *Node var body Nodes for _, ncase := range sw.List.Slice() { @@ -290,13 +289,17 @@ func walkExprSwitch(sw *Node) { // Process body. body.Append(npos(ncase.Pos, nodSym(OLABEL, nil, label))) body.Append(ncase.Nbody.Slice()...) - if !hasFall(ncase.Nbody.Slice()) { + if fall, pos := hasFall(ncase.Nbody.Slice()); !fall { + br := nod(OBREAK, nil, nil) + br.Pos = pos body.Append(br) } } sw.List.Set(nil) if defaultGoto == nil { + br := nod(OBREAK, nil, nil) + br.Pos = br.Pos.WithNotStmt() defaultGoto = br } @@ -469,7 +472,7 @@ func allCaseExprsAreSideEffectFree(sw *Node) bool { } // hasFall reports whether stmts ends with a "fallthrough" statement. -func hasFall(stmts []*Node) bool { +func hasFall(stmts []*Node) (bool, src.XPos) { // Search backwards for the index of the fallthrough // statement. Do not assume it'll be in the last // position, since in some cases (e.g. when the statement @@ -480,7 +483,10 @@ func hasFall(stmts []*Node) bool { for i >= 0 && stmts[i].Op == OVARKILL { i-- } - return i >= 0 && stmts[i].Op == OFALL + if i < 0 { + return false, src.NoXPos + } + return stmts[i].Op == OFALL, stmts[i].Pos } // walkTypeSwitch generates an AST that implements sw, where sw is a -- cgit v1.3 From 53bd9151099c54ffb4fee73d8b1771e311f6a271 Mon Sep 17 00:00:00 2001 From: David Chase Date: Mon, 30 Sep 2019 11:08:43 -0400 Subject: cmd/compile: classify more nodes as "poor choices" for statements Aggregate-making nodes that are later decomposed are poor choices for statements, because the decomposition phase turns them into multiple sub-values, some of which may be dead. Better to look elsewhere for a statement mark. Change-Id: Ibd9584138ab3d1384548686896a28580a2e43f54 Reviewed-on: https://go-review.googlesource.com/c/go/+/198477 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller Reviewed-by: Cherry Zhang --- src/cmd/compile/internal/ssa/numberlines.go | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/numberlines.go b/src/cmd/compile/internal/ssa/numberlines.go index a39e597d59..3e6afd72ff 100644 --- a/src/cmd/compile/internal/ssa/numberlines.go +++ b/src/cmd/compile/internal/ssa/numberlines.go @@ -15,7 +15,9 @@ func isPoorStatementOp(op Op) bool { switch op { // Note that Nilcheck often vanishes, but when it doesn't, you'd love to start the statement there // so that a debugger-user sees the stop before the panic, and can examine the value. - case OpAddr, OpLocalAddr, OpOffPtr, OpStructSelect, OpConstBool, OpConst8, OpConst16, OpConst32, OpConst64, OpConst32F, OpConst64F: + case OpAddr, OpLocalAddr, OpOffPtr, OpStructSelect, + OpIMake, OpStringMake, OpSliceMake, OpStructMake0, OpStructMake1, OpStructMake2, OpStructMake3, OpStructMake4, + OpConstBool, OpConst8, OpConst16, OpConst32, OpConst64, OpConst32F, OpConst64F: return true } return false -- cgit v1.3 From 08a87938bb95ae8859600be20a998fbb4b904915 Mon Sep 17 00:00:00 2001 From: David Chase Date: Mon, 30 Sep 2019 11:10:36 -0400 Subject: cmd/compile: make nilcheck more careful about statement relocations The earlier code was picking nodes that were "poor choices" and thus sometimes losing statements altogether. Change-Id: Ibe5ed800ffbd3c926c0ab1bc10c77d72d3042e45 Reviewed-on: https://go-review.googlesource.com/c/go/+/198478 Run-TryBot: David Chase Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/nilcheck.go | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/nilcheck.go b/src/cmd/compile/internal/ssa/nilcheck.go index 009c68afa1..9516d58a6e 100644 --- a/src/cmd/compile/internal/ssa/nilcheck.go +++ b/src/cmd/compile/internal/ssa/nilcheck.go @@ -153,12 +153,20 @@ func nilcheckelim(f *Func) { work = append(work, bp{op: ClearPtr, ptr: ptr}) fallthrough // a non-eliminated nil check might be a good place for a statement boundary. default: - if pendingLines.contains(v.Pos) && v.Pos.IsStmt() != src.PosNotStmt { + if v.Pos.IsStmt() != src.PosNotStmt && !isPoorStatementOp(v.Op) && pendingLines.contains(v.Pos) { v.Pos = v.Pos.WithIsStmt() pendingLines.remove(v.Pos) } } } + // This reduces the lost statement count in "go" by 5 (out of 500 total). + for j := 0; j < i; j++ { // is this an ordering problem? + v := b.Values[j] + if v.Pos.IsStmt() != src.PosNotStmt && !isPoorStatementOp(v.Op) && pendingLines.contains(v.Pos) { + v.Pos = v.Pos.WithIsStmt() + pendingLines.remove(v.Pos) + } + } if pendingLines.contains(b.Pos) { b.Pos = b.Pos.WithIsStmt() pendingLines.remove(b.Pos) -- cgit v1.3 From adc4d2cc2dbc20c14bae7bbdbca8d75421e1bef5 Mon Sep 17 00:00:00 2001 From: David Chase Date: Mon, 30 Sep 2019 11:12:29 -0400 Subject: cmd/compile: run deadcode before nilcheck for better statement relocation Nilcheck would move statements from NilCheck values to others that turned out were already dead, which leads to lost statements. Better to eliminate the dead code first. One "error" is removed from test/prove.go because the code is actually dead, and the additional deadcode pass removes it before prove can run. Change-Id: If75926ca1acbb59c7ab9c8ef14d60a02a0a94f8b Reviewed-on: https://go-review.googlesource.com/c/go/+/198479 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/compile.go | 1 + test/prove.go | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/compile.go b/src/cmd/compile/internal/ssa/compile.go index f061b62448..1a0a46c154 100644 --- a/src/cmd/compile/internal/ssa/compile.go +++ b/src/cmd/compile/internal/ssa/compile.go @@ -409,6 +409,7 @@ var passes = [...]pass{ {name: "opt deadcode", fn: deadcode, required: true}, // remove any blocks orphaned during opt {name: "generic cse", fn: cse}, {name: "phiopt", fn: phiopt}, + {name: "gcse deadcode", fn: deadcode, required: true}, // clean out after cse and phiopt {name: "nilcheckelim", fn: nilcheckelim}, {name: "prove", fn: prove}, {name: "fuse plain", fn: fusePlain}, diff --git a/test/prove.go b/test/prove.go index 6629982ba8..00fc94e721 100644 --- a/test/prove.go +++ b/test/prove.go @@ -507,7 +507,7 @@ func sm1(b []int, x int) { useSlice(b[2:8]) // ERROR "Proved slicemask not needed$" // Test non-constant argument with known limits. if cap(b) > 10 { - useSlice(b[2:]) // ERROR "Proved slicemask not needed$" + useSlice(b[2:]) } } -- cgit v1.3 From a7042249abdba39a7c8dce35661b62094eb97117 Mon Sep 17 00:00:00 2001 From: Josh Bleecher Snyder Date: Thu, 3 Oct 2019 14:06:08 -0700 Subject: os/exec: simplify doc wording for cmd.StdoutPipe and cmd.StderrPipe The existing text was hard to parse. Shorten the sentences and simplify the text. Change-Id: Ic16f486925090ea303c04e70969e5a4b27a60896 Reviewed-on: https://go-review.googlesource.com/c/go/+/198758 Reviewed-by: Ian Lance Taylor --- src/os/exec/exec.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/os/exec/exec.go b/src/os/exec/exec.go index 17ef003eca..19c7e2406a 100644 --- a/src/os/exec/exec.go +++ b/src/os/exec/exec.go @@ -606,8 +606,8 @@ func (c *closeOnce) close() { // standard output when the command starts. // // Wait will close the pipe after seeing the command exit, so most callers -// need not close the pipe themselves; however, an implication is that -// it is incorrect to call Wait before all reads from the pipe have completed. +// need not close the pipe themselves. It is thus incorrect to call Wait +// before all reads from the pipe have completed. // For the same reason, it is incorrect to call Run when using StdoutPipe. // See the example for idiomatic usage. func (c *Cmd) StdoutPipe() (io.ReadCloser, error) { @@ -631,8 +631,8 @@ func (c *Cmd) StdoutPipe() (io.ReadCloser, error) { // standard error when the command starts. // // Wait will close the pipe after seeing the command exit, so most callers -// need not close the pipe themselves; however, an implication is that -// it is incorrect to call Wait before all reads from the pipe have completed. +// need not close the pipe themselves. It is thus incorrect to call Wait +// before all reads from the pipe have completed. // For the same reason, it is incorrect to use Run when using StderrPipe. // See the StdoutPipe example for idiomatic usage. func (c *Cmd) StderrPipe() (io.ReadCloser, error) { -- cgit v1.3 From 8c74bfb491bc28d99b591eff0c062012e3717f68 Mon Sep 17 00:00:00 2001 From: Duco van Amstel Date: Fri, 4 Oct 2019 13:05:13 +0000 Subject: cmd/go: fix listing of ambiguous paths Passing ambiguous patterns, ending in `.go`, to `go list` results in them being interpreted as Go files despite potentially being package references. This can then result in errors on other package references. The parsing logic is modified to check for a locally present file corresponding to any pattern ending in `.go`. If no such file is present the pattern is considered to be a package reference. We're also adding a variety of non-regression tests that fail with the original parsing code but passes after applying the fix. Fixes #32483 Fixes #34653 Change-Id: I073871da0dfc5641a359643f95ac14608fdca09b GitHub-Last-Rev: 5abc200103ffc122df05422d79cf30c3ba0ee646 GitHub-Pull-Request: golang/go#34663 Reviewed-on: https://go-review.googlesource.com/c/go/+/198459 Run-TryBot: Bryan C. Mills TryBot-Result: Gobot Gobot Reviewed-by: Bryan C. Mills --- src/cmd/go/internal/load/pkg.go | 11 +++++-- src/cmd/go/internal/modget/get.go | 9 ------ src/cmd/go/testdata/script/list_ambiguous_path.txt | 37 ++++++++++++++++++++++ .../go/testdata/script/mod_get_trailing_slash.txt | 14 ++++---- 4 files changed, 51 insertions(+), 20 deletions(-) create mode 100644 src/cmd/go/testdata/script/list_ambiguous_path.txt (limited to 'src') diff --git a/src/cmd/go/internal/load/pkg.go b/src/cmd/go/internal/load/pkg.go index b8cd36f1da..205ecc596d 100644 --- a/src/cmd/go/internal/load/pkg.go +++ b/src/cmd/go/internal/load/pkg.go @@ -1950,9 +1950,14 @@ func Packages(args []string) []*Package { // cannot be loaded at all. // The packages that fail to load will have p.Error != nil. func PackagesAndErrors(patterns []string) []*Package { - if len(patterns) > 0 { - for _, p := range patterns { - if strings.HasSuffix(p, ".go") { + for _, p := range patterns { + // Listing is only supported with all patterns referring to either: + // - Files that are part of the same directory. + // - Explicit package paths or patterns. + if strings.HasSuffix(p, ".go") { + // We need to test whether the path is an actual Go file and not a + // package path or pattern ending in '.go' (see golang.org/issue/34653). + if fi, err := os.Stat(p); err == nil && !fi.IsDir() { return []*Package{GoFilesPackage(patterns)} } } diff --git a/src/cmd/go/internal/modget/get.go b/src/cmd/go/internal/modget/get.go index 3fcd2d412a..1cae311c4c 100644 --- a/src/cmd/go/internal/modget/get.go +++ b/src/cmd/go/internal/modget/get.go @@ -678,15 +678,6 @@ func runGet(cmd *base.Command, args []string) { if *getD || len(pkgPatterns) == 0 { return } - // TODO(golang.org/issue/32483): handle paths ending with ".go" consistently - // with 'go build'. When we load packages above, we interpret arguments as - // package patterns, not source files. To preserve that interpretation here, - // we add a trailing slash to any patterns ending with ".go". - for i := range pkgPatterns { - if strings.HasSuffix(pkgPatterns[i], ".go") { - pkgPatterns[i] += "/" - } - } work.BuildInit() pkgs := load.PackagesForBuild(pkgPatterns) work.InstallPackages(pkgPatterns, pkgs) diff --git a/src/cmd/go/testdata/script/list_ambiguous_path.txt b/src/cmd/go/testdata/script/list_ambiguous_path.txt new file mode 100644 index 0000000000..9f1aa37be8 --- /dev/null +++ b/src/cmd/go/testdata/script/list_ambiguous_path.txt @@ -0,0 +1,37 @@ +# Ensures that we can correctly list package patterns ending in '.go'. +# See golang.org/issue/34653. + +# A single pattern for a package ending in '.go'. +go list ./foo.go +stdout '^test/foo.go$' + +# Multiple patterns for packages including one ending in '.go'. +go list ./bar ./foo.go +stdout '^test/bar$' +stdout '^test/foo.go$' + +# A single pattern for a Go file. +go list ./a.go +stdout '^command-line-arguments$' + +# A single typo-ed pattern for a Go file. This should +# treat the wrong pattern as if it were a package. +! go list ./foo.go/b.go +stderr 'package ./foo.go/b.go: cannot find package "."' + +# Multiple patterns for Go files with a typo. This should +# treat the wrong pattern as if it were a non-existint file. +! go list ./foo.go/a.go ./foo.go/b.go +[windows] stderr './foo.go/b.go: The system cannot find the file specified' +[!windows] stderr './foo.go/b.go: no such file or directory' + +-- a.go -- +package main +-- bar/a.go -- +package bar +-- foo.go/a.go -- +package foo.go +-- go.mod -- +module "test" + +go 1.13 diff --git a/src/cmd/go/testdata/script/mod_get_trailing_slash.txt b/src/cmd/go/testdata/script/mod_get_trailing_slash.txt index 8828738abb..7b5d90c50b 100644 --- a/src/cmd/go/testdata/script/mod_get_trailing_slash.txt +++ b/src/cmd/go/testdata/script/mod_get_trailing_slash.txt @@ -1,8 +1,9 @@ -# go list should fail to load a package ending with ".go" since that denotes -# a source file. However, ".go/" should work. -# TODO(golang.org/issue/32483): perhaps we should treat non-existent paths -# with .go suffixes as package paths instead. -! go list example.com/dotgo.go +# go list should succeed to load a package ending with ".go" if the path does +# not correspond to an existing local file. Listing a pattern ending with +# ".go/" should try to list a package regardless of whether a file exists at the +# path without the suffixed "/" or not. +go list example.com/dotgo.go +stdout ^example.com/dotgo.go$ go list example.com/dotgo.go/ stdout ^example.com/dotgo.go$ @@ -15,9 +16,6 @@ go get -d example.com/dotgo.go@v1.0.0 go get -d example.com/dotgo.go/@v1.0.0 # go get (without -d) should also succeed in either case. -# TODO(golang.org/issue/32483): we should be consistent with 'go build', -# 'go list', and other commands. 'go list example.com/dotgo.go' (above) and -# 'go get example.com/dotgo.go' should both succeed or both fail. [short] skip go get example.com/dotgo.go go get example.com/dotgo.go/ -- cgit v1.3 From 6145a80608087b309251b4edf1a612739331bdee Mon Sep 17 00:00:00 2001 From: "Bryan C. Mills" Date: Wed, 2 Oct 2019 10:51:09 -0400 Subject: cmd/go: remove the -mod flag from 'go get' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 'GOFLAGS=-mod=vendor' currently causes 'go get' to always fail unless the '-mod' flag is explicitly overwritten. Moreover, as of CL 198319 we plan to set -mod=vendor by default if a vendor directory is present, so all users with vendor directories will be affected — not just those who set 'GOFLAGS' explicitly. Similarly, an explicit '-mod=readonly' argument to 'go get' is currently ignored as a special case, but the fact that it is ignored (rather than rejected) can be very surprising. Rather than adding more special cases, we should remove the '-mod' flag from 'go get' entirely. Fixes #30345 Fixes #32502 Updates #33848 Change-Id: Iecd3233ca3ef580ca3a66bd5e6ee8d86d4cbd8a7 Reviewed-on: https://go-review.googlesource.com/c/go/+/198438 Run-TryBot: Bryan C. Mills TryBot-Result: Gobot Gobot Reviewed-by: Jay Conrod --- doc/go1.14.html | 7 +++++++ src/cmd/go/internal/clean/clean.go | 2 +- src/cmd/go/internal/generate/generate.go | 2 +- src/cmd/go/internal/get/get.go | 2 +- src/cmd/go/internal/list/list.go | 2 +- src/cmd/go/internal/modget/get.go | 12 +----------- src/cmd/go/internal/run/run.go | 2 +- src/cmd/go/internal/test/testflag.go | 2 +- src/cmd/go/internal/vet/vetflag.go | 2 +- src/cmd/go/internal/work/build.go | 17 +++++++++++++---- src/cmd/go/testdata/script/mod_getmode_vendor.txt | 2 +- 11 files changed, 29 insertions(+), 23 deletions(-) (limited to 'src') diff --git a/doc/go1.14.html b/doc/go1.14.html index e68cca56df..322481c9e3 100644 --- a/doc/go1.14.html +++ b/doc/go1.14.html @@ -58,6 +58,13 @@ TODO graphic characters and spaces.

+

+ The go get subcommand no longer accepts + the -mod flag. Previously, the flag's setting either + was ignored or + caused the build to fail. +

+

Runtime

diff --git a/src/cmd/go/internal/clean/clean.go b/src/cmd/go/internal/clean/clean.go index f7d80ff6dc..5f4bf4e6c8 100644 --- a/src/cmd/go/internal/clean/clean.go +++ b/src/cmd/go/internal/clean/clean.go @@ -102,7 +102,7 @@ func init() { // mentioned explicitly in the docs but they // are part of the build flags. - work.AddBuildFlags(CmdClean) + work.AddBuildFlags(CmdClean, work.DefaultBuildFlags) } func runClean(cmd *base.Command, args []string) { diff --git a/src/cmd/go/internal/generate/generate.go b/src/cmd/go/internal/generate/generate.go index f2ae80e5dc..198ca1c1b9 100644 --- a/src/cmd/go/internal/generate/generate.go +++ b/src/cmd/go/internal/generate/generate.go @@ -149,7 +149,7 @@ var ( ) func init() { - work.AddBuildFlags(CmdGenerate) + work.AddBuildFlags(CmdGenerate, work.DefaultBuildFlags) CmdGenerate.Flag.StringVar(&generateRunFlag, "run", "", "") } diff --git a/src/cmd/go/internal/get/get.go b/src/cmd/go/internal/get/get.go index e4945fe144..44fd316f35 100644 --- a/src/cmd/go/internal/get/get.go +++ b/src/cmd/go/internal/get/get.go @@ -108,7 +108,7 @@ var ( ) func init() { - work.AddBuildFlags(CmdGet) + work.AddBuildFlags(CmdGet, work.OmitModFlag) CmdGet.Run = runGet // break init loop CmdGet.Flag.BoolVar(&Insecure, "insecure", Insecure, "") } diff --git a/src/cmd/go/internal/list/list.go b/src/cmd/go/internal/list/list.go index a5f1abe64a..67819939e6 100644 --- a/src/cmd/go/internal/list/list.go +++ b/src/cmd/go/internal/list/list.go @@ -287,7 +287,7 @@ For more about modules, see 'go help modules'. func init() { CmdList.Run = runList // break init cycle - work.AddBuildFlags(CmdList) + work.AddBuildFlags(CmdList, work.DefaultBuildFlags) } var ( diff --git a/src/cmd/go/internal/modget/get.go b/src/cmd/go/internal/modget/get.go index 1cae311c4c..ced5abcc71 100644 --- a/src/cmd/go/internal/modget/get.go +++ b/src/cmd/go/internal/modget/get.go @@ -7,7 +7,6 @@ package modget import ( "cmd/go/internal/base" - "cmd/go/internal/cfg" "cmd/go/internal/get" "cmd/go/internal/imports" "cmd/go/internal/load" @@ -199,7 +198,7 @@ func (v *upgradeFlag) Set(s string) error { func (v *upgradeFlag) String() string { return "" } func init() { - work.AddBuildFlags(CmdGet) + work.AddBuildFlags(CmdGet, work.OmitModFlag) CmdGet.Run = runGet // break init loop CmdGet.Flag.BoolVar(&get.Insecure, "insecure", get.Insecure, "") CmdGet.Flag.Var(&getU, "u", "") @@ -256,11 +255,6 @@ type query struct { } func runGet(cmd *base.Command, args []string) { - // -mod=readonly has no effect on "go get". - if cfg.BuildMod == "readonly" { - cfg.BuildMod = "" - } - switch getU { case "", "upgrade", "patch": // ok @@ -278,10 +272,6 @@ func runGet(cmd *base.Command, args []string) { } modload.LoadTests = *getT - if cfg.BuildMod == "vendor" { - base.Fatalf("go get: disabled by -mod=%s", cfg.BuildMod) - } - buildList := modload.LoadBuildList() buildList = buildList[:len(buildList):len(buildList)] // copy on append versionByPath := make(map[string]string) diff --git a/src/cmd/go/internal/run/run.go b/src/cmd/go/internal/run/run.go index 71da5adc93..648a87f665 100644 --- a/src/cmd/go/internal/run/run.go +++ b/src/cmd/go/internal/run/run.go @@ -49,7 +49,7 @@ See also: go build. func init() { CmdRun.Run = runRun // break init loop - work.AddBuildFlags(CmdRun) + work.AddBuildFlags(CmdRun, work.DefaultBuildFlags) CmdRun.Flag.Var((*base.StringsFlag)(&work.ExecCmd), "exec", "") } diff --git a/src/cmd/go/internal/test/testflag.go b/src/cmd/go/internal/test/testflag.go index 138e1f9d2a..79dc5eb2a0 100644 --- a/src/cmd/go/internal/test/testflag.go +++ b/src/cmd/go/internal/test/testflag.go @@ -65,7 +65,7 @@ var testFlagDefn = []*cmdflag.Defn{ func init() { cmdflag.AddKnownFlags("test", testFlagDefn) var cmd base.Command - work.AddBuildFlags(&cmd) + work.AddBuildFlags(&cmd, work.DefaultBuildFlags) cmd.Flag.VisitAll(func(f *flag.Flag) { if f.Name == "v" { // test overrides the build -v flag diff --git a/src/cmd/go/internal/vet/vetflag.go b/src/cmd/go/internal/vet/vetflag.go index cbe7f8ce08..7179f73cfc 100644 --- a/src/cmd/go/internal/vet/vetflag.go +++ b/src/cmd/go/internal/vet/vetflag.go @@ -114,7 +114,7 @@ func vetFlags(usage func(), args []string) (passToVet, packageNames []string) { // Add build flags to vetFlagDefn. var cmd base.Command - work.AddBuildFlags(&cmd) + work.AddBuildFlags(&cmd, work.DefaultBuildFlags) // This flag declaration is a placeholder: // -vettool is actually parsed by the init function above. cmd.Flag.StringVar(new(string), "vettool", "", "path to vet tool binary") diff --git a/src/cmd/go/internal/work/build.go b/src/cmd/go/internal/work/build.go index 9d6fa0c25b..1fc47a36c7 100644 --- a/src/cmd/go/internal/work/build.go +++ b/src/cmd/go/internal/work/build.go @@ -167,8 +167,8 @@ func init() { CmdInstall.Flag.BoolVar(&cfg.BuildI, "i", false, "") - AddBuildFlags(CmdBuild) - AddBuildFlags(CmdInstall) + AddBuildFlags(CmdBuild, DefaultBuildFlags) + AddBuildFlags(CmdInstall, DefaultBuildFlags) } // Note that flags consulted by other parts of the code @@ -216,9 +216,16 @@ func init() { } } +type BuildFlagMask int + +const ( + DefaultBuildFlags BuildFlagMask = 0 + OmitModFlag BuildFlagMask = 1 << iota +) + // addBuildFlags adds the flags common to the build, clean, get, // install, list, run, and test commands. -func AddBuildFlags(cmd *base.Command) { +func AddBuildFlags(cmd *base.Command, mask BuildFlagMask) { cmd.Flag.BoolVar(&cfg.BuildA, "a", false, "") cmd.Flag.BoolVar(&cfg.BuildN, "n", false, "") cmd.Flag.IntVar(&cfg.BuildP, "p", cfg.BuildP, "") @@ -230,7 +237,9 @@ func AddBuildFlags(cmd *base.Command) { cmd.Flag.StringVar(&cfg.BuildBuildmode, "buildmode", "default", "") cmd.Flag.Var(&load.BuildGcflags, "gcflags", "") cmd.Flag.Var(&load.BuildGccgoflags, "gccgoflags", "") - cmd.Flag.StringVar(&cfg.BuildMod, "mod", "", "") + if mask&OmitModFlag == 0 { + cmd.Flag.StringVar(&cfg.BuildMod, "mod", "", "") + } cmd.Flag.StringVar(&cfg.BuildContext.InstallSuffix, "installsuffix", "", "") cmd.Flag.Var(&load.BuildLdflags, "ldflags", "") cmd.Flag.BoolVar(&cfg.BuildLinkshared, "linkshared", false, "") diff --git a/src/cmd/go/testdata/script/mod_getmode_vendor.txt b/src/cmd/go/testdata/script/mod_getmode_vendor.txt index 7e1f6aa323..c532cee9cb 100644 --- a/src/cmd/go/testdata/script/mod_getmode_vendor.txt +++ b/src/cmd/go/testdata/script/mod_getmode_vendor.txt @@ -13,7 +13,7 @@ stdout '^golang.org/x/text v0.0.0.* .*vendor[\\/]golang.org[\\/]x[\\/]text$' ! go list -mod=vendor -m rsc.io/quote@latest stderr 'module lookup disabled by -mod=vendor' ! go get -mod=vendor -u -stderr 'go get: disabled by -mod=vendor' +stderr 'flag provided but not defined: -mod' -- go.mod -- module x -- cgit v1.3 From 72dc3a0919bebbf166302a6fdac41ab8046d4a0f Mon Sep 17 00:00:00 2001 From: Vojtech Bocek Date: Fri, 4 Oct 2019 05:24:55 +0000 Subject: crypto/x509: truncate signed hash before DSA signature verification According to spec, the hash must be truncated, but crypto/dsa does not do it. We can't fix it in crypto/dsa, because it would break verification of previously generated signatures. In crypto/x509 however, go can't generate DSA certs, only verify them, so the fix here should be safe. Fixes #22017 Change-Id: Iee7e20a5d76f45da8901a7ca686063639092949f GitHub-Last-Rev: 8041cde8d25d3a336b81d86bd52bff5039568246 GitHub-Pull-Request: golang/go#34630 Reviewed-on: https://go-review.googlesource.com/c/go/+/198138 Reviewed-by: Filippo Valsorda --- src/crypto/x509/x509.go | 5 +++++ src/crypto/x509/x509_test.go | 43 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+) (limited to 'src') diff --git a/src/crypto/x509/x509.go b/src/crypto/x509/x509.go index 9b47033947..cc382e52c6 100644 --- a/src/crypto/x509/x509.go +++ b/src/crypto/x509/x509.go @@ -892,6 +892,11 @@ func checkSignature(algo SignatureAlgorithm, signed, signature []byte, publicKey if dsaSig.R.Sign() <= 0 || dsaSig.S.Sign() <= 0 { return errors.New("x509: DSA signature contained zero or negative values") } + // According to FIPS 186-3, section 4.6, the hash must be truncated if it is longer + // than the key length, but crypto/dsa doesn't do it automatically. + if maxHashLen := pub.Q.BitLen() / 8; maxHashLen < len(signed) { + signed = signed[:maxHashLen] + } if !dsa.Verify(pub, signed, dsaSig.R, dsaSig.S) { return errors.New("x509: DSA verification failure") } diff --git a/src/crypto/x509/x509_test.go b/src/crypto/x509/x509_test.go index 1aaf093937..d5b168e78f 100644 --- a/src/crypto/x509/x509_test.go +++ b/src/crypto/x509/x509_test.go @@ -975,6 +975,49 @@ func TestVerifyCertificateWithDSASignature(t *testing.T) { } } +const dsaCert1024WithSha256 = `-----BEGIN CERTIFICATE----- +MIIDKzCCAumgAwIBAgIUOXWPK4gTRZVVY7OSXTU00QEWQU8wCwYJYIZIAWUDBAMC +MEUxCzAJBgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJ +bnRlcm5ldCBXaWRnaXRzIFB0eSBMdGQwIBcNMTkxMDAxMDYxODUyWhgPMzAxOTAy +MDEwNjE4NTJaMEUxCzAJBgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEw +HwYDVQQKDBhJbnRlcm5ldCBXaWRnaXRzIFB0eSBMdGQwggG4MIIBLAYHKoZIzjgE +ATCCAR8CgYEAr79m/1ypU1aUbbLX1jikTyX7w2QYP+EkxNtXUiiTuxkC1KBqqxT3 +0Aht2vxFR47ODEK4B79rHO+UevhaqDaAHSH7Z/9umS0h0aS32KLDLb+LI5AneCrn +eW5YbVhfD03N7uR4kKUCKOnWj5hAk9xiE3y7oFR0bBXzqrrHJF9LMd0CFQCB6lSj +HSW0rGmNxIZsBl72u7JFLQKBgQCOFd1PGEQmddn0cdFgby5QQfjrqmoD1zNlFZEt +L0x1EbndFwelLlF1ChNh3NPNUkjwRbla07FDlONs1GMJq6w4vW11ns+pUvAZ2+RM +EVFjugip8az2ncn3UujGTVdFxnSTLBsRlMP/tFDK3ky//8zn/5ha9SKKw4v1uv6M +JuoIbwOBhQACgYEAoeKeR90nwrnoPi5MOUPBLQvuzB87slfr+3kL8vFCmgjA6MtB +7TxQKoBTOo5aVgWDp0lMIMxLd6btzBrm6r3VdRlh/cL8/PtbxkFwBa+Upe4o5NAh +ISCe2/f2leT1PxtF8xxYjz/fszeUeHsJbVMilE2cuB2SYrR5tMExiqy+QpqjUzBR +MB0GA1UdDgQWBBQDMIEL8Z3jc1d9wCxWtksUWc8RkjAfBgNVHSMEGDAWgBQDMIEL +8Z3jc1d9wCxWtksUWc8RkjAPBgNVHRMBAf8EBTADAQH/MAsGCWCGSAFlAwQDAgMv +ADAsAhQFehZgI4OyKBGpfnXvyJ0Z/0a6nAIUTO265Ane87LfJuQr3FrqvuCI354= +-----END CERTIFICATE----- +` + +func TestVerifyCertificateWithDSATooLongHash(t *testing.T) { + pemBlock, _ := pem.Decode([]byte(dsaCert1024WithSha256)) + cert, err := ParseCertificate(pemBlock.Bytes) + if err != nil { + t.Fatalf("Failed to parse certificate: %s", err) + } + + // test cert is self-signed + if err = cert.CheckSignatureFrom(cert); err != nil { + t.Fatalf("DSA Certificate self-signature verification failed: %s", err) + } + + signed := []byte("A wild Gopher appears!\n") + signature, _ := hex.DecodeString("302c0214417aca7ff458f5b566e43e7b82f994953da84be50214625901e249e33f4e4838f8b5966020c286dd610e") + + // This signature is using SHA256, but only has 1024 DSA key. The hash has to be truncated + // in CheckSignature, otherwise it won't pass. + if err = cert.CheckSignature(DSAWithSHA256, signed, signature); err != nil { + t.Fatalf("DSA signature verification failed: %s", err) + } +} + var rsaPSSSelfSignedPEM = `-----BEGIN CERTIFICATE----- MIIGHjCCA9KgAwIBAgIBdjBBBgkqhkiG9w0BAQowNKAPMA0GCWCGSAFlAwQCAQUA oRwwGgYJKoZIhvcNAQEIMA0GCWCGSAFlAwQCAQUAogMCASAwbjELMAkGA1UEBhMC -- cgit v1.3 From 33ab6ccba066d94f8b8f9f502fddf04df90ea8cd Mon Sep 17 00:00:00 2001 From: David Chase Date: Tue, 1 Oct 2019 11:05:59 -0400 Subject: cmd/compile: don't attach statement marks to OpPhi OpPhi nodes tend to disappear or get rearranged, and cause statement marks to vanish. Change-Id: I2f5a222903b7fcd0d1a72e8f6d7e156036b23f30 Reviewed-on: https://go-review.googlesource.com/c/go/+/198481 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/numberlines.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/numberlines.go b/src/cmd/compile/internal/ssa/numberlines.go index 3e6afd72ff..68195e9b65 100644 --- a/src/cmd/compile/internal/ssa/numberlines.go +++ b/src/cmd/compile/internal/ssa/numberlines.go @@ -15,7 +15,7 @@ func isPoorStatementOp(op Op) bool { switch op { // Note that Nilcheck often vanishes, but when it doesn't, you'd love to start the statement there // so that a debugger-user sees the stop before the panic, and can examine the value. - case OpAddr, OpLocalAddr, OpOffPtr, OpStructSelect, + case OpAddr, OpLocalAddr, OpOffPtr, OpStructSelect, OpPhi, OpIMake, OpStringMake, OpSliceMake, OpStructMake0, OpStructMake1, OpStructMake2, OpStructMake3, OpStructMake4, OpConstBool, OpConst8, OpConst16, OpConst32, OpConst64, OpConst32F, OpConst64F: return true -- cgit v1.3 From c8e7c53b40023c92c9d7fa6beb1ca4223bd461ae Mon Sep 17 00:00:00 2001 From: David Chase Date: Mon, 30 Sep 2019 15:16:54 -0400 Subject: cmd/compile: preserve statement mark in rematerialized values Statement markers on rematerializable values were getting lost in register allocation. This checks for that case (rematerializable input and using value share line number, but mark is on the input) and preserves the mark. When combined with other CLs in this series, this CL reduces the "nostmt" count (a line appears in the assembly, but no statement marker) for cmd/go from 413 to 277. The rematerialized input is usually a LEAQ (on AMD64). The cause is "complicated"; for example, a NilCheck originally has the statement mark (a good thing, if the NilCheck remains) but the NilCheck is removed and the mark floats to a Block end, then to a SliceMake. The SliceMake decomposes and goes dead without preserving its marker (its component values are elided in other rewrites and may target inputs with different line numbers), but before deadcode removes it from the graph it moves the mark to an input, which at that time happens to be a LocalAddr. This eventually transforms to a LEAQ. Change-Id: Iff91fc2a934357fb59ec46ac87b4a9b1057d9160 Reviewed-on: https://go-review.googlesource.com/c/go/+/198480 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/value.go | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/value.go b/src/cmd/compile/internal/ssa/value.go index d2038fcfa5..c08eba3d44 100644 --- a/src/cmd/compile/internal/ssa/value.go +++ b/src/cmd/compile/internal/ssa/value.go @@ -266,6 +266,7 @@ func (v *Value) reset(op Op) { } // copyInto makes a new value identical to v and adds it to the end of b. +// unlike copyIntoWithXPos this does not check for v.Pos being a statement. func (v *Value) copyInto(b *Block) *Value { c := b.NewValue0(v.Pos.WithNotStmt(), v.Op, v.Type) // Lose the position, this causes line number churn otherwise. c.Aux = v.Aux @@ -281,7 +282,14 @@ func (v *Value) copyInto(b *Block) *Value { // copyIntoWithXPos makes a new value identical to v and adds it to the end of b. // The supplied position is used as the position of the new value. +// Because this is used for rematerialization, check for case that (rematerialized) +// input to value with position 'pos' carried a statement mark, and that the supplied +// position (of the instruction using the rematerialized value) is not marked, and +// preserve that mark if its line matches the supplied position. func (v *Value) copyIntoWithXPos(b *Block, pos src.XPos) *Value { + if v.Pos.IsStmt() == src.PosIsStmt && pos.IsStmt() != src.PosIsStmt && v.Pos.SameFileAndLine(pos) { + pos = pos.WithIsStmt() + } c := b.NewValue0(pos, v.Op, v.Type) c.Aux = v.Aux c.AuxInt = v.AuxInt -- cgit v1.3 From 43a4c61e125d184a8c9dac2d55cfa4ae31153fe8 Mon Sep 17 00:00:00 2001 From: Cuong Manh Le Date: Sat, 5 Oct 2019 00:00:38 +0700 Subject: cmd/compile: update comment in order.go to refer new methods/functions Change-Id: I2d6b73ae7447e4bdeffcdac90f7422a9280666e5 Reviewed-on: https://go-review.googlesource.com/c/go/+/198678 Run-TryBot: Cuong Manh Le TryBot-Result: Gobot Gobot Reviewed-by: Matthew Dempsky --- src/cmd/compile/internal/gc/order.go | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/order.go b/src/cmd/compile/internal/gc/order.go index 786067c49c..2ab87a2f7b 100644 --- a/src/cmd/compile/internal/gc/order.go +++ b/src/cmd/compile/internal/gc/order.go @@ -89,7 +89,7 @@ func (o *Order) newTemp(t *types.Type, clear bool) *Node { return v } -// copyExpr behaves like ordertemp but also emits +// copyExpr behaves like newTemp but also emits // code to initialize the temporary to the value n. // // The clear argument is provided for use when the evaluation @@ -181,12 +181,12 @@ func (o *Order) safeExpr(n *Node) *Node { return typecheck(a, ctxExpr) default: - Fatalf("ordersafeexpr %v", n.Op) + Fatalf("order.safeExpr %v", n.Op) return nil // not reached } } -// Isaddrokay reports whether it is okay to pass n's address to runtime routines. +// isaddrokay reports whether it is okay to pass n's address to runtime routines. // Taking the address of a variable makes the liveness and optimization analyses // lose track of where the variable's lifetime ends. To avoid hurting the analyses // of ordinary stack variables, those are not 'isaddrokay'. Temporaries are okay, @@ -274,13 +274,13 @@ func mapKeyReplaceStrConv(n *Node) bool { type ordermarker int -// Marktemp returns the top of the temporary variable stack. +// markTemp returns the top of the temporary variable stack. func (o *Order) markTemp() ordermarker { return ordermarker(len(o.temp)) } -// Poptemp pops temporaries off the stack until reaching the mark, -// which must have been returned by marktemp. +// popTemp pops temporaries off the stack until reaching the mark, +// which must have been returned by markTemp. func (o *Order) popTemp(mark ordermarker) { for _, n := range o.temp[mark:] { key := n.Type.LongString() @@ -289,7 +289,7 @@ func (o *Order) popTemp(mark ordermarker) { o.temp = o.temp[:mark] } -// Cleantempnopop emits VARKILL and if needed VARLIVE instructions +// cleanTempNoPop emits VARKILL and if needed VARLIVE instructions // to *out for each temporary above the mark on the temporary stack. // It does not pop the temporaries from the stack. func (o *Order) cleanTempNoPop(mark ordermarker) []*Node { @@ -372,7 +372,7 @@ func (o *Order) init(n *Node) { // For concurrency safety, don't mutate potentially shared nodes. // First, ensure that no work is required here. if n.Ninit.Len() > 0 { - Fatalf("orderinit shared node with ninit") + Fatalf("order.init shared node with ninit") } return } @@ -445,7 +445,7 @@ func (o *Order) call(n *Node) { func (o *Order) mapAssign(n *Node) { switch n.Op { default: - Fatalf("ordermapassign %v", n.Op) + Fatalf("order.mapAssign %v", n.Op) case OAS, OASOP: if n.Left.Op == OINDEXMAP { @@ -501,7 +501,7 @@ func (o *Order) stmt(n *Node) { switch n.Op { default: - Fatalf("orderstmt %v", n.Op) + Fatalf("order.stmt %v", n.Op) case OVARKILL, OVARLIVE, OINLMARK: o.out = append(o.out, n) @@ -713,7 +713,7 @@ func (o *Order) stmt(n *Node) { orderBody := true switch n.Type.Etype { default: - Fatalf("orderstmt range %v", n.Type) + Fatalf("order.stmt range %v", n.Type) case TARRAY, TSLICE: if n.List.Len() < 2 || n.List.Second().isBlank() { @@ -930,7 +930,7 @@ func (o *Order) stmt(n *Node) { // TODO(rsc): Clean temporaries more aggressively. // Note that because walkswitch will rewrite some of the // switch into a binary search, this is not as easy as it looks. - // (If we ran that code here we could invoke orderstmt on + // (If we ran that code here we could invoke order.stmt on // the if-else chain instead.) // For now just clean all the temporaries at the end. // In practice that's fine. -- cgit v1.3 From 3ce29b44bb8eaecbd5000202564ad4f52ad1cf69 Mon Sep 17 00:00:00 2001 From: Jordi Martin Date: Fri, 4 Oct 2019 11:56:26 +0000 Subject: cmd/go: set expected filename when building a local package with -o is pointing to a folder In the local package build process, when -o is pointing to an existing folder, the object the filename is generated from files listed on the command line like when the -o is not pointing to a folder instead of using the `importPath` that is going to be `command-line-arguments` Fixes #34535 Change-Id: I09a7609c17a2ccdd83da32f01247c0ef473dea1e GitHub-Last-Rev: b3224226a3914aa2573e47a6daff9fd5a48ca225 GitHub-Pull-Request: golang/go#34562 Reviewed-on: https://go-review.googlesource.com/c/go/+/197544 Run-TryBot: Jay Conrod TryBot-Result: Gobot Gobot Reviewed-by: Jay Conrod --- src/cmd/go/internal/load/pkg.go | 48 ++++++++++++++++++------- src/cmd/go/internal/load/pkg_test.go | 44 ++++++++++++++--------- src/cmd/go/internal/test/test.go | 2 +- src/cmd/go/internal/work/build.go | 7 ++-- src/cmd/go/testdata/script/build_multi_main.txt | 10 ++++++ 5 files changed, 77 insertions(+), 34 deletions(-) (limited to 'src') diff --git a/src/cmd/go/internal/load/pkg.go b/src/cmd/go/internal/load/pkg.go index 205ecc596d..115bc29694 100644 --- a/src/cmd/go/internal/load/pkg.go +++ b/src/cmd/go/internal/load/pkg.go @@ -1391,26 +1391,51 @@ var cgoSyscallExclude = map[string]bool{ var foldPath = make(map[string]string) -// DefaultExecName returns the default executable name -// for a package with the import path importPath. +// exeFromImportPath returns an executable name +// for a package using the import path. // -// The default executable name is the last element of the import path. +// The executable name is the last element of the import path. // In module-aware mode, an additional rule is used on import paths // consisting of two or more path elements. If the last element is // a vN path element specifying the major version, then the // second last element of the import path is used instead. -func DefaultExecName(importPath string) string { - _, elem := pathpkg.Split(importPath) +func (p *Package) exeFromImportPath() string { + _, elem := pathpkg.Split(p.ImportPath) if cfg.ModulesEnabled { // If this is example.com/mycmd/v2, it's more useful to // install it as mycmd than as v2. See golang.org/issue/24667. - if elem != importPath && isVersionElement(elem) { - _, elem = pathpkg.Split(pathpkg.Dir(importPath)) + if elem != p.ImportPath && isVersionElement(elem) { + _, elem = pathpkg.Split(pathpkg.Dir(p.ImportPath)) } } return elem } +// exeFromFiles returns an executable name for a package +// using the first element in GoFiles or CgoFiles collections without the prefix. +// +// Returns empty string in case of empty collection. +func (p *Package) exeFromFiles() string { + var src string + if len(p.GoFiles) > 0 { + src = p.GoFiles[0] + } else if len(p.CgoFiles) > 0 { + src = p.CgoFiles[0] + } else { + return "" + } + _, elem := filepath.Split(src) + return elem[:len(elem)-len(".go")] +} + +// DefaultExecName returns the default executable name for a package +func (p *Package) DefaultExecName() string { + if p.Internal.CmdlineFiles { + return p.exeFromFiles() + } + return p.exeFromImportPath() +} + // load populates p using information from bp, err, which should // be the result of calling build.Context.Import. func (p *Package) load(stk *ImportStack, bp *build.Package, err error) { @@ -1451,7 +1476,7 @@ func (p *Package) load(stk *ImportStack, bp *build.Package, err error) { p.Error = &PackageError{Err: e} return } - elem := DefaultExecName(p.ImportPath) + elem := p.DefaultExecName() full := cfg.BuildContext.GOOS + "_" + cfg.BuildContext.GOARCH + "/" + elem if cfg.BuildContext.GOOS != base.ToolGOOS || cfg.BuildContext.GOARCH != base.ToolGOARCH { // Install cross-compiled binaries to subdirectories of bin. @@ -2140,11 +2165,8 @@ func GoFilesPackage(gofiles []string) *Package { pkg.Match = gofiles if pkg.Name == "main" { - _, elem := filepath.Split(gofiles[0]) - exe := elem[:len(elem)-len(".go")] + cfg.ExeSuffix - if cfg.BuildO == "" { - cfg.BuildO = exe - } + exe := pkg.DefaultExecName() + cfg.ExeSuffix + if cfg.GOBIN != "" { pkg.Target = filepath.Join(cfg.GOBIN, exe) } else if cfg.ModulesEnabled { diff --git a/src/cmd/go/internal/load/pkg_test.go b/src/cmd/go/internal/load/pkg_test.go index 9ddc20d050..1e59fb989c 100644 --- a/src/cmd/go/internal/load/pkg_test.go +++ b/src/cmd/go/internal/load/pkg_test.go @@ -5,39 +5,49 @@ import ( "testing" ) -func TestDefaultExecName(t *testing.T) { +func TestPkgDefaultExecName(t *testing.T) { oldModulesEnabled := cfg.ModulesEnabled defer func() { cfg.ModulesEnabled = oldModulesEnabled }() for _, tt := range []struct { in string + files []string wantMod string wantGopath string }{ - {"example.com/mycmd", "mycmd", "mycmd"}, - {"example.com/mycmd/v0", "v0", "v0"}, - {"example.com/mycmd/v1", "v1", "v1"}, - {"example.com/mycmd/v2", "mycmd", "v2"}, // Semantic import versioning, use second last element in module mode. - {"example.com/mycmd/v3", "mycmd", "v3"}, // Semantic import versioning, use second last element in module mode. - {"mycmd", "mycmd", "mycmd"}, - {"mycmd/v0", "v0", "v0"}, - {"mycmd/v1", "v1", "v1"}, - {"mycmd/v2", "mycmd", "v2"}, // Semantic import versioning, use second last element in module mode. - {"v0", "v0", "v0"}, - {"v1", "v1", "v1"}, - {"v2", "v2", "v2"}, + {"example.com/mycmd", []string{}, "mycmd", "mycmd"}, + {"example.com/mycmd/v0", []string{}, "v0", "v0"}, + {"example.com/mycmd/v1", []string{}, "v1", "v1"}, + {"example.com/mycmd/v2", []string{}, "mycmd", "v2"}, // Semantic import versioning, use second last element in module mode. + {"example.com/mycmd/v3", []string{}, "mycmd", "v3"}, // Semantic import versioning, use second last element in module mode. + {"mycmd", []string{}, "mycmd", "mycmd"}, + {"mycmd/v0", []string{}, "v0", "v0"}, + {"mycmd/v1", []string{}, "v1", "v1"}, + {"mycmd/v2", []string{}, "mycmd", "v2"}, // Semantic import versioning, use second last element in module mode. + {"v0", []string{}, "v0", "v0"}, + {"v1", []string{}, "v1", "v1"}, + {"v2", []string{}, "v2", "v2"}, + {"command-line-arguments", []string{"output.go", "foo.go"}, "output", "output"}, } { { cfg.ModulesEnabled = true - gotMod := DefaultExecName(tt.in) + pkg := new(Package) + pkg.ImportPath = tt.in + pkg.GoFiles = tt.files + pkg.Internal.CmdlineFiles = len(tt.files) > 0 + gotMod := pkg.DefaultExecName() if gotMod != tt.wantMod { - t.Errorf("DefaultExecName(%q) in module mode = %v; want %v", tt.in, gotMod, tt.wantMod) + t.Errorf("pkg.DefaultExecName with ImportPath = %q in module mode = %v; want %v", tt.in, gotMod, tt.wantMod) } } { cfg.ModulesEnabled = false - gotGopath := DefaultExecName(tt.in) + pkg := new(Package) + pkg.ImportPath = tt.in + pkg.GoFiles = tt.files + pkg.Internal.CmdlineFiles = len(tt.files) > 0 + gotGopath := pkg.DefaultExecName() if gotGopath != tt.wantGopath { - t.Errorf("DefaultExecName(%q) in gopath mode = %v; want %v", tt.in, gotGopath, tt.wantGopath) + t.Errorf("pkg.DefaultExecName with ImportPath = %q in gopath mode = %v; want %v", tt.in, gotGopath, tt.wantGopath) } } } diff --git a/src/cmd/go/internal/test/test.go b/src/cmd/go/internal/test/test.go index 8141e31c99..fb011d4c03 100644 --- a/src/cmd/go/internal/test/test.go +++ b/src/cmd/go/internal/test/test.go @@ -829,7 +829,7 @@ func builderTest(b *work.Builder, p *load.Package) (buildAction, runAction, prin if p.ImportPath == "command-line-arguments" { elem = p.Name } else { - elem = load.DefaultExecName(p.ImportPath) + elem = p.DefaultExecName() } testBinary := elem + ".test" diff --git a/src/cmd/go/internal/work/build.go b/src/cmd/go/internal/work/build.go index 1fc47a36c7..54b049b68f 100644 --- a/src/cmd/go/internal/work/build.go +++ b/src/cmd/go/internal/work/build.go @@ -329,7 +329,7 @@ func runBuild(cmd *base.Command, args []string) { explicitO := len(cfg.BuildO) > 0 if len(pkgs) == 1 && pkgs[0].Name == "main" && cfg.BuildO == "" { - cfg.BuildO = load.DefaultExecName(pkgs[0].ImportPath) + cfg.BuildO = pkgs[0].DefaultExecName() cfg.BuildO += cfg.ExeSuffix } @@ -373,7 +373,8 @@ func runBuild(cmd *base.Command, args []string) { if p.Name != "main" { continue } - p.Target = filepath.Join(cfg.BuildO, load.DefaultExecName(p.ImportPath)) + + p.Target = filepath.Join(cfg.BuildO, p.DefaultExecName()) p.Target += cfg.ExeSuffix p.Stale = true p.StaleReason = "build -o flag in use" @@ -595,7 +596,7 @@ func InstallPackages(patterns []string, pkgs []*load.Package) { if len(patterns) == 0 && len(pkgs) == 1 && pkgs[0].Name == "main" { // Compute file 'go build' would have created. // If it exists and is an executable file, remove it. - targ := load.DefaultExecName(pkgs[0].ImportPath) + targ := pkgs[0].DefaultExecName() targ += cfg.ExeSuffix if filepath.Join(pkgs[0].Dir, targ) != pkgs[0].Target { // maybe $GOBIN is the current directory fi, err := os.Stat(targ) diff --git a/src/cmd/go/testdata/script/build_multi_main.txt b/src/cmd/go/testdata/script/build_multi_main.txt index 1d4926d979..8afd8b8a2e 100644 --- a/src/cmd/go/testdata/script/build_multi_main.txt +++ b/src/cmd/go/testdata/script/build_multi_main.txt @@ -10,6 +10,11 @@ stderr 'no main packages' ! go build ./cmd/c1 stderr 'already exists and is a directory' +# Verify build -o output correctly local packages +mkdir $WORK/local +go build -o $WORK/local ./exec.go +exists $WORK/local/exec$GOEXE + -- go.mod -- module exmod @@ -29,5 +34,10 @@ package pkg1 -- pkg2/pkg2.go -- package pkg2 +-- exec.go -- +package main + +func main() {} + -- c1$GOEXE/keep.txt -- Create c1 directory. -- cgit v1.3 From 91b55b4fa3a5351aba0e9f79f1c94e27ab2004e7 Mon Sep 17 00:00:00 2001 From: David Chase Date: Tue, 1 Oct 2019 11:07:43 -0400 Subject: cmd/compile: attempt to preserve statement marks when empty blocks are trimmed. This was a cause of some statements being lost. Change-Id: Ia4805c2dafd7a880d485a678a48427de8930d57e Reviewed-on: https://go-review.googlesource.com/c/go/+/198482 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/trim.go | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/trim.go b/src/cmd/compile/internal/ssa/trim.go index 1293548aad..c930a205c1 100644 --- a/src/cmd/compile/internal/ssa/trim.go +++ b/src/cmd/compile/internal/ssa/trim.go @@ -4,6 +4,8 @@ package ssa +import "cmd/internal/src" + // trim removes blocks with no code in them. // These blocks were inserted to remove critical edges. func trim(f *Func) { @@ -15,6 +17,9 @@ func trim(f *Func) { continue } + bPos := b.Pos + bIsStmt := bPos.IsStmt() == src.PosIsStmt + // Splice b out of the graph. NOTE: `mergePhi` depends on the // order, in which the predecessors edges are merged here. p, i := b.Preds[0].b, b.Preds[0].i @@ -29,6 +34,23 @@ func trim(f *Func) { s.Preds = append(s.Preds, Edge{p, i}) } + // Attempt to preserve a statement boundary + if bIsStmt { + sawStmt := false + for _, v := range s.Values { + if isPoorStatementOp(v.Op) { + continue + } + if v.Pos.SameFileAndLine(bPos) { + v.Pos = v.Pos.WithIsStmt() + } + sawStmt = true + break + } + if !sawStmt && s.Pos.SameFileAndLine(bPos) { + s.Pos = s.Pos.WithIsStmt() + } + } // If `s` had more than one predecessor, update its phi-ops to // account for the merge. if ns > 1 { @@ -36,6 +58,7 @@ func trim(f *Func) { if v.Op == OpPhi { mergePhi(v, j, b) } + } // Remove the phi-ops from `b` if they were merged into the // phi-ops of `s`. -- cgit v1.3 From 0fb95e788e8639712b7200a5c08ec023fb3588cb Mon Sep 17 00:00:00 2001 From: Brad Fitzpatrick Date: Mon, 29 Apr 2019 22:04:09 +0000 Subject: crypto/tls: remove NPN support RELNOTE=yes Fixes #28362 Change-Id: I43813c0c17bbe6c4cbb4d1f121518c434b3f5aa8 Reviewed-on: https://go-review.googlesource.com/c/go/+/174329 Reviewed-by: Filippo Valsorda --- doc/go1.14.html | 8 ++ src/crypto/tls/conn.go | 2 - src/crypto/tls/handshake_client.go | 25 ----- src/crypto/tls/handshake_client_tls13.go | 4 +- src/crypto/tls/handshake_messages.go | 94 +---------------- src/crypto/tls/handshake_messages_test.go | 17 --- src/crypto/tls/handshake_server.go | 23 ---- src/crypto/tls/handshake_server_tls13.go | 1 - src/crypto/tls/testdata/Client-TLSv12-ALPN | 74 ++++++------- src/crypto/tls/testdata/Client-TLSv13-ALPN | 162 ++++++++++++++--------------- 10 files changed, 129 insertions(+), 281 deletions(-) (limited to 'src') diff --git a/doc/go1.14.html b/doc/go1.14.html index 322481c9e3..7afda4c07e 100644 --- a/doc/go1.14.html +++ b/doc/go1.14.html @@ -96,6 +96,14 @@ TODO TODO: https://golang.org/cl/191999: remove TLS 1.3 opt-out

+

+ The tls package no longer supports NPN and now only + supports ALPN. In previous releases it supported both. There are + no API changes and code should function identically as before. + Most other clients & servers have already removed NPN support in + favor of the standardized ALPN. +

+
encoding/asn1
diff --git a/src/crypto/tls/conn.go b/src/crypto/tls/conn.go index 750e45ee4d..05048776d4 100644 --- a/src/crypto/tls/conn.go +++ b/src/crypto/tls/conn.go @@ -1027,8 +1027,6 @@ func (c *Conn) readHandshake() (interface{}, error) { m = &certificateVerifyMsg{ hasSignatureAlgorithm: c.vers >= VersionTLS12, } - case typeNextProtocol: - m = new(nextProtoMsg) case typeFinished: m = new(finishedMsg) case typeEncryptedExtensions: diff --git a/src/crypto/tls/handshake_client.go b/src/crypto/tls/handshake_client.go index f04311320e..75d710b2e2 100644 --- a/src/crypto/tls/handshake_client.go +++ b/src/crypto/tls/handshake_client.go @@ -73,7 +73,6 @@ func (c *Conn) makeClientHello() (*clientHelloMsg, ecdheParameters, error) { serverName: hostnameInSNI(config.ServerName), supportedCurves: config.curvePreferences(), supportedPoints: []uint8{pointFormatUncompressed}, - nextProtoNeg: len(config.NextProtos) > 0, secureRenegotiationSupported: true, alpnProtocols: config.NextProtos, supportedVersions: supportedVersions, @@ -673,26 +672,14 @@ func (hs *clientHandshakeState) processServerHello() (bool, error) { } } - clientDidNPN := hs.hello.nextProtoNeg clientDidALPN := len(hs.hello.alpnProtocols) > 0 - serverHasNPN := hs.serverHello.nextProtoNeg serverHasALPN := len(hs.serverHello.alpnProtocol) > 0 - if !clientDidNPN && serverHasNPN { - c.sendAlert(alertHandshakeFailure) - return false, errors.New("tls: server advertised unrequested NPN extension") - } - if !clientDidALPN && serverHasALPN { c.sendAlert(alertHandshakeFailure) return false, errors.New("tls: server advertised unrequested ALPN extension") } - if serverHasNPN && serverHasALPN { - c.sendAlert(alertHandshakeFailure) - return false, errors.New("tls: server advertised both NPN and ALPN extensions") - } - if serverHasALPN { c.clientProtocol = hs.serverHello.alpnProtocol c.clientProtocolFallback = false @@ -784,18 +771,6 @@ func (hs *clientHandshakeState) sendFinished(out []byte) error { if _, err := c.writeRecord(recordTypeChangeCipherSpec, []byte{1}); err != nil { return err } - if hs.serverHello.nextProtoNeg { - nextProto := new(nextProtoMsg) - proto, fallback := mutualProtocol(c.config.NextProtos, hs.serverHello.nextProtos) - nextProto.proto = proto - c.clientProtocol = proto - c.clientProtocolFallback = fallback - - hs.finishedHash.Write(nextProto.marshal()) - if _, err := c.writeRecord(recordTypeHandshake, nextProto.marshal()); err != nil { - return err - } - } finished := new(finishedMsg) finished.verifyData = hs.finishedHash.clientSum(hs.masterSecret) diff --git a/src/crypto/tls/handshake_client_tls13.go b/src/crypto/tls/handshake_client_tls13.go index 82207eb646..a561cbfe3c 100644 --- a/src/crypto/tls/handshake_client_tls13.go +++ b/src/crypto/tls/handshake_client_tls13.go @@ -123,9 +123,7 @@ func (hs *clientHandshakeStateTLS13) checkServerHelloOrHRR() error { return errors.New("tls: server sent an incorrect legacy version") } - if hs.serverHello.nextProtoNeg || - len(hs.serverHello.nextProtos) != 0 || - hs.serverHello.ocspStapling || + if hs.serverHello.ocspStapling || hs.serverHello.ticketSupported || hs.serverHello.secureRenegotiationSupported || len(hs.serverHello.secureRenegotiation) != 0 || diff --git a/src/crypto/tls/handshake_messages.go b/src/crypto/tls/handshake_messages.go index 2d21377737..5524782e71 100644 --- a/src/crypto/tls/handshake_messages.go +++ b/src/crypto/tls/handshake_messages.go @@ -6,8 +6,9 @@ package tls import ( "fmt" - "golang.org/x/crypto/cryptobyte" "strings" + + "golang.org/x/crypto/cryptobyte" ) // The marshalingFunction type is an adapter to allow the use of ordinary @@ -72,7 +73,6 @@ type clientHelloMsg struct { sessionId []byte cipherSuites []uint16 compressionMethods []uint8 - nextProtoNeg bool serverName string ocspStapling bool supportedCurves []CurveID @@ -121,11 +121,6 @@ func (m *clientHelloMsg) marshal() []byte { bWithoutExtensions := *b b.AddUint16LengthPrefixed(func(b *cryptobyte.Builder) { - if m.nextProtoNeg { - // draft-agl-tls-nextprotoneg-04 - b.AddUint16(extensionNextProtoNeg) - b.AddUint16(0) // empty extension_data - } if len(m.serverName) > 0 { // RFC 6066, Section 3 b.AddUint16(extensionServerName) @@ -426,9 +421,6 @@ func (m *clientHelloMsg) unmarshal(data []byte) bool { return false } } - case extensionNextProtoNeg: - // draft-agl-tls-nextprotoneg-04 - m.nextProtoNeg = true case extensionStatusRequest: // RFC 4366, Section 3.6 var statusType uint8 @@ -604,8 +596,6 @@ type serverHelloMsg struct { sessionId []byte cipherSuite uint16 compressionMethod uint8 - nextProtoNeg bool - nextProtos []string ocspStapling bool ticketSupported bool secureRenegotiationSupported bool @@ -643,16 +633,6 @@ func (m *serverHelloMsg) marshal() []byte { bWithoutExtensions := *b b.AddUint16LengthPrefixed(func(b *cryptobyte.Builder) { - if m.nextProtoNeg { - b.AddUint16(extensionNextProtoNeg) - b.AddUint16LengthPrefixed(func(b *cryptobyte.Builder) { - for _, proto := range m.nextProtos { - b.AddUint8LengthPrefixed(func(b *cryptobyte.Builder) { - b.AddBytes([]byte(proto)) - }) - } - }) - } if m.ocspStapling { b.AddUint16(extensionStatusRequest) b.AddUint16(0) // empty extension_data @@ -771,16 +751,6 @@ func (m *serverHelloMsg) unmarshal(data []byte) bool { } switch extension { - case extensionNextProtoNeg: - m.nextProtoNeg = true - for !extData.Empty() { - var proto cryptobyte.String - if !extData.ReadUint8LengthPrefixed(&proto) || - proto.Empty() { - return false - } - m.nextProtos = append(m.nextProtos, string(proto)) - } case extensionStatusRequest: m.ocspStapling = true case extensionSessionTicket: @@ -1579,66 +1549,6 @@ func (m *finishedMsg) unmarshal(data []byte) bool { s.Empty() } -type nextProtoMsg struct { - raw []byte - proto string -} - -func (m *nextProtoMsg) marshal() []byte { - if m.raw != nil { - return m.raw - } - l := len(m.proto) - if l > 255 { - l = 255 - } - - padding := 32 - (l+2)%32 - length := l + padding + 2 - x := make([]byte, length+4) - x[0] = typeNextProtocol - x[1] = uint8(length >> 16) - x[2] = uint8(length >> 8) - x[3] = uint8(length) - - y := x[4:] - y[0] = byte(l) - copy(y[1:], []byte(m.proto[0:l])) - y = y[1+l:] - y[0] = byte(padding) - - m.raw = x - - return x -} - -func (m *nextProtoMsg) unmarshal(data []byte) bool { - m.raw = data - - if len(data) < 5 { - return false - } - data = data[4:] - protoLen := int(data[0]) - data = data[1:] - if len(data) < protoLen { - return false - } - m.proto = string(data[0:protoLen]) - data = data[protoLen:] - - if len(data) < 1 { - return false - } - paddingLen := int(data[0]) - data = data[1:] - if len(data) != paddingLen { - return false - } - - return true -} - type certificateRequestMsg struct { raw []byte // hasSignatureAlgorithm indicates whether this message includes a list of diff --git a/src/crypto/tls/handshake_messages_test.go b/src/crypto/tls/handshake_messages_test.go index 21beb8ef2d..9b01692566 100644 --- a/src/crypto/tls/handshake_messages_test.go +++ b/src/crypto/tls/handshake_messages_test.go @@ -26,7 +26,6 @@ var tests = []interface{}{ }, &certificateStatusMsg{}, &clientKeyExchangeMsg{}, - &nextProtoMsg{}, &newSessionTicketMsg{}, &sessionState{}, &sessionStateTLS13{}, @@ -127,9 +126,6 @@ func (*clientHelloMsg) Generate(rand *rand.Rand, size int) reflect.Value { m.cipherSuites[i] = cs } m.compressionMethods = randomBytes(rand.Intn(63)+1, rand) - if rand.Intn(10) > 5 { - m.nextProtoNeg = true - } if rand.Intn(10) > 5 { m.serverName = randomString(rand.Intn(255), rand) for strings.HasSuffix(m.serverName, ".") { @@ -206,13 +202,6 @@ func (*serverHelloMsg) Generate(rand *rand.Rand, size int) reflect.Value { m.cipherSuite = uint16(rand.Int31()) m.compressionMethod = uint8(rand.Intn(256)) - if rand.Intn(10) > 5 { - m.nextProtoNeg = true - for i := 0; i < rand.Intn(10); i++ { - m.nextProtos = append(m.nextProtos, randomString(20, rand)) - } - } - if rand.Intn(10) > 5 { m.ocspStapling = true } @@ -308,12 +297,6 @@ func (*finishedMsg) Generate(rand *rand.Rand, size int) reflect.Value { return reflect.ValueOf(m) } -func (*nextProtoMsg) Generate(rand *rand.Rand, size int) reflect.Value { - m := &nextProtoMsg{} - m.proto = randomString(rand.Intn(255), rand) - return reflect.ValueOf(m) -} - func (*newSessionTicketMsg) Generate(rand *rand.Rand, size int) reflect.Value { m := &newSessionTicketMsg{} m.ticket = randomBytes(rand.Intn(4), rand) diff --git a/src/crypto/tls/handshake_server.go b/src/crypto/tls/handshake_server.go index c6c40b360a..ab5be72f76 100644 --- a/src/crypto/tls/handshake_server.go +++ b/src/crypto/tls/handshake_server.go @@ -244,15 +244,6 @@ Curves: hs.hello.alpnProtocol = selectedProto c.clientProtocol = selectedProto } - } else { - // Although sending an empty NPN extension is reasonable, Firefox has - // had a bug around this. Best to send nothing at all if - // c.config.NextProtos is empty. See - // https://golang.org/issue/5445. - if hs.clientHello.nextProtoNeg && len(c.config.NextProtos) > 0 { - hs.hello.nextProtoNeg = true - hs.hello.nextProtos = c.config.NextProtos - } } hs.cert, err = c.config.getCertificate(clientHelloInfo(c, hs.clientHello)) @@ -618,20 +609,6 @@ func (hs *serverHandshakeState) readFinished(out []byte) error { return err } - if hs.hello.nextProtoNeg { - msg, err := c.readHandshake() - if err != nil { - return err - } - nextProto, ok := msg.(*nextProtoMsg) - if !ok { - c.sendAlert(alertUnexpectedMessage) - return unexpectedMessageError(nextProto, msg) - } - hs.finishedHash.Write(nextProto.marshal()) - c.clientProtocol = nextProto.proto - } - msg, err := c.readHandshake() if err != nil { return err diff --git a/src/crypto/tls/handshake_server_tls13.go b/src/crypto/tls/handshake_server_tls13.go index 979ead5f78..feaa5bb6fa 100644 --- a/src/crypto/tls/handshake_server_tls13.go +++ b/src/crypto/tls/handshake_server_tls13.go @@ -510,7 +510,6 @@ func illegalClientHelloChange(ch, ch1 *clientHelloMsg) bool { !bytes.Equal(ch.random, ch1.random) || !bytes.Equal(ch.sessionId, ch1.sessionId) || !bytes.Equal(ch.compressionMethods, ch1.compressionMethods) || - ch.nextProtoNeg != ch1.nextProtoNeg || ch.serverName != ch1.serverName || ch.ocspStapling != ch1.ocspStapling || !bytes.Equal(ch.supportedPoints, ch1.supportedPoints) || diff --git a/src/crypto/tls/testdata/Client-TLSv12-ALPN b/src/crypto/tls/testdata/Client-TLSv12-ALPN index 2708b262b6..358b211fc1 100644 --- a/src/crypto/tls/testdata/Client-TLSv12-ALPN +++ b/src/crypto/tls/testdata/Client-TLSv12-ALPN @@ -1,5 +1,5 @@ >>> Flow 1 (client to server) -00000000 16 03 01 01 12 01 00 01 0e 03 03 00 00 00 00 00 |................| +00000000 16 03 01 01 0e 01 00 01 0a 03 03 00 00 00 00 00 |................| 00000010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| 00000020 00 00 00 00 00 00 00 00 00 00 00 20 00 00 00 00 |........... ....| 00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| @@ -7,22 +7,22 @@ 00000050 cc a9 c0 2f c0 2b c0 30 c0 2c c0 27 c0 13 c0 23 |.../.+.0.,.'...#| 00000060 c0 09 c0 14 c0 0a 00 9c 00 9d 00 3c 00 2f 00 35 |...........<./.5| 00000070 c0 12 00 0a 00 05 c0 11 c0 07 13 01 13 03 13 02 |................| -00000080 01 00 00 93 33 74 00 00 00 05 00 05 01 00 00 00 |....3t..........| -00000090 00 00 0a 00 0a 00 08 00 1d 00 17 00 18 00 19 00 |................| -000000a0 0b 00 02 01 00 00 0d 00 1a 00 18 08 04 04 03 08 |................| -000000b0 07 08 05 08 06 04 01 05 01 06 01 05 03 06 03 02 |................| -000000c0 01 02 03 ff 01 00 01 00 00 10 00 10 00 0e 06 70 |...............p| -000000d0 72 6f 74 6f 32 06 70 72 6f 74 6f 31 00 12 00 00 |roto2.proto1....| -000000e0 00 2b 00 09 08 03 04 03 03 03 02 03 01 00 33 00 |.+............3.| -000000f0 26 00 24 00 1d 00 20 2f e5 7d a3 47 cd 62 43 15 |&.$... /.}.G.bC.| -00000100 28 da ac 5f bb 29 07 30 ff f6 84 af c4 cf c2 ed |(.._.).0........| -00000110 90 99 5f 58 cb 3b 74 |.._X.;t| +00000080 01 00 00 8f 00 05 00 05 01 00 00 00 00 00 0a 00 |................| +00000090 0a 00 08 00 1d 00 17 00 18 00 19 00 0b 00 02 01 |................| +000000a0 00 00 0d 00 1a 00 18 08 04 04 03 08 07 08 05 08 |................| +000000b0 06 04 01 05 01 06 01 05 03 06 03 02 01 02 03 ff |................| +000000c0 01 00 01 00 00 10 00 10 00 0e 06 70 72 6f 74 6f |...........proto| +000000d0 32 06 70 72 6f 74 6f 31 00 12 00 00 00 2b 00 09 |2.proto1.....+..| +000000e0 08 03 04 03 03 03 02 03 01 00 33 00 26 00 24 00 |..........3.&.$.| +000000f0 1d 00 20 2f e5 7d a3 47 cd 62 43 15 28 da ac 5f |.. /.}.G.bC.(.._| +00000100 bb 29 07 30 ff f6 84 af c4 cf c2 ed 90 99 5f 58 |.).0.........._X| +00000110 cb 3b 74 |.;t| >>> Flow 2 (server to client) -00000000 16 03 03 00 66 02 00 00 62 03 03 0e b3 00 4c e5 |....f...b.....L.| -00000010 e4 08 c5 3d c2 9c 19 a1 de ae 43 24 9a 4d 81 99 |...=......C$.M..| -00000020 df 60 cf a5 be ae c1 e8 e8 b9 a8 20 14 e6 e1 91 |.`......... ....| -00000030 7a ab 9f 7b 3c dc c5 71 4b 28 80 5e fa 56 c9 b7 |z..{<..qK(.^.V..| -00000040 d4 2f 0e 80 49 df 81 93 df 5d 34 49 cc a8 00 00 |./..I....]4I....| +00000000 16 03 03 00 66 02 00 00 62 03 03 95 14 55 52 0b |....f...b....UR.| +00000010 e7 c1 15 6b dc 19 3b 17 9e bb 6a b7 61 82 dc 59 |...k..;...j.a..Y| +00000020 d3 a4 7c e1 c3 83 cc e2 e5 56 e0 20 3c 82 0d 54 |..|......V. <..T| +00000030 2b 78 fe 50 cb 4e c1 69 d7 6f b3 9f ac 2e 27 c8 |+x.P.N.i.o....'.| +00000040 c6 7a 70 27 1e 14 67 43 4c f1 7d d7 cc a8 00 00 |.zp'..gCL.}.....| 00000050 1a ff 01 00 01 00 00 0b 00 04 03 00 01 02 00 10 |................| 00000060 00 09 00 07 06 70 72 6f 74 6f 31 16 03 03 02 59 |.....proto1....Y| 00000070 0b 00 02 55 00 02 52 00 02 4f 30 82 02 4b 30 82 |...U..R..O0..K0.| @@ -63,31 +63,31 @@ 000002a0 1c f1 0f a1 d8 40 83 61 c9 4c 72 2b 9d ae db 46 |.....@.a.Lr+...F| 000002b0 06 06 4d f4 c1 b3 3e c0 d1 bd 42 d4 db fe 3d 13 |..M...>...B...=.| 000002c0 60 84 5c 21 d3 3b e9 fa e7 16 03 03 00 ac 0c 00 |`.\!.;..........| -000002d0 00 a8 03 00 1d 20 18 37 3a d3 0a 4f 9b 95 c7 f0 |..... .7:..O....| -000002e0 a2 00 43 5f df 2e a8 16 a9 9f 2a 0e 51 cf c9 b9 |..C_......*.Q...| -000002f0 14 62 a7 ab 4b 6a 08 04 00 80 1a b2 78 e7 cd b6 |.b..Kj......x...| -00000300 18 65 31 19 f9 91 9f a6 cb 77 97 69 86 27 ef 06 |.e1......w.i.'..| -00000310 b5 bc f4 8f 75 96 01 72 64 2c d4 e4 67 0a d5 58 |....u..rd,..g..X| -00000320 e0 e1 05 82 a6 58 f6 e0 06 c2 15 03 69 ba 5a a0 |.....X......i.Z.| -00000330 2b af 6f b1 cd 16 84 1d 89 9c d0 c7 d2 c7 83 e8 |+.o.............| -00000340 43 b7 4f e8 ca 97 c0 e2 57 d0 10 48 0c 26 cf 58 |C.O.....W..H.&.X| -00000350 50 69 d8 86 b6 f5 aa 02 b8 f6 41 c4 15 52 99 52 |Pi........A..R.R| -00000360 05 05 5b 42 80 6d 8a bf 7a e6 f3 60 c5 67 23 dc |..[B.m..z..`.g#.| -00000370 39 4b e6 74 0e 0e 47 a7 57 02 16 03 03 00 04 0e |9K.t..G.W.......| +000002d0 00 a8 03 00 1d 20 c3 e3 43 9c 5d 0f 09 61 ae 18 |..... ..C.]..a..| +000002e0 66 05 b1 7d c1 9f e5 26 9c a7 97 d6 1f 9a 7c ff |f..}...&......|.| +000002f0 8c 34 a1 32 a2 35 08 04 00 80 6c 50 a1 80 d9 20 |.4.2.5....lP... | +00000300 56 08 da d9 5b 77 4d ad 43 66 71 15 ec fe db 02 |V...[wM.Cfq.....| +00000310 fb 40 d8 8d 67 22 e2 1b ec 8d b9 4e ba 65 01 8b |.@..g".....N.e..| +00000320 70 e0 83 bc 06 1b 14 8f 07 cf a6 08 58 c3 77 94 |p...........X.w.| +00000330 0f 94 53 62 54 6c 1f 92 22 9d ae f8 5a ad d5 f3 |..SbTl.."...Z...| +00000340 8a f7 e6 93 8c 0e 48 1b 23 89 d8 bd e9 5c 50 cd |......H.#....\P.| +00000350 07 3d 7e 8e b0 d6 65 44 58 62 03 a1 d9 94 72 f0 |.=~...eDXb....r.| +00000360 25 a9 e0 c1 be ac 32 05 59 f7 7f 6e 13 23 70 5a |%.....2.Y..n.#pZ| +00000370 65 ba a2 d7 da 3c a2 9e 6b 13 16 03 03 00 04 0e |e....<..k.......| 00000380 00 00 00 |...| >>> Flow 3 (client to server) 00000000 16 03 03 00 25 10 00 00 21 20 2f e5 7d a3 47 cd |....%...! /.}.G.| 00000010 62 43 15 28 da ac 5f bb 29 07 30 ff f6 84 af c4 |bC.(.._.).0.....| 00000020 cf c2 ed 90 99 5f 58 cb 3b 74 14 03 03 00 01 01 |....._X.;t......| -00000030 16 03 03 00 20 0d 3c cf 6f 13 e3 73 d2 c5 05 06 |.... .<.o..s....| -00000040 85 8d 41 e0 46 3b 25 e7 0a ae b9 00 1e c3 3f 61 |..A.F;%.......?a| -00000050 82 2d e1 19 a4 |.-...| +00000030 16 03 03 00 20 5e 91 45 7d ab 7c b7 6f 57 a6 d0 |.... ^.E}.|.oW..| +00000040 17 83 cb 40 1b 76 6b 5e 80 39 03 2f 6d 2f 10 8e |...@.vk^.9./m/..| +00000050 74 33 12 54 8d |t3.T.| >>> Flow 4 (server to client) -00000000 14 03 03 00 01 01 16 03 03 00 20 43 1a 5d c1 dc |.......... C.]..| -00000010 42 10 81 bc af 2d 40 82 fa 27 41 81 cc e5 97 99 |B....-@..'A.....| -00000020 80 27 3a b5 db f5 8e 2a 6d 72 86 |.':....*mr.| +00000000 14 03 03 00 01 01 16 03 03 00 20 f1 3c 7a 28 eb |.......... .>> Flow 5 (client to server) -00000000 17 03 03 00 16 f1 0a 98 3b 2a 06 98 ad 46 f5 f7 |........;*...F..| -00000010 42 cf 89 c0 d4 a7 08 df bb dc 4d 15 03 03 00 12 |B.........M.....| -00000020 9c d4 d2 a1 fb 38 98 31 7d ce 39 50 0b 58 d8 a8 |.....8.1}.9P.X..| -00000030 3e 19 |>.| +00000000 17 03 03 00 16 dc f6 18 54 22 e0 9c 08 bf db a8 |........T"......| +00000010 62 2a 64 9e 06 43 0f 22 18 0e 34 15 03 03 00 12 |b*d..C."..4.....| +00000020 20 2f f4 76 cd dc 82 eb 30 f9 e0 42 6b 29 16 ed | /.v....0..Bk)..| +00000030 7c f0 ||.| diff --git a/src/crypto/tls/testdata/Client-TLSv13-ALPN b/src/crypto/tls/testdata/Client-TLSv13-ALPN index f2ca5acfbd..0ac9b36933 100644 --- a/src/crypto/tls/testdata/Client-TLSv13-ALPN +++ b/src/crypto/tls/testdata/Client-TLSv13-ALPN @@ -1,5 +1,5 @@ >>> Flow 1 (client to server) -00000000 16 03 01 01 12 01 00 01 0e 03 03 00 00 00 00 00 |................| +00000000 16 03 01 01 0e 01 00 01 0a 03 03 00 00 00 00 00 |................| 00000010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| 00000020 00 00 00 00 00 00 00 00 00 00 00 20 00 00 00 00 |........... ....| 00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| @@ -7,87 +7,87 @@ 00000050 cc a9 c0 2f c0 2b c0 30 c0 2c c0 27 c0 13 c0 23 |.../.+.0.,.'...#| 00000060 c0 09 c0 14 c0 0a 00 9c 00 9d 00 3c 00 2f 00 35 |...........<./.5| 00000070 c0 12 00 0a 00 05 c0 11 c0 07 13 01 13 03 13 02 |................| -00000080 01 00 00 93 33 74 00 00 00 05 00 05 01 00 00 00 |....3t..........| -00000090 00 00 0a 00 0a 00 08 00 1d 00 17 00 18 00 19 00 |................| -000000a0 0b 00 02 01 00 00 0d 00 1a 00 18 08 04 04 03 08 |................| -000000b0 07 08 05 08 06 04 01 05 01 06 01 05 03 06 03 02 |................| -000000c0 01 02 03 ff 01 00 01 00 00 10 00 10 00 0e 06 70 |...............p| -000000d0 72 6f 74 6f 32 06 70 72 6f 74 6f 31 00 12 00 00 |roto2.proto1....| -000000e0 00 2b 00 09 08 03 04 03 03 03 02 03 01 00 33 00 |.+............3.| -000000f0 26 00 24 00 1d 00 20 2f e5 7d a3 47 cd 62 43 15 |&.$... /.}.G.bC.| -00000100 28 da ac 5f bb 29 07 30 ff f6 84 af c4 cf c2 ed |(.._.).0........| -00000110 90 99 5f 58 cb 3b 74 |.._X.;t| +00000080 01 00 00 8f 00 05 00 05 01 00 00 00 00 00 0a 00 |................| +00000090 0a 00 08 00 1d 00 17 00 18 00 19 00 0b 00 02 01 |................| +000000a0 00 00 0d 00 1a 00 18 08 04 04 03 08 07 08 05 08 |................| +000000b0 06 04 01 05 01 06 01 05 03 06 03 02 01 02 03 ff |................| +000000c0 01 00 01 00 00 10 00 10 00 0e 06 70 72 6f 74 6f |...........proto| +000000d0 32 06 70 72 6f 74 6f 31 00 12 00 00 00 2b 00 09 |2.proto1.....+..| +000000e0 08 03 04 03 03 03 02 03 01 00 33 00 26 00 24 00 |..........3.&.$.| +000000f0 1d 00 20 2f e5 7d a3 47 cd 62 43 15 28 da ac 5f |.. /.}.G.bC.(.._| +00000100 bb 29 07 30 ff f6 84 af c4 cf c2 ed 90 99 5f 58 |.).0.........._X| +00000110 cb 3b 74 |.;t| >>> Flow 2 (server to client) -00000000 16 03 03 00 7a 02 00 00 76 03 03 9a f4 f5 6b ec |....z...v.....k.| -00000010 37 69 ea a2 43 05 46 fe dd 55 27 2e 78 cb f6 cc |7i..C.F..U'.x...| -00000020 96 ea fd 68 98 bb 3e 9d 75 ad 6e 20 00 00 00 00 |...h..>.u.n ....| +00000000 16 03 03 00 7a 02 00 00 76 03 03 23 c5 c4 0c 4a |....z...v..#...J| +00000010 d2 5f 0b f6 ea 21 7a d1 a0 7d 21 26 b5 a3 94 ca |._...!z..}!&....| +00000020 91 6c 13 58 60 4f 39 cc 1a f7 c0 20 00 00 00 00 |.l.X`O9.... ....| 00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| 00000040 00 00 00 00 00 00 00 00 00 00 00 00 13 01 00 00 |................| -00000050 2e 00 2b 00 02 03 04 00 33 00 24 00 1d 00 20 04 |..+.....3.$... .| -00000060 67 13 de c7 ca 6c 02 d8 ee c4 80 d8 43 c2 ef 3e |g....l......C..>| -00000070 94 e1 51 d6 bf c7 1f 0c 4a b0 af 7f 91 a5 61 14 |..Q.....J.....a.| -00000080 03 03 00 01 01 17 03 03 00 24 3f 87 40 f6 93 e3 |.........$?.@...| -00000090 c9 cb 6e 83 75 c5 2f e3 af 0f 84 9a 3b 88 ad cc |..n.u./.....;...| -000000a0 99 c9 1b a8 26 e0 14 d4 ab fe 50 5f ad 79 17 03 |....&.....P_.y..| -000000b0 03 02 6d 67 86 8e eb e3 15 65 21 e5 2f aa 8d c7 |..mg.....e!./...| -000000c0 d5 34 6a b6 d3 ab 5f 96 f6 b2 79 b0 bc 3e f7 9c |.4j..._...y..>..| -000000d0 5d 8d 62 50 91 35 e1 7d fe 61 9b 8c 9d e1 4a 7f |].bP.5.}.a....J.| -000000e0 54 4b ad c5 35 3d c9 05 d1 b0 6c 3f b2 c4 f7 75 |TK..5=....l?...u| -000000f0 57 84 50 62 8d 50 80 be b6 71 b8 59 02 52 5d 55 |W.Pb.P...q.Y.R]U| -00000100 70 5e 76 61 77 d9 d1 f6 20 d1 d9 bf e2 03 16 1e |p^vaw... .......| -00000110 eb 1c 55 85 48 8d 43 72 56 2a d2 16 fc a3 cc 94 |..U.H.CrV*......| -00000120 08 6d a8 73 55 9d a8 0c 36 da f4 02 c9 23 7b d5 |.m.sU...6....#{.| -00000130 06 e7 63 63 a1 fa 80 1c ca 77 d3 ee 4a f8 61 31 |..cc.....w..J.a1| -00000140 4b 1c d6 8c f3 86 d3 16 ba fe 1c ff 5a f6 fa fc |K...........Z...| -00000150 d6 c7 ab b6 5a db 51 f3 cc 42 f0 65 b6 8f f3 d7 |....Z.Q..B.e....| -00000160 44 5a e7 1e a9 d4 a7 bd cd 20 bf a1 13 f1 b5 29 |DZ....... .....)| -00000170 91 a4 28 78 f5 b6 c2 09 a5 95 e5 98 ab c9 f4 4b |..(x...........K| -00000180 10 da eb 07 ff 46 44 f9 85 f6 4f 78 5c b0 fa 2d |.....FD...Ox\..-| -00000190 0b 3b 79 3f 11 a2 eb 12 96 a3 01 ac 13 d3 65 cc |.;y?..........e.| -000001a0 98 e8 c9 8c c3 c6 c9 09 aa f6 af 01 1e e5 30 40 |..............0@| -000001b0 40 88 44 26 ee 49 91 68 18 56 b9 ce 22 f6 80 ff |@.D&.I.h.V.."...| -000001c0 32 d0 ee 15 e3 8a 96 c0 e5 47 51 c1 7f 70 e1 fc |2........GQ..p..| -000001d0 3a 44 1a 36 b9 e7 ee f0 9c 4e 62 1f 78 2f cc dd |:D.6.....Nb.x/..| -000001e0 62 a3 3b 9b ae d1 34 ea 7f d7 dc b4 c5 2c d7 96 |b.;...4......,..| -000001f0 61 59 0b ed de cc 70 68 06 2c 93 3d a9 9f 0a 9b |aY....ph.,.=....| -00000200 46 0d 39 fa b0 db 7f 9b c1 80 c8 55 35 bb 10 4c |F.9........U5..L| -00000210 2d 8f 88 ae 94 bf 4a 5f 3b f5 95 e7 7a 47 e2 0e |-.....J_;...zG..| -00000220 19 b2 e7 69 f5 bb c0 08 9d e8 5e 23 f0 85 12 c0 |...i......^#....| -00000230 01 cf 7a 87 19 b1 98 97 8d 5a 19 5c 37 52 0b a7 |..z......Z.\7R..| -00000240 45 e8 8f 9b 0c 76 5f a6 5b d9 45 87 5b 6e 0e db |E....v_.[.E.[n..| -00000250 6a 6a e2 b2 1d f9 e6 31 13 09 8c 32 93 43 46 17 |jj.....1...2.CF.| -00000260 15 45 c8 26 7f f2 23 7b b1 da c4 20 56 59 4b c9 |.E.&..#{... VYK.| -00000270 3e 90 a6 77 ea 28 ea 05 74 b8 04 55 68 7a 60 91 |>..w.(..t..Uhz`.| -00000280 b7 8e 7d 96 11 ac 2d af f2 26 c5 03 99 57 80 a7 |..}...-..&...W..| -00000290 80 1f 6f ce fd 0e 81 af 2e d6 b0 6b 7c 4c 71 02 |..o........k|Lq.| -000002a0 4c 56 fc e9 0a 58 56 5e 4d fd 2d ea e8 ae d5 b7 |LV...XV^M.-.....| -000002b0 cf aa 66 48 a9 42 76 59 81 52 18 cf c4 6d d8 8c |..fH.BvY.R...m..| -000002c0 90 e3 57 28 53 43 5e ae cd 33 ac 64 e2 ff 65 17 |..W(SC^..3.d..e.| -000002d0 11 e2 6a 07 aa 57 40 63 90 51 11 43 9f 9e 6d 56 |..j..W@c.Q.C..mV| -000002e0 69 c2 44 bb f9 83 84 79 bf 98 be 62 e8 20 6e cc |i.D....y...b. n.| -000002f0 69 a9 c4 33 de 40 d5 e9 95 12 87 d5 28 24 05 62 |i..3.@......($.b| -00000300 ca b8 c2 bd d9 96 dc 16 03 c8 7d 9c 7a 83 de 55 |..........}.z..U| -00000310 3b 4f 90 7b af 36 9a a7 80 46 c5 76 14 70 6c f4 |;O.{.6...F.v.pl.| -00000320 17 03 03 00 99 6e 39 2c 0d 81 12 85 c2 1c 42 56 |.....n9,......BV| -00000330 6a 3a e2 04 60 af 78 13 20 d2 b5 b2 58 9e 2f b9 |j:..`.x. ...X./.| -00000340 f8 11 4f 52 cd 31 c3 a1 ec 83 bd 2e ea 9a 53 6b |..OR.1........Sk| -00000350 55 99 a6 8a 25 1c f7 b6 83 4e 9f 1e 5d c5 b2 b2 |U...%....N..]...| -00000360 a5 6b ea 87 96 0e 29 5b a4 24 f2 16 4c ad e1 9b |.k....)[.$..L...| -00000370 24 d2 95 7e 74 37 44 1a d7 83 f5 4c 28 3f 3d 92 |$..~t7D....L(?=.| -00000380 a7 6f 6e 70 1c 27 93 19 64 ee 61 dc 81 35 67 c8 |.onp.'..d.a..5g.| -00000390 f3 e6 de b0 8f 32 6c df b1 66 97 6b b9 4a 81 f0 |.....2l..f.k.J..| -000003a0 cd 3a b4 56 14 e3 27 50 b0 f3 9b 63 05 a5 99 3a |.:.V..'P...c...:| -000003b0 26 d6 a5 3c e4 ea 8a 5a 04 5e fb de 86 bb 17 03 |&..<...Z.^......| -000003c0 03 00 35 eb 5f 0f df 9f e0 c7 4d b4 3d a6 c8 1a |..5._.....M.=...| -000003d0 df f1 f8 1e 36 ea ae 30 32 da 78 0e 00 fe d3 54 |....6..02.x....T| -000003e0 cc 90 08 1a cb 92 1c 5f f7 0a 3c f7 19 ed a3 3b |......._..<....;| -000003f0 cb fd 56 cb 4f 30 83 07 |..V.O0..| +00000050 2e 00 2b 00 02 03 04 00 33 00 24 00 1d 00 20 f9 |..+.....3.$... .| +00000060 64 7e 54 8f 64 ec 3d 7c 17 f1 96 3c 44 ca cd d7 |d~T.d.=|...>> Flow 3 (client to server) -00000000 14 03 03 00 01 01 17 03 03 00 35 ec 05 98 86 f9 |..........5.....| -00000010 a1 e4 14 c1 e2 85 17 62 f9 ff 5f 1f 53 8f 00 14 |.......b.._.S...| -00000020 28 dd 31 bc 9a 7e 2d 54 53 c2 57 f0 24 0f e1 ca |(.1..~-TS.W.$...| -00000030 5e 17 07 bc 32 a5 72 3f 3e 90 dd be f1 a1 cc 6b |^...2.r?>......k| -00000040 17 03 03 00 17 93 58 dd 95 9a 88 82 3d 63 41 f7 |......X.....=cA.| -00000050 ba da 0e 24 3f f2 b1 e5 db 83 2d bd 17 03 03 00 |...$?.....-.....| -00000060 13 03 a4 42 58 3b d7 c5 c2 08 45 e5 c1 bc eb 47 |...BX;....E....G| -00000070 b5 20 ea ce |. ..| +00000000 14 03 03 00 01 01 17 03 03 00 35 3e e7 50 e1 d1 |..........5>.P..| +00000010 4d 9f 84 fe ca 83 c4 3b a6 86 45 c2 7e e7 af 00 |M......;..E.~...| +00000020 db e6 23 3c 06 b8 a3 1e 36 2e ab 45 7e d8 07 8c |..#<....6..E~...| +00000030 66 bf 5a 0f ff e6 3f 09 a4 d3 cf 74 1c d6 cf c7 |f.Z...?....t....| +00000040 17 03 03 00 17 4c db af a7 f3 73 b3 84 b9 a7 d1 |.....L....s.....| +00000050 1c 2f cb 27 d8 ba 2c c6 84 48 88 18 17 03 03 00 |./.'..,..H......| +00000060 13 a3 41 6f fb da f5 5a 4d 85 0c e0 ff 3a fb 91 |..Ao...ZM....:..| +00000070 e2 5e ab 96 |.^..| -- cgit v1.3 From 047141797c160430c9f41e1225bbfbf562fd7795 Mon Sep 17 00:00:00 2001 From: Cuong Manh Le Date: Sun, 29 Sep 2019 23:42:42 +0700 Subject: cmd/compile: lookup methods of base type for named pointer type Passed toolstash-check. Updates #21738 Fixes #21934 Change-Id: I59f0b2c9890146565ff913b04aeeeff7dc7a4499 Reviewed-on: https://go-review.googlesource.com/c/go/+/197561 Run-TryBot: Cuong Manh Le Reviewed-by: Matthew Dempsky TryBot-Result: Gobot Gobot --- src/cmd/compile/internal/gc/subr.go | 7 ++++++- test/fixedbugs/issue21934.go | 26 ++++++++++++++++++++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) create mode 100644 test/fixedbugs/issue21934.go (limited to 'src') diff --git a/src/cmd/compile/internal/gc/subr.go b/src/cmd/compile/internal/gc/subr.go index 3fc59194e4..27326f67a1 100644 --- a/src/cmd/compile/internal/gc/subr.go +++ b/src/cmd/compile/internal/gc/subr.go @@ -1189,7 +1189,12 @@ func lookdot0(s *types.Sym, t *types.Type, save **types.Field, ignorecase bool) } } - u = methtype(t) + u = t + if t.Sym != nil && t.IsPtr() && !t.Elem().IsPtr() { + // If t is a defined pointer type, then x.m is shorthand for (*x).m. + u = t.Elem() + } + u = methtype(u) if u != nil { for _, f := range u.Methods().Slice() { if f.Embedded == 0 && (f.Sym == s || (ignorecase && strings.EqualFold(f.Sym.Name, s.Name))) { diff --git a/test/fixedbugs/issue21934.go b/test/fixedbugs/issue21934.go new file mode 100644 index 0000000000..e9a430f18f --- /dev/null +++ b/test/fixedbugs/issue21934.go @@ -0,0 +1,26 @@ +// errorcheck + +// Copyright 2019 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +// selector expression resolves incorrectly for defined +// pointer types. + +package main + +type E struct{ f int } +type T struct{ E } + +func (*T) f() int { return 0 } + +type P *T +type PP **T + +func main() { + var x P + _ = x.f // ERROR "x\.f undefined \(type P has no field or method f\)" + + var y PP + _ = y.f // ERROR "y\.f undefined \(type PP has no field or method f\)" +} -- cgit v1.3 From 961837dec23f900bbf8b04230c72397a0aab4be6 Mon Sep 17 00:00:00 2001 From: "Bryan C. Mills" Date: Thu, 3 Oct 2019 18:55:59 +0000 Subject: Revert "cmd/go: add a Latest field to the output of 'go mod download -json'" This reverts CL 183841. Fixes #34533 Reason for revert: Introduced a significant performance regression for repos with many incompatible-version tags. Change-Id: I75d7fd76e6e1a0902b114b00167b38439e0f8221 Reviewed-on: https://go-review.googlesource.com/c/go/+/198699 Run-TryBot: Bryan C. Mills TryBot-Result: Gobot Gobot Reviewed-by: Katie Hockman Reviewed-by: Jay Conrod --- src/cmd/go/alldocs.go | 1 - src/cmd/go/internal/modcmd/download.go | 30 ---------------------- src/cmd/go/testdata/script/mod_download.txt | 4 +-- src/cmd/go/testdata/script/mod_download_latest.txt | 20 --------------- src/cmd/go/testdata/script/mod_list_upgrade.txt | 20 --------------- 5 files changed, 1 insertion(+), 74 deletions(-) delete mode 100644 src/cmd/go/testdata/script/mod_download_latest.txt (limited to 'src') diff --git a/src/cmd/go/alldocs.go b/src/cmd/go/alldocs.go index 847a7c5020..115eec4167 100644 --- a/src/cmd/go/alldocs.go +++ b/src/cmd/go/alldocs.go @@ -1022,7 +1022,6 @@ // Dir string // absolute path to cached source root directory // Sum string // checksum for path, version (as in go.sum) // GoModSum string // checksum for go.mod (as in go.sum) -// Latest bool // would @latest resolve to this version? // } // // See 'go help modules' for more about module queries. diff --git a/src/cmd/go/internal/modcmd/download.go b/src/cmd/go/internal/modcmd/download.go index 60d0d5b6e2..0d432e9549 100644 --- a/src/cmd/go/internal/modcmd/download.go +++ b/src/cmd/go/internal/modcmd/download.go @@ -43,7 +43,6 @@ corresponding to this Go struct: Dir string // absolute path to cached source root directory Sum string // checksum for path, version (as in go.sum) GoModSum string // checksum for go.mod (as in go.sum) - Latest bool // would @latest resolve to this version? } See 'go help modules' for more about module queries. @@ -66,7 +65,6 @@ type moduleJSON struct { Dir string `json:",omitempty"` Sum string `json:",omitempty"` GoModSum string `json:",omitempty"` - Latest bool `json:",omitempty"` } func runDownload(cmd *base.Command, args []string) { @@ -105,31 +103,6 @@ func runDownload(cmd *base.Command, args []string) { work.Add(m) } - latest := map[string]string{} // path → version - if *downloadJSON { - // We need to populate the Latest field, but if the main module depends on a - // version newer than latest — or if the version requested on the command - // line is itself newer than latest — that's not trivial to determine from - // the info returned by ListModules. Instead, we issue a separate - // ListModules request for "latest", which should be inexpensive relative to - // downloading the modules. - var latestArgs []string - for _, m := range mods { - if m.Error != "" { - continue - } - latestArgs = append(latestArgs, m.Path+"@latest") - } - - if len(latestArgs) > 0 { - for _, info := range modload.ListModules(latestArgs, listU, listVersions) { - if info.Version != "" { - latest[info.Path] = info.Version - } - } - } - } - work.Do(10, func(item interface{}) { m := item.(*moduleJSON) var err error @@ -160,9 +133,6 @@ func runDownload(cmd *base.Command, args []string) { m.Error = err.Error() return } - if latest[m.Path] == m.Version { - m.Latest = true - } }) if *downloadJSON { diff --git a/src/cmd/go/testdata/script/mod_download.txt b/src/cmd/go/testdata/script/mod_download.txt index 9eb3140c33..0777913786 100644 --- a/src/cmd/go/testdata/script/mod_download.txt +++ b/src/cmd/go/testdata/script/mod_download.txt @@ -17,7 +17,6 @@ stderr 'this.domain.is.invalid' stdout '"Error": ".*this.domain.is.invalid.*"' # download -json with version should print JSON -# and download the .info file for the 'latest' version. go mod download -json 'rsc.io/quote@<=v1.5.0' stdout '^\t"Path": "rsc.io/quote"' stdout '^\t"Version": "v1.5.0"' @@ -28,14 +27,13 @@ stdout '^\t"Sum": "h1:6fJa6E\+wGadANKkUMlZ0DhXFpoKlslOQDCo259XtdIE="' # hash of stdout '^\t"GoModSum": "h1:LzX7hefJvL54yjefDEDHNONDjII0t9xZLPXsUe\+TKr0="' ! stdout '"Error"' -exists $GOPATH/pkg/mod/cache/download/rsc.io/quote/@v/v1.5.2.info - # download queries above should not have added to go.mod. go list -m all ! stdout rsc.io # add to go.mod so we can test non-query downloads go mod edit -require rsc.io/quote@v1.5.2 +! exists $GOPATH/pkg/mod/cache/download/rsc.io/quote/@v/v1.5.2.info ! exists $GOPATH/pkg/mod/cache/download/rsc.io/quote/@v/v1.5.2.mod ! exists $GOPATH/pkg/mod/cache/download/rsc.io/quote/@v/v1.5.2.zip diff --git a/src/cmd/go/testdata/script/mod_download_latest.txt b/src/cmd/go/testdata/script/mod_download_latest.txt deleted file mode 100644 index 60d860e4da..0000000000 --- a/src/cmd/go/testdata/script/mod_download_latest.txt +++ /dev/null @@ -1,20 +0,0 @@ -env GO111MODULE=on - -# If the module is the latest version of itself, -# the Latest field should be set. -go mod download -json rsc.io/quote@v1.5.2 -stdout '"Latest":\s*true' - -# If the module is older than latest, the field should be unset. -go mod download -json rsc.io/quote@v1.5.1 -! stdout '"Latest":' - -# If the module is newer than "latest", the field should be unset... -go mod download -json rsc.io/quote@v1.5.3-pre1 -! stdout '"Latest":' - -# ...even if that version is also what is required by the main module. -go mod init example.com -go mod edit -require rsc.io/quote@v1.5.3-pre1 -go mod download -json rsc.io/quote@v1.5.3-pre1 -! stdout '"Latest":' diff --git a/src/cmd/go/testdata/script/mod_list_upgrade.txt b/src/cmd/go/testdata/script/mod_list_upgrade.txt index f2d0649092..474df0dc26 100644 --- a/src/cmd/go/testdata/script/mod_list_upgrade.txt +++ b/src/cmd/go/testdata/script/mod_list_upgrade.txt @@ -1,28 +1,8 @@ env GO111MODULE=on -# If the current version is not latest, 'go list -u' should include its upgrade. go list -m -u all stdout 'rsc.io/quote v1.2.0 \[v1\.5\.2\]' -# If the current version is latest, 'go list -u' should omit the upgrade. -go get -d rsc.io/quote@v1.5.2 -go list -m -u all -stdout 'rsc.io/quote v1.5.2$' - -# If the current version is newer than latest, 'go list -u' should -# omit the upgrade. -go get -d rsc.io/quote@v1.5.3-pre1 -go list -m -u all -stdout 'rsc.io/quote v1.5.3-pre1$' - -# If the current build list has a higher version and the user asks about -# a lower one, -u should report the upgrade for the lower one -# but leave the build list unchanged. -go list -m -u rsc.io/quote@v1.5.1 -stdout 'rsc.io/quote v1.5.1 \[v1.5.2\]$' -go list -m -u rsc.io/quote -stdout 'rsc.io/quote v1.5.3-pre1$' - -- go.mod -- module x require rsc.io/quote v1.2.0 -- cgit v1.3 From 86ea7d5171a5b9a3c2d606444ef9985214fcec71 Mon Sep 17 00:00:00 2001 From: Jay Conrod Date: Fri, 4 Oct 2019 13:27:49 -0400 Subject: cmd/go/internal/modfile: report error for extra text around version Fixes #34697 Change-Id: Iedfa3d46d558510f3bd1fdf9466cd974793d9ecd Reviewed-on: https://go-review.googlesource.com/c/go/+/199017 Run-TryBot: Jay Conrod TryBot-Result: Gobot Gobot Reviewed-by: Bryan C. Mills --- src/cmd/go/internal/modfile/read_test.go | 23 +++++++++++++++++++++++ src/cmd/go/internal/modfile/rule.go | 2 +- 2 files changed, 24 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/go/internal/modfile/read_test.go b/src/cmd/go/internal/modfile/read_test.go index 8cb1a3908c..32401304b9 100644 --- a/src/cmd/go/internal/modfile/read_test.go +++ b/src/cmd/go/internal/modfile/read_test.go @@ -363,3 +363,26 @@ func TestModulePath(t *testing.T) { }) } } + +func TestGoVersion(t *testing.T) { + for _, test := range []struct { + desc, input string + ok bool + }{ + {desc: "empty", input: "module m\ngo \n", ok: false}, + {desc: "one", input: "module m\ngo 1\n", ok: false}, + {desc: "two", input: "module m\ngo 1.22\n", ok: true}, + {desc: "three", input: "module m\ngo 1.22.333", ok: false}, + {desc: "before", input: "module m\ngo v1.2\n", ok: false}, + {desc: "after", input: "module m\ngo 1.2rc1\n", ok: false}, + {desc: "space", input: "module m\ngo 1.2 3.4\n", ok: false}, + } { + t.Run(test.desc, func(t *testing.T) { + if _, err := Parse("go.mod", []byte(test.input), nil); err == nil && !test.ok { + t.Error("unexpected success") + } else if err != nil && test.ok { + t.Errorf("unexpected error: %v", err) + } + }) + } +} diff --git a/src/cmd/go/internal/modfile/rule.go b/src/cmd/go/internal/modfile/rule.go index 6e1a22f3ca..e1f2687840 100644 --- a/src/cmd/go/internal/modfile/rule.go +++ b/src/cmd/go/internal/modfile/rule.go @@ -153,7 +153,7 @@ func parseToFile(file string, data []byte, fix VersionFixer, strict bool) (*File return f, nil } -var GoVersionRE = lazyregexp.New(`([1-9][0-9]*)\.(0|[1-9][0-9]*)`) +var GoVersionRE = lazyregexp.New(`^([1-9][0-9]*)\.(0|[1-9][0-9]*)$`) func (f *File) add(errs *bytes.Buffer, line *Line, verb string, args []string, fix VersionFixer, strict bool) { // If strict is false, this module is a dependency. -- cgit v1.3 From e06829b9772ca3a7d5ba3c573b345699f51d69b0 Mon Sep 17 00:00:00 2001 From: David Chase Date: Tue, 1 Oct 2019 11:08:46 -0400 Subject: cmd/compile: preserve statement marks in branch elimination This reduces the number of missing-statement lines. Change-Id: Iefa56c2a253220d17d8b53210c8c6af78ee68756 Reviewed-on: https://go-review.googlesource.com/c/go/+/198483 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/branchelim.go | 96 ++++++++++++++++++++++++++++-- 1 file changed, 92 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/branchelim.go b/src/cmd/compile/internal/ssa/branchelim.go index c79b913d72..298eed362a 100644 --- a/src/cmd/compile/internal/ssa/branchelim.go +++ b/src/cmd/compile/internal/ssa/branchelim.go @@ -4,6 +4,8 @@ package ssa +import "cmd/internal/src" + // branchelim tries to eliminate branches by // generating CondSelect instructions. // @@ -174,12 +176,98 @@ func elimIf(f *Func, loadAddr *sparseSet, dom *Block) bool { e.b.Preds[e.i].b = dom } - for i := range simple.Values { - simple.Values[i].Block = dom + // Try really hard to preserve statement marks attached to blocks. + simplePos := simple.Pos + postPos := post.Pos + simpleStmt := simplePos.IsStmt() == src.PosIsStmt + postStmt := postPos.IsStmt() == src.PosIsStmt + + for _, v := range simple.Values { + v.Block = dom } - for i := range post.Values { - post.Values[i].Block = dom + for _, v := range post.Values { + v.Block = dom } + + // findBlockPos determines if b contains a stmt-marked value + // that has the same line number as the Pos for b itself. + // (i.e. is the position on b actually redundant?) + findBlockPos := func(b *Block) bool { + pos := b.Pos + for _, v := range b.Values { + // See if there is a stmt-marked value already that matches simple.Pos (and perhaps post.Pos) + if pos.SameFileAndLine(v.Pos) && v.Pos.IsStmt() == src.PosIsStmt { + return true + } + } + return false + } + if simpleStmt { + simpleStmt = !findBlockPos(simple) + if !simpleStmt && simplePos.SameFileAndLine(postPos) { + postStmt = false + } + + } + if postStmt { + postStmt = !findBlockPos(post) + } + + // If simpleStmt and/or postStmt are still true, then try harder + // to find the corresponding statement marks new homes. + + // setBlockPos determines if b contains a can-be-statement value + // that has the same line number as the Pos for b itself, and + // puts a statement mark on it, and returns whether it succeeded + // in this operation. + setBlockPos := func (b *Block) bool { + pos := b.Pos + for _, v := range b.Values { + if pos.SameFileAndLine(v.Pos) && !isPoorStatementOp(v.Op) { + v.Pos = v.Pos.WithIsStmt() + return true + } + } + return false + } + // If necessary and possible, add a mark to a value in simple + if simpleStmt { + if setBlockPos(simple) && simplePos.SameFileAndLine(postPos) { + postStmt = false + } + } + // If necessary and possible, add a mark to a value in post + if postStmt { + postStmt = !setBlockPos(post) + } + + // Before giving up (this was added because it helps), try the end of "dom", and if that is not available, + // try the values in the successor block if it is uncomplicated. + if postStmt { + if dom.Pos.IsStmt() != src.PosIsStmt { + dom.Pos = postPos + } else { + // Try the successor block + if len(dom.Succs) == 1 && len(dom.Succs[0].Block().Preds) == 1 { + succ := dom.Succs[0].Block() + for _, v := range succ.Values { + if isPoorStatementOp(v.Op) { + continue + } + if postPos.SameFileAndLine(v.Pos) { + v.Pos = v.Pos.WithIsStmt() + } + postStmt = false + break + } + // If postStmt still true, tag the block itself if possible + if postStmt && succ.Pos.IsStmt() != src.PosIsStmt { + succ.Pos = postPos + } + } + } + } + dom.Values = append(dom.Values, simple.Values...) dom.Values = append(dom.Values, post.Values...) -- cgit v1.3 From 7e4d87b7708dbd319f3c44c8b4d49ef7f51504c8 Mon Sep 17 00:00:00 2001 From: "Jason A. Donenfeld" Date: Fri, 4 Oct 2019 16:48:17 +0200 Subject: syscall: replace mksyscall_windows.go with wrapper to new x/sys home We replace the existing file with a thin wrapper around its target so that we don't break anybody's workflow. Updates #34388 Change-Id: I0d00371c483cb78f4be18fe987df33c79cd40f05 Reviewed-on: https://go-review.googlesource.com/c/go/+/198977 Run-TryBot: Jason A. Donenfeld TryBot-Result: Gobot Gobot Reviewed-by: Brad Fitzpatrick --- src/syscall/mksyscall_windows.go | 919 +-------------------------------------- 1 file changed, 8 insertions(+), 911 deletions(-) (limited to 'src') diff --git a/src/syscall/mksyscall_windows.go b/src/syscall/mksyscall_windows.go index dbeb684be6..d66bf7865f 100644 --- a/src/syscall/mksyscall_windows.go +++ b/src/syscall/mksyscall_windows.go @@ -4,926 +4,23 @@ // +build ignore -/* -mksyscall_windows generates windows system call bodies - -It parses all files specified on command line containing function -prototypes (like syscall_windows.go) and prints system call bodies -to standard output. - -The prototypes are marked by lines beginning with "//sys" and read -like func declarations if //sys is replaced by func, but: - -* The parameter lists must give a name for each argument. This - includes return parameters. - -* The parameter lists must give a type for each argument: - the (x, y, z int) shorthand is not allowed. - -* If the return parameter is an error number, it must be named err. - -* If go func name needs to be different from its winapi dll name, - the winapi name could be specified at the end, after "=" sign, like - //sys LoadLibrary(libname string) (handle uint32, err error) = LoadLibraryA - -* Each function that returns err needs to supply a condition, that - return value of winapi will be tested against to detect failure. - This would set err to windows "last-error", otherwise it will be nil. - The value can be provided at end of //sys declaration, like - //sys LoadLibrary(libname string) (handle uint32, err error) [failretval==-1] = LoadLibraryA - and is [failretval==0] by default. - -Usage: - mksyscall_windows [flags] [path ...] - -The flags are: - -output - Specify output file name (outputs to console if blank). - -trace - Generate print statement after every syscall. -*/ package main import ( - "bufio" - "bytes" - "errors" - "flag" - "fmt" - "go/format" - "go/parser" - "go/token" - "io" - "io/ioutil" - "log" "os" + "os/exec" "path/filepath" "runtime" - "sort" - "strconv" - "strings" - "text/template" -) - -var ( - filename = flag.String("output", "", "output file name (standard output if omitted)") - printTraceFlag = flag.Bool("trace", false, "generate print statement after every syscall") - systemDLL = flag.Bool("systemdll", true, "whether all DLLs should be loaded from the Windows system directory") ) -func trim(s string) string { - return strings.Trim(s, " \t") -} - -var packageName string - -func packagename() string { - return packageName -} - -func syscalldot() string { - if packageName == "syscall" { - return "" - } - return "syscall." -} - -// Param is function parameter -type Param struct { - Name string - Type string - fn *Fn - tmpVarIdx int -} - -// tmpVar returns temp variable name that will be used to represent p during syscall. -func (p *Param) tmpVar() string { - if p.tmpVarIdx < 0 { - p.tmpVarIdx = p.fn.curTmpVarIdx - p.fn.curTmpVarIdx++ - } - return fmt.Sprintf("_p%d", p.tmpVarIdx) -} - -// BoolTmpVarCode returns source code for bool temp variable. -func (p *Param) BoolTmpVarCode() string { - const code = `var %s uint32 - if %s { - %s = 1 - } else { - %s = 0 - }` - tmp := p.tmpVar() - return fmt.Sprintf(code, tmp, p.Name, tmp, tmp) -} - -// BoolPointerTmpVarCode returns source code for bool temp variable. -func (p *Param) BoolPointerTmpVarCode() string { - const code = `var %s uint32 - if *%s { - %s = 1 - } else { - %s = 0 - }` - tmp := p.tmpVar() - return fmt.Sprintf(code, tmp, p.Name, tmp, tmp) -} - -// SliceTmpVarCode returns source code for slice temp variable. -func (p *Param) SliceTmpVarCode() string { - const code = `var %s *%s - if len(%s) > 0 { - %s = &%s[0] - }` - tmp := p.tmpVar() - return fmt.Sprintf(code, tmp, p.Type[2:], p.Name, tmp, p.Name) -} - -// StringTmpVarCode returns source code for string temp variable. -func (p *Param) StringTmpVarCode() string { - errvar := p.fn.Rets.ErrorVarName() - if errvar == "" { - errvar = "_" - } - tmp := p.tmpVar() - const code = `var %s %s - %s, %s = %s(%s)` - s := fmt.Sprintf(code, tmp, p.fn.StrconvType(), tmp, errvar, p.fn.StrconvFunc(), p.Name) - if errvar == "-" { - return s - } - const morecode = ` - if %s != nil { - return - }` - return s + fmt.Sprintf(morecode, errvar) -} - -// TmpVarCode returns source code for temp variable. -func (p *Param) TmpVarCode() string { - switch { - case p.Type == "bool": - return p.BoolTmpVarCode() - case p.Type == "*bool": - return p.BoolPointerTmpVarCode() - case strings.HasPrefix(p.Type, "[]"): - return p.SliceTmpVarCode() - default: - return "" - } -} - -// TmpVarReadbackCode returns source code for reading back the temp variable into the original variable. -func (p *Param) TmpVarReadbackCode() string { - switch { - case p.Type == "*bool": - return fmt.Sprintf("*%s = %s != 0", p.Name, p.tmpVar()) - default: - return "" - } -} - -// TmpVarHelperCode returns source code for helper's temp variable. -func (p *Param) TmpVarHelperCode() string { - if p.Type != "string" { - return "" - } - return p.StringTmpVarCode() -} - -// SyscallArgList returns source code fragments representing p parameter -// in syscall. Slices are translated into 2 syscall parameters: pointer to -// the first element and length. -func (p *Param) SyscallArgList() []string { - t := p.HelperType() - var s string - switch { - case t == "*bool": - s = fmt.Sprintf("unsafe.Pointer(&%s)", p.tmpVar()) - case t[0] == '*': - s = fmt.Sprintf("unsafe.Pointer(%s)", p.Name) - case t == "bool": - s = p.tmpVar() - case strings.HasPrefix(t, "[]"): - return []string{ - fmt.Sprintf("uintptr(unsafe.Pointer(%s))", p.tmpVar()), - fmt.Sprintf("uintptr(len(%s))", p.Name), - } - default: - s = p.Name - } - return []string{fmt.Sprintf("uintptr(%s)", s)} -} - -// IsError determines if p parameter is used to return error. -func (p *Param) IsError() bool { - return p.Name == "err" && p.Type == "error" -} - -// HelperType returns type of parameter p used in helper function. -func (p *Param) HelperType() string { - if p.Type == "string" { - return p.fn.StrconvType() - } - return p.Type -} - -// join concatenates parameters ps into a string with sep separator. -// Each parameter is converted into string by applying fn to it -// before conversion. -func join(ps []*Param, fn func(*Param) string, sep string) string { - if len(ps) == 0 { - return "" - } - a := make([]string, 0) - for _, p := range ps { - a = append(a, fn(p)) - } - return strings.Join(a, sep) -} - -// Rets describes function return parameters. -type Rets struct { - Name string - Type string - ReturnsError bool - FailCond string -} - -// ErrorVarName returns error variable name for r. -func (r *Rets) ErrorVarName() string { - if r.ReturnsError { - return "err" - } - if r.Type == "error" { - return r.Name - } - return "" -} - -// ToParams converts r into slice of *Param. -func (r *Rets) ToParams() []*Param { - ps := make([]*Param, 0) - if len(r.Name) > 0 { - ps = append(ps, &Param{Name: r.Name, Type: r.Type}) - } - if r.ReturnsError { - ps = append(ps, &Param{Name: "err", Type: "error"}) - } - return ps -} - -// List returns source code of syscall return parameters. -func (r *Rets) List() string { - s := join(r.ToParams(), func(p *Param) string { return p.Name + " " + p.Type }, ", ") - if len(s) > 0 { - s = "(" + s + ")" - } - return s -} - -// PrintList returns source code of trace printing part correspondent -// to syscall return values. -func (r *Rets) PrintList() string { - return join(r.ToParams(), func(p *Param) string { return fmt.Sprintf(`"%s=", %s, `, p.Name, p.Name) }, `", ", `) -} - -// SetReturnValuesCode returns source code that accepts syscall return values. -func (r *Rets) SetReturnValuesCode() string { - if r.Name == "" && !r.ReturnsError { - return "" - } - retvar := "r0" - if r.Name == "" { - retvar = "r1" - } - errvar := "_" - if r.ReturnsError { - errvar = "e1" - } - return fmt.Sprintf("%s, _, %s := ", retvar, errvar) -} - -func (r *Rets) useLongHandleErrorCode(retvar string) string { - const code = `if %s { - if e1 != 0 { - err = errnoErr(e1) - } else { - err = %sEINVAL - } - }` - cond := retvar + " == 0" - if r.FailCond != "" { - cond = strings.Replace(r.FailCond, "failretval", retvar, 1) - } - return fmt.Sprintf(code, cond, syscalldot()) -} - -// SetErrorCode returns source code that sets return parameters. -func (r *Rets) SetErrorCode() string { - const code = `if r0 != 0 { - %s = %sErrno(r0) - }` - if r.Name == "" && !r.ReturnsError { - return "" - } - if r.Name == "" { - return r.useLongHandleErrorCode("r1") - } - if r.Type == "error" { - return fmt.Sprintf(code, r.Name, syscalldot()) - } - s := "" - switch { - case r.Type[0] == '*': - s = fmt.Sprintf("%s = (%s)(unsafe.Pointer(r0))", r.Name, r.Type) - case r.Type == "bool": - s = fmt.Sprintf("%s = r0 != 0", r.Name) - default: - s = fmt.Sprintf("%s = %s(r0)", r.Name, r.Type) - } - if !r.ReturnsError { - return s - } - return s + "\n\t" + r.useLongHandleErrorCode(r.Name) -} - -// Fn describes syscall function. -type Fn struct { - Name string - Params []*Param - Rets *Rets - PrintTrace bool - dllname string - dllfuncname string - src string - // TODO: get rid of this field and just use parameter index instead - curTmpVarIdx int // insure tmp variables have uniq names -} - -// extractParams parses s to extract function parameters. -func extractParams(s string, f *Fn) ([]*Param, error) { - s = trim(s) - if s == "" { - return nil, nil - } - a := strings.Split(s, ",") - ps := make([]*Param, len(a)) - for i := range ps { - s2 := trim(a[i]) - b := strings.Split(s2, " ") - if len(b) != 2 { - b = strings.Split(s2, "\t") - if len(b) != 2 { - return nil, errors.New("Could not extract function parameter from \"" + s2 + "\"") - } - } - ps[i] = &Param{ - Name: trim(b[0]), - Type: trim(b[1]), - fn: f, - tmpVarIdx: -1, - } - } - return ps, nil -} - -// extractSection extracts text out of string s starting after start -// and ending just before end. found return value will indicate success, -// and prefix, body and suffix will contain correspondent parts of string s. -func extractSection(s string, start, end rune) (prefix, body, suffix string, found bool) { - s = trim(s) - if strings.HasPrefix(s, string(start)) { - // no prefix - body = s[1:] - } else { - a := strings.SplitN(s, string(start), 2) - if len(a) != 2 { - return "", "", s, false - } - prefix = a[0] - body = a[1] - } - a := strings.SplitN(body, string(end), 2) - if len(a) != 2 { - return "", "", "", false - } - return prefix, a[0], a[1], true -} - -// newFn parses string s and return created function Fn. -func newFn(s string) (*Fn, error) { - s = trim(s) - f := &Fn{ - Rets: &Rets{}, - src: s, - PrintTrace: *printTraceFlag, - } - // function name and args - prefix, body, s, found := extractSection(s, '(', ')') - if !found || prefix == "" { - return nil, errors.New("Could not extract function name and parameters from \"" + f.src + "\"") - } - f.Name = prefix - var err error - f.Params, err = extractParams(body, f) - if err != nil { - return nil, err - } - // return values - _, body, s, found = extractSection(s, '(', ')') - if found { - r, err := extractParams(body, f) - if err != nil { - return nil, err - } - switch len(r) { - case 0: - case 1: - if r[0].IsError() { - f.Rets.ReturnsError = true - } else { - f.Rets.Name = r[0].Name - f.Rets.Type = r[0].Type - } - case 2: - if !r[1].IsError() { - return nil, errors.New("Only last windows error is allowed as second return value in \"" + f.src + "\"") - } - f.Rets.ReturnsError = true - f.Rets.Name = r[0].Name - f.Rets.Type = r[0].Type - default: - return nil, errors.New("Too many return values in \"" + f.src + "\"") - } - } - // fail condition - _, body, s, found = extractSection(s, '[', ']') - if found { - f.Rets.FailCond = body - } - // dll and dll function names - s = trim(s) - if s == "" { - return f, nil - } - if !strings.HasPrefix(s, "=") { - return nil, errors.New("Could not extract dll name from \"" + f.src + "\"") - } - s = trim(s[1:]) - a := strings.Split(s, ".") - switch len(a) { - case 1: - f.dllfuncname = a[0] - case 2: - f.dllname = a[0] - f.dllfuncname = a[1] - default: - return nil, errors.New("Could not extract dll name from \"" + f.src + "\"") - } - return f, nil -} - -// DLLName returns DLL name for function f. -func (f *Fn) DLLName() string { - if f.dllname == "" { - return "kernel32" - } - return f.dllname -} - -// DLLName returns DLL function name for function f. -func (f *Fn) DLLFuncName() string { - if f.dllfuncname == "" { - return f.Name - } - return f.dllfuncname -} - -// ParamList returns source code for function f parameters. -func (f *Fn) ParamList() string { - return join(f.Params, func(p *Param) string { return p.Name + " " + p.Type }, ", ") -} - -// HelperParamList returns source code for helper function f parameters. -func (f *Fn) HelperParamList() string { - return join(f.Params, func(p *Param) string { return p.Name + " " + p.HelperType() }, ", ") -} - -// ParamPrintList returns source code of trace printing part correspondent -// to syscall input parameters. -func (f *Fn) ParamPrintList() string { - return join(f.Params, func(p *Param) string { return fmt.Sprintf(`"%s=", %s, `, p.Name, p.Name) }, `", ", `) -} - -// ParamCount return number of syscall parameters for function f. -func (f *Fn) ParamCount() int { - n := 0 - for _, p := range f.Params { - n += len(p.SyscallArgList()) - } - return n -} - -// SyscallParamCount determines which version of Syscall/Syscall6/Syscall9/... -// to use. It returns parameter count for correspondent SyscallX function. -func (f *Fn) SyscallParamCount() int { - n := f.ParamCount() - switch { - case n <= 3: - return 3 - case n <= 6: - return 6 - case n <= 9: - return 9 - case n <= 12: - return 12 - case n <= 15: - return 15 - default: - panic("too many arguments to system call") - } -} - -// Syscall determines which SyscallX function to use for function f. -func (f *Fn) Syscall() string { - c := f.SyscallParamCount() - if c == 3 { - return syscalldot() + "Syscall" - } - return syscalldot() + "Syscall" + strconv.Itoa(c) -} - -// SyscallParamList returns source code for SyscallX parameters for function f. -func (f *Fn) SyscallParamList() string { - a := make([]string, 0) - for _, p := range f.Params { - a = append(a, p.SyscallArgList()...) - } - for len(a) < f.SyscallParamCount() { - a = append(a, "0") - } - return strings.Join(a, ", ") -} - -// HelperCallParamList returns source code of call into function f helper. -func (f *Fn) HelperCallParamList() string { - a := make([]string, 0, len(f.Params)) - for _, p := range f.Params { - s := p.Name - if p.Type == "string" { - s = p.tmpVar() - } - a = append(a, s) - } - return strings.Join(a, ", ") -} - -// IsUTF16 is true, if f is W (utf16) function. It is false -// for all A (ascii) functions. -func (f *Fn) IsUTF16() bool { - s := f.DLLFuncName() - return s[len(s)-1] == 'W' -} - -// StrconvFunc returns name of Go string to OS string function for f. -func (f *Fn) StrconvFunc() string { - if f.IsUTF16() { - return syscalldot() + "UTF16PtrFromString" - } - return syscalldot() + "BytePtrFromString" -} - -// StrconvType returns Go type name used for OS string for f. -func (f *Fn) StrconvType() string { - if f.IsUTF16() { - return "*uint16" - } - return "*byte" -} - -// HasStringParam is true, if f has at least one string parameter. -// Otherwise it is false. -func (f *Fn) HasStringParam() bool { - for _, p := range f.Params { - if p.Type == "string" { - return true - } - } - return false -} - -// HelperName returns name of function f helper. -func (f *Fn) HelperName() string { - if !f.HasStringParam() { - return f.Name - } - return "_" + f.Name -} - -// Source files and functions. -type Source struct { - Funcs []*Fn - Files []string - StdLibImports []string - ExternalImports []string -} - -func (src *Source) Import(pkg string) { - src.StdLibImports = append(src.StdLibImports, pkg) - sort.Strings(src.StdLibImports) -} - -func (src *Source) ExternalImport(pkg string) { - src.ExternalImports = append(src.ExternalImports, pkg) - sort.Strings(src.ExternalImports) -} - -// ParseFiles parses files listed in fs and extracts all syscall -// functions listed in sys comments. It returns source files -// and functions collection *Source if successful. -func ParseFiles(fs []string) (*Source, error) { - src := &Source{ - Funcs: make([]*Fn, 0), - Files: make([]string, 0), - StdLibImports: []string{ - "unsafe", - }, - ExternalImports: make([]string, 0), - } - for _, file := range fs { - if err := src.ParseFile(file); err != nil { - return nil, err - } - } - return src, nil -} - -// DLLs return dll names for a source set src. -func (src *Source) DLLs() []string { - uniq := make(map[string]bool) - r := make([]string, 0) - for _, f := range src.Funcs { - name := f.DLLName() - if _, found := uniq[name]; !found { - uniq[name] = true - r = append(r, name) - } - } - return r -} - -// ParseFile adds additional file path to a source set src. -func (src *Source) ParseFile(path string) error { - file, err := os.Open(path) - if err != nil { - return err - } - defer file.Close() - - s := bufio.NewScanner(file) - for s.Scan() { - t := trim(s.Text()) - if len(t) < 7 { - continue - } - if !strings.HasPrefix(t, "//sys") { - continue - } - t = t[5:] - if !(t[0] == ' ' || t[0] == '\t') { - continue - } - f, err := newFn(t[1:]) - if err != nil { - return err - } - src.Funcs = append(src.Funcs, f) - } - if err := s.Err(); err != nil { - return err - } - src.Files = append(src.Files, path) - - // get package name - fset := token.NewFileSet() - _, err = file.Seek(0, 0) - if err != nil { - return err - } - pkg, err := parser.ParseFile(fset, "", file, parser.PackageClauseOnly) - if err != nil { - return err - } - packageName = pkg.Name.Name - - return nil -} - -// IsStdRepo reports whether src is part of standard library. -func (src *Source) IsStdRepo() (bool, error) { - if len(src.Files) == 0 { - return false, errors.New("no input files provided") - } - abspath, err := filepath.Abs(src.Files[0]) - if err != nil { - return false, err - } - goroot := runtime.GOROOT() - if runtime.GOOS == "windows" { - abspath = strings.ToLower(abspath) - goroot = strings.ToLower(goroot) - } - sep := string(os.PathSeparator) - if !strings.HasSuffix(goroot, sep) { - goroot += sep - } - return strings.HasPrefix(abspath, goroot), nil -} - -// Generate output source file from a source set src. -func (src *Source) Generate(w io.Writer) error { - const ( - pkgStd = iota // any package in std library - pkgXSysWindows // x/sys/windows package - pkgOther - ) - isStdRepo, err := src.IsStdRepo() - if err != nil { - return err - } - var pkgtype int - switch { - case isStdRepo: - pkgtype = pkgStd - case packageName == "windows": - // TODO: this needs better logic than just using package name - pkgtype = pkgXSysWindows - default: - pkgtype = pkgOther - } - if *systemDLL { - switch pkgtype { - case pkgStd: - src.Import("internal/syscall/windows/sysdll") - case pkgXSysWindows: - default: - src.ExternalImport("golang.org/x/sys/windows") - } - } - if packageName != "syscall" { - src.Import("syscall") - } - funcMap := template.FuncMap{ - "packagename": packagename, - "syscalldot": syscalldot, - "newlazydll": func(dll string) string { - arg := "\"" + dll + ".dll\"" - if !*systemDLL { - return syscalldot() + "NewLazyDLL(" + arg + ")" - } - switch pkgtype { - case pkgStd: - return syscalldot() + "NewLazyDLL(sysdll.Add(" + arg + "))" - case pkgXSysWindows: - return "NewLazySystemDLL(" + arg + ")" - default: - return "windows.NewLazySystemDLL(" + arg + ")" - } - }, - } - t := template.Must(template.New("main").Funcs(funcMap).Parse(srcTemplate)) - err = t.Execute(w, src) - if err != nil { - return errors.New("Failed to execute template: " + err.Error()) - } - return nil -} - -func usage() { - fmt.Fprintf(os.Stderr, "usage: mksyscall_windows [flags] [path ...]\n") - flag.PrintDefaults() - os.Exit(1) -} - func main() { - flag.Usage = usage - flag.Parse() - if len(flag.Args()) <= 0 { - fmt.Fprintf(os.Stderr, "no files to parse provided\n") - usage() - } - - src, err := ParseFiles(flag.Args()) - if err != nil { - log.Fatal(err) - } - - var buf bytes.Buffer - if err := src.Generate(&buf); err != nil { - log.Fatal(err) - } - - data, err := format.Source(buf.Bytes()) + os.Stderr.WriteString("WARNING: Please switch from using:\n go run $GOROOT/src/syscall/mksyscall_windows.go\nto using:\n go run golang.org/x/sys/windows/mkwinsyscall\n") + args := append([]string{"run", "golang.org/x/sys/windows/mkwinsyscall"}, os.Args[1:]...) + cmd := exec.Command(filepath.Join(runtime.GOROOT(), "bin", "go"), args...) + cmd.Stdout = os.Stdout + cmd.Stderr = os.Stderr + err := cmd.Run() if err != nil { - log.Fatal(err) - } - if *filename == "" { - _, err = os.Stdout.Write(data) - } else { - err = ioutil.WriteFile(*filename, data, 0644) - } - if err != nil { - log.Fatal(err) - } -} - -// TODO: use println instead to print in the following template -const srcTemplate = ` - -{{define "main"}}// Code generated by 'go generate'; DO NOT EDIT. - -package {{packagename}} - -import ( -{{range .StdLibImports}}"{{.}}" -{{end}} - -{{range .ExternalImports}}"{{.}}" -{{end}} -) - -var _ unsafe.Pointer - -// Do the interface allocations only once for common -// Errno values. -const ( - errnoERROR_IO_PENDING = 997 -) - -var ( - errERROR_IO_PENDING error = {{syscalldot}}Errno(errnoERROR_IO_PENDING) -) - -// errnoErr returns common boxed Errno values, to prevent -// allocations at runtime. -func errnoErr(e {{syscalldot}}Errno) error { - switch e { - case 0: - return nil - case errnoERROR_IO_PENDING: - return errERROR_IO_PENDING + os.Exit(1) } - // TODO: add more here, after collecting data on the common - // error values see on Windows. (perhaps when running - // all.bat?) - return e } - -var ( -{{template "dlls" .}} -{{template "funcnames" .}}) -{{range .Funcs}}{{if .HasStringParam}}{{template "helperbody" .}}{{end}}{{template "funcbody" .}}{{end}} -{{end}} - -{{/* help functions */}} - -{{define "dlls"}}{{range .DLLs}} mod{{.}} = {{newlazydll .}} -{{end}}{{end}} - -{{define "funcnames"}}{{range .Funcs}} proc{{.DLLFuncName}} = mod{{.DLLName}}.NewProc("{{.DLLFuncName}}") -{{end}}{{end}} - -{{define "helperbody"}} -func {{.Name}}({{.ParamList}}) {{template "results" .}}{ -{{template "helpertmpvars" .}} return {{.HelperName}}({{.HelperCallParamList}}) -} -{{end}} - -{{define "funcbody"}} -func {{.HelperName}}({{.HelperParamList}}) {{template "results" .}}{ -{{template "tmpvars" .}} {{template "syscall" .}} {{template "tmpvarsreadback" .}} -{{template "seterror" .}}{{template "printtrace" .}} return -} -{{end}} - -{{define "helpertmpvars"}}{{range .Params}}{{if .TmpVarHelperCode}} {{.TmpVarHelperCode}} -{{end}}{{end}}{{end}} - -{{define "tmpvars"}}{{range .Params}}{{if .TmpVarCode}} {{.TmpVarCode}} -{{end}}{{end}}{{end}} - -{{define "results"}}{{if .Rets.List}}{{.Rets.List}} {{end}}{{end}} - -{{define "syscall"}}{{.Rets.SetReturnValuesCode}}{{.Syscall}}(proc{{.DLLFuncName}}.Addr(), {{.ParamCount}}, {{.SyscallParamList}}){{end}} - -{{define "tmpvarsreadback"}}{{range .Params}}{{if .TmpVarReadbackCode}} -{{.TmpVarReadbackCode}}{{end}}{{end}}{{end}} - -{{define "seterror"}}{{if .Rets.SetErrorCode}} {{.Rets.SetErrorCode}} -{{end}}{{end}} - -{{define "printtrace"}}{{if .PrintTrace}} print("SYSCALL: {{.Name}}(", {{.ParamPrintList}}") (", {{.Rets.PrintList}}")\n") -{{end}}{{end}} - -` -- cgit v1.3 From 9a926911fea73017a25d6d38035946c59cf1b047 Mon Sep 17 00:00:00 2001 From: David Chase Date: Tue, 1 Oct 2019 11:10:22 -0400 Subject: cmd/compile: attempt to preserve statements when prove removes code This was a cause of some statements being lost. Change-Id: I81c95dcf3df6ed8a03b7578a27f9b21d33b3cf39 Reviewed-on: https://go-review.googlesource.com/c/go/+/198484 Run-TryBot: David Chase Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/ssa/prove.go | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/cmd/compile/internal/ssa/prove.go b/src/cmd/compile/internal/ssa/prove.go index efa4453f75..4f9a4d53fb 100644 --- a/src/cmd/compile/internal/ssa/prove.go +++ b/src/cmd/compile/internal/ssa/prove.go @@ -5,6 +5,7 @@ package ssa import ( + "cmd/internal/src" "fmt" "math" ) @@ -1284,18 +1285,22 @@ func simplifyBlock(sdom SparseTree, ft *factsTable, b *Block) { } func removeBranch(b *Block, branch branch) { + c := b.Controls[0] if b.Func.pass.debug > 0 { verb := "Proved" if branch == positive { verb = "Disproved" } - c := b.Controls[0] if b.Func.pass.debug > 1 { b.Func.Warnl(b.Pos, "%s %s (%s)", verb, c.Op, c) } else { b.Func.Warnl(b.Pos, "%s %s", verb, c.Op) } } + if c != nil && c.Pos.IsStmt() == src.PosIsStmt && c.Pos.SameFileAndLine(b.Pos) { + // attempt to preserve statement marker. + b.Pos = b.Pos.WithIsStmt() + } b.Kind = BlockFirst b.ResetControls() if branch == positive { -- cgit v1.3 From c450ace12c657e3953d79975c04f51605395cd50 Mon Sep 17 00:00:00 2001 From: David Chase Date: Mon, 29 Jul 2019 16:23:31 -0400 Subject: cmd/compile: remove statement marks from secondary calls Calls are code-generated in an alternate path that inherits its positions from values, not from *SSAGenState. The default position on *SSAGenState was marked as not-a-statement, but this was not applied to the value itself, leading to spurious "is statement" marks in the output (convention: after code generation in the compiler, everything is either definitely a statement or definitely not a statement, nothing is in the undetermined state). This CL causes a 35 statement regression in ssa/stmtlines_test. This is down from the earlier 150 because of all the other CLs preceding this one that deal with the root causes of the missing lines (repeated lines on nested calls hid missing lines). This also removes some line repeats from ssa/debug_test. Change-Id: Ie9a507bd5447e906b35bbd098e3295211df2ae01 Reviewed-on: https://go-review.googlesource.com/c/go/+/188018 Run-TryBot: David Chase TryBot-Result: Gobot Gobot Reviewed-by: Jeremy Faller --- src/cmd/compile/internal/gc/ssa.go | 10 ++++- .../internal/ssa/testdata/hist.dlv-opt.nexts | 8 ---- .../internal/ssa/testdata/hist.gdb-dbg.nexts | 2 +- .../internal/ssa/testdata/hist.gdb-opt.nexts | 44 +++++----------------- 4 files changed, 19 insertions(+), 45 deletions(-) (limited to 'src') diff --git a/src/cmd/compile/internal/gc/ssa.go b/src/cmd/compile/internal/gc/ssa.go index ed1cccc6b0..a263fa7e99 100644 --- a/src/cmd/compile/internal/gc/ssa.go +++ b/src/cmd/compile/internal/gc/ssa.go @@ -5238,8 +5238,11 @@ func (s *SSAGenState) DebugFriendlySetPosFrom(v *ssa.Value) { // in the generated code. if p.IsStmt() != src.PosIsStmt { p = p.WithNotStmt() + // Calls use the pos attached to v, but copy the statement mark from SSAGenState } s.SetPos(p) + } else { + s.SetPos(s.pp.pos.WithNotStmt()) } } } @@ -5878,10 +5881,15 @@ func (s *SSAGenState) AddrScratch(a *obj.Addr) { // Call returns a new CALL instruction for the SSA value v. // It uses PrepareCall to prepare the call. func (s *SSAGenState) Call(v *ssa.Value) *obj.Prog { + pPosIsStmt := s.pp.pos.IsStmt() // The statement-ness fo the call comes from ssaGenState s.PrepareCall(v) p := s.Prog(obj.ACALL) - p.Pos = v.Pos + if pPosIsStmt == src.PosIsStmt { + p.Pos = v.Pos.WithIsStmt() + } else { + p.Pos = v.Pos.WithNotStmt() + } if sym, ok := v.Aux.(*obj.LSym); ok { p.To.Type = obj.TYPE_MEM p.To.Name = obj.NAME_EXTERN diff --git a/src/cmd/compile/internal/ssa/testdata/hist.dlv-opt.nexts b/src/cmd/compile/internal/ssa/testdata/hist.dlv-opt.nexts index 1e4d35051b..2be83ce936 100644 --- a/src/cmd/compile/internal/ssa/testdata/hist.dlv-opt.nexts +++ b/src/cmd/compile/internal/ssa/testdata/hist.dlv-opt.nexts @@ -70,32 +70,24 @@ 87: if a == 0 { //gdb-opt=(a,n,t) 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) 86: for i, a := range hist { diff --git a/src/cmd/compile/internal/ssa/testdata/hist.gdb-dbg.nexts b/src/cmd/compile/internal/ssa/testdata/hist.gdb-dbg.nexts index 4fde3bcc66..72df60c76f 100644 --- a/src/cmd/compile/internal/ssa/testdata/hist.gdb-dbg.nexts +++ b/src/cmd/compile/internal/ssa/testdata/hist.gdb-dbg.nexts @@ -9,7 +9,7 @@ l.end.y = 4 61: sink = dx + dy //gdb-opt=(dx,dy) 63: hist := make([]int, 7) //gdb-opt=(dx/O,dy/O) // TODO sink is missing if this code is in 'test' instead of 'main' 64: var reader io.Reader = strings.NewReader(cannedInput) //gdb-dbg=(hist/A) // TODO cannedInput/A is missing if this code is in 'test' instead of 'main' -hist = []int = {0, 0, 0, 0, 0, 0, 0} +hist = {array = , len = 7, cap = 7} 65: if len(os.Args) > 1 { 73: scanner := bufio.NewScanner(reader) 74: for scanner.Scan() { //gdb-opt=(scanner/A) diff --git a/src/cmd/compile/internal/ssa/testdata/hist.gdb-opt.nexts b/src/cmd/compile/internal/ssa/testdata/hist.gdb-opt.nexts index 65c5d0a2ce..d3a34acf69 100644 --- a/src/cmd/compile/internal/ssa/testdata/hist.gdb-opt.nexts +++ b/src/cmd/compile/internal/ssa/testdata/hist.gdb-opt.nexts @@ -24,92 +24,74 @@ scanner = (bufio.Scanner *) 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 0, 0, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 1 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 1, 0, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 1 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 2, 0, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 1 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 0, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 2 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 1, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 2 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 2, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 2 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 3, 0, 0, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 4 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 3, 0, 1, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 4 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 75: s := scanner.Text() 76: i, err := strconv.ParseInt(s, 10, 64) 77: if err != nil { //gdb-dbg=(i) //gdb-opt=(err,hist,i) err = {tab = 0x0, data = 0x0} -hist = []int = {0, 3, 3, 0, 2, 0, 0} +hist = {array = 0xc00005ae50, len = 7, cap = 7} i = 5 81: hist = ensure(int(i), hist) 82: hist[int(i)]++ -74: for scanner.Scan() { //gdb-opt=(scanner/A) -scanner = (bufio.Scanner *) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) a = 0 @@ -122,9 +104,7 @@ n = 0 t = 0 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) a = 3 @@ -132,9 +112,7 @@ n = 3 t = 3 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) a = 0 @@ -147,9 +125,7 @@ n = 6 t = 9 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) a = 1 @@ -157,9 +133,7 @@ n = 8 t = 17 92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 91: n += a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 90: t += i * a -92: fmt.Fprintf(os.Stderr, "%d\t%d\t%d\t%d\t%d\n", i, a, n, i*a, t) //gdb-dbg=(n,i,t) 86: for i, a := range hist { 87: if a == 0 { //gdb-opt=(a,n,t) a = 0 -- cgit v1.3