github.com/shogo82148/std@v1.22.1-0.20240327122250-4e474527810c/cmd/compile/internal/ssa/func.go (about) 1 // Copyright 2015 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package ssa 6 7 import ( 8 "github.com/shogo82148/std/cmd/compile/internal/abi" 9 "github.com/shogo82148/std/cmd/compile/internal/ir" 10 "github.com/shogo82148/std/cmd/compile/internal/types" 11 "github.com/shogo82148/std/cmd/internal/obj" 12 "github.com/shogo82148/std/cmd/internal/src" 13 ) 14 15 // A Func represents a Go func declaration (or function literal) and its body. 16 // This package compiles each Func independently. 17 // Funcs are single-use; a new Func must be created for every compiled function. 18 type Func struct { 19 Config *Config 20 Cache *Cache 21 fe Frontend 22 pass *pass 23 Name string 24 Type *types.Type 25 Blocks []*Block 26 Entry *Block 27 28 bid idAlloc 29 vid idAlloc 30 31 HTMLWriter *HTMLWriter 32 PrintOrHtmlSSA bool 33 ruleMatches map[string]int 34 ABI0 *abi.ABIConfig 35 ABI1 *abi.ABIConfig 36 ABISelf *abi.ABIConfig 37 ABIDefault *abi.ABIConfig 38 39 scheduled bool 40 laidout bool 41 NoSplit bool 42 dumpFileSeq uint8 43 44 // when register allocation is done, maps value ids to locations 45 RegAlloc []Location 46 47 // temporary registers allocated to rare instructions 48 tempRegs map[ID]*Register 49 50 // map from LocalSlot to set of Values that we want to store in that slot. 51 NamedValues map[LocalSlot][]*Value 52 // Names is a copy of NamedValues.Keys. We keep a separate list 53 // of keys to make iteration order deterministic. 54 Names []*LocalSlot 55 // Canonicalize root/top-level local slots, and canonicalize their pieces. 56 // Because LocalSlot pieces refer to their parents with a pointer, this ensures that equivalent slots really are equal. 57 CanonicalLocalSlots map[LocalSlot]*LocalSlot 58 CanonicalLocalSplits map[LocalSlotSplitKey]*LocalSlot 59 60 // RegArgs is a slice of register-memory pairs that must be spilled and unspilled in the uncommon path of function entry. 61 RegArgs []Spill 62 // OwnAux describes parameters and results for this function. 63 OwnAux *AuxCall 64 65 freeValues *Value 66 freeBlocks *Block 67 68 cachedPostorder []*Block 69 cachedIdom []*Block 70 cachedSdom SparseTree 71 cachedLoopnest *loopnest 72 cachedLineStarts *xposmap 73 74 auxmap auxmap 75 constants map[int64][]*Value 76 } 77 78 type LocalSlotSplitKey struct { 79 parent *LocalSlot 80 Off int64 81 Type *types.Type 82 } 83 84 // NewFunc returns a new, empty function object. 85 // Caller must reset cache before calling NewFunc. 86 func (c *Config) NewFunc(fe Frontend, cache *Cache) *Func 87 88 // NumBlocks returns an integer larger than the id of any Block in the Func. 89 func (f *Func) NumBlocks() int 90 91 // NumValues returns an integer larger than the id of any Value in the Func. 92 func (f *Func) NumValues() int 93 94 // NameABI returns the function name followed by comma and the ABI number. 95 // This is intended for use with GOSSAFUNC and HTML dumps, and differs from 96 // the linker's "<1>" convention because "<" and ">" require shell quoting 97 // and are not legal file names (for use with GOSSADIR) on Windows. 98 func (f *Func) NameABI() string 99 100 // FuncNameABI returns n followed by a comma and the value of a. 101 // This is a separate function to allow a single point encoding 102 // of the format, which is used in places where there's not a Func yet. 103 func FuncNameABI(n string, a obj.ABI) string 104 105 func (f *Func) SplitString(name *LocalSlot) (*LocalSlot, *LocalSlot) 106 107 func (f *Func) SplitInterface(name *LocalSlot) (*LocalSlot, *LocalSlot) 108 109 func (f *Func) SplitSlice(name *LocalSlot) (*LocalSlot, *LocalSlot, *LocalSlot) 110 111 func (f *Func) SplitComplex(name *LocalSlot) (*LocalSlot, *LocalSlot) 112 113 func (f *Func) SplitInt64(name *LocalSlot) (*LocalSlot, *LocalSlot) 114 115 func (f *Func) SplitStruct(name *LocalSlot, i int) *LocalSlot 116 117 func (f *Func) SplitArray(name *LocalSlot) *LocalSlot 118 119 func (f *Func) SplitSlot(name *LocalSlot, sfx string, offset int64, t *types.Type) *LocalSlot 120 121 // LogStat writes a string key and int value as a warning in a 122 // tab-separated format easily handled by spreadsheets or awk. 123 // file names, lines, and function names are included to provide enough (?) 124 // context to allow item-by-item comparisons across runs. 125 // For example: 126 // awk 'BEGIN {FS="\t"} $3~/TIME/{sum+=$4} END{print "t(ns)=",sum}' t.log 127 func (f *Func) LogStat(key string, args ...interface{}) 128 129 // NewBlock allocates a new Block of the given kind and places it at the end of f.Blocks. 130 func (f *Func) NewBlock(kind BlockKind) *Block 131 132 // NewValue0 returns a new value in the block with no arguments and zero aux values. 133 func (b *Block) NewValue0(pos src.XPos, op Op, t *types.Type) *Value 134 135 // NewValue0I returns a new value in the block with no arguments and an auxint value. 136 func (b *Block) NewValue0I(pos src.XPos, op Op, t *types.Type, auxint int64) *Value 137 138 // NewValue0A returns a new value in the block with no arguments and an aux value. 139 func (b *Block) NewValue0A(pos src.XPos, op Op, t *types.Type, aux Aux) *Value 140 141 // NewValue0IA returns a new value in the block with no arguments and both an auxint and aux values. 142 func (b *Block) NewValue0IA(pos src.XPos, op Op, t *types.Type, auxint int64, aux Aux) *Value 143 144 // NewValue1 returns a new value in the block with one argument and zero aux values. 145 func (b *Block) NewValue1(pos src.XPos, op Op, t *types.Type, arg *Value) *Value 146 147 // NewValue1I returns a new value in the block with one argument and an auxint value. 148 func (b *Block) NewValue1I(pos src.XPos, op Op, t *types.Type, auxint int64, arg *Value) *Value 149 150 // NewValue1A returns a new value in the block with one argument and an aux value. 151 func (b *Block) NewValue1A(pos src.XPos, op Op, t *types.Type, aux Aux, arg *Value) *Value 152 153 // NewValue1IA returns a new value in the block with one argument and both an auxint and aux values. 154 func (b *Block) NewValue1IA(pos src.XPos, op Op, t *types.Type, auxint int64, aux Aux, arg *Value) *Value 155 156 // NewValue2 returns a new value in the block with two arguments and zero aux values. 157 func (b *Block) NewValue2(pos src.XPos, op Op, t *types.Type, arg0, arg1 *Value) *Value 158 159 // NewValue2A returns a new value in the block with two arguments and one aux values. 160 func (b *Block) NewValue2A(pos src.XPos, op Op, t *types.Type, aux Aux, arg0, arg1 *Value) *Value 161 162 // NewValue2I returns a new value in the block with two arguments and an auxint value. 163 func (b *Block) NewValue2I(pos src.XPos, op Op, t *types.Type, auxint int64, arg0, arg1 *Value) *Value 164 165 // NewValue2IA returns a new value in the block with two arguments and both an auxint and aux values. 166 func (b *Block) NewValue2IA(pos src.XPos, op Op, t *types.Type, auxint int64, aux Aux, arg0, arg1 *Value) *Value 167 168 // NewValue3 returns a new value in the block with three arguments and zero aux values. 169 func (b *Block) NewValue3(pos src.XPos, op Op, t *types.Type, arg0, arg1, arg2 *Value) *Value 170 171 // NewValue3I returns a new value in the block with three arguments and an auxint value. 172 func (b *Block) NewValue3I(pos src.XPos, op Op, t *types.Type, auxint int64, arg0, arg1, arg2 *Value) *Value 173 174 // NewValue3A returns a new value in the block with three argument and an aux value. 175 func (b *Block) NewValue3A(pos src.XPos, op Op, t *types.Type, aux Aux, arg0, arg1, arg2 *Value) *Value 176 177 // NewValue4 returns a new value in the block with four arguments and zero aux values. 178 func (b *Block) NewValue4(pos src.XPos, op Op, t *types.Type, arg0, arg1, arg2, arg3 *Value) *Value 179 180 // NewValue4I returns a new value in the block with four arguments and auxint value. 181 func (b *Block) NewValue4I(pos src.XPos, op Op, t *types.Type, auxint int64, arg0, arg1, arg2, arg3 *Value) *Value 182 183 // ConstBool returns an int constant representing its argument. 184 func (f *Func) ConstBool(t *types.Type, c bool) *Value 185 186 func (f *Func) ConstInt8(t *types.Type, c int8) *Value 187 188 func (f *Func) ConstInt16(t *types.Type, c int16) *Value 189 190 func (f *Func) ConstInt32(t *types.Type, c int32) *Value 191 192 func (f *Func) ConstInt64(t *types.Type, c int64) *Value 193 194 func (f *Func) ConstFloat32(t *types.Type, c float64) *Value 195 196 func (f *Func) ConstFloat64(t *types.Type, c float64) *Value 197 198 func (f *Func) ConstSlice(t *types.Type) *Value 199 200 func (f *Func) ConstInterface(t *types.Type) *Value 201 202 func (f *Func) ConstNil(t *types.Type) *Value 203 204 func (f *Func) ConstEmptyString(t *types.Type) *Value 205 206 func (f *Func) ConstOffPtrSP(t *types.Type, c int64, sp *Value) *Value 207 208 func (f *Func) Frontend() Frontend 209 func (f *Func) Warnl(pos src.XPos, msg string, args ...interface{}) 210 func (f *Func) Logf(msg string, args ...interface{}) 211 func (f *Func) Log() bool 212 213 func (f *Func) Fatalf(msg string, args ...interface{}) 214 215 func (f *Func) Postorder() []*Block 216 217 // Idom returns a map from block ID to the immediate dominator of that block. 218 // f.Entry.ID maps to nil. Unreachable blocks map to nil as well. 219 func (f *Func) Idom() []*Block 220 221 // Sdom returns a sparse tree representing the dominator relationships 222 // among the blocks of f. 223 func (f *Func) Sdom() SparseTree 224 225 // DebugHashMatch returns 226 // 227 // base.DebugHashMatch(this function's package.name) 228 // 229 // for use in bug isolation. The return value is true unless 230 // environment variable GOSSAHASH is set, in which case "it depends". 231 // See [base.DebugHashMatch] for more information. 232 func (f *Func) DebugHashMatch() bool 233 234 // NewLocal returns a new anonymous local variable of the given type. 235 func (f *Func) NewLocal(pos src.XPos, typ *types.Type) *ir.Name