1// cmd/9l/optab.c, cmd/9l/asmout.c from Vita Nuova. 2// 3// Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved. 4// Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net) 5// Portions Copyright © 1997-1999 Vita Nuova Limited 6// Portions Copyright © 2000-2008 Vita Nuova Holdings Limited (www.vitanuova.com) 7// Portions Copyright © 2004,2006 Bruce Ellis 8// Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net) 9// Revisions Copyright © 2000-2008 Lucent Technologies Inc. and others 10// Portions Copyright © 2009 The Go Authors. All rights reserved. 11// 12// Permission is hereby granted, free of charge, to any person obtaining a copy 13// of this software and associated documentation files (the "Software"), to deal 14// in the Software without restriction, including without limitation the rights 15// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 16// copies of the Software, and to permit persons to whom the Software is 17// furnished to do so, subject to the following conditions: 18// 19// The above copyright notice and this permission notice shall be included in 20// all copies or substantial portions of the Software. 21// 22// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 23// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 24// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 25// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 26// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 27// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 28// THE SOFTWARE. 29 30package ppc64 31 32import ( 33 "cmd/internal/obj" 34 "cmd/internal/objabi" 35 "encoding/binary" 36 "fmt" 37 "log" 38 "math" 39 "math/bits" 40 "sort" 41) 42 43// ctxt9 holds state while assembling a single function. 44// Each function gets a fresh ctxt9. 45// This allows for multiple functions to be safely concurrently assembled. 46type ctxt9 struct { 47 ctxt *obj.Link 48 newprog obj.ProgAlloc 49 cursym *obj.LSym 50 autosize int32 51 instoffset int64 52 pc int64 53} 54 55// Instruction layout. 56 57const ( 58 funcAlign = 16 59 funcAlignMask = funcAlign - 1 60) 61 62const ( 63 r0iszero = 1 64) 65 66type Optab struct { 67 as obj.As // Opcode 68 a1 uint8 // p.From argument (obj.Addr). p is of type obj.Prog. 69 a2 uint8 // p.Reg argument (int16 Register) 70 a3 uint8 // p.RestArgs[0] (obj.AddrPos) 71 a4 uint8 // p.RestArgs[1] 72 a5 uint8 // p.RestARgs[2] 73 a6 uint8 // p.To (obj.Addr) 74 type_ int8 // cases in asmout below. E.g., 44 = st r,(ra+rb); 45 = ld (ra+rb), r 75 size int8 // Text space in bytes to lay operation 76 77 // A prefixed instruction is generated by this opcode. This cannot be placed 78 // across a 64B PC address. Opcodes should not translate to more than one 79 // prefixed instruction. The prefixed instruction should be written first 80 // (e.g when Optab.size > 8). 81 ispfx bool 82} 83 84// optab contains an array to be sliced of accepted operand combinations for an 85// instruction. Unused arguments and fields are not explicitly enumerated, and 86// should not be listed for clarity. Unused arguments and values should always 87// assume the default value for the given type. 88// 89// optab does not list every valid ppc64 opcode, it enumerates representative 90// operand combinations for a class of instruction. The variable oprange indexes 91// all valid ppc64 opcodes. 92// 93// oprange is initialized to point a slice within optab which contains the valid 94// operand combinations for a given instruction. This is initialized from buildop. 95// 96// Likewise, each slice of optab is dynamically sorted using the ocmp Sort interface 97// to arrange entries to minimize text size of each opcode. 98var optab = []Optab{ 99 {as: obj.ATEXT, a1: C_LOREG, a6: C_TEXTSIZE, type_: 0, size: 0}, 100 {as: obj.ATEXT, a1: C_LOREG, a3: C_LCON, a6: C_TEXTSIZE, type_: 0, size: 0}, 101 {as: obj.ATEXT, a1: C_ADDR, a6: C_TEXTSIZE, type_: 0, size: 0}, 102 {as: obj.ATEXT, a1: C_ADDR, a3: C_LCON, a6: C_TEXTSIZE, type_: 0, size: 0}, 103 /* move register */ 104 {as: AADD, a1: C_REG, a2: C_REG, a6: C_REG, type_: 2, size: 4}, 105 {as: AADD, a1: C_REG, a6: C_REG, type_: 2, size: 4}, 106 {as: AADD, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 4, size: 4}, 107 {as: AADD, a1: C_SCON, a6: C_REG, type_: 4, size: 4}, 108 {as: AADD, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 4, size: 4}, 109 {as: AADD, a1: C_ADDCON, a6: C_REG, type_: 4, size: 4}, 110 {as: AADD, a1: C_UCON, a2: C_REG, a6: C_REG, type_: 20, size: 4}, 111 {as: AADD, a1: C_UCON, a6: C_REG, type_: 20, size: 4}, 112 {as: AADD, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 22, size: 8}, 113 {as: AADD, a1: C_ANDCON, a6: C_REG, type_: 22, size: 8}, 114 {as: AADD, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 22, size: 12}, 115 {as: AADD, a1: C_LCON, a6: C_REG, type_: 22, size: 12}, 116 {as: AADDIS, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 20, size: 4}, 117 {as: AADDIS, a1: C_ADDCON, a6: C_REG, type_: 20, size: 4}, 118 {as: AADDC, a1: C_REG, a2: C_REG, a6: C_REG, type_: 2, size: 4}, 119 {as: AADDC, a1: C_REG, a6: C_REG, type_: 2, size: 4}, 120 {as: AADDC, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 4, size: 4}, 121 {as: AADDC, a1: C_ADDCON, a6: C_REG, type_: 4, size: 4}, 122 {as: AADDC, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 22, size: 12}, 123 {as: AADDC, a1: C_LCON, a6: C_REG, type_: 22, size: 12}, 124 {as: AAND, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, /* logical, no literal */ 125 {as: AAND, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 126 {as: AANDCC, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, 127 {as: AANDCC, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 128 {as: AANDCC, a1: C_ANDCON, a6: C_REG, type_: 58, size: 4}, 129 {as: AANDCC, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 58, size: 4}, 130 {as: AANDCC, a1: C_UCON, a6: C_REG, type_: 59, size: 4}, 131 {as: AANDCC, a1: C_UCON, a2: C_REG, a6: C_REG, type_: 59, size: 4}, 132 {as: AANDCC, a1: C_ADDCON, a6: C_REG, type_: 23, size: 8}, 133 {as: AANDCC, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 23, size: 8}, 134 {as: AANDCC, a1: C_LCON, a6: C_REG, type_: 23, size: 12}, 135 {as: AANDCC, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 23, size: 12}, 136 {as: AANDISCC, a1: C_ANDCON, a6: C_REG, type_: 59, size: 4}, 137 {as: AANDISCC, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 59, size: 4}, 138 {as: AMULLW, a1: C_REG, a2: C_REG, a6: C_REG, type_: 2, size: 4}, 139 {as: AMULLW, a1: C_REG, a6: C_REG, type_: 2, size: 4}, 140 {as: AMULLW, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 4, size: 4}, 141 {as: AMULLW, a1: C_ADDCON, a6: C_REG, type_: 4, size: 4}, 142 {as: AMULLW, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 4, size: 4}, 143 {as: AMULLW, a1: C_ANDCON, a6: C_REG, type_: 4, size: 4}, 144 {as: AMULLW, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 22, size: 12}, 145 {as: AMULLW, a1: C_LCON, a6: C_REG, type_: 22, size: 12}, 146 {as: ASUBC, a1: C_REG, a2: C_REG, a6: C_REG, type_: 10, size: 4}, 147 {as: ASUBC, a1: C_REG, a6: C_REG, type_: 10, size: 4}, 148 {as: ASUBC, a1: C_REG, a3: C_ADDCON, a6: C_REG, type_: 27, size: 4}, 149 {as: ASUBC, a1: C_REG, a3: C_LCON, a6: C_REG, type_: 28, size: 12}, 150 {as: AOR, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, /* logical, literal not cc (or/xor) */ 151 {as: AOR, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 152 {as: AOR, a1: C_ANDCON, a6: C_REG, type_: 58, size: 4}, 153 {as: AOR, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 58, size: 4}, 154 {as: AOR, a1: C_UCON, a6: C_REG, type_: 59, size: 4}, 155 {as: AOR, a1: C_UCON, a2: C_REG, a6: C_REG, type_: 59, size: 4}, 156 {as: AOR, a1: C_ADDCON, a6: C_REG, type_: 23, size: 8}, 157 {as: AOR, a1: C_ADDCON, a2: C_REG, a6: C_REG, type_: 23, size: 8}, 158 {as: AOR, a1: C_LCON, a6: C_REG, type_: 23, size: 12}, 159 {as: AOR, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 23, size: 12}, 160 {as: AORIS, a1: C_ANDCON, a6: C_REG, type_: 59, size: 4}, 161 {as: AORIS, a1: C_ANDCON, a2: C_REG, a6: C_REG, type_: 59, size: 4}, 162 {as: ADIVW, a1: C_REG, a2: C_REG, a6: C_REG, type_: 2, size: 4}, /* op r1[,r2],r3 */ 163 {as: ADIVW, a1: C_REG, a6: C_REG, type_: 2, size: 4}, 164 {as: ASUB, a1: C_REG, a2: C_REG, a6: C_REG, type_: 10, size: 4}, /* op r2[,r1],r3 */ 165 {as: ASUB, a1: C_REG, a6: C_REG, type_: 10, size: 4}, 166 {as: ASLW, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 167 {as: ASLW, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, 168 {as: ASLD, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 169 {as: ASLD, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, 170 {as: ASLD, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 25, size: 4}, 171 {as: ASLD, a1: C_SCON, a6: C_REG, type_: 25, size: 4}, 172 {as: AEXTSWSLI, a1: C_SCON, a6: C_REG, type_: 25, size: 4}, 173 {as: AEXTSWSLI, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 25, size: 4}, 174 {as: ASLW, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 57, size: 4}, 175 {as: ASLW, a1: C_SCON, a6: C_REG, type_: 57, size: 4}, 176 {as: ASRAW, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 177 {as: ASRAW, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, 178 {as: ASRAW, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 56, size: 4}, 179 {as: ASRAW, a1: C_SCON, a6: C_REG, type_: 56, size: 4}, 180 {as: ASRAD, a1: C_REG, a6: C_REG, type_: 6, size: 4}, 181 {as: ASRAD, a1: C_REG, a2: C_REG, a6: C_REG, type_: 6, size: 4}, 182 {as: ASRAD, a1: C_SCON, a2: C_REG, a6: C_REG, type_: 56, size: 4}, 183 {as: ASRAD, a1: C_SCON, a6: C_REG, type_: 56, size: 4}, 184 {as: ARLWMI, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 62, size: 4}, 185 {as: ARLWMI, a1: C_SCON, a2: C_REG, a3: C_SCON, a4: C_SCON, a6: C_REG, type_: 102, size: 4}, 186 {as: ARLWMI, a1: C_REG, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 63, size: 4}, 187 {as: ARLWMI, a1: C_REG, a2: C_REG, a3: C_SCON, a4: C_SCON, a6: C_REG, type_: 103, size: 4}, 188 {as: ACLRLSLWI, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 62, size: 4}, 189 {as: ARLDMI, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 30, size: 4}, 190 {as: ARLDC, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 29, size: 4}, 191 {as: ARLDCL, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 29, size: 4}, 192 {as: ARLDCL, a1: C_REG, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 14, size: 4}, 193 {as: ARLDICL, a1: C_REG, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 14, size: 4}, 194 {as: ARLDICL, a1: C_SCON, a2: C_REG, a3: C_LCON, a6: C_REG, type_: 14, size: 4}, 195 {as: ARLDCL, a1: C_REG, a3: C_LCON, a6: C_REG, type_: 14, size: 4}, 196 {as: AFADD, a1: C_FREG, a6: C_FREG, type_: 2, size: 4}, 197 {as: AFADD, a1: C_FREG, a2: C_FREG, a6: C_FREG, type_: 2, size: 4}, 198 {as: AFABS, a1: C_FREG, a6: C_FREG, type_: 33, size: 4}, 199 {as: AFABS, a6: C_FREG, type_: 33, size: 4}, 200 {as: AFMADD, a1: C_FREG, a2: C_FREG, a3: C_FREG, a6: C_FREG, type_: 34, size: 4}, 201 {as: AFMUL, a1: C_FREG, a6: C_FREG, type_: 32, size: 4}, 202 {as: AFMUL, a1: C_FREG, a2: C_FREG, a6: C_FREG, type_: 32, size: 4}, 203 204 {as: AMOVBU, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 205 {as: AMOVBU, a1: C_SOREG, a6: C_REG, type_: 8, size: 8}, 206 207 {as: AMOVBZU, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 208 {as: AMOVBZU, a1: C_SOREG, a6: C_REG, type_: 8, size: 4}, 209 210 {as: AMOVHBR, a1: C_REG, a6: C_ZOREG, type_: 44, size: 4}, 211 {as: AMOVHBR, a1: C_ZOREG, a6: C_REG, type_: 45, size: 4}, 212 213 {as: AMOVB, a1: C_ADDR, a6: C_REG, type_: 75, size: 12}, 214 {as: AMOVB, a1: C_LOREG, a6: C_REG, type_: 36, size: 12}, 215 {as: AMOVB, a1: C_SOREG, a6: C_REG, type_: 8, size: 8}, 216 {as: AMOVB, a1: C_REG, a6: C_ADDR, type_: 74, size: 8}, 217 {as: AMOVB, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 218 {as: AMOVB, a1: C_REG, a6: C_LOREG, type_: 35, size: 8}, 219 {as: AMOVB, a1: C_REG, a6: C_REG, type_: 13, size: 4}, 220 221 {as: AMOVBZ, a1: C_ADDR, a6: C_REG, type_: 75, size: 8}, 222 {as: AMOVBZ, a1: C_LOREG, a6: C_REG, type_: 36, size: 8}, 223 {as: AMOVBZ, a1: C_SOREG, a6: C_REG, type_: 8, size: 4}, 224 {as: AMOVBZ, a1: C_REG, a6: C_ADDR, type_: 74, size: 8}, 225 {as: AMOVBZ, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 226 {as: AMOVBZ, a1: C_REG, a6: C_LOREG, type_: 35, size: 8}, 227 {as: AMOVBZ, a1: C_REG, a6: C_REG, type_: 13, size: 4}, 228 229 {as: AMOVD, a1: C_ADDCON, a6: C_REG, type_: 3, size: 4}, 230 {as: AMOVD, a1: C_ANDCON, a6: C_REG, type_: 3, size: 4}, 231 {as: AMOVD, a1: C_UCON, a6: C_REG, type_: 3, size: 4}, 232 {as: AMOVD, a1: C_LCON, a6: C_REG, type_: 19, size: 8}, 233 {as: AMOVD, a1: C_SACON, a6: C_REG, type_: 3, size: 4}, 234 {as: AMOVD, a1: C_LACON, a6: C_REG, type_: 26, size: 8}, 235 {as: AMOVD, a1: C_ADDR, a6: C_REG, type_: 75, size: 8}, 236 {as: AMOVD, a1: C_SOREG, a6: C_REG, type_: 8, size: 4}, 237 {as: AMOVD, a1: C_LOREG, a6: C_REG, type_: 36, size: 8}, 238 {as: AMOVD, a1: C_TLS_LE, a6: C_REG, type_: 79, size: 8}, 239 {as: AMOVD, a1: C_TLS_IE, a6: C_REG, type_: 80, size: 12}, 240 {as: AMOVD, a1: C_SPR, a6: C_REG, type_: 66, size: 4}, 241 {as: AMOVD, a1: C_REG, a6: C_ADDR, type_: 74, size: 8}, 242 {as: AMOVD, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 243 {as: AMOVD, a1: C_REG, a6: C_LOREG, type_: 35, size: 8}, 244 {as: AMOVD, a1: C_REG, a6: C_SPR, type_: 66, size: 4}, 245 {as: AMOVD, a1: C_REG, a6: C_REG, type_: 13, size: 4}, 246 247 {as: AMOVW, a1: C_ADDCON, a6: C_REG, type_: 3, size: 4}, 248 {as: AMOVW, a1: C_ANDCON, a6: C_REG, type_: 3, size: 4}, 249 {as: AMOVW, a1: C_UCON, a6: C_REG, type_: 3, size: 4}, 250 {as: AMOVW, a1: C_LCON, a6: C_REG, type_: 19, size: 8}, 251 {as: AMOVW, a1: C_SACON, a6: C_REG, type_: 3, size: 4}, 252 {as: AMOVW, a1: C_LACON, a6: C_REG, type_: 26, size: 8}, 253 {as: AMOVW, a1: C_ADDR, a6: C_REG, type_: 75, size: 8}, 254 {as: AMOVW, a1: C_CREG, a6: C_REG, type_: 68, size: 4}, 255 {as: AMOVW, a1: C_SOREG, a6: C_REG, type_: 8, size: 4}, 256 {as: AMOVW, a1: C_LOREG, a6: C_REG, type_: 36, size: 8}, 257 {as: AMOVW, a1: C_SPR, a6: C_REG, type_: 66, size: 4}, 258 {as: AMOVW, a1: C_REG, a6: C_ADDR, type_: 74, size: 8}, 259 {as: AMOVW, a1: C_REG, a6: C_CREG, type_: 69, size: 4}, 260 {as: AMOVW, a1: C_REG, a6: C_SOREG, type_: 7, size: 4}, 261 {as: AMOVW, a1: C_REG, a6: C_LOREG, type_: 35, size: 8}, 262 {as: AMOVW, a1: C_REG, a6: C_SPR, type_: 66, size: 4}, 263 {as: AMOVW, a1: C_REG, a6: C_REG, type_: 13, size: 4}, 264 265 {as: AFMOVD, a1: C_ADDCON, a6: C_FREG, type_: 24, size: 8}, 266 {as: AFMOVD, a1: C_SOREG, a6: C_FREG, type_: 8, size: 4}, 267 {as: AFMOVD, a1: C_LOREG, a6: C_FREG, type_: 36, size: 8}, 268 {as: AFMOVD, a1: C_ZCON, a6: C_FREG, type_: 24, size: 4}, 269 {as: AFMOVD, a1: C_ADDR, a6: C_FREG, type_: 75, size: 8}, 270 {as: AFMOVD, a1: C_FREG, a6: C_FREG, type_: 33, size: 4}, 271 {as: AFMOVD, a1: C_FREG, a6: C_SOREG, type_: 7, size: 4}, 272 {as: AFMOVD, a1: C_FREG, a6: C_LOREG, type_: 35, size: 8}, 273 {as: AFMOVD, a1: C_FREG, a6: C_ADDR, type_: 74, size: 8}, 274 275 {as: AFMOVSX, a1: C_ZOREG, a6: C_FREG, type_: 45, size: 4}, 276 {as: AFMOVSX, a1: C_FREG, a6: C_ZOREG, type_: 44, size: 4}, 277 278 {as: AFMOVSZ, a1: C_ZOREG, a6: C_FREG, type_: 45, size: 4}, 279 280 {as: AMOVFL, a1: C_CREG, a6: C_CREG, type_: 67, size: 4}, 281 {as: AMOVFL, a1: C_FPSCR, a6: C_CREG, type_: 73, size: 4}, 282 {as: AMOVFL, a1: C_FPSCR, a6: C_FREG, type_: 53, size: 4}, 283 {as: AMOVFL, a1: C_FREG, a3: C_LCON, a6: C_FPSCR, type_: 64, size: 4}, 284 {as: AMOVFL, a1: C_FREG, a6: C_FPSCR, type_: 64, size: 4}, 285 {as: AMOVFL, a1: C_LCON, a6: C_FPSCR, type_: 65, size: 4}, 286 {as: AMOVFL, a1: C_REG, a6: C_CREG, type_: 69, size: 4}, 287 {as: AMOVFL, a1: C_REG, a6: C_LCON, type_: 69, size: 4}, 288 289 {as: ASYSCALL, type_: 5, size: 4}, 290 {as: ASYSCALL, a1: C_REG, type_: 77, size: 12}, 291 {as: ASYSCALL, a1: C_SCON, type_: 77, size: 12}, 292 {as: ABEQ, a6: C_SBRA, type_: 16, size: 4}, 293 {as: ABEQ, a1: C_CREG, a6: C_SBRA, type_: 16, size: 4}, 294 {as: ABR, a6: C_LBRA, type_: 11, size: 4}, 295 {as: ABR, a6: C_LBRAPIC, type_: 11, size: 8}, 296 {as: ABC, a1: C_SCON, a2: C_REG, a6: C_SBRA, type_: 16, size: 4}, 297 {as: ABC, a1: C_SCON, a2: C_REG, a6: C_LBRA, type_: 17, size: 4}, 298 {as: ABR, a6: C_LR, type_: 18, size: 4}, 299 {as: ABR, a3: C_SCON, a6: C_LR, type_: 18, size: 4}, 300 {as: ABR, a6: C_CTR, type_: 18, size: 4}, 301 {as: ABR, a1: C_REG, a6: C_CTR, type_: 18, size: 4}, 302 {as: ABR, a6: C_ZOREG, type_: 15, size: 8}, 303 {as: ABC, a2: C_REG, a6: C_LR, type_: 18, size: 4}, 304 {as: ABC, a2: C_REG, a6: C_CTR, type_: 18, size: 4}, 305 {as: ABC, a1: C_SCON, a2: C_REG, a6: C_LR, type_: 18, size: 4}, 306 {as: ABC, a1: C_SCON, a2: C_REG, a6: C_CTR, type_: 18, size: 4}, 307 {as: ABC, a6: C_ZOREG, type_: 15, size: 8}, 308 {as: ASYNC, type_: 46, size: 4}, 309 {as: AWORD, a1: C_LCON, type_: 40, size: 4}, 310 {as: ADWORD, a1: C_64CON, type_: 31, size: 8}, 311 {as: ADWORD, a1: C_LACON, type_: 31, size: 8}, 312 {as: AADDME, a1: C_REG, a6: C_REG, type_: 47, size: 4}, 313 {as: AEXTSB, a1: C_REG, a6: C_REG, type_: 48, size: 4}, 314 {as: AEXTSB, a6: C_REG, type_: 48, size: 4}, 315 {as: AISEL, a1: C_LCON, a2: C_REG, a3: C_REG, a6: C_REG, type_: 84, size: 4}, 316 {as: AISEL, a1: C_ZCON, a2: C_REG, a3: C_REG, a6: C_REG, type_: 84, size: 4}, 317 {as: ANEG, a1: C_REG, a6: C_REG, type_: 47, size: 4}, 318 {as: ANEG, a6: C_REG, type_: 47, size: 4}, 319 {as: AREM, a1: C_REG, a6: C_REG, type_: 50, size: 12}, 320 {as: AREM, a1: C_REG, a2: C_REG, a6: C_REG, type_: 50, size: 12}, 321 {as: AREMU, a1: C_REG, a6: C_REG, type_: 50, size: 16}, 322 {as: AREMU, a1: C_REG, a2: C_REG, a6: C_REG, type_: 50, size: 16}, 323 {as: AREMD, a1: C_REG, a6: C_REG, type_: 51, size: 12}, 324 {as: AREMD, a1: C_REG, a2: C_REG, a6: C_REG, type_: 51, size: 12}, 325 {as: AMTFSB0, a1: C_SCON, type_: 52, size: 4}, 326 /* Other ISA 2.05+ instructions */ 327 {as: APOPCNTD, a1: C_REG, a6: C_REG, type_: 93, size: 4}, /* population count, x-form */ 328 {as: ACMPB, a1: C_REG, a2: C_REG, a6: C_REG, type_: 92, size: 4}, /* compare byte, x-form */ 329 {as: ACMPEQB, a1: C_REG, a2: C_REG, a6: C_CREG, type_: 92, size: 4}, /* compare equal byte, x-form, ISA 3.0 */ 330 {as: ACMPEQB, a1: C_REG, a6: C_REG, type_: 70, size: 4}, 331 {as: AFTDIV, a1: C_FREG, a2: C_FREG, a6: C_SCON, type_: 92, size: 4}, /* floating test for sw divide, x-form */ 332 {as: AFTSQRT, a1: C_FREG, a6: C_SCON, type_: 93, size: 4}, /* floating test for sw square root, x-form */ 333 {as: ACOPY, a1: C_REG, a6: C_REG, type_: 92, size: 4}, /* copy/paste facility, x-form */ 334 {as: ADARN, a1: C_SCON, a6: C_REG, type_: 92, size: 4}, /* deliver random number, x-form */ 335 {as: ALDMX, a1: C_SOREG, a6: C_REG, type_: 45, size: 4}, /* load doubleword monitored, x-form */ 336 {as: AMADDHD, a1: C_REG, a2: C_REG, a3: C_REG, a6: C_REG, type_: 83, size: 4}, /* multiply-add high/low doubleword, va-form */ 337 {as: AADDEX, a1: C_REG, a2: C_REG, a3: C_SCON, a6: C_REG, type_: 94, size: 4}, /* add extended using alternate carry, z23-form */ 338 {as: ACRAND, a1: C_CRBIT, a2: C_CRBIT, a6: C_CRBIT, type_: 2, size: 4}, /* logical ops for condition register bits xl-form */ 339 340 /* Vector instructions */ 341 342 /* Vector load */ 343 {as: ALV, a1: C_SOREG, a6: C_VREG, type_: 45, size: 4}, /* vector load, x-form */ 344 345 /* Vector store */ 346 {as: ASTV, a1: C_VREG, a6: C_SOREG, type_: 44, size: 4}, /* vector store, x-form */ 347 348 /* Vector logical */ 349 {as: AVAND, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector and, vx-form */ 350 {as: AVOR, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector or, vx-form */ 351 352 /* Vector add */ 353 {as: AVADDUM, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector add unsigned modulo, vx-form */ 354 {as: AVADDCU, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector add & write carry unsigned, vx-form */ 355 {as: AVADDUS, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector add unsigned saturate, vx-form */ 356 {as: AVADDSS, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector add signed saturate, vx-form */ 357 {as: AVADDE, a1: C_VREG, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector add extended, va-form */ 358 359 /* Vector subtract */ 360 {as: AVSUBUM, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector subtract unsigned modulo, vx-form */ 361 {as: AVSUBCU, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector subtract & write carry unsigned, vx-form */ 362 {as: AVSUBUS, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector subtract unsigned saturate, vx-form */ 363 {as: AVSUBSS, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector subtract signed saturate, vx-form */ 364 {as: AVSUBE, a1: C_VREG, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector subtract extended, va-form */ 365 366 /* Vector multiply */ 367 {as: AVMULESB, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector multiply, vx-form */ 368 {as: AVPMSUM, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector polynomial multiply & sum, vx-form */ 369 {as: AVMSUMUDM, a1: C_VREG, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector multiply-sum, va-form */ 370 371 /* Vector rotate */ 372 {as: AVR, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector rotate, vx-form */ 373 374 /* Vector shift */ 375 {as: AVS, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector shift, vx-form */ 376 {as: AVSA, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector shift algebraic, vx-form */ 377 {as: AVSOI, a1: C_ANDCON, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector shift by octet immediate, va-form */ 378 379 /* Vector count */ 380 {as: AVCLZ, a1: C_VREG, a6: C_VREG, type_: 85, size: 4}, /* vector count leading zeros, vx-form */ 381 {as: AVPOPCNT, a1: C_VREG, a6: C_VREG, type_: 85, size: 4}, /* vector population count, vx-form */ 382 383 /* Vector compare */ 384 {as: AVCMPEQ, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector compare equal, vc-form */ 385 {as: AVCMPGT, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector compare greater than, vc-form */ 386 {as: AVCMPNEZB, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector compare not equal, vx-form */ 387 388 /* Vector merge */ 389 {as: AVMRGOW, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector merge odd word, vx-form */ 390 391 /* Vector permute */ 392 {as: AVPERM, a1: C_VREG, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector permute, va-form */ 393 394 /* Vector bit permute */ 395 {as: AVBPERMQ, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector bit permute, vx-form */ 396 397 /* Vector select */ 398 {as: AVSEL, a1: C_VREG, a2: C_VREG, a3: C_VREG, a6: C_VREG, type_: 83, size: 4}, /* vector select, va-form */ 399 400 /* Vector splat */ 401 {as: AVSPLTB, a1: C_SCON, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector splat, vx-form */ 402 {as: AVSPLTB, a1: C_ADDCON, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, 403 {as: AVSPLTISB, a1: C_SCON, a6: C_VREG, type_: 82, size: 4}, /* vector splat immediate, vx-form */ 404 {as: AVSPLTISB, a1: C_ADDCON, a6: C_VREG, type_: 82, size: 4}, 405 406 /* Vector AES */ 407 {as: AVCIPH, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector AES cipher, vx-form */ 408 {as: AVNCIPH, a1: C_VREG, a2: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector AES inverse cipher, vx-form */ 409 {as: AVSBOX, a1: C_VREG, a6: C_VREG, type_: 82, size: 4}, /* vector AES subbytes, vx-form */ 410 411 /* Vector SHA */ 412 {as: AVSHASIGMA, a1: C_ANDCON, a2: C_VREG, a3: C_ANDCON, a6: C_VREG, type_: 82, size: 4}, /* vector SHA sigma, vx-form */ 413 414 /* VSX vector load */ 415 {as: ALXVD2X, a1: C_SOREG, a6: C_VSREG, type_: 87, size: 4}, /* vsx vector load, xx1-form */ 416 {as: ALXV, a1: C_SOREG, a6: C_VSREG, type_: 96, size: 4}, /* vsx vector load, dq-form */ 417 {as: ALXVL, a1: C_REG, a2: C_REG, a6: C_VSREG, type_: 98, size: 4}, /* vsx vector load length */ 418 419 /* VSX vector store */ 420 {as: ASTXVD2X, a1: C_VSREG, a6: C_SOREG, type_: 86, size: 4}, /* vsx vector store, xx1-form */ 421 {as: ASTXV, a1: C_VSREG, a6: C_SOREG, type_: 97, size: 4}, /* vsx vector store, dq-form */ 422 {as: ASTXVL, a1: C_VSREG, a2: C_REG, a6: C_REG, type_: 99, size: 4}, /* vsx vector store with length x-form */ 423 424 /* VSX scalar load */ 425 {as: ALXSDX, a1: C_SOREG, a6: C_VSREG, type_: 87, size: 4}, /* vsx scalar load, xx1-form */ 426 427 /* VSX scalar store */ 428 {as: ASTXSDX, a1: C_VSREG, a6: C_SOREG, type_: 86, size: 4}, /* vsx scalar store, xx1-form */ 429 430 /* VSX scalar as integer load */ 431 {as: ALXSIWAX, a1: C_SOREG, a6: C_VSREG, type_: 87, size: 4}, /* vsx scalar as integer load, xx1-form */ 432 433 /* VSX scalar store as integer */ 434 {as: ASTXSIWX, a1: C_VSREG, a6: C_SOREG, type_: 86, size: 4}, /* vsx scalar as integer store, xx1-form */ 435 436 /* VSX move from VSR */ 437 {as: AMFVSRD, a1: C_VSREG, a6: C_REG, type_: 88, size: 4}, 438 {as: AMFVSRD, a1: C_FREG, a6: C_REG, type_: 88, size: 4}, 439 440 /* VSX move to VSR */ 441 {as: AMTVSRD, a1: C_REG, a6: C_VSREG, type_: 104, size: 4}, 442 {as: AMTVSRD, a1: C_REG, a6: C_FREG, type_: 104, size: 4}, 443 {as: AMTVSRDD, a1: C_REG, a2: C_REG, a6: C_VSREG, type_: 104, size: 4}, 444 445 /* VSX logical */ 446 {as: AXXLAND, a1: C_VSREG, a2: C_VSREG, a6: C_VSREG, type_: 90, size: 4}, /* vsx and, xx3-form */ 447 {as: AXXLOR, a1: C_VSREG, a2: C_VSREG, a6: C_VSREG, type_: 90, size: 4}, /* vsx or, xx3-form */ 448 449 /* VSX select */ 450 {as: AXXSEL, a1: C_VSREG, a2: C_VSREG, a3: C_VSREG, a6: C_VSREG, type_: 91, size: 4}, /* vsx select, xx4-form */ 451 452 /* VSX merge */ 453 {as: AXXMRGHW, a1: C_VSREG, a2: C_VSREG, a6: C_VSREG, type_: 90, size: 4}, /* vsx merge, xx3-form */ 454 455 /* VSX splat */ 456 {as: AXXSPLTW, a1: C_VSREG, a3: C_SCON, a6: C_VSREG, type_: 89, size: 4}, /* vsx splat, xx2-form */ 457 {as: AXXSPLTIB, a1: C_SCON, a6: C_VSREG, type_: 100, size: 4}, /* vsx splat, xx2-form */ 458 459 /* VSX permute */ 460 {as: AXXPERM, a1: C_VSREG, a2: C_VSREG, a6: C_VSREG, type_: 90, size: 4}, /* vsx permute, xx3-form */ 461 462 /* VSX shift */ 463 {as: AXXSLDWI, a1: C_VSREG, a2: C_VSREG, a3: C_SCON, a6: C_VSREG, type_: 90, size: 4}, /* vsx shift immediate, xx3-form */ 464 465 /* VSX reverse bytes */ 466 {as: AXXBRQ, a1: C_VSREG, a6: C_VSREG, type_: 101, size: 4}, /* vsx reverse bytes */ 467 468 /* VSX scalar FP-FP conversion */ 469 {as: AXSCVDPSP, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx scalar fp-fp conversion, xx2-form */ 470 471 /* VSX vector FP-FP conversion */ 472 {as: AXVCVDPSP, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx vector fp-fp conversion, xx2-form */ 473 474 /* VSX scalar FP-integer conversion */ 475 {as: AXSCVDPSXDS, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx scalar fp-integer conversion, xx2-form */ 476 477 /* VSX scalar integer-FP conversion */ 478 {as: AXSCVSXDDP, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx scalar integer-fp conversion, xx2-form */ 479 480 /* VSX vector FP-integer conversion */ 481 {as: AXVCVDPSXDS, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx vector fp-integer conversion, xx2-form */ 482 483 /* VSX vector integer-FP conversion */ 484 {as: AXVCVSXDDP, a1: C_VSREG, a6: C_VSREG, type_: 89, size: 4}, /* vsx vector integer-fp conversion, xx2-form */ 485 486 {as: ACMP, a1: C_REG, a6: C_REG, type_: 70, size: 4}, 487 {as: ACMP, a1: C_REG, a2: C_CREG, a6: C_REG, type_: 70, size: 4}, 488 {as: ACMP, a1: C_REG, a6: C_ADDCON, type_: 71, size: 4}, 489 {as: ACMP, a1: C_REG, a2: C_CREG, a6: C_ADDCON, type_: 71, size: 4}, 490 {as: ACMPU, a1: C_REG, a6: C_REG, type_: 70, size: 4}, 491 {as: ACMPU, a1: C_REG, a2: C_CREG, a6: C_REG, type_: 70, size: 4}, 492 {as: ACMPU, a1: C_REG, a6: C_ANDCON, type_: 71, size: 4}, 493 {as: ACMPU, a1: C_REG, a2: C_CREG, a6: C_ANDCON, type_: 71, size: 4}, 494 {as: AFCMPO, a1: C_FREG, a6: C_FREG, type_: 70, size: 4}, 495 {as: AFCMPO, a1: C_FREG, a2: C_CREG, a6: C_FREG, type_: 70, size: 4}, 496 {as: ATW, a1: C_LCON, a2: C_REG, a6: C_REG, type_: 60, size: 4}, 497 {as: ATW, a1: C_LCON, a2: C_REG, a6: C_ADDCON, type_: 61, size: 4}, 498 {as: ADCBF, a1: C_ZOREG, type_: 43, size: 4}, 499 {as: ADCBF, a1: C_SOREG, type_: 43, size: 4}, 500 {as: ADCBF, a1: C_ZOREG, a2: C_REG, a6: C_SCON, type_: 43, size: 4}, 501 {as: ADCBF, a1: C_SOREG, a6: C_SCON, type_: 43, size: 4}, 502 {as: AECOWX, a1: C_REG, a2: C_REG, a6: C_ZOREG, type_: 44, size: 4}, 503 {as: AECIWX, a1: C_ZOREG, a2: C_REG, a6: C_REG, type_: 45, size: 4}, 504 {as: AECOWX, a1: C_REG, a6: C_ZOREG, type_: 44, size: 4}, 505 {as: AECIWX, a1: C_ZOREG, a6: C_REG, type_: 45, size: 4}, 506 {as: ALDAR, a1: C_ZOREG, a6: C_REG, type_: 45, size: 4}, 507 {as: ALDAR, a1: C_ZOREG, a3: C_ANDCON, a6: C_REG, type_: 45, size: 4}, 508 {as: AEIEIO, type_: 46, size: 4}, 509 {as: ATLBIE, a1: C_REG, type_: 49, size: 4}, 510 {as: ATLBIE, a1: C_SCON, a6: C_REG, type_: 49, size: 4}, 511 {as: ASLBMFEE, a1: C_REG, a6: C_REG, type_: 55, size: 4}, 512 {as: ASLBMTE, a1: C_REG, a6: C_REG, type_: 55, size: 4}, 513 {as: ASTSW, a1: C_REG, a6: C_ZOREG, type_: 44, size: 4}, 514 {as: ASTSW, a1: C_REG, a3: C_LCON, a6: C_ZOREG, type_: 41, size: 4}, 515 {as: ALSW, a1: C_ZOREG, a6: C_REG, type_: 45, size: 4}, 516 {as: ALSW, a1: C_ZOREG, a3: C_LCON, a6: C_REG, type_: 42, size: 4}, 517 518 {as: APNOP, type_: 105, size: 8, ispfx: true}, 519 520 {as: obj.AUNDEF, type_: 78, size: 4}, 521 {as: obj.APCDATA, a1: C_LCON, a6: C_LCON, type_: 0, size: 0}, 522 {as: obj.AFUNCDATA, a1: C_SCON, a6: C_ADDR, type_: 0, size: 0}, 523 {as: obj.ANOP, type_: 0, size: 0}, 524 {as: obj.ANOP, a1: C_LCON, type_: 0, size: 0}, // NOP operand variations added for #40689 525 {as: obj.ANOP, a1: C_REG, type_: 0, size: 0}, // to preserve previous behavior 526 {as: obj.ANOP, a1: C_FREG, type_: 0, size: 0}, 527 {as: obj.ADUFFZERO, a6: C_LBRA, type_: 11, size: 4}, // same as ABR/ABL 528 {as: obj.ADUFFCOPY, a6: C_LBRA, type_: 11, size: 4}, // same as ABR/ABL 529 {as: obj.APCALIGN, a1: C_LCON, type_: 0, size: 0}, // align code 530 531 {as: obj.AXXX, type_: 0, size: 4}, 532} 533 534var oprange [ALAST & obj.AMask][]Optab 535 536var xcmp [C_NCLASS][C_NCLASS]bool 537 538// padding bytes to add to align code as requested 539func addpad(pc, a int64, ctxt *obj.Link, cursym *obj.LSym) int { 540 // For 16 and 32 byte alignment, there is a tradeoff 541 // between aligning the code and adding too many NOPs. 542 switch a { 543 case 8: 544 if pc&7 != 0 { 545 return 4 546 } 547 case 16: 548 // Align to 16 bytes if possible but add at 549 // most 2 NOPs. 550 switch pc & 15 { 551 case 4, 12: 552 return 4 553 case 8: 554 return 8 555 } 556 case 32: 557 // Align to 32 bytes if possible but add at 558 // most 3 NOPs. 559 switch pc & 31 { 560 case 4, 20: 561 return 12 562 case 8, 24: 563 return 8 564 case 12, 28: 565 return 4 566 } 567 // When 32 byte alignment is requested on Linux, 568 // promote the function's alignment to 32. On AIX 569 // the function alignment is not changed which might 570 // result in 16 byte alignment but that is still fine. 571 // TODO: alignment on AIX 572 if ctxt.Headtype != objabi.Haix && cursym.Func().Align < 32 { 573 cursym.Func().Align = 32 574 } 575 default: 576 ctxt.Diag("Unexpected alignment: %d for PCALIGN directive\n", a) 577 } 578 return 0 579} 580 581// Get the implied register of a operand which doesn't specify one. These show up 582// in handwritten asm like "MOVD R5, foosymbol" where a base register is not supplied, 583// or "MOVD R5, foo+10(SP) or pseudo-register is used. The other common case is when 584// generating constants in register like "MOVD $constant, Rx". 585func (c *ctxt9) getimpliedreg(a *obj.Addr, p *obj.Prog) int { 586 class := oclass(a) 587 if class >= C_ZCON && class <= C_64CON { 588 return REGZERO 589 } 590 switch class { 591 case C_SACON, C_LACON: 592 return REGSP 593 case C_LOREG, C_SOREG, C_ZOREG: 594 switch a.Name { 595 case obj.NAME_EXTERN, obj.NAME_STATIC: 596 return REGSB 597 case obj.NAME_AUTO, obj.NAME_PARAM: 598 return REGSP 599 case obj.NAME_NONE: 600 return REGZERO 601 } 602 } 603 c.ctxt.Diag("failed to determine implied reg for class %v (%v)", DRconv(oclass(a)), p) 604 return 0 605} 606 607func span9(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) { 608 p := cursym.Func().Text 609 if p == nil || p.Link == nil { // handle external functions and ELF section symbols 610 return 611 } 612 613 if oprange[AANDN&obj.AMask] == nil { 614 ctxt.Diag("ppc64 ops not initialized, call ppc64.buildop first") 615 } 616 617 c := ctxt9{ctxt: ctxt, newprog: newprog, cursym: cursym, autosize: int32(p.To.Offset)} 618 619 pc := int64(0) 620 p.Pc = pc 621 622 var m int 623 var o *Optab 624 for p = p.Link; p != nil; p = p.Link { 625 p.Pc = pc 626 o = c.oplook(p) 627 m = int(o.size) 628 if m == 0 { 629 if p.As == obj.APCALIGN { 630 a := c.vregoff(&p.From) 631 m = addpad(pc, a, ctxt, cursym) 632 } else { 633 if p.As != obj.ANOP && p.As != obj.AFUNCDATA && p.As != obj.APCDATA { 634 ctxt.Diag("zero-width instruction\n%v", p) 635 } 636 continue 637 } 638 } 639 pc += int64(m) 640 } 641 642 c.cursym.Size = pc 643 644 /* 645 * if any procedure is large enough to 646 * generate a large SBRA branch, then 647 * generate extra passes putting branches 648 * around jmps to fix. this is rare. 649 */ 650 bflag := 1 651 652 var otxt int64 653 var q *obj.Prog 654 var out [6]uint32 655 var falign int32 // Track increased alignment requirements for prefix. 656 for bflag != 0 { 657 bflag = 0 658 pc = 0 659 falign = 0 // Note, linker bumps function symbols to funcAlign. 660 for p = c.cursym.Func().Text.Link; p != nil; p = p.Link { 661 p.Pc = pc 662 o = c.oplook(p) 663 664 // very large conditional branches 665 if (o.type_ == 16 || o.type_ == 17) && p.To.Target() != nil { 666 otxt = p.To.Target().Pc - pc 667 if otxt < -(1<<15)+10 || otxt >= (1<<15)-10 { 668 // Assemble the instruction with a target not too far to figure out BI and BO fields. 669 // If only the CTR or BI (the CR bit) are tested, the conditional branch can be inverted, 670 // and only one extra branch is needed to reach the target. 671 tgt := p.To.Target() 672 p.To.SetTarget(p.Link) 673 c.asmout(p, o, out[:]) 674 p.To.SetTarget(tgt) 675 676 bo := int64(out[0]>>21) & 31 677 bi := int16((out[0] >> 16) & 31) 678 invertible := false 679 680 if bo&0x14 == 0x14 { 681 // A conditional branch that is unconditionally taken. This cannot be inverted. 682 } else if bo&0x10 == 0x10 { 683 // A branch based on the value of CTR. Invert the CTR comparison against zero bit. 684 bo ^= 0x2 685 invertible = true 686 } else if bo&0x04 == 0x04 { 687 // A branch based on CR bit. Invert the BI comparison bit. 688 bo ^= 0x8 689 invertible = true 690 } 691 692 if invertible { 693 // Rewrite 694 // BC bo,...,far_away_target 695 // NEXT_INSN 696 // to: 697 // BC invert(bo),next_insn 698 // JMP far_away_target 699 // next_insn: 700 // NEXT_INSN 701 p.As = ABC 702 p.From = obj.Addr{Type: obj.TYPE_CONST, Name: obj.NAME_NONE, Offset: bo} 703 q = c.newprog() 704 q.As = ABR 705 q.To.Type = obj.TYPE_BRANCH 706 q.To.SetTarget(p.To.Target()) 707 q.Link = p.Link 708 p.To.SetTarget(p.Link) 709 p.Link = q 710 p.Reg = bi // TODO: This is a hack since BI bits are not enumerated as registers 711 } else { 712 // Rewrite 713 // BC ...,far_away_target 714 // NEXT_INSN 715 // to 716 // BC ...,tmp 717 // JMP next_insn 718 // tmp: 719 // JMP far_away_target 720 // next_insn: 721 // NEXT_INSN 722 q = c.newprog() 723 q.Link = p.Link 724 p.Link = q 725 q.As = ABR 726 q.To.Type = obj.TYPE_BRANCH 727 q.To.SetTarget(p.To.Target()) 728 p.To.SetTarget(q) 729 q = c.newprog() 730 q.Link = p.Link 731 p.Link = q 732 q.As = ABR 733 q.To.Type = obj.TYPE_BRANCH 734 q.To.SetTarget(q.Link.Link) 735 } 736 bflag = 1 737 } 738 } 739 740 m = int(o.size) 741 if m == 0 { 742 if p.As == obj.APCALIGN { 743 a := c.vregoff(&p.From) 744 m = addpad(pc, a, ctxt, cursym) 745 } else { 746 if p.As != obj.ANOP && p.As != obj.AFUNCDATA && p.As != obj.APCDATA { 747 ctxt.Diag("zero-width instruction\n%v", p) 748 } 749 continue 750 } 751 } 752 753 // Prefixed instructions cannot be placed across a 64B boundary. 754 // Mark and adjust the PC of those which do. A nop will be 755 // inserted during final assembly. 756 if o.ispfx { 757 mark := p.Mark &^ PFX_X64B 758 if pc&63 == 60 { 759 p.Pc += 4 760 m += 4 761 mark |= PFX_X64B 762 } 763 764 // Marks may be adjusted if a too-far conditional branch is 765 // fixed up above. Likewise, inserting a NOP may cause a 766 // branch target to become too far away. We need to run 767 // another iteration and verify no additional changes 768 // are needed. 769 if mark != p.Mark { 770 bflag = 1 771 p.Mark = mark 772 } 773 774 // Check for 16 or 32B crossing of this prefixed insn. 775 // These do no require padding, but do require increasing 776 // the function alignment to prevent them from potentially 777 // crossing a 64B boundary when the linker assigns the final 778 // PC. 779 switch p.Pc & 31 { 780 case 28: // 32B crossing 781 falign = 64 782 case 12: // 16B crossing 783 if falign < 64 { 784 falign = 32 785 } 786 } 787 } 788 789 pc += int64(m) 790 } 791 792 c.cursym.Size = pc 793 } 794 795 c.cursym.Size = pc 796 c.cursym.Func().Align = falign 797 c.cursym.Grow(c.cursym.Size) 798 799 // lay out the code, emitting code and data relocations. 800 801 bp := c.cursym.P 802 nop := LOP_IRR(OP_ORI, REGZERO, REGZERO, 0) 803 var i int32 804 for p := c.cursym.Func().Text.Link; p != nil; p = p.Link { 805 c.pc = p.Pc 806 o = c.oplook(p) 807 if int(o.size) > 4*len(out) { 808 log.Fatalf("out array in span9 is too small, need at least %d for %v", o.size/4, p) 809 } 810 // asmout is not set up to add large amounts of padding 811 if o.type_ == 0 && p.As == obj.APCALIGN { 812 aln := c.vregoff(&p.From) 813 v := addpad(p.Pc, aln, c.ctxt, c.cursym) 814 if v > 0 { 815 // Same padding instruction for all 816 for i = 0; i < int32(v/4); i++ { 817 c.ctxt.Arch.ByteOrder.PutUint32(bp, nop) 818 bp = bp[4:] 819 } 820 } 821 } else { 822 if p.Mark&PFX_X64B != 0 { 823 c.ctxt.Arch.ByteOrder.PutUint32(bp, nop) 824 bp = bp[4:] 825 } 826 c.asmout(p, o, out[:]) 827 for i = 0; i < int32(o.size/4); i++ { 828 c.ctxt.Arch.ByteOrder.PutUint32(bp, out[i]) 829 bp = bp[4:] 830 } 831 } 832 } 833} 834 835func isint32(v int64) bool { 836 return int64(int32(v)) == v 837} 838 839func isuint32(v uint64) bool { 840 return uint64(uint32(v)) == v 841} 842 843func (c *ctxt9) aclassreg(reg int16) int { 844 if REG_R0 <= reg && reg <= REG_R31 { 845 return C_REGP + int(reg&1) 846 } 847 if REG_F0 <= reg && reg <= REG_F31 { 848 return C_FREGP + int(reg&1) 849 } 850 if REG_V0 <= reg && reg <= REG_V31 { 851 return C_VREG 852 } 853 if REG_VS0 <= reg && reg <= REG_VS63 { 854 return C_VSREGP + int(reg&1) 855 } 856 if REG_CR0 <= reg && reg <= REG_CR7 || reg == REG_CR { 857 return C_CREG 858 } 859 if REG_CR0LT <= reg && reg <= REG_CR7SO { 860 return C_CRBIT 861 } 862 if REG_SPR0 <= reg && reg <= REG_SPR0+1023 { 863 switch reg { 864 case REG_LR: 865 return C_LR 866 867 case REG_XER: 868 return C_XER 869 870 case REG_CTR: 871 return C_CTR 872 } 873 874 return C_SPR 875 } 876 if reg == REG_FPSCR { 877 return C_FPSCR 878 } 879 return C_GOK 880} 881 882func (c *ctxt9) aclass(a *obj.Addr) int { 883 switch a.Type { 884 case obj.TYPE_NONE: 885 return C_NONE 886 887 case obj.TYPE_REG: 888 return c.aclassreg(a.Reg) 889 890 case obj.TYPE_MEM: 891 switch a.Name { 892 case obj.NAME_GOTREF, obj.NAME_TOCREF: 893 return C_ADDR 894 895 case obj.NAME_EXTERN, 896 obj.NAME_STATIC: 897 c.instoffset = a.Offset 898 if a.Sym == nil { 899 break 900 } else if a.Sym.Type == objabi.STLSBSS { 901 // For PIC builds, use 12 byte got initial-exec TLS accesses. 902 if c.ctxt.Flag_shared { 903 return C_TLS_IE 904 } 905 // Otherwise, use 8 byte local-exec TLS accesses. 906 return C_TLS_LE 907 } else { 908 return C_ADDR 909 } 910 911 case obj.NAME_AUTO: 912 c.instoffset = int64(c.autosize) + a.Offset 913 if c.instoffset >= -BIG && c.instoffset < BIG { 914 return C_SOREG 915 } 916 return C_LOREG 917 918 case obj.NAME_PARAM: 919 c.instoffset = int64(c.autosize) + a.Offset + c.ctxt.FixedFrameSize() 920 if c.instoffset >= -BIG && c.instoffset < BIG { 921 return C_SOREG 922 } 923 return C_LOREG 924 925 case obj.NAME_NONE: 926 c.instoffset = a.Offset 927 if c.instoffset == 0 { 928 return C_ZOREG 929 } 930 if c.instoffset >= -BIG && c.instoffset < BIG { 931 return C_SOREG 932 } 933 return C_LOREG 934 } 935 936 return C_GOK 937 938 case obj.TYPE_TEXTSIZE: 939 return C_TEXTSIZE 940 941 case obj.TYPE_FCONST: 942 // The only cases where FCONST will occur are with float64 +/- 0. 943 // All other float constants are generated in memory. 944 f64 := a.Val.(float64) 945 if f64 == 0 { 946 if math.Signbit(f64) { 947 return C_ADDCON 948 } 949 return C_ZCON 950 } 951 log.Fatalf("Unexpected nonzero FCONST operand %v", a) 952 953 case obj.TYPE_CONST, 954 obj.TYPE_ADDR: 955 switch a.Name { 956 case obj.NAME_NONE: 957 c.instoffset = a.Offset 958 if a.Reg != 0 { 959 if -BIG <= c.instoffset && c.instoffset < BIG { 960 return C_SACON 961 } 962 if isint32(c.instoffset) { 963 return C_LACON 964 } 965 return C_DACON 966 } 967 968 case obj.NAME_EXTERN, 969 obj.NAME_STATIC: 970 s := a.Sym 971 if s == nil { 972 return C_GOK 973 } 974 c.instoffset = a.Offset 975 return C_LACON 976 977 case obj.NAME_AUTO: 978 c.instoffset = int64(c.autosize) + a.Offset 979 if c.instoffset >= -BIG && c.instoffset < BIG { 980 return C_SACON 981 } 982 return C_LACON 983 984 case obj.NAME_PARAM: 985 c.instoffset = int64(c.autosize) + a.Offset + c.ctxt.FixedFrameSize() 986 if c.instoffset >= -BIG && c.instoffset < BIG { 987 return C_SACON 988 } 989 return C_LACON 990 991 default: 992 return C_GOK 993 } 994 995 if c.instoffset >= 0 { 996 sbits := bits.Len64(uint64(c.instoffset)) 997 switch { 998 case sbits <= 5: 999 return C_ZCON + sbits 1000 case sbits <= 8: 1001 return C_U8CON 1002 case sbits <= 15: 1003 return C_U15CON 1004 case sbits <= 16: 1005 return C_U16CON 1006 case sbits <= 31: 1007 // Special case, a positive int32 value which is a multiple of 2^16 1008 if c.instoffset&0xFFFF == 0 { 1009 return C_U3216CON 1010 } 1011 return C_U32CON 1012 case sbits <= 32: 1013 return C_U32CON 1014 case sbits <= 33: 1015 return C_S34CON 1016 default: 1017 return C_64CON 1018 } 1019 } else { 1020 sbits := bits.Len64(uint64(^c.instoffset)) 1021 switch { 1022 case sbits <= 15: 1023 return C_S16CON 1024 case sbits <= 31: 1025 // Special case, a negative int32 value which is a multiple of 2^16 1026 if c.instoffset&0xFFFF == 0 { 1027 return C_S3216CON 1028 } 1029 return C_S32CON 1030 case sbits <= 33: 1031 return C_S34CON 1032 default: 1033 return C_64CON 1034 } 1035 } 1036 1037 case obj.TYPE_BRANCH: 1038 if a.Sym != nil && c.ctxt.Flag_dynlink { 1039 return C_LBRAPIC 1040 } 1041 return C_SBRA 1042 } 1043 1044 return C_GOK 1045} 1046 1047func prasm(p *obj.Prog) { 1048 fmt.Printf("%v\n", p) 1049} 1050 1051func (c *ctxt9) oplook(p *obj.Prog) *Optab { 1052 a1 := int(p.Optab) 1053 if a1 != 0 { 1054 return &optab[a1-1] 1055 } 1056 a1 = int(p.From.Class) 1057 if a1 == 0 { 1058 a1 = c.aclass(&p.From) + 1 1059 p.From.Class = int8(a1) 1060 } 1061 a1-- 1062 1063 argsv := [3]int{C_NONE + 1, C_NONE + 1, C_NONE + 1} 1064 for i, ap := range p.RestArgs { 1065 argsv[i] = int(ap.Addr.Class) 1066 if argsv[i] == 0 { 1067 argsv[i] = c.aclass(&ap.Addr) + 1 1068 ap.Addr.Class = int8(argsv[i]) 1069 } 1070 1071 } 1072 a3 := argsv[0] - 1 1073 a4 := argsv[1] - 1 1074 a5 := argsv[2] - 1 1075 1076 a6 := int(p.To.Class) 1077 if a6 == 0 { 1078 a6 = c.aclass(&p.To) + 1 1079 p.To.Class = int8(a6) 1080 } 1081 a6-- 1082 1083 a2 := C_NONE 1084 if p.Reg != 0 { 1085 a2 = c.aclassreg(p.Reg) 1086 } 1087 1088 // c.ctxt.Logf("oplook %v %d %d %d %d\n", p, a1, a2, a3, a4, a5, a6) 1089 ops := oprange[p.As&obj.AMask] 1090 c1 := &xcmp[a1] 1091 c2 := &xcmp[a2] 1092 c3 := &xcmp[a3] 1093 c4 := &xcmp[a4] 1094 c5 := &xcmp[a5] 1095 c6 := &xcmp[a6] 1096 for i := range ops { 1097 op := &ops[i] 1098 if c1[op.a1] && c2[op.a2] && c3[op.a3] && c4[op.a4] && c5[op.a5] && c6[op.a6] { 1099 p.Optab = uint16(cap(optab) - cap(ops) + i + 1) 1100 return op 1101 } 1102 } 1103 1104 c.ctxt.Diag("illegal combination %v %v %v %v %v %v %v", p.As, DRconv(a1), DRconv(a2), DRconv(a3), DRconv(a4), DRconv(a5), DRconv(a6)) 1105 prasm(p) 1106 if ops == nil { 1107 ops = optab 1108 } 1109 return &ops[0] 1110} 1111 1112// Compare two operand types (ex C_REG, or C_SCON) 1113// and return true if b is compatible with a. 1114// 1115// Argument comparison isn't reflexitive, so care must be taken. 1116// a is the argument type as found in optab, b is the argument as 1117// fitted by aclass. 1118func cmp(a int, b int) bool { 1119 if a == b { 1120 return true 1121 } 1122 switch a { 1123 1124 case C_SPR: 1125 if b == C_LR || b == C_XER || b == C_CTR { 1126 return true 1127 } 1128 1129 case C_U1CON: 1130 return cmp(C_ZCON, b) 1131 case C_U2CON: 1132 return cmp(C_U1CON, b) 1133 case C_U3CON: 1134 return cmp(C_U2CON, b) 1135 case C_U4CON: 1136 return cmp(C_U3CON, b) 1137 case C_U5CON: 1138 return cmp(C_U4CON, b) 1139 case C_U8CON: 1140 return cmp(C_U5CON, b) 1141 case C_U15CON: 1142 return cmp(C_U8CON, b) 1143 case C_U16CON: 1144 return cmp(C_U15CON, b) 1145 1146 case C_S16CON: 1147 return cmp(C_U15CON, b) 1148 case C_32CON: 1149 return cmp(C_S16CON, b) || cmp(C_U16CON, b) || cmp(C_32S16CON, b) 1150 case C_S34CON: 1151 return cmp(C_32CON, b) 1152 case C_64CON: 1153 return cmp(C_S34CON, b) 1154 1155 case C_32S16CON: 1156 return cmp(C_ZCON, b) 1157 1158 case C_LACON: 1159 return cmp(C_SACON, b) 1160 1161 case C_LBRA: 1162 return cmp(C_SBRA, b) 1163 1164 case C_SOREG: 1165 return cmp(C_ZOREG, b) 1166 1167 case C_LOREG: 1168 return cmp(C_SOREG, b) 1169 1170 // An even/odd register input always matches the regular register types. 1171 case C_REG: 1172 return cmp(C_REGP, b) || (b == C_ZCON && r0iszero != 0) 1173 case C_FREG: 1174 return cmp(C_FREGP, b) 1175 case C_VSREG: 1176 /* Allow any VR argument as a VSR operand. */ 1177 return cmp(C_VSREGP, b) || cmp(C_VREG, b) 1178 1179 case C_ANY: 1180 return true 1181 } 1182 1183 return false 1184} 1185 1186type ocmp []Optab 1187 1188func (x ocmp) Len() int { 1189 return len(x) 1190} 1191 1192func (x ocmp) Swap(i, j int) { 1193 x[i], x[j] = x[j], x[i] 1194} 1195 1196// Used when sorting the optab. Sorting is 1197// done in a way so that the best choice of 1198// opcode/operand combination is considered first. 1199func (x ocmp) Less(i, j int) bool { 1200 p1 := &x[i] 1201 p2 := &x[j] 1202 n := int(p1.as) - int(p2.as) 1203 // same opcode 1204 if n != 0 { 1205 return n < 0 1206 } 1207 // Consider those that generate fewer 1208 // instructions first. 1209 n = int(p1.size) - int(p2.size) 1210 if n != 0 { 1211 return n < 0 1212 } 1213 // operand order should match 1214 // better choices first 1215 n = int(p1.a1) - int(p2.a1) 1216 if n != 0 { 1217 return n < 0 1218 } 1219 n = int(p1.a2) - int(p2.a2) 1220 if n != 0 { 1221 return n < 0 1222 } 1223 n = int(p1.a3) - int(p2.a3) 1224 if n != 0 { 1225 return n < 0 1226 } 1227 n = int(p1.a4) - int(p2.a4) 1228 if n != 0 { 1229 return n < 0 1230 } 1231 n = int(p1.a5) - int(p2.a5) 1232 if n != 0 { 1233 return n < 0 1234 } 1235 n = int(p1.a6) - int(p2.a6) 1236 if n != 0 { 1237 return n < 0 1238 } 1239 return false 1240} 1241 1242// Add an entry to the opcode table for 1243// a new opcode b0 with the same operand combinations 1244// as opcode a. 1245func opset(a, b0 obj.As) { 1246 oprange[a&obj.AMask] = oprange[b0] 1247} 1248 1249// Build the opcode table 1250func buildop(ctxt *obj.Link) { 1251 if oprange[AANDN&obj.AMask] != nil { 1252 // Already initialized; stop now. 1253 // This happens in the cmd/asm tests, 1254 // each of which re-initializes the arch. 1255 return 1256 } 1257 1258 var n int 1259 1260 for i := 0; i < C_NCLASS; i++ { 1261 for n = 0; n < C_NCLASS; n++ { 1262 if cmp(n, i) { 1263 xcmp[i][n] = true 1264 } 1265 } 1266 } 1267 for n = 0; optab[n].as != obj.AXXX; n++ { 1268 } 1269 sort.Sort(ocmp(optab[:n])) 1270 for i := 0; i < n; i++ { 1271 r := optab[i].as 1272 r0 := r & obj.AMask 1273 start := i 1274 for optab[i].as == r { 1275 i++ 1276 } 1277 oprange[r0] = optab[start:i] 1278 i-- 1279 1280 switch r { 1281 default: 1282 ctxt.Diag("unknown op in build: %v", r) 1283 log.Fatalf("instruction missing from switch in asm9.go:buildop: %v", r) 1284 1285 case ADCBF: /* unary indexed: op (b+a); op (b) */ 1286 opset(ADCBI, r0) 1287 1288 opset(ADCBST, r0) 1289 opset(ADCBT, r0) 1290 opset(ADCBTST, r0) 1291 opset(ADCBZ, r0) 1292 opset(AICBI, r0) 1293 1294 case AECOWX: /* indexed store: op s,(b+a); op s,(b) */ 1295 opset(ASTWCCC, r0) 1296 opset(ASTHCCC, r0) 1297 opset(ASTBCCC, r0) 1298 opset(ASTDCCC, r0) 1299 1300 case AREM: /* macro */ 1301 opset(AREM, r0) 1302 1303 case AREMU: 1304 opset(AREMU, r0) 1305 1306 case AREMD: 1307 opset(AREMDU, r0) 1308 1309 case AMULLW: 1310 opset(AMULLD, r0) 1311 1312 case ADIVW: /* op Rb[,Ra],Rd */ 1313 opset(AMULHW, r0) 1314 1315 opset(AMULHWCC, r0) 1316 opset(AMULHWU, r0) 1317 opset(AMULHWUCC, r0) 1318 opset(AMULLWCC, r0) 1319 opset(AMULLWVCC, r0) 1320 opset(AMULLWV, r0) 1321 opset(ADIVWCC, r0) 1322 opset(ADIVWV, r0) 1323 opset(ADIVWVCC, r0) 1324 opset(ADIVWU, r0) 1325 opset(ADIVWUCC, r0) 1326 opset(ADIVWUV, r0) 1327 opset(ADIVWUVCC, r0) 1328 opset(AMODUD, r0) 1329 opset(AMODUW, r0) 1330 opset(AMODSD, r0) 1331 opset(AMODSW, r0) 1332 opset(AADDCC, r0) 1333 opset(AADDCV, r0) 1334 opset(AADDCVCC, r0) 1335 opset(AADDV, r0) 1336 opset(AADDVCC, r0) 1337 opset(AADDE, r0) 1338 opset(AADDECC, r0) 1339 opset(AADDEV, r0) 1340 opset(AADDEVCC, r0) 1341 opset(AMULHD, r0) 1342 opset(AMULHDCC, r0) 1343 opset(AMULHDU, r0) 1344 opset(AMULHDUCC, r0) 1345 opset(AMULLDCC, r0) 1346 opset(AMULLDVCC, r0) 1347 opset(AMULLDV, r0) 1348 opset(ADIVD, r0) 1349 opset(ADIVDCC, r0) 1350 opset(ADIVDE, r0) 1351 opset(ADIVDEU, r0) 1352 opset(ADIVDECC, r0) 1353 opset(ADIVDEUCC, r0) 1354 opset(ADIVDVCC, r0) 1355 opset(ADIVDV, r0) 1356 opset(ADIVDU, r0) 1357 opset(ADIVDUV, r0) 1358 opset(ADIVDUVCC, r0) 1359 opset(ADIVDUCC, r0) 1360 1361 case ACRAND: 1362 opset(ACRANDN, r0) 1363 opset(ACREQV, r0) 1364 opset(ACRNAND, r0) 1365 opset(ACRNOR, r0) 1366 opset(ACROR, r0) 1367 opset(ACRORN, r0) 1368 opset(ACRXOR, r0) 1369 1370 case APOPCNTD: /* popcntd, popcntw, popcntb, cnttzw, cnttzd */ 1371 opset(APOPCNTW, r0) 1372 opset(APOPCNTB, r0) 1373 opset(ACNTTZW, r0) 1374 opset(ACNTTZWCC, r0) 1375 opset(ACNTTZD, r0) 1376 opset(ACNTTZDCC, r0) 1377 1378 case ACOPY: /* copy, paste. */ 1379 opset(APASTECC, r0) 1380 1381 case AMADDHD: /* maddhd, maddhdu, maddld */ 1382 opset(AMADDHDU, r0) 1383 opset(AMADDLD, r0) 1384 1385 case AMOVBZ: /* lbz, stz, rlwm(r/r), lhz, lha, stz, and x variants */ 1386 opset(AMOVH, r0) 1387 opset(AMOVHZ, r0) 1388 1389 case AMOVBZU: /* lbz[x]u, stb[x]u, lhz[x]u, lha[x]u, sth[u]x, ld[x]u, std[u]x */ 1390 opset(AMOVHU, r0) 1391 1392 opset(AMOVHZU, r0) 1393 opset(AMOVWU, r0) 1394 opset(AMOVWZU, r0) 1395 opset(AMOVDU, r0) 1396 opset(AMOVMW, r0) 1397 1398 case ALV: /* lvebx, lvehx, lvewx, lvx, lvxl, lvsl, lvsr */ 1399 opset(ALVEBX, r0) 1400 opset(ALVEHX, r0) 1401 opset(ALVEWX, r0) 1402 opset(ALVX, r0) 1403 opset(ALVXL, r0) 1404 opset(ALVSL, r0) 1405 opset(ALVSR, r0) 1406 1407 case ASTV: /* stvebx, stvehx, stvewx, stvx, stvxl */ 1408 opset(ASTVEBX, r0) 1409 opset(ASTVEHX, r0) 1410 opset(ASTVEWX, r0) 1411 opset(ASTVX, r0) 1412 opset(ASTVXL, r0) 1413 1414 case AVAND: /* vand, vandc, vnand */ 1415 opset(AVAND, r0) 1416 opset(AVANDC, r0) 1417 opset(AVNAND, r0) 1418 1419 case AVMRGOW: /* vmrgew, vmrgow */ 1420 opset(AVMRGEW, r0) 1421 1422 case AVOR: /* vor, vorc, vxor, vnor, veqv */ 1423 opset(AVOR, r0) 1424 opset(AVORC, r0) 1425 opset(AVXOR, r0) 1426 opset(AVNOR, r0) 1427 opset(AVEQV, r0) 1428 1429 case AVADDUM: /* vaddubm, vadduhm, vadduwm, vaddudm, vadduqm */ 1430 opset(AVADDUBM, r0) 1431 opset(AVADDUHM, r0) 1432 opset(AVADDUWM, r0) 1433 opset(AVADDUDM, r0) 1434 opset(AVADDUQM, r0) 1435 1436 case AVADDCU: /* vaddcuq, vaddcuw */ 1437 opset(AVADDCUQ, r0) 1438 opset(AVADDCUW, r0) 1439 1440 case AVADDUS: /* vaddubs, vadduhs, vadduws */ 1441 opset(AVADDUBS, r0) 1442 opset(AVADDUHS, r0) 1443 opset(AVADDUWS, r0) 1444 1445 case AVADDSS: /* vaddsbs, vaddshs, vaddsws */ 1446 opset(AVADDSBS, r0) 1447 opset(AVADDSHS, r0) 1448 opset(AVADDSWS, r0) 1449 1450 case AVADDE: /* vaddeuqm, vaddecuq */ 1451 opset(AVADDEUQM, r0) 1452 opset(AVADDECUQ, r0) 1453 1454 case AVSUBUM: /* vsububm, vsubuhm, vsubuwm, vsubudm, vsubuqm */ 1455 opset(AVSUBUBM, r0) 1456 opset(AVSUBUHM, r0) 1457 opset(AVSUBUWM, r0) 1458 opset(AVSUBUDM, r0) 1459 opset(AVSUBUQM, r0) 1460 1461 case AVSUBCU: /* vsubcuq, vsubcuw */ 1462 opset(AVSUBCUQ, r0) 1463 opset(AVSUBCUW, r0) 1464 1465 case AVSUBUS: /* vsububs, vsubuhs, vsubuws */ 1466 opset(AVSUBUBS, r0) 1467 opset(AVSUBUHS, r0) 1468 opset(AVSUBUWS, r0) 1469 1470 case AVSUBSS: /* vsubsbs, vsubshs, vsubsws */ 1471 opset(AVSUBSBS, r0) 1472 opset(AVSUBSHS, r0) 1473 opset(AVSUBSWS, r0) 1474 1475 case AVSUBE: /* vsubeuqm, vsubecuq */ 1476 opset(AVSUBEUQM, r0) 1477 opset(AVSUBECUQ, r0) 1478 1479 case AVMULESB: /* vmulesb, vmulosb, vmuleub, vmuloub, vmulosh, vmulouh, vmulesw, vmulosw, vmuleuw, vmulouw, vmuluwm */ 1480 opset(AVMULOSB, r0) 1481 opset(AVMULEUB, r0) 1482 opset(AVMULOUB, r0) 1483 opset(AVMULESH, r0) 1484 opset(AVMULOSH, r0) 1485 opset(AVMULEUH, r0) 1486 opset(AVMULOUH, r0) 1487 opset(AVMULESW, r0) 1488 opset(AVMULOSW, r0) 1489 opset(AVMULEUW, r0) 1490 opset(AVMULOUW, r0) 1491 opset(AVMULUWM, r0) 1492 case AVPMSUM: /* vpmsumb, vpmsumh, vpmsumw, vpmsumd */ 1493 opset(AVPMSUMB, r0) 1494 opset(AVPMSUMH, r0) 1495 opset(AVPMSUMW, r0) 1496 opset(AVPMSUMD, r0) 1497 1498 case AVR: /* vrlb, vrlh, vrlw, vrld */ 1499 opset(AVRLB, r0) 1500 opset(AVRLH, r0) 1501 opset(AVRLW, r0) 1502 opset(AVRLD, r0) 1503 1504 case AVS: /* vs[l,r], vs[l,r]o, vs[l,r]b, vs[l,r]h, vs[l,r]w, vs[l,r]d */ 1505 opset(AVSLB, r0) 1506 opset(AVSLH, r0) 1507 opset(AVSLW, r0) 1508 opset(AVSL, r0) 1509 opset(AVSLO, r0) 1510 opset(AVSRB, r0) 1511 opset(AVSRH, r0) 1512 opset(AVSRW, r0) 1513 opset(AVSR, r0) 1514 opset(AVSRO, r0) 1515 opset(AVSLD, r0) 1516 opset(AVSRD, r0) 1517 1518 case AVSA: /* vsrab, vsrah, vsraw, vsrad */ 1519 opset(AVSRAB, r0) 1520 opset(AVSRAH, r0) 1521 opset(AVSRAW, r0) 1522 opset(AVSRAD, r0) 1523 1524 case AVSOI: /* vsldoi */ 1525 opset(AVSLDOI, r0) 1526 1527 case AVCLZ: /* vclzb, vclzh, vclzw, vclzd */ 1528 opset(AVCLZB, r0) 1529 opset(AVCLZH, r0) 1530 opset(AVCLZW, r0) 1531 opset(AVCLZD, r0) 1532 1533 case AVPOPCNT: /* vpopcntb, vpopcnth, vpopcntw, vpopcntd */ 1534 opset(AVPOPCNTB, r0) 1535 opset(AVPOPCNTH, r0) 1536 opset(AVPOPCNTW, r0) 1537 opset(AVPOPCNTD, r0) 1538 1539 case AVCMPEQ: /* vcmpequb[.], vcmpequh[.], vcmpequw[.], vcmpequd[.] */ 1540 opset(AVCMPEQUB, r0) 1541 opset(AVCMPEQUBCC, r0) 1542 opset(AVCMPEQUH, r0) 1543 opset(AVCMPEQUHCC, r0) 1544 opset(AVCMPEQUW, r0) 1545 opset(AVCMPEQUWCC, r0) 1546 opset(AVCMPEQUD, r0) 1547 opset(AVCMPEQUDCC, r0) 1548 1549 case AVCMPGT: /* vcmpgt[u,s]b[.], vcmpgt[u,s]h[.], vcmpgt[u,s]w[.], vcmpgt[u,s]d[.] */ 1550 opset(AVCMPGTUB, r0) 1551 opset(AVCMPGTUBCC, r0) 1552 opset(AVCMPGTUH, r0) 1553 opset(AVCMPGTUHCC, r0) 1554 opset(AVCMPGTUW, r0) 1555 opset(AVCMPGTUWCC, r0) 1556 opset(AVCMPGTUD, r0) 1557 opset(AVCMPGTUDCC, r0) 1558 opset(AVCMPGTSB, r0) 1559 opset(AVCMPGTSBCC, r0) 1560 opset(AVCMPGTSH, r0) 1561 opset(AVCMPGTSHCC, r0) 1562 opset(AVCMPGTSW, r0) 1563 opset(AVCMPGTSWCC, r0) 1564 opset(AVCMPGTSD, r0) 1565 opset(AVCMPGTSDCC, r0) 1566 1567 case AVCMPNEZB: /* vcmpnezb[.] */ 1568 opset(AVCMPNEZBCC, r0) 1569 opset(AVCMPNEB, r0) 1570 opset(AVCMPNEBCC, r0) 1571 opset(AVCMPNEH, r0) 1572 opset(AVCMPNEHCC, r0) 1573 opset(AVCMPNEW, r0) 1574 opset(AVCMPNEWCC, r0) 1575 1576 case AVPERM: /* vperm */ 1577 opset(AVPERMXOR, r0) 1578 opset(AVPERMR, r0) 1579 1580 case AVBPERMQ: /* vbpermq, vbpermd */ 1581 opset(AVBPERMD, r0) 1582 1583 case AVSEL: /* vsel */ 1584 opset(AVSEL, r0) 1585 1586 case AVSPLTB: /* vspltb, vsplth, vspltw */ 1587 opset(AVSPLTH, r0) 1588 opset(AVSPLTW, r0) 1589 1590 case AVSPLTISB: /* vspltisb, vspltish, vspltisw */ 1591 opset(AVSPLTISH, r0) 1592 opset(AVSPLTISW, r0) 1593 1594 case AVCIPH: /* vcipher, vcipherlast */ 1595 opset(AVCIPHER, r0) 1596 opset(AVCIPHERLAST, r0) 1597 1598 case AVNCIPH: /* vncipher, vncipherlast */ 1599 opset(AVNCIPHER, r0) 1600 opset(AVNCIPHERLAST, r0) 1601 1602 case AVSBOX: /* vsbox */ 1603 opset(AVSBOX, r0) 1604 1605 case AVSHASIGMA: /* vshasigmaw, vshasigmad */ 1606 opset(AVSHASIGMAW, r0) 1607 opset(AVSHASIGMAD, r0) 1608 1609 case ALXVD2X: /* lxvd2x, lxvdsx, lxvw4x, lxvh8x, lxvb16x */ 1610 opset(ALXVDSX, r0) 1611 opset(ALXVW4X, r0) 1612 opset(ALXVH8X, r0) 1613 opset(ALXVB16X, r0) 1614 1615 case ALXV: /* lxv */ 1616 opset(ALXV, r0) 1617 1618 case ALXVL: /* lxvl, lxvll, lxvx */ 1619 opset(ALXVLL, r0) 1620 opset(ALXVX, r0) 1621 1622 case ASTXVD2X: /* stxvd2x, stxvdsx, stxvw4x, stxvh8x, stxvb16x */ 1623 opset(ASTXVW4X, r0) 1624 opset(ASTXVH8X, r0) 1625 opset(ASTXVB16X, r0) 1626 1627 case ASTXV: /* stxv */ 1628 opset(ASTXV, r0) 1629 1630 case ASTXVL: /* stxvl, stxvll, stvx */ 1631 opset(ASTXVLL, r0) 1632 opset(ASTXVX, r0) 1633 1634 case ALXSDX: /* lxsdx */ 1635 opset(ALXSDX, r0) 1636 1637 case ASTXSDX: /* stxsdx */ 1638 opset(ASTXSDX, r0) 1639 1640 case ALXSIWAX: /* lxsiwax, lxsiwzx */ 1641 opset(ALXSIWZX, r0) 1642 1643 case ASTXSIWX: /* stxsiwx */ 1644 opset(ASTXSIWX, r0) 1645 1646 case AMFVSRD: /* mfvsrd, mfvsrwz (and extended mnemonics), mfvsrld */ 1647 opset(AMFFPRD, r0) 1648 opset(AMFVRD, r0) 1649 opset(AMFVSRWZ, r0) 1650 opset(AMFVSRLD, r0) 1651 1652 case AMTVSRD: /* mtvsrd, mtvsrwa, mtvsrwz (and extended mnemonics), mtvsrdd, mtvsrws */ 1653 opset(AMTFPRD, r0) 1654 opset(AMTVRD, r0) 1655 opset(AMTVSRWA, r0) 1656 opset(AMTVSRWZ, r0) 1657 opset(AMTVSRWS, r0) 1658 1659 case AXXLAND: /* xxland, xxlandc, xxleqv, xxlnand */ 1660 opset(AXXLANDC, r0) 1661 opset(AXXLEQV, r0) 1662 opset(AXXLNAND, r0) 1663 1664 case AXXLOR: /* xxlorc, xxlnor, xxlor, xxlxor */ 1665 opset(AXXLORC, r0) 1666 opset(AXXLNOR, r0) 1667 opset(AXXLORQ, r0) 1668 opset(AXXLXOR, r0) 1669 1670 case AXXSEL: /* xxsel */ 1671 opset(AXXSEL, r0) 1672 1673 case AXXMRGHW: /* xxmrghw, xxmrglw */ 1674 opset(AXXMRGLW, r0) 1675 1676 case AXXSPLTW: /* xxspltw */ 1677 opset(AXXSPLTW, r0) 1678 1679 case AXXSPLTIB: /* xxspltib */ 1680 opset(AXXSPLTIB, r0) 1681 1682 case AXXPERM: /* xxpermdi */ 1683 opset(AXXPERM, r0) 1684 1685 case AXXSLDWI: /* xxsldwi */ 1686 opset(AXXPERMDI, r0) 1687 opset(AXXSLDWI, r0) 1688 1689 case AXXBRQ: /* xxbrq, xxbrd, xxbrw, xxbrh */ 1690 opset(AXXBRD, r0) 1691 opset(AXXBRW, r0) 1692 opset(AXXBRH, r0) 1693 1694 case AXSCVDPSP: /* xscvdpsp, xscvspdp, xscvdpspn, xscvspdpn */ 1695 opset(AXSCVSPDP, r0) 1696 opset(AXSCVDPSPN, r0) 1697 opset(AXSCVSPDPN, r0) 1698 1699 case AXVCVDPSP: /* xvcvdpsp, xvcvspdp */ 1700 opset(AXVCVSPDP, r0) 1701 1702 case AXSCVDPSXDS: /* xscvdpsxds, xscvdpsxws, xscvdpuxds, xscvdpuxws */ 1703 opset(AXSCVDPSXWS, r0) 1704 opset(AXSCVDPUXDS, r0) 1705 opset(AXSCVDPUXWS, r0) 1706 1707 case AXSCVSXDDP: /* xscvsxddp, xscvuxddp, xscvsxdsp, xscvuxdsp */ 1708 opset(AXSCVUXDDP, r0) 1709 opset(AXSCVSXDSP, r0) 1710 opset(AXSCVUXDSP, r0) 1711 1712 case AXVCVDPSXDS: /* xvcvdpsxds, xvcvdpsxws, xvcvdpuxds, xvcvdpuxws, xvcvspsxds, xvcvspsxws, xvcvspuxds, xvcvspuxws */ 1713 opset(AXVCVDPSXDS, r0) 1714 opset(AXVCVDPSXWS, r0) 1715 opset(AXVCVDPUXDS, r0) 1716 opset(AXVCVDPUXWS, r0) 1717 opset(AXVCVSPSXDS, r0) 1718 opset(AXVCVSPSXWS, r0) 1719 opset(AXVCVSPUXDS, r0) 1720 opset(AXVCVSPUXWS, r0) 1721 1722 case AXVCVSXDDP: /* xvcvsxddp, xvcvsxwdp, xvcvuxddp, xvcvuxwdp, xvcvsxdsp, xvcvsxwsp, xvcvuxdsp, xvcvuxwsp */ 1723 opset(AXVCVSXWDP, r0) 1724 opset(AXVCVUXDDP, r0) 1725 opset(AXVCVUXWDP, r0) 1726 opset(AXVCVSXDSP, r0) 1727 opset(AXVCVSXWSP, r0) 1728 opset(AXVCVUXDSP, r0) 1729 opset(AXVCVUXWSP, r0) 1730 1731 case AAND: /* logical op Rb,Rs,Ra; no literal */ 1732 opset(AANDN, r0) 1733 opset(AANDNCC, r0) 1734 opset(AEQV, r0) 1735 opset(AEQVCC, r0) 1736 opset(ANAND, r0) 1737 opset(ANANDCC, r0) 1738 opset(ANOR, r0) 1739 opset(ANORCC, r0) 1740 opset(AORCC, r0) 1741 opset(AORN, r0) 1742 opset(AORNCC, r0) 1743 opset(AXORCC, r0) 1744 1745 case AADDME: /* op Ra, Rd */ 1746 opset(AADDMECC, r0) 1747 1748 opset(AADDMEV, r0) 1749 opset(AADDMEVCC, r0) 1750 opset(AADDZE, r0) 1751 opset(AADDZECC, r0) 1752 opset(AADDZEV, r0) 1753 opset(AADDZEVCC, r0) 1754 opset(ASUBME, r0) 1755 opset(ASUBMECC, r0) 1756 opset(ASUBMEV, r0) 1757 opset(ASUBMEVCC, r0) 1758 opset(ASUBZE, r0) 1759 opset(ASUBZECC, r0) 1760 opset(ASUBZEV, r0) 1761 opset(ASUBZEVCC, r0) 1762 1763 case AADDC: 1764 opset(AADDCCC, r0) 1765 1766 case ABEQ: 1767 opset(ABGE, r0) 1768 opset(ABGT, r0) 1769 opset(ABLE, r0) 1770 opset(ABLT, r0) 1771 opset(ABNE, r0) 1772 opset(ABVC, r0) 1773 opset(ABVS, r0) 1774 1775 case ABR: 1776 opset(ABL, r0) 1777 1778 case ABC: 1779 opset(ABCL, r0) 1780 1781 case AEXTSB: /* op Rs, Ra */ 1782 opset(AEXTSBCC, r0) 1783 1784 opset(AEXTSH, r0) 1785 opset(AEXTSHCC, r0) 1786 opset(ACNTLZW, r0) 1787 opset(ACNTLZWCC, r0) 1788 opset(ACNTLZD, r0) 1789 opset(AEXTSW, r0) 1790 opset(AEXTSWCC, r0) 1791 opset(ACNTLZDCC, r0) 1792 1793 case AFABS: /* fop [s,]d */ 1794 opset(AFABSCC, r0) 1795 1796 opset(AFNABS, r0) 1797 opset(AFNABSCC, r0) 1798 opset(AFNEG, r0) 1799 opset(AFNEGCC, r0) 1800 opset(AFRSP, r0) 1801 opset(AFRSPCC, r0) 1802 opset(AFCTIW, r0) 1803 opset(AFCTIWCC, r0) 1804 opset(AFCTIWZ, r0) 1805 opset(AFCTIWZCC, r0) 1806 opset(AFCTID, r0) 1807 opset(AFCTIDCC, r0) 1808 opset(AFCTIDZ, r0) 1809 opset(AFCTIDZCC, r0) 1810 opset(AFCFID, r0) 1811 opset(AFCFIDCC, r0) 1812 opset(AFCFIDU, r0) 1813 opset(AFCFIDUCC, r0) 1814 opset(AFCFIDS, r0) 1815 opset(AFCFIDSCC, r0) 1816 opset(AFRES, r0) 1817 opset(AFRESCC, r0) 1818 opset(AFRIM, r0) 1819 opset(AFRIMCC, r0) 1820 opset(AFRIP, r0) 1821 opset(AFRIPCC, r0) 1822 opset(AFRIZ, r0) 1823 opset(AFRIZCC, r0) 1824 opset(AFRIN, r0) 1825 opset(AFRINCC, r0) 1826 opset(AFRSQRTE, r0) 1827 opset(AFRSQRTECC, r0) 1828 opset(AFSQRT, r0) 1829 opset(AFSQRTCC, r0) 1830 opset(AFSQRTS, r0) 1831 opset(AFSQRTSCC, r0) 1832 1833 case AFADD: 1834 opset(AFADDS, r0) 1835 opset(AFADDCC, r0) 1836 opset(AFADDSCC, r0) 1837 opset(AFCPSGN, r0) 1838 opset(AFCPSGNCC, r0) 1839 opset(AFDIV, r0) 1840 opset(AFDIVS, r0) 1841 opset(AFDIVCC, r0) 1842 opset(AFDIVSCC, r0) 1843 opset(AFSUB, r0) 1844 opset(AFSUBS, r0) 1845 opset(AFSUBCC, r0) 1846 opset(AFSUBSCC, r0) 1847 1848 case AFMADD: 1849 opset(AFMADDCC, r0) 1850 opset(AFMADDS, r0) 1851 opset(AFMADDSCC, r0) 1852 opset(AFMSUB, r0) 1853 opset(AFMSUBCC, r0) 1854 opset(AFMSUBS, r0) 1855 opset(AFMSUBSCC, r0) 1856 opset(AFNMADD, r0) 1857 opset(AFNMADDCC, r0) 1858 opset(AFNMADDS, r0) 1859 opset(AFNMADDSCC, r0) 1860 opset(AFNMSUB, r0) 1861 opset(AFNMSUBCC, r0) 1862 opset(AFNMSUBS, r0) 1863 opset(AFNMSUBSCC, r0) 1864 opset(AFSEL, r0) 1865 opset(AFSELCC, r0) 1866 1867 case AFMUL: 1868 opset(AFMULS, r0) 1869 opset(AFMULCC, r0) 1870 opset(AFMULSCC, r0) 1871 1872 case AFCMPO: 1873 opset(AFCMPU, r0) 1874 1875 case AISEL: 1876 opset(AISEL, r0) 1877 1878 case AMTFSB0: 1879 opset(AMTFSB0CC, r0) 1880 opset(AMTFSB1, r0) 1881 opset(AMTFSB1CC, r0) 1882 1883 case ANEG: /* op [Ra,] Rd */ 1884 opset(ANEGCC, r0) 1885 1886 opset(ANEGV, r0) 1887 opset(ANEGVCC, r0) 1888 1889 case AOR: /* or/xor Rb,Rs,Ra; ori/xori $uimm,Rs,R */ 1890 opset(AXOR, r0) 1891 1892 case AORIS: /* oris/xoris $uimm,Rs,Ra */ 1893 opset(AXORIS, r0) 1894 1895 case ASLW: 1896 opset(ASLWCC, r0) 1897 opset(ASRW, r0) 1898 opset(ASRWCC, r0) 1899 opset(AROTLW, r0) 1900 1901 case ASLD: 1902 opset(ASLDCC, r0) 1903 opset(ASRD, r0) 1904 opset(ASRDCC, r0) 1905 opset(AROTL, r0) 1906 1907 case ASRAW: /* sraw Rb,Rs,Ra; srawi sh,Rs,Ra */ 1908 opset(ASRAWCC, r0) 1909 1910 case AEXTSWSLI: 1911 opset(AEXTSWSLICC, r0) 1912 1913 case ASRAD: /* sraw Rb,Rs,Ra; srawi sh,Rs,Ra */ 1914 opset(ASRADCC, r0) 1915 1916 case ASUB: /* SUB Ra,Rb,Rd => subf Rd,ra,rb */ 1917 opset(ASUB, r0) 1918 1919 opset(ASUBCC, r0) 1920 opset(ASUBV, r0) 1921 opset(ASUBVCC, r0) 1922 opset(ASUBCCC, r0) 1923 opset(ASUBCV, r0) 1924 opset(ASUBCVCC, r0) 1925 opset(ASUBE, r0) 1926 opset(ASUBECC, r0) 1927 opset(ASUBEV, r0) 1928 opset(ASUBEVCC, r0) 1929 1930 case ASYNC: 1931 opset(AISYNC, r0) 1932 opset(ALWSYNC, r0) 1933 opset(APTESYNC, r0) 1934 opset(ATLBSYNC, r0) 1935 1936 case ARLWMI: 1937 opset(ARLWMICC, r0) 1938 opset(ARLWNM, r0) 1939 opset(ARLWNMCC, r0) 1940 1941 case ARLDMI: 1942 opset(ARLDMICC, r0) 1943 opset(ARLDIMI, r0) 1944 opset(ARLDIMICC, r0) 1945 1946 case ARLDC: 1947 opset(ARLDCCC, r0) 1948 1949 case ARLDCL: 1950 opset(ARLDCR, r0) 1951 opset(ARLDCLCC, r0) 1952 opset(ARLDCRCC, r0) 1953 1954 case ARLDICL: 1955 opset(ARLDICLCC, r0) 1956 opset(ARLDICR, r0) 1957 opset(ARLDICRCC, r0) 1958 opset(ARLDIC, r0) 1959 opset(ARLDICCC, r0) 1960 opset(ACLRLSLDI, r0) 1961 1962 case AFMOVD: 1963 opset(AFMOVDCC, r0) 1964 opset(AFMOVDU, r0) 1965 opset(AFMOVS, r0) 1966 opset(AFMOVSU, r0) 1967 1968 case ALDAR: 1969 opset(ALBAR, r0) 1970 opset(ALHAR, r0) 1971 opset(ALWAR, r0) 1972 1973 case ASYSCALL: /* just the op; flow of control */ 1974 opset(ARFI, r0) 1975 1976 opset(ARFCI, r0) 1977 opset(ARFID, r0) 1978 opset(AHRFID, r0) 1979 1980 case AMOVHBR: 1981 opset(AMOVWBR, r0) 1982 opset(AMOVDBR, r0) 1983 1984 case ASLBMFEE: 1985 opset(ASLBMFEV, r0) 1986 1987 case ATW: 1988 opset(ATD, r0) 1989 1990 case ATLBIE: 1991 opset(ASLBIE, r0) 1992 opset(ATLBIEL, r0) 1993 1994 case AEIEIO: 1995 opset(ASLBIA, r0) 1996 1997 case ACMP: 1998 opset(ACMPW, r0) 1999 2000 case ACMPU: 2001 opset(ACMPWU, r0) 2002 2003 case ACMPB: 2004 opset(ACMPB, r0) 2005 2006 case AFTDIV: 2007 opset(AFTDIV, r0) 2008 2009 case AFTSQRT: 2010 opset(AFTSQRT, r0) 2011 2012 case AMOVW: /* load/store/move word with sign extension; move 32-bit literals */ 2013 opset(AMOVWZ, r0) /* Same as above, but zero extended */ 2014 2015 case AADD, 2016 AADDIS, 2017 AANDCC, /* and. Rb,Rs,Ra; andi. $uimm,Rs,Ra */ 2018 AANDISCC, 2019 AFMOVSX, 2020 AFMOVSZ, 2021 ALSW, 2022 AMOVD, /* load/store/move 64-bit values, including 32-bit literals with/without sign-extension */ 2023 AMOVB, /* macro: move byte with sign extension */ 2024 AMOVBU, /* macro: move byte with sign extension & update */ 2025 AMOVFL, 2026 /* op $s[,r2],r3; op r1[,r2],r3; no cc/v */ 2027 ASUBC, /* op r1,$s,r3; op r1[,r2],r3 */ 2028 ASTSW, 2029 ASLBMTE, 2030 AWORD, 2031 ADWORD, 2032 ADARN, 2033 ALDMX, 2034 AVMSUMUDM, 2035 AADDEX, 2036 ACMPEQB, 2037 AECIWX, 2038 ACLRLSLWI, 2039 AMTVSRDD, 2040 APNOP, 2041 obj.ANOP, 2042 obj.ATEXT, 2043 obj.AUNDEF, 2044 obj.AFUNCDATA, 2045 obj.APCALIGN, 2046 obj.APCDATA, 2047 obj.ADUFFZERO, 2048 obj.ADUFFCOPY: 2049 break 2050 } 2051 } 2052} 2053 2054func OPVXX1(o uint32, xo uint32, oe uint32) uint32 { 2055 return o<<26 | xo<<1 | oe<<11 2056} 2057 2058func OPVXX2(o uint32, xo uint32, oe uint32) uint32 { 2059 return o<<26 | xo<<2 | oe<<11 2060} 2061 2062func OPVXX2VA(o uint32, xo uint32, oe uint32) uint32 { 2063 return o<<26 | xo<<2 | oe<<16 2064} 2065 2066func OPVXX3(o uint32, xo uint32, oe uint32) uint32 { 2067 return o<<26 | xo<<3 | oe<<11 2068} 2069 2070func OPVXX4(o uint32, xo uint32, oe uint32) uint32 { 2071 return o<<26 | xo<<4 | oe<<11 2072} 2073 2074func OPDQ(o uint32, xo uint32, oe uint32) uint32 { 2075 return o<<26 | xo | oe<<4 2076} 2077 2078func OPVX(o uint32, xo uint32, oe uint32, rc uint32) uint32 { 2079 return o<<26 | xo | oe<<11 | rc&1 2080} 2081 2082func OPVC(o uint32, xo uint32, oe uint32, rc uint32) uint32 { 2083 return o<<26 | xo | oe<<11 | (rc&1)<<10 2084} 2085 2086func OPVCC(o uint32, xo uint32, oe uint32, rc uint32) uint32 { 2087 return o<<26 | xo<<1 | oe<<10 | rc&1 2088} 2089 2090func OPCC(o uint32, xo uint32, rc uint32) uint32 { 2091 return OPVCC(o, xo, 0, rc) 2092} 2093 2094/* Generate MD-form opcode */ 2095func OPMD(o, xo, rc uint32) uint32 { 2096 return o<<26 | xo<<2 | rc&1 2097} 2098 2099/* the order is dest, a/s, b/imm for both arithmetic and logical operations */ 2100func AOP_RRR(op uint32, d uint32, a uint32, b uint32) uint32 { 2101 return op | (d&31)<<21 | (a&31)<<16 | (b&31)<<11 2102} 2103 2104/* VX-form 2-register operands, r/none/r */ 2105func AOP_RR(op uint32, d uint32, a uint32) uint32 { 2106 return op | (d&31)<<21 | (a&31)<<11 2107} 2108 2109/* VA-form 4-register operands */ 2110func AOP_RRRR(op uint32, d uint32, a uint32, b uint32, c uint32) uint32 { 2111 return op | (d&31)<<21 | (a&31)<<16 | (b&31)<<11 | (c&31)<<6 2112} 2113 2114func AOP_IRR(op uint32, d uint32, a uint32, simm uint32) uint32 { 2115 return op | (d&31)<<21 | (a&31)<<16 | simm&0xFFFF 2116} 2117 2118/* VX-form 2-register + UIM operands */ 2119func AOP_VIRR(op uint32, d uint32, a uint32, simm uint32) uint32 { 2120 return op | (d&31)<<21 | (simm&0xFFFF)<<16 | (a&31)<<11 2121} 2122 2123/* VX-form 2-register + ST + SIX operands */ 2124func AOP_IIRR(op uint32, d uint32, a uint32, sbit uint32, simm uint32) uint32 { 2125 return op | (d&31)<<21 | (a&31)<<16 | (sbit&1)<<15 | (simm&0xF)<<11 2126} 2127 2128/* VA-form 3-register + SHB operands */ 2129func AOP_IRRR(op uint32, d uint32, a uint32, b uint32, simm uint32) uint32 { 2130 return op | (d&31)<<21 | (a&31)<<16 | (b&31)<<11 | (simm&0xF)<<6 2131} 2132 2133/* VX-form 1-register + SIM operands */ 2134func AOP_IR(op uint32, d uint32, simm uint32) uint32 { 2135 return op | (d&31)<<21 | (simm&31)<<16 2136} 2137 2138/* XX1-form 3-register operands, 1 VSR operand */ 2139func AOP_XX1(op uint32, r uint32, a uint32, b uint32) uint32 { 2140 return op | (r&31)<<21 | (a&31)<<16 | (b&31)<<11 | (r&32)>>5 2141} 2142 2143/* XX2-form 3-register operands, 2 VSR operands */ 2144func AOP_XX2(op uint32, xt uint32, a uint32, xb uint32) uint32 { 2145 return op | (xt&31)<<21 | (a&3)<<16 | (xb&31)<<11 | (xb&32)>>4 | (xt&32)>>5 2146} 2147 2148/* XX3-form 3 VSR operands */ 2149func AOP_XX3(op uint32, xt uint32, xa uint32, xb uint32) uint32 { 2150 return op | (xt&31)<<21 | (xa&31)<<16 | (xb&31)<<11 | (xa&32)>>3 | (xb&32)>>4 | (xt&32)>>5 2151} 2152 2153/* XX3-form 3 VSR operands + immediate */ 2154func AOP_XX3I(op uint32, xt uint32, xa uint32, xb uint32, c uint32) uint32 { 2155 return op | (xt&31)<<21 | (xa&31)<<16 | (xb&31)<<11 | (c&3)<<8 | (xa&32)>>3 | (xb&32)>>4 | (xt&32)>>5 2156} 2157 2158/* XX4-form, 4 VSR operands */ 2159func AOP_XX4(op uint32, xt uint32, xa uint32, xb uint32, xc uint32) uint32 { 2160 return op | (xt&31)<<21 | (xa&31)<<16 | (xb&31)<<11 | (xc&31)<<6 | (xc&32)>>2 | (xa&32)>>3 | (xb&32)>>4 | (xt&32)>>5 2161} 2162 2163/* DQ-form, VSR register, register + offset operands */ 2164func AOP_DQ(op uint32, xt uint32, a uint32, b uint32) uint32 { 2165 /* The EA for this instruction form is (RA) + DQ << 4, where DQ is a 12-bit signed integer. */ 2166 /* In order to match the output of the GNU objdump (and make the usage in Go asm easier), the */ 2167 /* instruction is called using the sign extended value (i.e. a valid offset would be -32752 or 32752, */ 2168 /* not -2047 or 2047), so 'b' needs to be adjusted to the expected 12-bit DQ value. Bear in mind that */ 2169 /* bits 0 to 3 in 'dq' need to be zero, otherwise this will generate an illegal instruction. */ 2170 /* If in doubt how this instruction form is encoded, refer to ISA 3.0b, pages 492 and 507. */ 2171 dq := b >> 4 2172 return op | (xt&31)<<21 | (a&31)<<16 | (dq&4095)<<4 | (xt&32)>>2 2173} 2174 2175/* Z23-form, 3-register operands + CY field */ 2176func AOP_Z23I(op uint32, d uint32, a uint32, b uint32, c uint32) uint32 { 2177 return op | (d&31)<<21 | (a&31)<<16 | (b&31)<<11 | (c&3)<<9 2178} 2179 2180/* X-form, 3-register operands + EH field */ 2181func AOP_RRRI(op uint32, d uint32, a uint32, b uint32, c uint32) uint32 { 2182 return op | (d&31)<<21 | (a&31)<<16 | (b&31)<<11 | (c & 1) 2183} 2184 2185func LOP_RRR(op uint32, a uint32, s uint32, b uint32) uint32 { 2186 return op | (s&31)<<21 | (a&31)<<16 | (b&31)<<11 2187} 2188 2189func LOP_IRR(op uint32, a uint32, s uint32, uimm uint32) uint32 { 2190 return op | (s&31)<<21 | (a&31)<<16 | uimm&0xFFFF 2191} 2192 2193func OP_BR(op uint32, li uint32, aa uint32) uint32 { 2194 return op | li&0x03FFFFFC | aa<<1 2195} 2196 2197func OP_BC(op uint32, bo uint32, bi uint32, bd uint32, aa uint32) uint32 { 2198 return op | (bo&0x1F)<<21 | (bi&0x1F)<<16 | bd&0xFFFC | aa<<1 2199} 2200 2201func OP_BCR(op uint32, bo uint32, bi uint32) uint32 { 2202 return op | (bo&0x1F)<<21 | (bi&0x1F)<<16 2203} 2204 2205func OP_RLW(op uint32, a uint32, s uint32, sh uint32, mb uint32, me uint32) uint32 { 2206 return op | (s&31)<<21 | (a&31)<<16 | (sh&31)<<11 | (mb&31)<<6 | (me&31)<<1 2207} 2208 2209func AOP_RLDIC(op uint32, a uint32, s uint32, sh uint32, m uint32) uint32 { 2210 return op | (s&31)<<21 | (a&31)<<16 | (sh&31)<<11 | ((sh&32)>>5)<<1 | (m&31)<<6 | ((m&32)>>5)<<5 2211} 2212 2213func AOP_EXTSWSLI(op uint32, a uint32, s uint32, sh uint32) uint32 { 2214 return op | (a&31)<<21 | (s&31)<<16 | (sh&31)<<11 | ((sh&32)>>5)<<1 2215} 2216 2217func AOP_ISEL(op uint32, t uint32, a uint32, b uint32, bc uint32) uint32 { 2218 return op | (t&31)<<21 | (a&31)<<16 | (b&31)<<11 | (bc&0x1F)<<6 2219} 2220 2221const ( 2222 /* each rhs is OPVCC(_, _, _, _) */ 2223 OP_ADD = 31<<26 | 266<<1 | 0<<10 | 0 2224 OP_ADDI = 14<<26 | 0<<1 | 0<<10 | 0 2225 OP_ADDIS = 15<<26 | 0<<1 | 0<<10 | 0 2226 OP_ANDI = 28<<26 | 0<<1 | 0<<10 | 0 2227 OP_EXTSB = 31<<26 | 954<<1 | 0<<10 | 0 2228 OP_EXTSH = 31<<26 | 922<<1 | 0<<10 | 0 2229 OP_EXTSW = 31<<26 | 986<<1 | 0<<10 | 0 2230 OP_ISEL = 31<<26 | 15<<1 | 0<<10 | 0 2231 OP_MCRF = 19<<26 | 0<<1 | 0<<10 | 0 2232 OP_MCRFS = 63<<26 | 64<<1 | 0<<10 | 0 2233 OP_MCRXR = 31<<26 | 512<<1 | 0<<10 | 0 2234 OP_MFCR = 31<<26 | 19<<1 | 0<<10 | 0 2235 OP_MFFS = 63<<26 | 583<<1 | 0<<10 | 0 2236 OP_MFSPR = 31<<26 | 339<<1 | 0<<10 | 0 2237 OP_MFSR = 31<<26 | 595<<1 | 0<<10 | 0 2238 OP_MFSRIN = 31<<26 | 659<<1 | 0<<10 | 0 2239 OP_MTCRF = 31<<26 | 144<<1 | 0<<10 | 0 2240 OP_MTFSF = 63<<26 | 711<<1 | 0<<10 | 0 2241 OP_MTFSFI = 63<<26 | 134<<1 | 0<<10 | 0 2242 OP_MTSPR = 31<<26 | 467<<1 | 0<<10 | 0 2243 OP_MTSR = 31<<26 | 210<<1 | 0<<10 | 0 2244 OP_MTSRIN = 31<<26 | 242<<1 | 0<<10 | 0 2245 OP_MULLW = 31<<26 | 235<<1 | 0<<10 | 0 2246 OP_MULLD = 31<<26 | 233<<1 | 0<<10 | 0 2247 OP_OR = 31<<26 | 444<<1 | 0<<10 | 0 2248 OP_ORI = 24<<26 | 0<<1 | 0<<10 | 0 2249 OP_ORIS = 25<<26 | 0<<1 | 0<<10 | 0 2250 OP_RLWINM = 21<<26 | 0<<1 | 0<<10 | 0 2251 OP_RLWNM = 23<<26 | 0<<1 | 0<<10 | 0 2252 OP_SUBF = 31<<26 | 40<<1 | 0<<10 | 0 2253 OP_RLDIC = 30<<26 | 4<<1 | 0<<10 | 0 2254 OP_RLDICR = 30<<26 | 2<<1 | 0<<10 | 0 2255 OP_RLDICL = 30<<26 | 0<<1 | 0<<10 | 0 2256 OP_RLDCL = 30<<26 | 8<<1 | 0<<10 | 0 2257 OP_EXTSWSLI = 31<<26 | 445<<2 2258) 2259 2260func oclass(a *obj.Addr) int { 2261 return int(a.Class) - 1 2262} 2263 2264const ( 2265 D_FORM = iota 2266 DS_FORM 2267) 2268 2269// This function determines when a non-indexed load or store is D or 2270// DS form for use in finding the size of the offset field in the instruction. 2271// The size is needed when setting the offset value in the instruction 2272// and when generating relocation for that field. 2273// DS form instructions include: ld, ldu, lwa, std, stdu. All other 2274// loads and stores with an offset field are D form. This function should 2275// only be called with the same opcodes as are handled by opstore and opload. 2276func (c *ctxt9) opform(insn uint32) int { 2277 switch insn { 2278 default: 2279 c.ctxt.Diag("bad insn in loadform: %x", insn) 2280 case OPVCC(58, 0, 0, 0), // ld 2281 OPVCC(58, 0, 0, 1), // ldu 2282 OPVCC(58, 0, 0, 0) | 1<<1, // lwa 2283 OPVCC(62, 0, 0, 0), // std 2284 OPVCC(62, 0, 0, 1): //stdu 2285 return DS_FORM 2286 case OP_ADDI, // add 2287 OPVCC(32, 0, 0, 0), // lwz 2288 OPVCC(33, 0, 0, 0), // lwzu 2289 OPVCC(34, 0, 0, 0), // lbz 2290 OPVCC(35, 0, 0, 0), // lbzu 2291 OPVCC(40, 0, 0, 0), // lhz 2292 OPVCC(41, 0, 0, 0), // lhzu 2293 OPVCC(42, 0, 0, 0), // lha 2294 OPVCC(43, 0, 0, 0), // lhau 2295 OPVCC(46, 0, 0, 0), // lmw 2296 OPVCC(48, 0, 0, 0), // lfs 2297 OPVCC(49, 0, 0, 0), // lfsu 2298 OPVCC(50, 0, 0, 0), // lfd 2299 OPVCC(51, 0, 0, 0), // lfdu 2300 OPVCC(36, 0, 0, 0), // stw 2301 OPVCC(37, 0, 0, 0), // stwu 2302 OPVCC(38, 0, 0, 0), // stb 2303 OPVCC(39, 0, 0, 0), // stbu 2304 OPVCC(44, 0, 0, 0), // sth 2305 OPVCC(45, 0, 0, 0), // sthu 2306 OPVCC(47, 0, 0, 0), // stmw 2307 OPVCC(52, 0, 0, 0), // stfs 2308 OPVCC(53, 0, 0, 0), // stfsu 2309 OPVCC(54, 0, 0, 0), // stfd 2310 OPVCC(55, 0, 0, 0): // stfdu 2311 return D_FORM 2312 } 2313 return 0 2314} 2315 2316// Encode instructions and create relocation for accessing s+d according to the 2317// instruction op with source or destination (as appropriate) register reg. 2318func (c *ctxt9) symbolAccess(s *obj.LSym, d int64, reg int16, op uint32, reuse bool) (o1, o2 uint32) { 2319 if c.ctxt.Headtype == objabi.Haix { 2320 // Every symbol access must be made via a TOC anchor. 2321 c.ctxt.Diag("symbolAccess called for %s", s.Name) 2322 } 2323 var base uint32 2324 form := c.opform(op) 2325 if c.ctxt.Flag_shared { 2326 base = REG_R2 2327 } else { 2328 base = REG_R0 2329 } 2330 // If reg can be reused when computing the symbol address, 2331 // use it instead of REGTMP. 2332 if !reuse { 2333 o1 = AOP_IRR(OP_ADDIS, REGTMP, base, 0) 2334 o2 = AOP_IRR(op, uint32(reg), REGTMP, 0) 2335 } else { 2336 o1 = AOP_IRR(OP_ADDIS, uint32(reg), base, 0) 2337 o2 = AOP_IRR(op, uint32(reg), uint32(reg), 0) 2338 } 2339 rel := obj.Addrel(c.cursym) 2340 rel.Off = int32(c.pc) 2341 rel.Siz = 8 2342 rel.Sym = s 2343 rel.Add = d 2344 if c.ctxt.Flag_shared { 2345 switch form { 2346 case D_FORM: 2347 rel.Type = objabi.R_ADDRPOWER_TOCREL 2348 case DS_FORM: 2349 rel.Type = objabi.R_ADDRPOWER_TOCREL_DS 2350 } 2351 2352 } else { 2353 switch form { 2354 case D_FORM: 2355 rel.Type = objabi.R_ADDRPOWER 2356 case DS_FORM: 2357 rel.Type = objabi.R_ADDRPOWER_DS 2358 } 2359 } 2360 return 2361} 2362 2363/* 2364 * 32-bit masks 2365 */ 2366func getmask(m []byte, v uint32) bool { 2367 m[1] = 0 2368 m[0] = m[1] 2369 if v != ^uint32(0) && v&(1<<31) != 0 && v&1 != 0 { /* MB > ME */ 2370 if getmask(m, ^v) { 2371 i := int(m[0]) 2372 m[0] = m[1] + 1 2373 m[1] = byte(i - 1) 2374 return true 2375 } 2376 2377 return false 2378 } 2379 2380 for i := 0; i < 32; i++ { 2381 if v&(1<<uint(31-i)) != 0 { 2382 m[0] = byte(i) 2383 for { 2384 m[1] = byte(i) 2385 i++ 2386 if i >= 32 || v&(1<<uint(31-i)) == 0 { 2387 break 2388 } 2389 } 2390 2391 for ; i < 32; i++ { 2392 if v&(1<<uint(31-i)) != 0 { 2393 return false 2394 } 2395 } 2396 return true 2397 } 2398 } 2399 2400 return false 2401} 2402 2403func (c *ctxt9) maskgen(p *obj.Prog, m []byte, v uint32) { 2404 if !getmask(m, v) { 2405 c.ctxt.Diag("cannot generate mask #%x\n%v", v, p) 2406 } 2407} 2408 2409/* 2410 * 64-bit masks (rldic etc) 2411 */ 2412func getmask64(m []byte, v uint64) bool { 2413 m[1] = 0 2414 m[0] = m[1] 2415 for i := 0; i < 64; i++ { 2416 if v&(uint64(1)<<uint(63-i)) != 0 { 2417 m[0] = byte(i) 2418 for { 2419 m[1] = byte(i) 2420 i++ 2421 if i >= 64 || v&(uint64(1)<<uint(63-i)) == 0 { 2422 break 2423 } 2424 } 2425 2426 for ; i < 64; i++ { 2427 if v&(uint64(1)<<uint(63-i)) != 0 { 2428 return false 2429 } 2430 } 2431 return true 2432 } 2433 } 2434 2435 return false 2436} 2437 2438func (c *ctxt9) maskgen64(p *obj.Prog, m []byte, v uint64) { 2439 if !getmask64(m, v) { 2440 c.ctxt.Diag("cannot generate mask #%x\n%v", v, p) 2441 } 2442} 2443 2444func loadu32(r int, d int64) uint32 { 2445 v := int32(d >> 16) 2446 if isuint32(uint64(d)) { 2447 return LOP_IRR(OP_ORIS, uint32(r), REGZERO, uint32(v)) 2448 } 2449 return AOP_IRR(OP_ADDIS, uint32(r), REGZERO, uint32(v)) 2450} 2451 2452func high16adjusted(d int32) uint16 { 2453 if d&0x8000 != 0 { 2454 return uint16((d >> 16) + 1) 2455 } 2456 return uint16(d >> 16) 2457} 2458 2459func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) { 2460 o1 := uint32(0) 2461 o2 := uint32(0) 2462 o3 := uint32(0) 2463 o4 := uint32(0) 2464 o5 := uint32(0) 2465 2466 //print("%v => case %d\n", p, o->type); 2467 switch o.type_ { 2468 default: 2469 c.ctxt.Diag("unknown type %d", o.type_) 2470 prasm(p) 2471 2472 case 0: /* pseudo ops */ 2473 break 2474 2475 case 2: /* int/cr/fp op Rb,[Ra],Rd */ 2476 r := int(p.Reg) 2477 2478 if r == 0 { 2479 r = int(p.To.Reg) 2480 } 2481 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(p.From.Reg)) 2482 2483 case 3: /* mov $soreg/addcon/andcon/ucon, r ==> addis/oris/addi/ori $i,reg',r */ 2484 d := c.vregoff(&p.From) 2485 2486 v := int32(d) 2487 r := int(p.From.Reg) 2488 if r == 0 { 2489 r = c.getimpliedreg(&p.From, p) 2490 } 2491 if r0iszero != 0 /*TypeKind(100016)*/ && p.To.Reg == 0 && (r != 0 || v != 0) { 2492 c.ctxt.Diag("literal operation on R0\n%v", p) 2493 } 2494 a := OP_ADDI 2495 if o.a1 == C_UCON { 2496 if d&0xffff != 0 { 2497 log.Fatalf("invalid handling of %v", p) 2498 } 2499 // For UCON operands the value is right shifted 16, using ADDIS if the 2500 // value should be signed, ORIS if unsigned. 2501 v >>= 16 2502 if r == REGZERO && isuint32(uint64(d)) { 2503 o1 = LOP_IRR(OP_ORIS, uint32(p.To.Reg), REGZERO, uint32(v)) 2504 break 2505 } 2506 2507 a = OP_ADDIS 2508 } else if int64(int16(d)) != d { 2509 // Operand is 16 bit value with sign bit set 2510 if o.a1 == C_ANDCON { 2511 // Needs unsigned 16 bit so use ORI 2512 if r == 0 || r == REGZERO { 2513 o1 = LOP_IRR(uint32(OP_ORI), uint32(p.To.Reg), uint32(0), uint32(v)) 2514 break 2515 } 2516 // With ADDCON, needs signed 16 bit value, fall through to use ADDI 2517 } else if o.a1 != C_ADDCON { 2518 log.Fatalf("invalid handling of %v", p) 2519 } 2520 } 2521 2522 o1 = AOP_IRR(uint32(a), uint32(p.To.Reg), uint32(r), uint32(v)) 2523 2524 case 4: /* add/mul $scon,[r1],r2 */ 2525 v := c.regoff(&p.From) 2526 2527 r := int(p.Reg) 2528 if r == 0 { 2529 r = int(p.To.Reg) 2530 } 2531 if r0iszero != 0 /*TypeKind(100016)*/ && p.To.Reg == 0 { 2532 c.ctxt.Diag("literal operation on R0\n%v", p) 2533 } 2534 if int32(int16(v)) != v { 2535 log.Fatalf("mishandled instruction %v", p) 2536 } 2537 o1 = AOP_IRR(c.opirr(p.As), uint32(p.To.Reg), uint32(r), uint32(v)) 2538 2539 case 5: /* syscall */ 2540 o1 = c.oprrr(p.As) 2541 2542 case 6: /* logical op Rb,[Rs,]Ra; no literal */ 2543 r := int(p.Reg) 2544 2545 if r == 0 { 2546 r = int(p.To.Reg) 2547 } 2548 // AROTL and AROTLW are extended mnemonics, which map to RLDCL and RLWNM. 2549 switch p.As { 2550 case AROTL: 2551 o1 = AOP_RLDIC(OP_RLDCL, uint32(p.To.Reg), uint32(r), uint32(p.From.Reg), uint32(0)) 2552 case AROTLW: 2553 o1 = OP_RLW(OP_RLWNM, uint32(p.To.Reg), uint32(r), uint32(p.From.Reg), 0, 31) 2554 default: 2555 o1 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(p.From.Reg)) 2556 } 2557 2558 case 7: /* mov r, soreg ==> stw o(r) */ 2559 r := int(p.To.Reg) 2560 2561 if r == 0 { 2562 r = c.getimpliedreg(&p.To, p) 2563 } 2564 v := c.regoff(&p.To) 2565 if p.To.Type == obj.TYPE_MEM && p.To.Index != 0 { 2566 if v != 0 { 2567 c.ctxt.Diag("illegal indexed instruction\n%v", p) 2568 } 2569 o1 = AOP_RRR(c.opstorex(p.As), uint32(p.From.Reg), uint32(p.To.Index), uint32(r)) 2570 } else { 2571 if int32(int16(v)) != v { 2572 log.Fatalf("mishandled instruction %v", p) 2573 } 2574 // Offsets in DS form stores must be a multiple of 4 2575 inst := c.opstore(p.As) 2576 if c.opform(inst) == DS_FORM && v&0x3 != 0 { 2577 log.Fatalf("invalid offset for DS form load/store %v", p) 2578 } 2579 o1 = AOP_IRR(inst, uint32(p.From.Reg), uint32(r), uint32(v)) 2580 } 2581 2582 case 8: /* mov soreg, r ==> lbz/lhz/lwz o(r), lbz o(r) + extsb r,r */ 2583 r := int(p.From.Reg) 2584 2585 if r == 0 { 2586 r = c.getimpliedreg(&p.From, p) 2587 } 2588 v := c.regoff(&p.From) 2589 if p.From.Type == obj.TYPE_MEM && p.From.Index != 0 { 2590 if v != 0 { 2591 c.ctxt.Diag("illegal indexed instruction\n%v", p) 2592 } 2593 o1 = AOP_RRR(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(r)) 2594 } else { 2595 if int32(int16(v)) != v { 2596 log.Fatalf("mishandled instruction %v", p) 2597 } 2598 // Offsets in DS form loads must be a multiple of 4 2599 inst := c.opload(p.As) 2600 if c.opform(inst) == DS_FORM && v&0x3 != 0 { 2601 log.Fatalf("invalid offset for DS form load/store %v", p) 2602 } 2603 o1 = AOP_IRR(inst, uint32(p.To.Reg), uint32(r), uint32(v)) 2604 } 2605 2606 // Sign extend MOVB operations. This is ignored for other cases (o.size == 4). 2607 o2 = LOP_RRR(OP_EXTSB, uint32(p.To.Reg), uint32(p.To.Reg), 0) 2608 2609 case 10: /* sub Ra,[Rb],Rd => subf Rd,Ra,Rb */ 2610 r := int(p.Reg) 2611 2612 if r == 0 { 2613 r = int(p.To.Reg) 2614 } 2615 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(r)) 2616 2617 case 11: /* br/bl lbra */ 2618 v := int32(0) 2619 2620 if p.To.Target() != nil { 2621 v = int32(p.To.Target().Pc - p.Pc) 2622 if v&03 != 0 { 2623 c.ctxt.Diag("odd branch target address\n%v", p) 2624 v &^= 03 2625 } 2626 2627 if v < -(1<<25) || v >= 1<<24 { 2628 c.ctxt.Diag("branch too far\n%v", p) 2629 } 2630 } 2631 2632 o1 = OP_BR(c.opirr(p.As), uint32(v), 0) 2633 if p.To.Sym != nil { 2634 rel := obj.Addrel(c.cursym) 2635 rel.Off = int32(c.pc) 2636 rel.Siz = 4 2637 rel.Sym = p.To.Sym 2638 v += int32(p.To.Offset) 2639 if v&03 != 0 { 2640 c.ctxt.Diag("odd branch target address\n%v", p) 2641 v &^= 03 2642 } 2643 2644 rel.Add = int64(v) 2645 rel.Type = objabi.R_CALLPOWER 2646 } 2647 o2 = 0x60000000 // nop, sometimes overwritten by ld r2, 24(r1) when dynamic linking 2648 2649 case 13: /* mov[bhwd]{z,} r,r */ 2650 // This needs to handle "MOV* $0, Rx". This shows up because $0 also 2651 // matches C_REG if r0iszero. This happens because C_REG sorts before C_ANDCON 2652 // TODO: fix the above behavior and cleanup this exception. 2653 if p.From.Type == obj.TYPE_CONST { 2654 o1 = LOP_IRR(OP_ADDI, REGZERO, uint32(p.To.Reg), 0) 2655 break 2656 } 2657 if p.To.Type == obj.TYPE_CONST { 2658 c.ctxt.Diag("cannot move into constant 0\n%v", p) 2659 } 2660 2661 switch p.As { 2662 case AMOVB: 2663 o1 = LOP_RRR(OP_EXTSB, uint32(p.To.Reg), uint32(p.From.Reg), 0) 2664 case AMOVBZ: 2665 o1 = OP_RLW(OP_RLWINM, uint32(p.To.Reg), uint32(p.From.Reg), 0, 24, 31) 2666 case AMOVH: 2667 o1 = LOP_RRR(OP_EXTSH, uint32(p.To.Reg), uint32(p.From.Reg), 0) 2668 case AMOVHZ: 2669 o1 = OP_RLW(OP_RLWINM, uint32(p.To.Reg), uint32(p.From.Reg), 0, 16, 31) 2670 case AMOVW: 2671 o1 = LOP_RRR(OP_EXTSW, uint32(p.To.Reg), uint32(p.From.Reg), 0) 2672 case AMOVWZ: 2673 o1 = OP_RLW(OP_RLDIC, uint32(p.To.Reg), uint32(p.From.Reg), 0, 0, 0) | 1<<5 /* MB=32 */ 2674 case AMOVD: 2675 o1 = LOP_RRR(OP_OR, uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.From.Reg)) 2676 default: 2677 c.ctxt.Diag("internal: bad register move/truncation\n%v", p) 2678 } 2679 2680 case 14: /* rldc[lr] Rb,Rs,$mask,Ra -- left, right give different masks */ 2681 r := int(p.Reg) 2682 2683 if r == 0 { 2684 r = int(p.To.Reg) 2685 } 2686 d := c.vregoff(p.GetFrom3()) 2687 var a int 2688 switch p.As { 2689 2690 // These opcodes expect a mask operand that has to be converted into the 2691 // appropriate operand. The way these were defined, not all valid masks are possible. 2692 // Left here for compatibility in case they were used or generated. 2693 case ARLDCL, ARLDCLCC: 2694 var mask [2]uint8 2695 c.maskgen64(p, mask[:], uint64(d)) 2696 2697 a = int(mask[0]) /* MB */ 2698 if mask[1] != 63 { 2699 c.ctxt.Diag("invalid mask for rotate: %x (end != bit 63)\n%v", uint64(d), p) 2700 } 2701 o1 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(p.From.Reg)) 2702 o1 |= (uint32(a) & 31) << 6 2703 if a&0x20 != 0 { 2704 o1 |= 1 << 5 /* mb[5] is top bit */ 2705 } 2706 2707 case ARLDCR, ARLDCRCC: 2708 var mask [2]uint8 2709 c.maskgen64(p, mask[:], uint64(d)) 2710 2711 a = int(mask[1]) /* ME */ 2712 if mask[0] != 0 { 2713 c.ctxt.Diag("invalid mask for rotate: %x %x (start != 0)\n%v", uint64(d), mask[0], p) 2714 } 2715 o1 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(p.From.Reg)) 2716 o1 |= (uint32(a) & 31) << 6 2717 if a&0x20 != 0 { 2718 o1 |= 1 << 5 /* mb[5] is top bit */ 2719 } 2720 2721 // These opcodes use a shift count like the ppc64 asm, no mask conversion done 2722 case ARLDICR, ARLDICRCC: 2723 me := int(d) 2724 sh := c.regoff(&p.From) 2725 if me < 0 || me > 63 || sh > 63 { 2726 c.ctxt.Diag("Invalid me or sh for RLDICR: %x %x\n%v", int(d), sh, p) 2727 } 2728 o1 = AOP_RLDIC(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(sh), uint32(me)) 2729 2730 case ARLDICL, ARLDICLCC, ARLDIC, ARLDICCC: 2731 mb := int(d) 2732 sh := c.regoff(&p.From) 2733 if mb < 0 || mb > 63 || sh > 63 { 2734 c.ctxt.Diag("Invalid mb or sh for RLDIC, RLDICL: %x %x\n%v", mb, sh, p) 2735 } 2736 o1 = AOP_RLDIC(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), uint32(sh), uint32(mb)) 2737 2738 case ACLRLSLDI: 2739 // This is an extended mnemonic defined in the ISA section C.8.1 2740 // clrlsldi ra,rs,b,n --> rldic ra,rs,n,b-n 2741 // It maps onto RLDIC so is directly generated here based on the operands from 2742 // the clrlsldi. 2743 n := int32(d) 2744 b := c.regoff(&p.From) 2745 if n > b || b > 63 { 2746 c.ctxt.Diag("Invalid n or b for CLRLSLDI: %x %x\n%v", n, b, p) 2747 } 2748 o1 = AOP_RLDIC(OP_RLDIC, uint32(p.To.Reg), uint32(r), uint32(n), uint32(b)-uint32(n)) 2749 2750 default: 2751 c.ctxt.Diag("unexpected op in rldc case\n%v", p) 2752 a = 0 2753 } 2754 2755 case 17, /* bc bo,bi,lbra (same for now) */ 2756 16: /* bc bo,bi,sbra */ 2757 a := 0 2758 2759 r := int(p.Reg) 2760 2761 if p.From.Type == obj.TYPE_CONST { 2762 a = int(c.regoff(&p.From)) 2763 } else if p.From.Type == obj.TYPE_REG { 2764 if r != 0 { 2765 c.ctxt.Diag("unexpected register setting for branch with CR: %d\n", r) 2766 } 2767 // BI values for the CR 2768 switch p.From.Reg { 2769 case REG_CR0: 2770 r = BI_CR0 2771 case REG_CR1: 2772 r = BI_CR1 2773 case REG_CR2: 2774 r = BI_CR2 2775 case REG_CR3: 2776 r = BI_CR3 2777 case REG_CR4: 2778 r = BI_CR4 2779 case REG_CR5: 2780 r = BI_CR5 2781 case REG_CR6: 2782 r = BI_CR6 2783 case REG_CR7: 2784 r = BI_CR7 2785 default: 2786 c.ctxt.Diag("unrecognized register: expecting CR\n") 2787 } 2788 } 2789 v := int32(0) 2790 if p.To.Target() != nil { 2791 v = int32(p.To.Target().Pc - p.Pc) 2792 } 2793 if v&03 != 0 { 2794 c.ctxt.Diag("odd branch target address\n%v", p) 2795 v &^= 03 2796 } 2797 2798 if v < -(1<<16) || v >= 1<<15 { 2799 c.ctxt.Diag("branch too far\n%v", p) 2800 } 2801 o1 = OP_BC(c.opirr(p.As), uint32(a), uint32(r), uint32(v), 0) 2802 2803 case 15: /* br/bl (r) => mov r,lr; br/bl (lr) */ 2804 var v int32 2805 if p.As == ABC || p.As == ABCL { 2806 v = c.regoff(&p.To) & 31 2807 } else { 2808 v = 20 /* unconditional */ 2809 } 2810 o1 = AOP_RRR(OP_MTSPR, uint32(p.To.Reg), 0, 0) | (REG_LR&0x1f)<<16 | ((REG_LR>>5)&0x1f)<<11 2811 o2 = OPVCC(19, 16, 0, 0) 2812 if p.As == ABL || p.As == ABCL { 2813 o2 |= 1 2814 } 2815 o2 = OP_BCR(o2, uint32(v), uint32(p.To.Index)) 2816 2817 case 18: /* br/bl (lr/ctr); bc/bcl bo,bi,(lr/ctr) */ 2818 var v int32 2819 var bh uint32 = 0 2820 if p.As == ABC || p.As == ABCL { 2821 v = c.regoff(&p.From) & 31 2822 } else { 2823 v = 20 /* unconditional */ 2824 } 2825 r := int(p.Reg) 2826 if r == 0 { 2827 r = 0 2828 } 2829 switch oclass(&p.To) { 2830 case C_CTR: 2831 o1 = OPVCC(19, 528, 0, 0) 2832 2833 case C_LR: 2834 o1 = OPVCC(19, 16, 0, 0) 2835 2836 default: 2837 c.ctxt.Diag("bad optab entry (18): %d\n%v", p.To.Class, p) 2838 v = 0 2839 } 2840 2841 // Insert optional branch hint for bclr[l]/bcctr[l] 2842 if p.From3Type() != obj.TYPE_NONE { 2843 bh = uint32(p.GetFrom3().Offset) 2844 if bh == 2 || bh > 3 { 2845 log.Fatalf("BH must be 0,1,3 for %v", p) 2846 } 2847 o1 |= bh << 11 2848 } 2849 2850 if p.As == ABL || p.As == ABCL { 2851 o1 |= 1 2852 } 2853 o1 = OP_BCR(o1, uint32(v), uint32(r)) 2854 2855 case 19: /* mov $lcon,r ==> cau+or */ 2856 d := c.vregoff(&p.From) 2857 o1 = loadu32(int(p.To.Reg), d) 2858 o2 = LOP_IRR(OP_ORI, uint32(p.To.Reg), uint32(p.To.Reg), uint32(int32(d))) 2859 2860 case 20: /* add $ucon,,r | addis $addcon,r,r */ 2861 v := c.regoff(&p.From) 2862 2863 r := int(p.Reg) 2864 if r == 0 { 2865 r = int(p.To.Reg) 2866 } 2867 if p.As == AADD && (r0iszero == 0 /*TypeKind(100016)*/ && p.Reg == 0 || r0iszero != 0 /*TypeKind(100016)*/ && p.To.Reg == 0) { 2868 c.ctxt.Diag("literal operation on R0\n%v", p) 2869 } 2870 if p.As == AADDIS { 2871 o1 = AOP_IRR(c.opirr(p.As), uint32(p.To.Reg), uint32(r), uint32(v)) 2872 } else { 2873 o1 = AOP_IRR(c.opirr(AADDIS), uint32(p.To.Reg), uint32(r), uint32(v)>>16) 2874 } 2875 2876 case 22: /* add $lcon/$andcon,r1,r2 ==> oris+ori+add/ori+add */ 2877 if p.To.Reg == REGTMP || p.Reg == REGTMP { 2878 c.ctxt.Diag("can't synthesize large constant\n%v", p) 2879 } 2880 d := c.vregoff(&p.From) 2881 r := int(p.Reg) 2882 if r == 0 { 2883 r = int(p.To.Reg) 2884 } 2885 if p.From.Sym != nil { 2886 c.ctxt.Diag("%v is not supported", p) 2887 } 2888 // If operand is ANDCON, generate 2 instructions using 2889 // ORI for unsigned value; with LCON 3 instructions. 2890 if o.size == 8 { 2891 o1 = LOP_IRR(OP_ORI, REGTMP, REGZERO, uint32(int32(d))) 2892 o2 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), REGTMP, uint32(r)) 2893 } else { 2894 o1 = loadu32(REGTMP, d) 2895 o2 = LOP_IRR(OP_ORI, REGTMP, REGTMP, uint32(int32(d))) 2896 o3 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), REGTMP, uint32(r)) 2897 } 2898 2899 case 23: /* and $lcon/$addcon,r1,r2 ==> oris+ori+and/addi+and */ 2900 if p.To.Reg == REGTMP || p.Reg == REGTMP { 2901 c.ctxt.Diag("can't synthesize large constant\n%v", p) 2902 } 2903 d := c.vregoff(&p.From) 2904 r := int(p.Reg) 2905 if r == 0 { 2906 r = int(p.To.Reg) 2907 } 2908 2909 // With ADDCON operand, generate 2 instructions using ADDI for signed value, 2910 // with LCON operand generate 3 instructions. 2911 if o.size == 8 { 2912 o1 = LOP_IRR(OP_ADDI, REGZERO, REGTMP, uint32(int32(d))) 2913 o2 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), REGTMP, uint32(r)) 2914 } else { 2915 o1 = loadu32(REGTMP, d) 2916 o2 = LOP_IRR(OP_ORI, REGTMP, REGTMP, uint32(int32(d))) 2917 o3 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), REGTMP, uint32(r)) 2918 } 2919 if p.From.Sym != nil { 2920 c.ctxt.Diag("%v is not supported", p) 2921 } 2922 2923 case 24: /* lfd fA,float64(0) -> xxlxor xsA,xsaA,xsaA + fneg for -0 */ 2924 o1 = AOP_XX3I(c.oprrr(AXXLXOR), uint32(p.To.Reg), uint32(p.To.Reg), uint32(p.To.Reg), uint32(0)) 2925 // This is needed for -0. 2926 if o.size == 8 { 2927 o2 = AOP_RRR(c.oprrr(AFNEG), uint32(p.To.Reg), 0, uint32(p.To.Reg)) 2928 } 2929 2930 case 25: 2931 /* sld[.] $sh,rS,rA -> rldicr[.] $sh,rS,mask(0,63-sh),rA; srd[.] -> rldicl */ 2932 v := c.regoff(&p.From) 2933 2934 if v < 0 { 2935 v = 0 2936 } else if v > 63 { 2937 v = 63 2938 } 2939 r := int(p.Reg) 2940 if r == 0 { 2941 r = int(p.To.Reg) 2942 } 2943 var a int 2944 op := uint32(0) 2945 switch p.As { 2946 case ASLD, ASLDCC: 2947 a = int(63 - v) 2948 op = OP_RLDICR 2949 2950 case ASRD, ASRDCC: 2951 a = int(v) 2952 v = 64 - v 2953 op = OP_RLDICL 2954 case AROTL: 2955 a = int(0) 2956 op = OP_RLDICL 2957 case AEXTSWSLI: 2958 a = int(v) 2959 default: 2960 c.ctxt.Diag("unexpected op in sldi case\n%v", p) 2961 a = 0 2962 o1 = 0 2963 } 2964 2965 if p.As == AEXTSWSLI || p.As == AEXTSWSLICC { 2966 o1 = AOP_EXTSWSLI(OP_EXTSWSLI, uint32(r), uint32(p.To.Reg), uint32(v)) 2967 2968 } else { 2969 o1 = AOP_RLDIC(op, uint32(p.To.Reg), uint32(r), uint32(v), uint32(a)) 2970 } 2971 if p.As == ASLDCC || p.As == ASRDCC || p.As == AEXTSWSLICC { 2972 o1 |= 1 // Set the condition code bit 2973 } 2974 2975 case 26: /* mov $lsext/auto/oreg,,r2 ==> addis+addi */ 2976 v := c.vregoff(&p.From) 2977 r := int(p.From.Reg) 2978 2979 switch p.From.Name { 2980 case obj.NAME_EXTERN, obj.NAME_STATIC: 2981 // Load a 32 bit constant, or relocation depending on if a symbol is attached 2982 o1, o2 = c.symbolAccess(p.From.Sym, v, p.To.Reg, OP_ADDI, true) 2983 default: 2984 if r == 0 { 2985 r = c.getimpliedreg(&p.From, p) 2986 } 2987 // Add a 32 bit offset to a register. 2988 o1 = AOP_IRR(OP_ADDIS, uint32(p.To.Reg), uint32(r), uint32(high16adjusted(int32(v)))) 2989 o2 = AOP_IRR(OP_ADDI, uint32(p.To.Reg), uint32(p.To.Reg), uint32(v)) 2990 } 2991 2992 case 27: /* subc ra,$simm,rd => subfic rd,ra,$simm */ 2993 v := c.regoff(p.GetFrom3()) 2994 2995 r := int(p.From.Reg) 2996 o1 = AOP_IRR(c.opirr(p.As), uint32(p.To.Reg), uint32(r), uint32(v)) 2997 2998 case 28: /* subc r1,$lcon,r2 ==> cau+or+subfc */ 2999 if p.To.Reg == REGTMP || p.From.Reg == REGTMP { 3000 c.ctxt.Diag("can't synthesize large constant\n%v", p) 3001 } 3002 v := c.regoff(p.GetFrom3()) 3003 o1 = AOP_IRR(OP_ADDIS, REGTMP, REGZERO, uint32(v)>>16) 3004 o2 = LOP_IRR(OP_ORI, REGTMP, REGTMP, uint32(v)) 3005 o3 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), REGTMP) 3006 if p.From.Sym != nil { 3007 c.ctxt.Diag("%v is not supported", p) 3008 } 3009 3010 case 29: /* rldic[lr]? $sh,s,$mask,a -- left, right, plain give different masks */ 3011 v := c.regoff(&p.From) 3012 3013 d := c.vregoff(p.GetFrom3()) 3014 var mask [2]uint8 3015 c.maskgen64(p, mask[:], uint64(d)) 3016 var a int 3017 switch p.As { 3018 case ARLDC, ARLDCCC: 3019 a = int(mask[0]) /* MB */ 3020 if int32(mask[1]) != (63 - v) { 3021 c.ctxt.Diag("invalid mask for shift: %x %x (shift %d)\n%v", uint64(d), mask[1], v, p) 3022 } 3023 3024 case ARLDCL, ARLDCLCC: 3025 a = int(mask[0]) /* MB */ 3026 if mask[1] != 63 { 3027 c.ctxt.Diag("invalid mask for shift: %x %s (shift %d)\n%v", uint64(d), mask[1], v, p) 3028 } 3029 3030 case ARLDCR, ARLDCRCC: 3031 a = int(mask[1]) /* ME */ 3032 if mask[0] != 0 { 3033 c.ctxt.Diag("invalid mask for shift: %x %x (shift %d)\n%v", uint64(d), mask[0], v, p) 3034 } 3035 3036 default: 3037 c.ctxt.Diag("unexpected op in rldic case\n%v", p) 3038 a = 0 3039 } 3040 3041 o1 = AOP_RRR(c.opirr(p.As), uint32(p.Reg), uint32(p.To.Reg), (uint32(v) & 0x1F)) 3042 o1 |= (uint32(a) & 31) << 6 3043 if v&0x20 != 0 { 3044 o1 |= 1 << 1 3045 } 3046 if a&0x20 != 0 { 3047 o1 |= 1 << 5 /* mb[5] is top bit */ 3048 } 3049 3050 case 30: /* rldimi $sh,s,$mask,a */ 3051 v := c.regoff(&p.From) 3052 3053 d := c.vregoff(p.GetFrom3()) 3054 3055 // Original opcodes had mask operands which had to be converted to a shift count as expected by 3056 // the ppc64 asm. 3057 switch p.As { 3058 case ARLDMI, ARLDMICC: 3059 var mask [2]uint8 3060 c.maskgen64(p, mask[:], uint64(d)) 3061 if int32(mask[1]) != (63 - v) { 3062 c.ctxt.Diag("invalid mask for shift: %x %x (shift %d)\n%v", uint64(d), mask[1], v, p) 3063 } 3064 o1 = AOP_RRR(c.opirr(p.As), uint32(p.Reg), uint32(p.To.Reg), (uint32(v) & 0x1F)) 3065 o1 |= (uint32(mask[0]) & 31) << 6 3066 if v&0x20 != 0 { 3067 o1 |= 1 << 1 3068 } 3069 if mask[0]&0x20 != 0 { 3070 o1 |= 1 << 5 /* mb[5] is top bit */ 3071 } 3072 3073 // Opcodes with shift count operands. 3074 case ARLDIMI, ARLDIMICC: 3075 o1 = AOP_RRR(c.opirr(p.As), uint32(p.Reg), uint32(p.To.Reg), (uint32(v) & 0x1F)) 3076 o1 |= (uint32(d) & 31) << 6 3077 if d&0x20 != 0 { 3078 o1 |= 1 << 5 3079 } 3080 if v&0x20 != 0 { 3081 o1 |= 1 << 1 3082 } 3083 } 3084 3085 case 31: /* dword */ 3086 d := c.vregoff(&p.From) 3087 3088 if c.ctxt.Arch.ByteOrder == binary.BigEndian { 3089 o1 = uint32(d >> 32) 3090 o2 = uint32(d) 3091 } else { 3092 o1 = uint32(d) 3093 o2 = uint32(d >> 32) 3094 } 3095 3096 if p.From.Sym != nil { 3097 rel := obj.Addrel(c.cursym) 3098 rel.Off = int32(c.pc) 3099 rel.Siz = 8 3100 rel.Sym = p.From.Sym 3101 rel.Add = p.From.Offset 3102 rel.Type = objabi.R_ADDR 3103 o2 = 0 3104 o1 = o2 3105 } 3106 3107 case 32: /* fmul frc,fra,frd */ 3108 r := int(p.Reg) 3109 3110 if r == 0 { 3111 r = int(p.To.Reg) 3112 } 3113 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), 0) | (uint32(p.From.Reg)&31)<<6 3114 3115 case 33: /* fabs [frb,]frd; fmr. frb,frd */ 3116 r := int(p.From.Reg) 3117 3118 if oclass(&p.From) == C_NONE { 3119 r = int(p.To.Reg) 3120 } 3121 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), 0, uint32(r)) 3122 3123 case 34: /* FMADDx fra,frb,frc,frt (t=a*c±b) */ 3124 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg)) | (uint32(p.GetFrom3().Reg)&31)<<6 3125 3126 case 35: /* mov r,lext/lauto/loreg ==> cau $(v>>16),sb,r'; store o(r') */ 3127 v := c.regoff(&p.To) 3128 3129 r := int(p.To.Reg) 3130 if r == 0 { 3131 r = c.getimpliedreg(&p.To, p) 3132 } 3133 // Offsets in DS form stores must be a multiple of 4 3134 inst := c.opstore(p.As) 3135 if c.opform(inst) == DS_FORM && v&0x3 != 0 { 3136 log.Fatalf("invalid offset for DS form load/store %v", p) 3137 } 3138 o1 = AOP_IRR(OP_ADDIS, REGTMP, uint32(r), uint32(high16adjusted(v))) 3139 o2 = AOP_IRR(inst, uint32(p.From.Reg), REGTMP, uint32(v)) 3140 3141 case 36: /* mov b/bz/h/hz lext/lauto/lreg,r ==> lbz+extsb/lbz/lha/lhz etc */ 3142 v := c.regoff(&p.From) 3143 3144 r := int(p.From.Reg) 3145 if r == 0 { 3146 r = c.getimpliedreg(&p.From, p) 3147 } 3148 o1 = AOP_IRR(OP_ADDIS, uint32(p.To.Reg), uint32(r), uint32(high16adjusted(v))) 3149 o2 = AOP_IRR(c.opload(p.As), uint32(p.To.Reg), uint32(p.To.Reg), uint32(v)) 3150 3151 // Sign extend MOVB if needed 3152 o3 = LOP_RRR(OP_EXTSB, uint32(p.To.Reg), uint32(p.To.Reg), 0) 3153 3154 case 40: /* word */ 3155 o1 = uint32(c.regoff(&p.From)) 3156 3157 case 41: /* stswi */ 3158 o1 = AOP_RRR(c.opirr(p.As), uint32(p.From.Reg), uint32(p.To.Reg), 0) | (uint32(c.regoff(p.GetFrom3()))&0x7F)<<11 3159 3160 case 42: /* lswi */ 3161 o1 = AOP_RRR(c.opirr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), 0) | (uint32(c.regoff(p.GetFrom3()))&0x7F)<<11 3162 3163 case 43: /* data cache instructions: op (Ra+[Rb]), [th|l] */ 3164 /* TH field for dcbt/dcbtst: */ 3165 /* 0 = Block access - program will soon access EA. */ 3166 /* 8-15 = Stream access - sequence of access (data stream). See section 4.3.2 of the ISA for details. */ 3167 /* 16 = Block access - program will soon make a transient access to EA. */ 3168 /* 17 = Block access - program will not access EA for a long time. */ 3169 3170 /* L field for dcbf: */ 3171 /* 0 = invalidates the block containing EA in all processors. */ 3172 /* 1 = same as 0, but with limited scope (i.e. block in the current processor will not be reused soon). */ 3173 /* 3 = same as 1, but with even more limited scope (i.e. block in the current processor primary cache will not be reused soon). */ 3174 if p.To.Type == obj.TYPE_NONE { 3175 o1 = AOP_RRR(c.oprrr(p.As), 0, uint32(p.From.Index), uint32(p.From.Reg)) 3176 } else { 3177 th := c.regoff(&p.To) 3178 o1 = AOP_RRR(c.oprrr(p.As), uint32(th), uint32(p.From.Index), uint32(p.From.Reg)) 3179 } 3180 3181 case 44: /* indexed store */ 3182 o1 = AOP_RRR(c.opstorex(p.As), uint32(p.From.Reg), uint32(p.To.Index), uint32(p.To.Reg)) 3183 3184 case 45: /* indexed load */ 3185 switch p.As { 3186 /* The assembler accepts a 4-operand l*arx instruction. The fourth operand is an Exclusive Access Hint (EH) */ 3187 /* The EH field can be used as a lock acquire/release hint as follows: */ 3188 /* 0 = Atomic Update (fetch-and-operate or similar algorithm) */ 3189 /* 1 = Exclusive Access (lock acquire and release) */ 3190 case ALBAR, ALHAR, ALWAR, ALDAR: 3191 if p.From3Type() != obj.TYPE_NONE { 3192 eh := int(c.regoff(p.GetFrom3())) 3193 if eh > 1 { 3194 c.ctxt.Diag("illegal EH field\n%v", p) 3195 } 3196 o1 = AOP_RRRI(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(p.From.Reg), uint32(eh)) 3197 } else { 3198 o1 = AOP_RRR(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(p.From.Reg)) 3199 } 3200 default: 3201 o1 = AOP_RRR(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(p.From.Reg)) 3202 } 3203 case 46: /* plain op */ 3204 o1 = c.oprrr(p.As) 3205 3206 case 47: /* op Ra, Rd; also op [Ra,] Rd */ 3207 r := int(p.From.Reg) 3208 3209 if r == 0 { 3210 r = int(p.To.Reg) 3211 } 3212 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), 0) 3213 3214 case 48: /* op Rs, Ra */ 3215 r := int(p.From.Reg) 3216 3217 if r == 0 { 3218 r = int(p.To.Reg) 3219 } 3220 o1 = LOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(r), 0) 3221 3222 case 49: /* op Rb; op $n, Rb */ 3223 if p.From.Type != obj.TYPE_REG { /* tlbie $L, rB */ 3224 v := c.regoff(&p.From) & 1 3225 o1 = AOP_RRR(c.oprrr(p.As), 0, 0, uint32(p.To.Reg)) | uint32(v)<<21 3226 } else { 3227 o1 = AOP_RRR(c.oprrr(p.As), 0, 0, uint32(p.From.Reg)) 3228 } 3229 3230 case 50: /* rem[u] r1[,r2],r3 */ 3231 r := int(p.Reg) 3232 3233 if r == 0 { 3234 r = int(p.To.Reg) 3235 } 3236 v := c.oprrr(p.As) 3237 t := v & (1<<10 | 1) /* OE|Rc */ 3238 o1 = AOP_RRR(v&^t, REGTMP, uint32(r), uint32(p.From.Reg)) 3239 o2 = AOP_RRR(OP_MULLW, REGTMP, REGTMP, uint32(p.From.Reg)) 3240 o3 = AOP_RRR(OP_SUBF|t, uint32(p.To.Reg), REGTMP, uint32(r)) 3241 if p.As == AREMU { 3242 o4 = o3 3243 3244 /* Clear top 32 bits */ 3245 o3 = OP_RLW(OP_RLDIC, REGTMP, REGTMP, 0, 0, 0) | 1<<5 3246 } 3247 3248 case 51: /* remd[u] r1[,r2],r3 */ 3249 r := int(p.Reg) 3250 3251 if r == 0 { 3252 r = int(p.To.Reg) 3253 } 3254 v := c.oprrr(p.As) 3255 t := v & (1<<10 | 1) /* OE|Rc */ 3256 o1 = AOP_RRR(v&^t, REGTMP, uint32(r), uint32(p.From.Reg)) 3257 o2 = AOP_RRR(OP_MULLD, REGTMP, REGTMP, uint32(p.From.Reg)) 3258 o3 = AOP_RRR(OP_SUBF|t, uint32(p.To.Reg), REGTMP, uint32(r)) 3259 /* cases 50,51: removed; can be reused. */ 3260 3261 /* cases 50,51: removed; can be reused. */ 3262 3263 case 52: /* mtfsbNx cr(n) */ 3264 v := c.regoff(&p.From) & 31 3265 3266 o1 = AOP_RRR(c.oprrr(p.As), uint32(v), 0, 0) 3267 3268 case 53: /* mffsX ,fr1 */ 3269 o1 = AOP_RRR(OP_MFFS, uint32(p.To.Reg), 0, 0) 3270 3271 case 55: /* op Rb, Rd */ 3272 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), 0, uint32(p.From.Reg)) 3273 3274 case 56: /* sra $sh,[s,]a; srd $sh,[s,]a */ 3275 v := c.regoff(&p.From) 3276 3277 r := int(p.Reg) 3278 if r == 0 { 3279 r = int(p.To.Reg) 3280 } 3281 o1 = AOP_RRR(c.opirr(p.As), uint32(r), uint32(p.To.Reg), uint32(v)&31) 3282 if (p.As == ASRAD || p.As == ASRADCC) && (v&0x20 != 0) { 3283 o1 |= 1 << 1 /* mb[5] */ 3284 } 3285 3286 case 57: /* slw $sh,[s,]a -> rlwinm ... */ 3287 v := c.regoff(&p.From) 3288 3289 r := int(p.Reg) 3290 if r == 0 { 3291 r = int(p.To.Reg) 3292 } 3293 3294 /* 3295 * Let user (gs) shoot himself in the foot. 3296 * qc has already complained. 3297 * 3298 if(v < 0 || v > 31) 3299 ctxt->diag("illegal shift %ld\n%v", v, p); 3300 */ 3301 if v < 0 { 3302 v = 0 3303 } else if v > 32 { 3304 v = 32 3305 } 3306 var mask [2]uint8 3307 switch p.As { 3308 case AROTLW: 3309 mask[0], mask[1] = 0, 31 3310 case ASRW, ASRWCC: 3311 mask[0], mask[1] = uint8(v), 31 3312 v = 32 - v 3313 default: 3314 mask[0], mask[1] = 0, uint8(31-v) 3315 } 3316 o1 = OP_RLW(OP_RLWINM, uint32(p.To.Reg), uint32(r), uint32(v), uint32(mask[0]), uint32(mask[1])) 3317 if p.As == ASLWCC || p.As == ASRWCC { 3318 o1 |= 1 // set the condition code 3319 } 3320 3321 case 58: /* logical $andcon,[s],a */ 3322 v := c.regoff(&p.From) 3323 3324 r := int(p.Reg) 3325 if r == 0 { 3326 r = int(p.To.Reg) 3327 } 3328 o1 = LOP_IRR(c.opirr(p.As), uint32(p.To.Reg), uint32(r), uint32(v)) 3329 3330 case 59: /* or/xor/and $ucon,,r | oris/xoris/andis $addcon,r,r */ 3331 v := c.regoff(&p.From) 3332 3333 r := int(p.Reg) 3334 if r == 0 { 3335 r = int(p.To.Reg) 3336 } 3337 switch p.As { 3338 case AOR: 3339 o1 = LOP_IRR(c.opirr(AORIS), uint32(p.To.Reg), uint32(r), uint32(v)>>16) /* oris, xoris, andis. */ 3340 case AXOR: 3341 o1 = LOP_IRR(c.opirr(AXORIS), uint32(p.To.Reg), uint32(r), uint32(v)>>16) 3342 case AANDCC: 3343 o1 = LOP_IRR(c.opirr(AANDISCC), uint32(p.To.Reg), uint32(r), uint32(v)>>16) 3344 default: 3345 o1 = LOP_IRR(c.opirr(p.As), uint32(p.To.Reg), uint32(r), uint32(v)) 3346 } 3347 3348 case 60: /* tw to,a,b */ 3349 r := int(c.regoff(&p.From) & 31) 3350 3351 o1 = AOP_RRR(c.oprrr(p.As), uint32(r), uint32(p.Reg), uint32(p.To.Reg)) 3352 3353 case 61: /* tw to,a,$simm */ 3354 r := int(c.regoff(&p.From) & 31) 3355 3356 v := c.regoff(&p.To) 3357 o1 = AOP_IRR(c.opirr(p.As), uint32(r), uint32(p.Reg), uint32(v)) 3358 3359 case 62: /* rlwmi $sh,s,$mask,a */ 3360 v := c.regoff(&p.From) 3361 switch p.As { 3362 case ACLRLSLWI: 3363 n := c.regoff(p.GetFrom3()) 3364 // This is an extended mnemonic described in the ISA C.8.2 3365 // clrlslwi ra,rs,b,n -> rlwinm ra,rs,n,b-n,31-n 3366 // It maps onto rlwinm which is directly generated here. 3367 if n > v || v >= 32 { 3368 c.ctxt.Diag("Invalid n or b for CLRLSLWI: %x %x\n%v", v, n, p) 3369 } 3370 3371 o1 = OP_RLW(OP_RLWINM, uint32(p.To.Reg), uint32(p.Reg), uint32(n), uint32(v-n), uint32(31-n)) 3372 default: 3373 var mask [2]uint8 3374 c.maskgen(p, mask[:], uint32(c.regoff(p.GetFrom3()))) 3375 o1 = AOP_RRR(c.opirr(p.As), uint32(p.Reg), uint32(p.To.Reg), uint32(v)) 3376 o1 |= (uint32(mask[0])&31)<<6 | (uint32(mask[1])&31)<<1 3377 } 3378 3379 case 63: /* rlwmi b,s,$mask,a */ 3380 var mask [2]uint8 3381 c.maskgen(p, mask[:], uint32(c.regoff(p.GetFrom3()))) 3382 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.Reg), uint32(p.To.Reg), uint32(p.From.Reg)) 3383 o1 |= (uint32(mask[0])&31)<<6 | (uint32(mask[1])&31)<<1 3384 3385 case 64: /* mtfsf fr[, $m] {,fpcsr} */ 3386 var v int32 3387 if p.From3Type() != obj.TYPE_NONE { 3388 v = c.regoff(p.GetFrom3()) & 255 3389 } else { 3390 v = 255 3391 } 3392 o1 = OP_MTFSF | uint32(v)<<17 | uint32(p.From.Reg)<<11 3393 3394 case 65: /* MOVFL $imm,FPSCR(n) => mtfsfi crfd,imm */ 3395 if p.To.Reg == 0 { 3396 c.ctxt.Diag("must specify FPSCR(n)\n%v", p) 3397 } 3398 o1 = OP_MTFSFI | (uint32(p.To.Reg)&15)<<23 | (uint32(c.regoff(&p.From))&31)<<12 3399 3400 case 66: /* mov spr,r1; mov r1,spr */ 3401 var r int 3402 var v int32 3403 if REG_R0 <= p.From.Reg && p.From.Reg <= REG_R31 { 3404 r = int(p.From.Reg) 3405 v = int32(p.To.Reg) 3406 o1 = OPVCC(31, 467, 0, 0) /* mtspr */ 3407 } else { 3408 r = int(p.To.Reg) 3409 v = int32(p.From.Reg) 3410 o1 = OPVCC(31, 339, 0, 0) /* mfspr */ 3411 } 3412 3413 o1 = AOP_RRR(o1, uint32(r), 0, 0) | (uint32(v)&0x1f)<<16 | ((uint32(v)>>5)&0x1f)<<11 3414 3415 case 67: /* mcrf crfD,crfS */ 3416 if p.From.Reg == REG_CR || p.To.Reg == REG_CR { 3417 c.ctxt.Diag("CR argument must be a conditional register field (CR0-CR7)\n%v", p) 3418 } 3419 o1 = AOP_RRR(OP_MCRF, ((uint32(p.To.Reg) & 7) << 2), ((uint32(p.From.Reg) & 7) << 2), 0) 3420 3421 case 68: /* mfcr rD; mfocrf CRM,rD */ 3422 o1 = AOP_RRR(OP_MFCR, uint32(p.To.Reg), 0, 0) /* form, whole register */ 3423 if p.From.Reg != REG_CR { 3424 v := uint32(1) << uint(7-(p.From.Reg&7)) /* CR(n) */ 3425 o1 |= 1<<20 | v<<12 /* new form, mfocrf */ 3426 } 3427 3428 case 69: /* mtcrf CRM,rS, mtocrf CRx,rS */ 3429 var v uint32 3430 if p.To.Reg == REG_CR { 3431 v = 0xff 3432 } else if p.To.Offset != 0 { // MOVFL gpr, constant 3433 v = uint32(p.To.Offset) 3434 } else { // p.To.Reg == REG_CRx 3435 v = 1 << uint(7-(p.To.Reg&7)) 3436 } 3437 // Use mtocrf form if only one CR field moved. 3438 if bits.OnesCount32(v) == 1 { 3439 v |= 1 << 8 3440 } 3441 3442 o1 = AOP_RRR(OP_MTCRF, uint32(p.From.Reg), 0, 0) | uint32(v)<<12 3443 3444 case 70: /* [f]cmp r,r,cr*/ 3445 var r int 3446 if p.Reg == 0 { 3447 r = 0 3448 } else { 3449 r = (int(p.Reg) & 7) << 2 3450 } 3451 o1 = AOP_RRR(c.oprrr(p.As), uint32(r), uint32(p.From.Reg), uint32(p.To.Reg)) 3452 3453 case 71: /* cmp[l] r,i,cr*/ 3454 var r int 3455 if p.Reg == 0 { 3456 r = 0 3457 } else { 3458 r = (int(p.Reg) & 7) << 2 3459 } 3460 o1 = AOP_RRR(c.opirr(p.As), uint32(r), uint32(p.From.Reg), 0) | uint32(c.regoff(&p.To))&0xffff 3461 3462 case 72: /* slbmte (Rb+Rs -> slb[Rb]) -> Rs, Rb */ 3463 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.From.Reg), 0, uint32(p.To.Reg)) 3464 3465 case 73: /* mcrfs crfD,crfS */ 3466 if p.From.Type != obj.TYPE_REG || p.From.Reg != REG_FPSCR || p.To.Type != obj.TYPE_REG || p.To.Reg < REG_CR0 || REG_CR7 < p.To.Reg { 3467 c.ctxt.Diag("illegal FPSCR/CR field number\n%v", p) 3468 } 3469 o1 = AOP_RRR(OP_MCRFS, ((uint32(p.To.Reg) & 7) << 2), ((0 & 7) << 2), 0) 3470 3471 case 77: /* syscall $scon, syscall Rx */ 3472 if p.From.Type == obj.TYPE_CONST { 3473 if p.From.Offset > BIG || p.From.Offset < -BIG { 3474 c.ctxt.Diag("illegal syscall, sysnum too large: %v", p) 3475 } 3476 o1 = AOP_IRR(OP_ADDI, REGZERO, REGZERO, uint32(p.From.Offset)) 3477 } else if p.From.Type == obj.TYPE_REG { 3478 o1 = LOP_RRR(OP_OR, REGZERO, uint32(p.From.Reg), uint32(p.From.Reg)) 3479 } else { 3480 c.ctxt.Diag("illegal syscall: %v", p) 3481 o1 = 0x7fe00008 // trap always 3482 } 3483 3484 o2 = c.oprrr(p.As) 3485 o3 = AOP_RRR(c.oprrr(AXOR), REGZERO, REGZERO, REGZERO) // XOR R0, R0 3486 3487 case 78: /* undef */ 3488 o1 = 0 /* "An instruction consisting entirely of binary 0s is guaranteed 3489 always to be an illegal instruction." */ 3490 3491 /* relocation operations */ 3492 case 74: 3493 v := c.vregoff(&p.To) 3494 // Offsets in DS form stores must be a multiple of 4 3495 inst := c.opstore(p.As) 3496 if c.opform(inst) == DS_FORM && v&0x3 != 0 { 3497 log.Fatalf("invalid offset for DS form load/store %v", p) 3498 } 3499 // Can't reuse base for store instructions. 3500 o1, o2 = c.symbolAccess(p.To.Sym, v, p.From.Reg, inst, false) 3501 3502 case 75: // 32 bit offset symbol loads (got/toc/addr) 3503 v := p.From.Offset 3504 3505 // Offsets in DS form loads must be a multiple of 4 3506 inst := c.opload(p.As) 3507 if c.opform(inst) == DS_FORM && v&0x3 != 0 { 3508 log.Fatalf("invalid offset for DS form load/store %v", p) 3509 } 3510 switch p.From.Name { 3511 case obj.NAME_GOTREF, obj.NAME_TOCREF: 3512 if v != 0 { 3513 c.ctxt.Diag("invalid offset for GOT/TOC access %v", p) 3514 } 3515 o1 = AOP_IRR(OP_ADDIS, uint32(p.To.Reg), REG_R2, 0) 3516 o2 = AOP_IRR(inst, uint32(p.To.Reg), uint32(p.To.Reg), 0) 3517 rel := obj.Addrel(c.cursym) 3518 rel.Off = int32(c.pc) 3519 rel.Siz = 8 3520 rel.Sym = p.From.Sym 3521 switch p.From.Name { 3522 case obj.NAME_GOTREF: 3523 rel.Type = objabi.R_ADDRPOWER_GOT 3524 case obj.NAME_TOCREF: 3525 rel.Type = objabi.R_ADDRPOWER_TOCREL_DS 3526 } 3527 default: 3528 reuseBaseReg := p.As != AFMOVD && p.As != AFMOVS 3529 // Reuse To.Reg as base register if not FP move. 3530 o1, o2 = c.symbolAccess(p.From.Sym, v, p.To.Reg, inst, reuseBaseReg) 3531 } 3532 3533 o3 = LOP_RRR(OP_EXTSB, uint32(p.To.Reg), uint32(p.To.Reg), 0) 3534 3535 case 79: 3536 if p.From.Offset != 0 { 3537 c.ctxt.Diag("invalid offset against tls var %v", p) 3538 } 3539 o1 = AOP_IRR(OP_ADDIS, uint32(p.To.Reg), REG_R13, 0) 3540 o2 = AOP_IRR(OP_ADDI, uint32(p.To.Reg), uint32(p.To.Reg), 0) 3541 rel := obj.Addrel(c.cursym) 3542 rel.Off = int32(c.pc) 3543 rel.Siz = 8 3544 rel.Sym = p.From.Sym 3545 rel.Type = objabi.R_POWER_TLS_LE 3546 3547 case 80: 3548 if p.From.Offset != 0 { 3549 c.ctxt.Diag("invalid offset against tls var %v", p) 3550 } 3551 o1 = AOP_IRR(OP_ADDIS, uint32(p.To.Reg), REG_R2, 0) 3552 o2 = AOP_IRR(c.opload(AMOVD), uint32(p.To.Reg), uint32(p.To.Reg), 0) 3553 o3 = AOP_RRR(OP_ADD, uint32(p.To.Reg), uint32(p.To.Reg), REG_R13) 3554 rel := obj.Addrel(c.cursym) 3555 rel.Off = int32(c.pc) 3556 rel.Siz = 8 3557 rel.Sym = p.From.Sym 3558 rel.Type = objabi.R_POWER_TLS_IE 3559 rel = obj.Addrel(c.cursym) 3560 rel.Off = int32(c.pc) + 8 3561 rel.Siz = 4 3562 rel.Sym = p.From.Sym 3563 rel.Type = objabi.R_POWER_TLS 3564 3565 case 82: /* vector instructions, VX-form and VC-form */ 3566 if p.From.Type == obj.TYPE_REG { 3567 /* reg reg none OR reg reg reg */ 3568 /* 3-register operand order: VRA, VRB, VRT */ 3569 /* 2-register operand order: VRA, VRT */ 3570 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg)) 3571 } else if p.From3Type() == obj.TYPE_CONST { 3572 /* imm imm reg reg */ 3573 /* operand order: SIX, VRA, ST, VRT */ 3574 six := int(c.regoff(&p.From)) 3575 st := int(c.regoff(p.GetFrom3())) 3576 o1 = AOP_IIRR(c.opiirr(p.As), uint32(p.To.Reg), uint32(p.Reg), uint32(st), uint32(six)) 3577 } else if p.From3Type() == obj.TYPE_NONE && p.Reg != 0 { 3578 /* imm reg reg */ 3579 /* operand order: UIM, VRB, VRT */ 3580 uim := int(c.regoff(&p.From)) 3581 o1 = AOP_VIRR(c.opirr(p.As), uint32(p.To.Reg), uint32(p.Reg), uint32(uim)) 3582 } else { 3583 /* imm reg */ 3584 /* operand order: SIM, VRT */ 3585 sim := int(c.regoff(&p.From)) 3586 o1 = AOP_IR(c.opirr(p.As), uint32(p.To.Reg), uint32(sim)) 3587 } 3588 3589 case 83: /* vector instructions, VA-form */ 3590 if p.From.Type == obj.TYPE_REG { 3591 /* reg reg reg reg */ 3592 /* 4-register operand order: VRA, VRB, VRC, VRT */ 3593 o1 = AOP_RRRR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg), uint32(p.GetFrom3().Reg)) 3594 } else if p.From.Type == obj.TYPE_CONST { 3595 /* imm reg reg reg */ 3596 /* operand order: SHB, VRA, VRB, VRT */ 3597 shb := int(c.regoff(&p.From)) 3598 o1 = AOP_IRRR(c.opirrr(p.As), uint32(p.To.Reg), uint32(p.Reg), uint32(p.GetFrom3().Reg), uint32(shb)) 3599 } 3600 3601 case 84: // ISEL BC,RA,RB,RT -> isel rt,ra,rb,bc 3602 bc := c.vregoff(&p.From) 3603 3604 // rt = To.Reg, ra = p.Reg, rb = p.From3.Reg 3605 o1 = AOP_ISEL(OP_ISEL, uint32(p.To.Reg), uint32(p.Reg), uint32(p.GetFrom3().Reg), uint32(bc)) 3606 3607 case 85: /* vector instructions, VX-form */ 3608 /* reg none reg */ 3609 /* 2-register operand order: VRB, VRT */ 3610 o1 = AOP_RR(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg)) 3611 3612 case 86: /* VSX indexed store, XX1-form */ 3613 /* reg reg reg */ 3614 /* 3-register operand order: XT, (RB)(RA*1) */ 3615 o1 = AOP_XX1(c.opstorex(p.As), uint32(p.From.Reg), uint32(p.To.Index), uint32(p.To.Reg)) 3616 3617 case 87: /* VSX indexed load, XX1-form */ 3618 /* reg reg reg */ 3619 /* 3-register operand order: (RB)(RA*1), XT */ 3620 o1 = AOP_XX1(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(p.From.Reg)) 3621 3622 case 88: /* VSX mfvsr* instructions, XX1-form XS,RA */ 3623 o1 = AOP_XX1(c.oprrr(p.As), uint32(p.From.Reg), uint32(p.To.Reg), uint32(p.Reg)) 3624 3625 case 89: /* VSX instructions, XX2-form */ 3626 /* reg none reg OR reg imm reg */ 3627 /* 2-register operand order: XB, XT or XB, UIM, XT*/ 3628 uim := int(c.regoff(p.GetFrom3())) 3629 o1 = AOP_XX2(c.oprrr(p.As), uint32(p.To.Reg), uint32(uim), uint32(p.From.Reg)) 3630 3631 case 90: /* VSX instructions, XX3-form */ 3632 if p.From3Type() == obj.TYPE_NONE { 3633 /* reg reg reg */ 3634 /* 3-register operand order: XA, XB, XT */ 3635 o1 = AOP_XX3(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg)) 3636 } else if p.From3Type() == obj.TYPE_CONST { 3637 /* reg reg reg imm */ 3638 /* operand order: XA, XB, DM, XT */ 3639 dm := int(c.regoff(p.GetFrom3())) 3640 o1 = AOP_XX3I(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg), uint32(dm)) 3641 } 3642 3643 case 91: /* VSX instructions, XX4-form */ 3644 /* reg reg reg reg */ 3645 /* 3-register operand order: XA, XB, XC, XT */ 3646 o1 = AOP_XX4(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg), uint32(p.GetFrom3().Reg)) 3647 3648 case 92: /* X-form instructions, 3-operands */ 3649 if p.To.Type == obj.TYPE_CONST { 3650 /* imm reg reg */ 3651 xf := int32(p.From.Reg) 3652 if REG_F0 <= xf && xf <= REG_F31 { 3653 /* operand order: FRA, FRB, BF */ 3654 bf := int(c.regoff(&p.To)) << 2 3655 o1 = AOP_RRR(c.opirr(p.As), uint32(bf), uint32(p.From.Reg), uint32(p.Reg)) 3656 } else { 3657 /* operand order: RA, RB, L */ 3658 l := int(c.regoff(&p.To)) 3659 o1 = AOP_RRR(c.opirr(p.As), uint32(l), uint32(p.From.Reg), uint32(p.Reg)) 3660 } 3661 } else if p.From3Type() == obj.TYPE_CONST { 3662 /* reg reg imm */ 3663 /* operand order: RB, L, RA */ 3664 l := int(c.regoff(p.GetFrom3())) 3665 o1 = AOP_RRR(c.opirr(p.As), uint32(l), uint32(p.To.Reg), uint32(p.From.Reg)) 3666 } else if p.To.Type == obj.TYPE_REG { 3667 cr := int32(p.To.Reg) 3668 if REG_CR0 <= cr && cr <= REG_CR7 { 3669 /* cr reg reg */ 3670 /* operand order: RA, RB, BF */ 3671 bf := (int(p.To.Reg) & 7) << 2 3672 o1 = AOP_RRR(c.opirr(p.As), uint32(bf), uint32(p.From.Reg), uint32(p.Reg)) 3673 } else if p.From.Type == obj.TYPE_CONST { 3674 /* reg imm */ 3675 /* operand order: L, RT */ 3676 l := int(c.regoff(&p.From)) 3677 o1 = AOP_RRR(c.opirr(p.As), uint32(p.To.Reg), uint32(l), uint32(p.Reg)) 3678 } else { 3679 switch p.As { 3680 case ACOPY, APASTECC: 3681 o1 = AOP_RRR(c.opirr(p.As), uint32(1), uint32(p.From.Reg), uint32(p.To.Reg)) 3682 default: 3683 /* reg reg reg */ 3684 /* operand order: RS, RB, RA */ 3685 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.From.Reg), uint32(p.To.Reg), uint32(p.Reg)) 3686 } 3687 } 3688 } 3689 3690 case 93: /* X-form instructions, 2-operands */ 3691 if p.To.Type == obj.TYPE_CONST { 3692 /* imm reg */ 3693 /* operand order: FRB, BF */ 3694 bf := int(c.regoff(&p.To)) << 2 3695 o1 = AOP_RR(c.opirr(p.As), uint32(bf), uint32(p.From.Reg)) 3696 } else if p.Reg == 0 { 3697 /* popcnt* r,r, X-form */ 3698 /* operand order: RS, RA */ 3699 o1 = AOP_RRR(c.oprrr(p.As), uint32(p.From.Reg), uint32(p.To.Reg), uint32(p.Reg)) 3700 } 3701 3702 case 94: /* Z23-form instructions, 4-operands */ 3703 /* reg reg reg imm */ 3704 /* operand order: RA, RB, CY, RT */ 3705 cy := int(c.regoff(p.GetFrom3())) 3706 o1 = AOP_Z23I(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg), uint32(cy)) 3707 3708 case 96: /* VSX load, DQ-form */ 3709 /* reg imm reg */ 3710 /* operand order: (RA)(DQ), XT */ 3711 dq := int16(c.regoff(&p.From)) 3712 if (dq & 15) != 0 { 3713 c.ctxt.Diag("invalid offset for DQ form load/store %v", dq) 3714 } 3715 o1 = AOP_DQ(c.opload(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(dq)) 3716 3717 case 97: /* VSX store, DQ-form */ 3718 /* reg imm reg */ 3719 /* operand order: XT, (RA)(DQ) */ 3720 dq := int16(c.regoff(&p.To)) 3721 if (dq & 15) != 0 { 3722 c.ctxt.Diag("invalid offset for DQ form load/store %v", dq) 3723 } 3724 o1 = AOP_DQ(c.opstore(p.As), uint32(p.From.Reg), uint32(p.To.Reg), uint32(dq)) 3725 case 98: /* VSX indexed load or load with length (also left-justified), x-form */ 3726 /* vsreg, reg, reg */ 3727 o1 = AOP_XX1(c.opload(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg)) 3728 case 99: /* VSX store with length (also left-justified) x-form */ 3729 /* reg, reg, vsreg */ 3730 o1 = AOP_XX1(c.opstore(p.As), uint32(p.From.Reg), uint32(p.Reg), uint32(p.To.Reg)) 3731 case 100: /* VSX X-form XXSPLTIB */ 3732 if p.From.Type == obj.TYPE_CONST { 3733 /* imm reg */ 3734 uim := int(c.regoff(&p.From)) 3735 /* imm reg */ 3736 /* Use AOP_XX1 form with 0 for one of the registers. */ 3737 o1 = AOP_XX1(c.oprrr(p.As), uint32(p.To.Reg), uint32(0), uint32(uim)) 3738 } else { 3739 c.ctxt.Diag("invalid ops for %v", p.As) 3740 } 3741 case 101: 3742 o1 = AOP_XX2(c.oprrr(p.As), uint32(p.To.Reg), uint32(0), uint32(p.From.Reg)) 3743 3744 case 102: /* RLWMI $sh,rs,$mb,$me,rt (M-form opcode)*/ 3745 mb := uint32(c.regoff(&p.RestArgs[0].Addr)) 3746 me := uint32(c.regoff(&p.RestArgs[1].Addr)) 3747 sh := uint32(c.regoff(&p.From)) 3748 o1 = OP_RLW(c.opirr(p.As), uint32(p.To.Reg), uint32(p.Reg), sh, mb, me) 3749 3750 case 103: /* RLWMI rb,rs,$mb,$me,rt (M-form opcode)*/ 3751 mb := uint32(c.regoff(&p.RestArgs[0].Addr)) 3752 me := uint32(c.regoff(&p.RestArgs[1].Addr)) 3753 o1 = OP_RLW(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.Reg), uint32(p.From.Reg), mb, me) 3754 3755 case 104: /* VSX mtvsr* instructions, XX1-form RA,RB,XT */ 3756 o1 = AOP_XX1(c.oprrr(p.As), uint32(p.To.Reg), uint32(p.From.Reg), uint32(p.Reg)) 3757 3758 case 105: /* PNOP */ 3759 o1 = 0x07000000 3760 o2 = 0x00000000 3761 } 3762 3763 out[0] = o1 3764 out[1] = o2 3765 out[2] = o3 3766 out[3] = o4 3767 out[4] = o5 3768} 3769 3770func (c *ctxt9) vregoff(a *obj.Addr) int64 { 3771 c.instoffset = 0 3772 if a != nil { 3773 c.aclass(a) 3774 } 3775 return c.instoffset 3776} 3777 3778func (c *ctxt9) regoff(a *obj.Addr) int32 { 3779 return int32(c.vregoff(a)) 3780} 3781 3782func (c *ctxt9) oprrr(a obj.As) uint32 { 3783 switch a { 3784 case AADD: 3785 return OPVCC(31, 266, 0, 0) 3786 case AADDCC: 3787 return OPVCC(31, 266, 0, 1) 3788 case AADDV: 3789 return OPVCC(31, 266, 1, 0) 3790 case AADDVCC: 3791 return OPVCC(31, 266, 1, 1) 3792 case AADDC: 3793 return OPVCC(31, 10, 0, 0) 3794 case AADDCCC: 3795 return OPVCC(31, 10, 0, 1) 3796 case AADDCV: 3797 return OPVCC(31, 10, 1, 0) 3798 case AADDCVCC: 3799 return OPVCC(31, 10, 1, 1) 3800 case AADDE: 3801 return OPVCC(31, 138, 0, 0) 3802 case AADDECC: 3803 return OPVCC(31, 138, 0, 1) 3804 case AADDEV: 3805 return OPVCC(31, 138, 1, 0) 3806 case AADDEVCC: 3807 return OPVCC(31, 138, 1, 1) 3808 case AADDME: 3809 return OPVCC(31, 234, 0, 0) 3810 case AADDMECC: 3811 return OPVCC(31, 234, 0, 1) 3812 case AADDMEV: 3813 return OPVCC(31, 234, 1, 0) 3814 case AADDMEVCC: 3815 return OPVCC(31, 234, 1, 1) 3816 case AADDZE: 3817 return OPVCC(31, 202, 0, 0) 3818 case AADDZECC: 3819 return OPVCC(31, 202, 0, 1) 3820 case AADDZEV: 3821 return OPVCC(31, 202, 1, 0) 3822 case AADDZEVCC: 3823 return OPVCC(31, 202, 1, 1) 3824 case AADDEX: 3825 return OPVCC(31, 170, 0, 0) /* addex - v3.0b */ 3826 3827 case AAND: 3828 return OPVCC(31, 28, 0, 0) 3829 case AANDCC: 3830 return OPVCC(31, 28, 0, 1) 3831 case AANDN: 3832 return OPVCC(31, 60, 0, 0) 3833 case AANDNCC: 3834 return OPVCC(31, 60, 0, 1) 3835 3836 case ACMP: 3837 return OPVCC(31, 0, 0, 0) | 1<<21 /* L=1 */ 3838 case ACMPU: 3839 return OPVCC(31, 32, 0, 0) | 1<<21 3840 case ACMPW: 3841 return OPVCC(31, 0, 0, 0) /* L=0 */ 3842 case ACMPWU: 3843 return OPVCC(31, 32, 0, 0) 3844 case ACMPB: 3845 return OPVCC(31, 508, 0, 0) /* cmpb - v2.05 */ 3846 case ACMPEQB: 3847 return OPVCC(31, 224, 0, 0) /* cmpeqb - v3.00 */ 3848 3849 case ACNTLZW: 3850 return OPVCC(31, 26, 0, 0) 3851 case ACNTLZWCC: 3852 return OPVCC(31, 26, 0, 1) 3853 case ACNTLZD: 3854 return OPVCC(31, 58, 0, 0) 3855 case ACNTLZDCC: 3856 return OPVCC(31, 58, 0, 1) 3857 3858 case ACRAND: 3859 return OPVCC(19, 257, 0, 0) 3860 case ACRANDN: 3861 return OPVCC(19, 129, 0, 0) 3862 case ACREQV: 3863 return OPVCC(19, 289, 0, 0) 3864 case ACRNAND: 3865 return OPVCC(19, 225, 0, 0) 3866 case ACRNOR: 3867 return OPVCC(19, 33, 0, 0) 3868 case ACROR: 3869 return OPVCC(19, 449, 0, 0) 3870 case ACRORN: 3871 return OPVCC(19, 417, 0, 0) 3872 case ACRXOR: 3873 return OPVCC(19, 193, 0, 0) 3874 3875 case ADCBF: 3876 return OPVCC(31, 86, 0, 0) 3877 case ADCBI: 3878 return OPVCC(31, 470, 0, 0) 3879 case ADCBST: 3880 return OPVCC(31, 54, 0, 0) 3881 case ADCBT: 3882 return OPVCC(31, 278, 0, 0) 3883 case ADCBTST: 3884 return OPVCC(31, 246, 0, 0) 3885 case ADCBZ: 3886 return OPVCC(31, 1014, 0, 0) 3887 3888 case AMODUD: 3889 return OPVCC(31, 265, 0, 0) /* modud - v3.0 */ 3890 case AMODUW: 3891 return OPVCC(31, 267, 0, 0) /* moduw - v3.0 */ 3892 case AMODSD: 3893 return OPVCC(31, 777, 0, 0) /* modsd - v3.0 */ 3894 case AMODSW: 3895 return OPVCC(31, 779, 0, 0) /* modsw - v3.0 */ 3896 3897 case ADIVW, AREM: 3898 return OPVCC(31, 491, 0, 0) 3899 3900 case ADIVWCC: 3901 return OPVCC(31, 491, 0, 1) 3902 3903 case ADIVWV: 3904 return OPVCC(31, 491, 1, 0) 3905 3906 case ADIVWVCC: 3907 return OPVCC(31, 491, 1, 1) 3908 3909 case ADIVWU, AREMU: 3910 return OPVCC(31, 459, 0, 0) 3911 3912 case ADIVWUCC: 3913 return OPVCC(31, 459, 0, 1) 3914 3915 case ADIVWUV: 3916 return OPVCC(31, 459, 1, 0) 3917 3918 case ADIVWUVCC: 3919 return OPVCC(31, 459, 1, 1) 3920 3921 case ADIVD, AREMD: 3922 return OPVCC(31, 489, 0, 0) 3923 3924 case ADIVDCC: 3925 return OPVCC(31, 489, 0, 1) 3926 3927 case ADIVDE: 3928 return OPVCC(31, 425, 0, 0) 3929 3930 case ADIVDECC: 3931 return OPVCC(31, 425, 0, 1) 3932 3933 case ADIVDEU: 3934 return OPVCC(31, 393, 0, 0) 3935 3936 case ADIVDEUCC: 3937 return OPVCC(31, 393, 0, 1) 3938 3939 case ADIVDV: 3940 return OPVCC(31, 489, 1, 0) 3941 3942 case ADIVDVCC: 3943 return OPVCC(31, 489, 1, 1) 3944 3945 case ADIVDU, AREMDU: 3946 return OPVCC(31, 457, 0, 0) 3947 3948 case ADIVDUCC: 3949 return OPVCC(31, 457, 0, 1) 3950 3951 case ADIVDUV: 3952 return OPVCC(31, 457, 1, 0) 3953 3954 case ADIVDUVCC: 3955 return OPVCC(31, 457, 1, 1) 3956 3957 case AEIEIO: 3958 return OPVCC(31, 854, 0, 0) 3959 3960 case AEQV: 3961 return OPVCC(31, 284, 0, 0) 3962 case AEQVCC: 3963 return OPVCC(31, 284, 0, 1) 3964 3965 case AEXTSB: 3966 return OPVCC(31, 954, 0, 0) 3967 case AEXTSBCC: 3968 return OPVCC(31, 954, 0, 1) 3969 case AEXTSH: 3970 return OPVCC(31, 922, 0, 0) 3971 case AEXTSHCC: 3972 return OPVCC(31, 922, 0, 1) 3973 case AEXTSW: 3974 return OPVCC(31, 986, 0, 0) 3975 case AEXTSWCC: 3976 return OPVCC(31, 986, 0, 1) 3977 3978 case AFABS: 3979 return OPVCC(63, 264, 0, 0) 3980 case AFABSCC: 3981 return OPVCC(63, 264, 0, 1) 3982 case AFADD: 3983 return OPVCC(63, 21, 0, 0) 3984 case AFADDCC: 3985 return OPVCC(63, 21, 0, 1) 3986 case AFADDS: 3987 return OPVCC(59, 21, 0, 0) 3988 case AFADDSCC: 3989 return OPVCC(59, 21, 0, 1) 3990 case AFCMPO: 3991 return OPVCC(63, 32, 0, 0) 3992 case AFCMPU: 3993 return OPVCC(63, 0, 0, 0) 3994 case AFCFID: 3995 return OPVCC(63, 846, 0, 0) 3996 case AFCFIDCC: 3997 return OPVCC(63, 846, 0, 1) 3998 case AFCFIDU: 3999 return OPVCC(63, 974, 0, 0) 4000 case AFCFIDUCC: 4001 return OPVCC(63, 974, 0, 1) 4002 case AFCFIDS: 4003 return OPVCC(59, 846, 0, 0) 4004 case AFCFIDSCC: 4005 return OPVCC(59, 846, 0, 1) 4006 case AFCTIW: 4007 return OPVCC(63, 14, 0, 0) 4008 case AFCTIWCC: 4009 return OPVCC(63, 14, 0, 1) 4010 case AFCTIWZ: 4011 return OPVCC(63, 15, 0, 0) 4012 case AFCTIWZCC: 4013 return OPVCC(63, 15, 0, 1) 4014 case AFCTID: 4015 return OPVCC(63, 814, 0, 0) 4016 case AFCTIDCC: 4017 return OPVCC(63, 814, 0, 1) 4018 case AFCTIDZ: 4019 return OPVCC(63, 815, 0, 0) 4020 case AFCTIDZCC: 4021 return OPVCC(63, 815, 0, 1) 4022 case AFDIV: 4023 return OPVCC(63, 18, 0, 0) 4024 case AFDIVCC: 4025 return OPVCC(63, 18, 0, 1) 4026 case AFDIVS: 4027 return OPVCC(59, 18, 0, 0) 4028 case AFDIVSCC: 4029 return OPVCC(59, 18, 0, 1) 4030 case AFMADD: 4031 return OPVCC(63, 29, 0, 0) 4032 case AFMADDCC: 4033 return OPVCC(63, 29, 0, 1) 4034 case AFMADDS: 4035 return OPVCC(59, 29, 0, 0) 4036 case AFMADDSCC: 4037 return OPVCC(59, 29, 0, 1) 4038 4039 case AFMOVS, AFMOVD: 4040 return OPVCC(63, 72, 0, 0) /* load */ 4041 case AFMOVDCC: 4042 return OPVCC(63, 72, 0, 1) 4043 case AFMSUB: 4044 return OPVCC(63, 28, 0, 0) 4045 case AFMSUBCC: 4046 return OPVCC(63, 28, 0, 1) 4047 case AFMSUBS: 4048 return OPVCC(59, 28, 0, 0) 4049 case AFMSUBSCC: 4050 return OPVCC(59, 28, 0, 1) 4051 case AFMUL: 4052 return OPVCC(63, 25, 0, 0) 4053 case AFMULCC: 4054 return OPVCC(63, 25, 0, 1) 4055 case AFMULS: 4056 return OPVCC(59, 25, 0, 0) 4057 case AFMULSCC: 4058 return OPVCC(59, 25, 0, 1) 4059 case AFNABS: 4060 return OPVCC(63, 136, 0, 0) 4061 case AFNABSCC: 4062 return OPVCC(63, 136, 0, 1) 4063 case AFNEG: 4064 return OPVCC(63, 40, 0, 0) 4065 case AFNEGCC: 4066 return OPVCC(63, 40, 0, 1) 4067 case AFNMADD: 4068 return OPVCC(63, 31, 0, 0) 4069 case AFNMADDCC: 4070 return OPVCC(63, 31, 0, 1) 4071 case AFNMADDS: 4072 return OPVCC(59, 31, 0, 0) 4073 case AFNMADDSCC: 4074 return OPVCC(59, 31, 0, 1) 4075 case AFNMSUB: 4076 return OPVCC(63, 30, 0, 0) 4077 case AFNMSUBCC: 4078 return OPVCC(63, 30, 0, 1) 4079 case AFNMSUBS: 4080 return OPVCC(59, 30, 0, 0) 4081 case AFNMSUBSCC: 4082 return OPVCC(59, 30, 0, 1) 4083 case AFCPSGN: 4084 return OPVCC(63, 8, 0, 0) 4085 case AFCPSGNCC: 4086 return OPVCC(63, 8, 0, 1) 4087 case AFRES: 4088 return OPVCC(59, 24, 0, 0) 4089 case AFRESCC: 4090 return OPVCC(59, 24, 0, 1) 4091 case AFRIM: 4092 return OPVCC(63, 488, 0, 0) 4093 case AFRIMCC: 4094 return OPVCC(63, 488, 0, 1) 4095 case AFRIP: 4096 return OPVCC(63, 456, 0, 0) 4097 case AFRIPCC: 4098 return OPVCC(63, 456, 0, 1) 4099 case AFRIZ: 4100 return OPVCC(63, 424, 0, 0) 4101 case AFRIZCC: 4102 return OPVCC(63, 424, 0, 1) 4103 case AFRIN: 4104 return OPVCC(63, 392, 0, 0) 4105 case AFRINCC: 4106 return OPVCC(63, 392, 0, 1) 4107 case AFRSP: 4108 return OPVCC(63, 12, 0, 0) 4109 case AFRSPCC: 4110 return OPVCC(63, 12, 0, 1) 4111 case AFRSQRTE: 4112 return OPVCC(63, 26, 0, 0) 4113 case AFRSQRTECC: 4114 return OPVCC(63, 26, 0, 1) 4115 case AFSEL: 4116 return OPVCC(63, 23, 0, 0) 4117 case AFSELCC: 4118 return OPVCC(63, 23, 0, 1) 4119 case AFSQRT: 4120 return OPVCC(63, 22, 0, 0) 4121 case AFSQRTCC: 4122 return OPVCC(63, 22, 0, 1) 4123 case AFSQRTS: 4124 return OPVCC(59, 22, 0, 0) 4125 case AFSQRTSCC: 4126 return OPVCC(59, 22, 0, 1) 4127 case AFSUB: 4128 return OPVCC(63, 20, 0, 0) 4129 case AFSUBCC: 4130 return OPVCC(63, 20, 0, 1) 4131 case AFSUBS: 4132 return OPVCC(59, 20, 0, 0) 4133 case AFSUBSCC: 4134 return OPVCC(59, 20, 0, 1) 4135 4136 case AICBI: 4137 return OPVCC(31, 982, 0, 0) 4138 case AISYNC: 4139 return OPVCC(19, 150, 0, 0) 4140 4141 case AMTFSB0: 4142 return OPVCC(63, 70, 0, 0) 4143 case AMTFSB0CC: 4144 return OPVCC(63, 70, 0, 1) 4145 case AMTFSB1: 4146 return OPVCC(63, 38, 0, 0) 4147 case AMTFSB1CC: 4148 return OPVCC(63, 38, 0, 1) 4149 4150 case AMULHW: 4151 return OPVCC(31, 75, 0, 0) 4152 case AMULHWCC: 4153 return OPVCC(31, 75, 0, 1) 4154 case AMULHWU: 4155 return OPVCC(31, 11, 0, 0) 4156 case AMULHWUCC: 4157 return OPVCC(31, 11, 0, 1) 4158 case AMULLW: 4159 return OPVCC(31, 235, 0, 0) 4160 case AMULLWCC: 4161 return OPVCC(31, 235, 0, 1) 4162 case AMULLWV: 4163 return OPVCC(31, 235, 1, 0) 4164 case AMULLWVCC: 4165 return OPVCC(31, 235, 1, 1) 4166 4167 case AMULHD: 4168 return OPVCC(31, 73, 0, 0) 4169 case AMULHDCC: 4170 return OPVCC(31, 73, 0, 1) 4171 case AMULHDU: 4172 return OPVCC(31, 9, 0, 0) 4173 case AMULHDUCC: 4174 return OPVCC(31, 9, 0, 1) 4175 case AMULLD: 4176 return OPVCC(31, 233, 0, 0) 4177 case AMULLDCC: 4178 return OPVCC(31, 233, 0, 1) 4179 case AMULLDV: 4180 return OPVCC(31, 233, 1, 0) 4181 case AMULLDVCC: 4182 return OPVCC(31, 233, 1, 1) 4183 4184 case ANAND: 4185 return OPVCC(31, 476, 0, 0) 4186 case ANANDCC: 4187 return OPVCC(31, 476, 0, 1) 4188 case ANEG: 4189 return OPVCC(31, 104, 0, 0) 4190 case ANEGCC: 4191 return OPVCC(31, 104, 0, 1) 4192 case ANEGV: 4193 return OPVCC(31, 104, 1, 0) 4194 case ANEGVCC: 4195 return OPVCC(31, 104, 1, 1) 4196 case ANOR: 4197 return OPVCC(31, 124, 0, 0) 4198 case ANORCC: 4199 return OPVCC(31, 124, 0, 1) 4200 case AOR: 4201 return OPVCC(31, 444, 0, 0) 4202 case AORCC: 4203 return OPVCC(31, 444, 0, 1) 4204 case AORN: 4205 return OPVCC(31, 412, 0, 0) 4206 case AORNCC: 4207 return OPVCC(31, 412, 0, 1) 4208 4209 case APOPCNTD: 4210 return OPVCC(31, 506, 0, 0) /* popcntd - v2.06 */ 4211 case APOPCNTW: 4212 return OPVCC(31, 378, 0, 0) /* popcntw - v2.06 */ 4213 case APOPCNTB: 4214 return OPVCC(31, 122, 0, 0) /* popcntb - v2.02 */ 4215 case ACNTTZW: 4216 return OPVCC(31, 538, 0, 0) /* cnttzw - v3.00 */ 4217 case ACNTTZWCC: 4218 return OPVCC(31, 538, 0, 1) /* cnttzw. - v3.00 */ 4219 case ACNTTZD: 4220 return OPVCC(31, 570, 0, 0) /* cnttzd - v3.00 */ 4221 case ACNTTZDCC: 4222 return OPVCC(31, 570, 0, 1) /* cnttzd. - v3.00 */ 4223 4224 case ARFI: 4225 return OPVCC(19, 50, 0, 0) 4226 case ARFCI: 4227 return OPVCC(19, 51, 0, 0) 4228 case ARFID: 4229 return OPVCC(19, 18, 0, 0) 4230 case AHRFID: 4231 return OPVCC(19, 274, 0, 0) 4232 4233 case ARLWMI: 4234 return OPVCC(20, 0, 0, 0) 4235 case ARLWMICC: 4236 return OPVCC(20, 0, 0, 1) 4237 case ARLWNM: 4238 return OPVCC(23, 0, 0, 0) 4239 case ARLWNMCC: 4240 return OPVCC(23, 0, 0, 1) 4241 4242 case ARLDCL: 4243 return OPVCC(30, 8, 0, 0) 4244 case ARLDCLCC: 4245 return OPVCC(30, 0, 0, 1) 4246 4247 case ARLDCR: 4248 return OPVCC(30, 9, 0, 0) 4249 case ARLDCRCC: 4250 return OPVCC(30, 9, 0, 1) 4251 4252 case ARLDICL: 4253 return OPVCC(30, 0, 0, 0) 4254 case ARLDICLCC: 4255 return OPVCC(30, 0, 0, 1) 4256 case ARLDICR: 4257 return OPMD(30, 1, 0) // rldicr 4258 case ARLDICRCC: 4259 return OPMD(30, 1, 1) // rldicr. 4260 4261 case ARLDIC: 4262 return OPMD(30, 2, 0) // rldic 4263 case ARLDICCC: 4264 return OPMD(30, 2, 1) // rldic. 4265 4266 case ASYSCALL: 4267 return OPVCC(17, 1, 0, 0) 4268 4269 case ASLW: 4270 return OPVCC(31, 24, 0, 0) 4271 case ASLWCC: 4272 return OPVCC(31, 24, 0, 1) 4273 case ASLD: 4274 return OPVCC(31, 27, 0, 0) 4275 case ASLDCC: 4276 return OPVCC(31, 27, 0, 1) 4277 4278 case ASRAW: 4279 return OPVCC(31, 792, 0, 0) 4280 case ASRAWCC: 4281 return OPVCC(31, 792, 0, 1) 4282 case ASRAD: 4283 return OPVCC(31, 794, 0, 0) 4284 case ASRADCC: 4285 return OPVCC(31, 794, 0, 1) 4286 4287 case AEXTSWSLI: 4288 return OPVCC(31, 445, 0, 0) 4289 case AEXTSWSLICC: 4290 return OPVCC(31, 445, 0, 1) 4291 4292 case ASRW: 4293 return OPVCC(31, 536, 0, 0) 4294 case ASRWCC: 4295 return OPVCC(31, 536, 0, 1) 4296 case ASRD: 4297 return OPVCC(31, 539, 0, 0) 4298 case ASRDCC: 4299 return OPVCC(31, 539, 0, 1) 4300 4301 case ASUB: 4302 return OPVCC(31, 40, 0, 0) 4303 case ASUBCC: 4304 return OPVCC(31, 40, 0, 1) 4305 case ASUBV: 4306 return OPVCC(31, 40, 1, 0) 4307 case ASUBVCC: 4308 return OPVCC(31, 40, 1, 1) 4309 case ASUBC: 4310 return OPVCC(31, 8, 0, 0) 4311 case ASUBCCC: 4312 return OPVCC(31, 8, 0, 1) 4313 case ASUBCV: 4314 return OPVCC(31, 8, 1, 0) 4315 case ASUBCVCC: 4316 return OPVCC(31, 8, 1, 1) 4317 case ASUBE: 4318 return OPVCC(31, 136, 0, 0) 4319 case ASUBECC: 4320 return OPVCC(31, 136, 0, 1) 4321 case ASUBEV: 4322 return OPVCC(31, 136, 1, 0) 4323 case ASUBEVCC: 4324 return OPVCC(31, 136, 1, 1) 4325 case ASUBME: 4326 return OPVCC(31, 232, 0, 0) 4327 case ASUBMECC: 4328 return OPVCC(31, 232, 0, 1) 4329 case ASUBMEV: 4330 return OPVCC(31, 232, 1, 0) 4331 case ASUBMEVCC: 4332 return OPVCC(31, 232, 1, 1) 4333 case ASUBZE: 4334 return OPVCC(31, 200, 0, 0) 4335 case ASUBZECC: 4336 return OPVCC(31, 200, 0, 1) 4337 case ASUBZEV: 4338 return OPVCC(31, 200, 1, 0) 4339 case ASUBZEVCC: 4340 return OPVCC(31, 200, 1, 1) 4341 4342 case ASYNC: 4343 return OPVCC(31, 598, 0, 0) 4344 case ALWSYNC: 4345 return OPVCC(31, 598, 0, 0) | 1<<21 4346 4347 case APTESYNC: 4348 return OPVCC(31, 598, 0, 0) | 2<<21 4349 4350 case ATLBIE: 4351 return OPVCC(31, 306, 0, 0) 4352 case ATLBIEL: 4353 return OPVCC(31, 274, 0, 0) 4354 case ATLBSYNC: 4355 return OPVCC(31, 566, 0, 0) 4356 case ASLBIA: 4357 return OPVCC(31, 498, 0, 0) 4358 case ASLBIE: 4359 return OPVCC(31, 434, 0, 0) 4360 case ASLBMFEE: 4361 return OPVCC(31, 915, 0, 0) 4362 case ASLBMFEV: 4363 return OPVCC(31, 851, 0, 0) 4364 case ASLBMTE: 4365 return OPVCC(31, 402, 0, 0) 4366 4367 case ATW: 4368 return OPVCC(31, 4, 0, 0) 4369 case ATD: 4370 return OPVCC(31, 68, 0, 0) 4371 4372 /* Vector (VMX/Altivec) instructions */ 4373 /* ISA 2.03 enables these for PPC970. For POWERx processors, these */ 4374 /* are enabled starting at POWER6 (ISA 2.05). */ 4375 case AVAND: 4376 return OPVX(4, 1028, 0, 0) /* vand - v2.03 */ 4377 case AVANDC: 4378 return OPVX(4, 1092, 0, 0) /* vandc - v2.03 */ 4379 case AVNAND: 4380 return OPVX(4, 1412, 0, 0) /* vnand - v2.07 */ 4381 4382 case AVOR: 4383 return OPVX(4, 1156, 0, 0) /* vor - v2.03 */ 4384 case AVORC: 4385 return OPVX(4, 1348, 0, 0) /* vorc - v2.07 */ 4386 case AVNOR: 4387 return OPVX(4, 1284, 0, 0) /* vnor - v2.03 */ 4388 case AVXOR: 4389 return OPVX(4, 1220, 0, 0) /* vxor - v2.03 */ 4390 case AVEQV: 4391 return OPVX(4, 1668, 0, 0) /* veqv - v2.07 */ 4392 4393 case AVADDUBM: 4394 return OPVX(4, 0, 0, 0) /* vaddubm - v2.03 */ 4395 case AVADDUHM: 4396 return OPVX(4, 64, 0, 0) /* vadduhm - v2.03 */ 4397 case AVADDUWM: 4398 return OPVX(4, 128, 0, 0) /* vadduwm - v2.03 */ 4399 case AVADDUDM: 4400 return OPVX(4, 192, 0, 0) /* vaddudm - v2.07 */ 4401 case AVADDUQM: 4402 return OPVX(4, 256, 0, 0) /* vadduqm - v2.07 */ 4403 4404 case AVADDCUQ: 4405 return OPVX(4, 320, 0, 0) /* vaddcuq - v2.07 */ 4406 case AVADDCUW: 4407 return OPVX(4, 384, 0, 0) /* vaddcuw - v2.03 */ 4408 4409 case AVADDUBS: 4410 return OPVX(4, 512, 0, 0) /* vaddubs - v2.03 */ 4411 case AVADDUHS: 4412 return OPVX(4, 576, 0, 0) /* vadduhs - v2.03 */ 4413 case AVADDUWS: 4414 return OPVX(4, 640, 0, 0) /* vadduws - v2.03 */ 4415 4416 case AVADDSBS: 4417 return OPVX(4, 768, 0, 0) /* vaddsbs - v2.03 */ 4418 case AVADDSHS: 4419 return OPVX(4, 832, 0, 0) /* vaddshs - v2.03 */ 4420 case AVADDSWS: 4421 return OPVX(4, 896, 0, 0) /* vaddsws - v2.03 */ 4422 4423 case AVADDEUQM: 4424 return OPVX(4, 60, 0, 0) /* vaddeuqm - v2.07 */ 4425 case AVADDECUQ: 4426 return OPVX(4, 61, 0, 0) /* vaddecuq - v2.07 */ 4427 4428 case AVMULESB: 4429 return OPVX(4, 776, 0, 0) /* vmulesb - v2.03 */ 4430 case AVMULOSB: 4431 return OPVX(4, 264, 0, 0) /* vmulosb - v2.03 */ 4432 case AVMULEUB: 4433 return OPVX(4, 520, 0, 0) /* vmuleub - v2.03 */ 4434 case AVMULOUB: 4435 return OPVX(4, 8, 0, 0) /* vmuloub - v2.03 */ 4436 case AVMULESH: 4437 return OPVX(4, 840, 0, 0) /* vmulesh - v2.03 */ 4438 case AVMULOSH: 4439 return OPVX(4, 328, 0, 0) /* vmulosh - v2.03 */ 4440 case AVMULEUH: 4441 return OPVX(4, 584, 0, 0) /* vmuleuh - v2.03 */ 4442 case AVMULOUH: 4443 return OPVX(4, 72, 0, 0) /* vmulouh - v2.03 */ 4444 case AVMULESW: 4445 return OPVX(4, 904, 0, 0) /* vmulesw - v2.07 */ 4446 case AVMULOSW: 4447 return OPVX(4, 392, 0, 0) /* vmulosw - v2.07 */ 4448 case AVMULEUW: 4449 return OPVX(4, 648, 0, 0) /* vmuleuw - v2.07 */ 4450 case AVMULOUW: 4451 return OPVX(4, 136, 0, 0) /* vmulouw - v2.07 */ 4452 case AVMULUWM: 4453 return OPVX(4, 137, 0, 0) /* vmuluwm - v2.07 */ 4454 4455 case AVPMSUMB: 4456 return OPVX(4, 1032, 0, 0) /* vpmsumb - v2.07 */ 4457 case AVPMSUMH: 4458 return OPVX(4, 1096, 0, 0) /* vpmsumh - v2.07 */ 4459 case AVPMSUMW: 4460 return OPVX(4, 1160, 0, 0) /* vpmsumw - v2.07 */ 4461 case AVPMSUMD: 4462 return OPVX(4, 1224, 0, 0) /* vpmsumd - v2.07 */ 4463 4464 case AVMSUMUDM: 4465 return OPVX(4, 35, 0, 0) /* vmsumudm - v3.00b */ 4466 4467 case AVSUBUBM: 4468 return OPVX(4, 1024, 0, 0) /* vsububm - v2.03 */ 4469 case AVSUBUHM: 4470 return OPVX(4, 1088, 0, 0) /* vsubuhm - v2.03 */ 4471 case AVSUBUWM: 4472 return OPVX(4, 1152, 0, 0) /* vsubuwm - v2.03 */ 4473 case AVSUBUDM: 4474 return OPVX(4, 1216, 0, 0) /* vsubudm - v2.07 */ 4475 case AVSUBUQM: 4476 return OPVX(4, 1280, 0, 0) /* vsubuqm - v2.07 */ 4477 4478 case AVSUBCUQ: 4479 return OPVX(4, 1344, 0, 0) /* vsubcuq - v2.07 */ 4480 case AVSUBCUW: 4481 return OPVX(4, 1408, 0, 0) /* vsubcuw - v2.03 */ 4482 4483 case AVSUBUBS: 4484 return OPVX(4, 1536, 0, 0) /* vsububs - v2.03 */ 4485 case AVSUBUHS: 4486 return OPVX(4, 1600, 0, 0) /* vsubuhs - v2.03 */ 4487 case AVSUBUWS: 4488 return OPVX(4, 1664, 0, 0) /* vsubuws - v2.03 */ 4489 4490 case AVSUBSBS: 4491 return OPVX(4, 1792, 0, 0) /* vsubsbs - v2.03 */ 4492 case AVSUBSHS: 4493 return OPVX(4, 1856, 0, 0) /* vsubshs - v2.03 */ 4494 case AVSUBSWS: 4495 return OPVX(4, 1920, 0, 0) /* vsubsws - v2.03 */ 4496 4497 case AVSUBEUQM: 4498 return OPVX(4, 62, 0, 0) /* vsubeuqm - v2.07 */ 4499 case AVSUBECUQ: 4500 return OPVX(4, 63, 0, 0) /* vsubecuq - v2.07 */ 4501 4502 case AVRLB: 4503 return OPVX(4, 4, 0, 0) /* vrlb - v2.03 */ 4504 case AVRLH: 4505 return OPVX(4, 68, 0, 0) /* vrlh - v2.03 */ 4506 case AVRLW: 4507 return OPVX(4, 132, 0, 0) /* vrlw - v2.03 */ 4508 case AVRLD: 4509 return OPVX(4, 196, 0, 0) /* vrld - v2.07 */ 4510 4511 case AVMRGOW: 4512 return OPVX(4, 1676, 0, 0) /* vmrgow - v2.07 */ 4513 case AVMRGEW: 4514 return OPVX(4, 1932, 0, 0) /* vmrgew - v2.07 */ 4515 4516 case AVSLB: 4517 return OPVX(4, 260, 0, 0) /* vslh - v2.03 */ 4518 case AVSLH: 4519 return OPVX(4, 324, 0, 0) /* vslh - v2.03 */ 4520 case AVSLW: 4521 return OPVX(4, 388, 0, 0) /* vslw - v2.03 */ 4522 case AVSL: 4523 return OPVX(4, 452, 0, 0) /* vsl - v2.03 */ 4524 case AVSLO: 4525 return OPVX(4, 1036, 0, 0) /* vsl - v2.03 */ 4526 case AVSRB: 4527 return OPVX(4, 516, 0, 0) /* vsrb - v2.03 */ 4528 case AVSRH: 4529 return OPVX(4, 580, 0, 0) /* vsrh - v2.03 */ 4530 case AVSRW: 4531 return OPVX(4, 644, 0, 0) /* vsrw - v2.03 */ 4532 case AVSR: 4533 return OPVX(4, 708, 0, 0) /* vsr - v2.03 */ 4534 case AVSRO: 4535 return OPVX(4, 1100, 0, 0) /* vsro - v2.03 */ 4536 case AVSLD: 4537 return OPVX(4, 1476, 0, 0) /* vsld - v2.07 */ 4538 case AVSRD: 4539 return OPVX(4, 1732, 0, 0) /* vsrd - v2.07 */ 4540 4541 case AVSRAB: 4542 return OPVX(4, 772, 0, 0) /* vsrab - v2.03 */ 4543 case AVSRAH: 4544 return OPVX(4, 836, 0, 0) /* vsrah - v2.03 */ 4545 case AVSRAW: 4546 return OPVX(4, 900, 0, 0) /* vsraw - v2.03 */ 4547 case AVSRAD: 4548 return OPVX(4, 964, 0, 0) /* vsrad - v2.07 */ 4549 4550 case AVBPERMQ: 4551 return OPVC(4, 1356, 0, 0) /* vbpermq - v2.07 */ 4552 case AVBPERMD: 4553 return OPVC(4, 1484, 0, 0) /* vbpermd - v3.00 */ 4554 4555 case AVCLZB: 4556 return OPVX(4, 1794, 0, 0) /* vclzb - v2.07 */ 4557 case AVCLZH: 4558 return OPVX(4, 1858, 0, 0) /* vclzh - v2.07 */ 4559 case AVCLZW: 4560 return OPVX(4, 1922, 0, 0) /* vclzw - v2.07 */ 4561 case AVCLZD: 4562 return OPVX(4, 1986, 0, 0) /* vclzd - v2.07 */ 4563 4564 case AVPOPCNTB: 4565 return OPVX(4, 1795, 0, 0) /* vpopcntb - v2.07 */ 4566 case AVPOPCNTH: 4567 return OPVX(4, 1859, 0, 0) /* vpopcnth - v2.07 */ 4568 case AVPOPCNTW: 4569 return OPVX(4, 1923, 0, 0) /* vpopcntw - v2.07 */ 4570 case AVPOPCNTD: 4571 return OPVX(4, 1987, 0, 0) /* vpopcntd - v2.07 */ 4572 4573 case AVCMPEQUB: 4574 return OPVC(4, 6, 0, 0) /* vcmpequb - v2.03 */ 4575 case AVCMPEQUBCC: 4576 return OPVC(4, 6, 0, 1) /* vcmpequb. - v2.03 */ 4577 case AVCMPEQUH: 4578 return OPVC(4, 70, 0, 0) /* vcmpequh - v2.03 */ 4579 case AVCMPEQUHCC: 4580 return OPVC(4, 70, 0, 1) /* vcmpequh. - v2.03 */ 4581 case AVCMPEQUW: 4582 return OPVC(4, 134, 0, 0) /* vcmpequw - v2.03 */ 4583 case AVCMPEQUWCC: 4584 return OPVC(4, 134, 0, 1) /* vcmpequw. - v2.03 */ 4585 case AVCMPEQUD: 4586 return OPVC(4, 199, 0, 0) /* vcmpequd - v2.07 */ 4587 case AVCMPEQUDCC: 4588 return OPVC(4, 199, 0, 1) /* vcmpequd. - v2.07 */ 4589 4590 case AVCMPGTUB: 4591 return OPVC(4, 518, 0, 0) /* vcmpgtub - v2.03 */ 4592 case AVCMPGTUBCC: 4593 return OPVC(4, 518, 0, 1) /* vcmpgtub. - v2.03 */ 4594 case AVCMPGTUH: 4595 return OPVC(4, 582, 0, 0) /* vcmpgtuh - v2.03 */ 4596 case AVCMPGTUHCC: 4597 return OPVC(4, 582, 0, 1) /* vcmpgtuh. - v2.03 */ 4598 case AVCMPGTUW: 4599 return OPVC(4, 646, 0, 0) /* vcmpgtuw - v2.03 */ 4600 case AVCMPGTUWCC: 4601 return OPVC(4, 646, 0, 1) /* vcmpgtuw. - v2.03 */ 4602 case AVCMPGTUD: 4603 return OPVC(4, 711, 0, 0) /* vcmpgtud - v2.07 */ 4604 case AVCMPGTUDCC: 4605 return OPVC(4, 711, 0, 1) /* vcmpgtud. v2.07 */ 4606 case AVCMPGTSB: 4607 return OPVC(4, 774, 0, 0) /* vcmpgtsb - v2.03 */ 4608 case AVCMPGTSBCC: 4609 return OPVC(4, 774, 0, 1) /* vcmpgtsb. - v2.03 */ 4610 case AVCMPGTSH: 4611 return OPVC(4, 838, 0, 0) /* vcmpgtsh - v2.03 */ 4612 case AVCMPGTSHCC: 4613 return OPVC(4, 838, 0, 1) /* vcmpgtsh. - v2.03 */ 4614 case AVCMPGTSW: 4615 return OPVC(4, 902, 0, 0) /* vcmpgtsw - v2.03 */ 4616 case AVCMPGTSWCC: 4617 return OPVC(4, 902, 0, 1) /* vcmpgtsw. - v2.03 */ 4618 case AVCMPGTSD: 4619 return OPVC(4, 967, 0, 0) /* vcmpgtsd - v2.07 */ 4620 case AVCMPGTSDCC: 4621 return OPVC(4, 967, 0, 1) /* vcmpgtsd. - v2.07 */ 4622 4623 case AVCMPNEZB: 4624 return OPVC(4, 263, 0, 0) /* vcmpnezb - v3.00 */ 4625 case AVCMPNEZBCC: 4626 return OPVC(4, 263, 0, 1) /* vcmpnezb. - v3.00 */ 4627 case AVCMPNEB: 4628 return OPVC(4, 7, 0, 0) /* vcmpneb - v3.00 */ 4629 case AVCMPNEBCC: 4630 return OPVC(4, 7, 0, 1) /* vcmpneb. - v3.00 */ 4631 case AVCMPNEH: 4632 return OPVC(4, 71, 0, 0) /* vcmpneh - v3.00 */ 4633 case AVCMPNEHCC: 4634 return OPVC(4, 71, 0, 1) /* vcmpneh. - v3.00 */ 4635 case AVCMPNEW: 4636 return OPVC(4, 135, 0, 0) /* vcmpnew - v3.00 */ 4637 case AVCMPNEWCC: 4638 return OPVC(4, 135, 0, 1) /* vcmpnew. - v3.00 */ 4639 4640 case AVPERM: 4641 return OPVX(4, 43, 0, 0) /* vperm - v2.03 */ 4642 case AVPERMXOR: 4643 return OPVX(4, 45, 0, 0) /* vpermxor - v2.03 */ 4644 case AVPERMR: 4645 return OPVX(4, 59, 0, 0) /* vpermr - v3.0 */ 4646 4647 case AVSEL: 4648 return OPVX(4, 42, 0, 0) /* vsel - v2.03 */ 4649 4650 case AVCIPHER: 4651 return OPVX(4, 1288, 0, 0) /* vcipher - v2.07 */ 4652 case AVCIPHERLAST: 4653 return OPVX(4, 1289, 0, 0) /* vcipherlast - v2.07 */ 4654 case AVNCIPHER: 4655 return OPVX(4, 1352, 0, 0) /* vncipher - v2.07 */ 4656 case AVNCIPHERLAST: 4657 return OPVX(4, 1353, 0, 0) /* vncipherlast - v2.07 */ 4658 case AVSBOX: 4659 return OPVX(4, 1480, 0, 0) /* vsbox - v2.07 */ 4660 /* End of vector instructions */ 4661 4662 /* Vector scalar (VSX) instructions */ 4663 /* ISA 2.06 enables these for POWER7. */ 4664 case AMFVSRD, AMFVRD, AMFFPRD: 4665 return OPVXX1(31, 51, 0) /* mfvsrd - v2.07 */ 4666 case AMFVSRWZ: 4667 return OPVXX1(31, 115, 0) /* mfvsrwz - v2.07 */ 4668 case AMFVSRLD: 4669 return OPVXX1(31, 307, 0) /* mfvsrld - v3.00 */ 4670 4671 case AMTVSRD, AMTFPRD, AMTVRD: 4672 return OPVXX1(31, 179, 0) /* mtvsrd - v2.07 */ 4673 case AMTVSRWA: 4674 return OPVXX1(31, 211, 0) /* mtvsrwa - v2.07 */ 4675 case AMTVSRWZ: 4676 return OPVXX1(31, 243, 0) /* mtvsrwz - v2.07 */ 4677 case AMTVSRDD: 4678 return OPVXX1(31, 435, 0) /* mtvsrdd - v3.00 */ 4679 case AMTVSRWS: 4680 return OPVXX1(31, 403, 0) /* mtvsrws - v3.00 */ 4681 4682 case AXXLAND: 4683 return OPVXX3(60, 130, 0) /* xxland - v2.06 */ 4684 case AXXLANDC: 4685 return OPVXX3(60, 138, 0) /* xxlandc - v2.06 */ 4686 case AXXLEQV: 4687 return OPVXX3(60, 186, 0) /* xxleqv - v2.07 */ 4688 case AXXLNAND: 4689 return OPVXX3(60, 178, 0) /* xxlnand - v2.07 */ 4690 4691 case AXXLORC: 4692 return OPVXX3(60, 170, 0) /* xxlorc - v2.07 */ 4693 case AXXLNOR: 4694 return OPVXX3(60, 162, 0) /* xxlnor - v2.06 */ 4695 case AXXLOR, AXXLORQ: 4696 return OPVXX3(60, 146, 0) /* xxlor - v2.06 */ 4697 case AXXLXOR: 4698 return OPVXX3(60, 154, 0) /* xxlxor - v2.06 */ 4699 4700 case AXXSEL: 4701 return OPVXX4(60, 3, 0) /* xxsel - v2.06 */ 4702 4703 case AXXMRGHW: 4704 return OPVXX3(60, 18, 0) /* xxmrghw - v2.06 */ 4705 case AXXMRGLW: 4706 return OPVXX3(60, 50, 0) /* xxmrglw - v2.06 */ 4707 4708 case AXXSPLTW: 4709 return OPVXX2(60, 164, 0) /* xxspltw - v2.06 */ 4710 4711 case AXXSPLTIB: 4712 return OPVCC(60, 360, 0, 0) /* xxspltib - v3.0 */ 4713 4714 case AXXPERM: 4715 return OPVXX3(60, 26, 0) /* xxperm - v2.06 */ 4716 case AXXPERMDI: 4717 return OPVXX3(60, 10, 0) /* xxpermdi - v2.06 */ 4718 4719 case AXXSLDWI: 4720 return OPVXX3(60, 2, 0) /* xxsldwi - v2.06 */ 4721 4722 case AXXBRQ: 4723 return OPVXX2VA(60, 475, 31) /* xxbrq - v3.0 */ 4724 case AXXBRD: 4725 return OPVXX2VA(60, 475, 23) /* xxbrd - v3.0 */ 4726 case AXXBRW: 4727 return OPVXX2VA(60, 475, 15) /* xxbrw - v3.0 */ 4728 case AXXBRH: 4729 return OPVXX2VA(60, 475, 7) /* xxbrh - v3.0 */ 4730 4731 case AXSCVDPSP: 4732 return OPVXX2(60, 265, 0) /* xscvdpsp - v2.06 */ 4733 case AXSCVSPDP: 4734 return OPVXX2(60, 329, 0) /* xscvspdp - v2.06 */ 4735 case AXSCVDPSPN: 4736 return OPVXX2(60, 267, 0) /* xscvdpspn - v2.07 */ 4737 case AXSCVSPDPN: 4738 return OPVXX2(60, 331, 0) /* xscvspdpn - v2.07 */ 4739 4740 case AXVCVDPSP: 4741 return OPVXX2(60, 393, 0) /* xvcvdpsp - v2.06 */ 4742 case AXVCVSPDP: 4743 return OPVXX2(60, 457, 0) /* xvcvspdp - v2.06 */ 4744 4745 case AXSCVDPSXDS: 4746 return OPVXX2(60, 344, 0) /* xscvdpsxds - v2.06 */ 4747 case AXSCVDPSXWS: 4748 return OPVXX2(60, 88, 0) /* xscvdpsxws - v2.06 */ 4749 case AXSCVDPUXDS: 4750 return OPVXX2(60, 328, 0) /* xscvdpuxds - v2.06 */ 4751 case AXSCVDPUXWS: 4752 return OPVXX2(60, 72, 0) /* xscvdpuxws - v2.06 */ 4753 4754 case AXSCVSXDDP: 4755 return OPVXX2(60, 376, 0) /* xscvsxddp - v2.06 */ 4756 case AXSCVUXDDP: 4757 return OPVXX2(60, 360, 0) /* xscvuxddp - v2.06 */ 4758 case AXSCVSXDSP: 4759 return OPVXX2(60, 312, 0) /* xscvsxdsp - v2.06 */ 4760 case AXSCVUXDSP: 4761 return OPVXX2(60, 296, 0) /* xscvuxdsp - v2.06 */ 4762 4763 case AXVCVDPSXDS: 4764 return OPVXX2(60, 472, 0) /* xvcvdpsxds - v2.06 */ 4765 case AXVCVDPSXWS: 4766 return OPVXX2(60, 216, 0) /* xvcvdpsxws - v2.06 */ 4767 case AXVCVDPUXDS: 4768 return OPVXX2(60, 456, 0) /* xvcvdpuxds - v2.06 */ 4769 case AXVCVDPUXWS: 4770 return OPVXX2(60, 200, 0) /* xvcvdpuxws - v2.06 */ 4771 case AXVCVSPSXDS: 4772 return OPVXX2(60, 408, 0) /* xvcvspsxds - v2.07 */ 4773 case AXVCVSPSXWS: 4774 return OPVXX2(60, 152, 0) /* xvcvspsxws - v2.07 */ 4775 case AXVCVSPUXDS: 4776 return OPVXX2(60, 392, 0) /* xvcvspuxds - v2.07 */ 4777 case AXVCVSPUXWS: 4778 return OPVXX2(60, 136, 0) /* xvcvspuxws - v2.07 */ 4779 4780 case AXVCVSXDDP: 4781 return OPVXX2(60, 504, 0) /* xvcvsxddp - v2.06 */ 4782 case AXVCVSXWDP: 4783 return OPVXX2(60, 248, 0) /* xvcvsxwdp - v2.06 */ 4784 case AXVCVUXDDP: 4785 return OPVXX2(60, 488, 0) /* xvcvuxddp - v2.06 */ 4786 case AXVCVUXWDP: 4787 return OPVXX2(60, 232, 0) /* xvcvuxwdp - v2.06 */ 4788 case AXVCVSXDSP: 4789 return OPVXX2(60, 440, 0) /* xvcvsxdsp - v2.06 */ 4790 case AXVCVSXWSP: 4791 return OPVXX2(60, 184, 0) /* xvcvsxwsp - v2.06 */ 4792 case AXVCVUXDSP: 4793 return OPVXX2(60, 424, 0) /* xvcvuxdsp - v2.06 */ 4794 case AXVCVUXWSP: 4795 return OPVXX2(60, 168, 0) /* xvcvuxwsp - v2.06 */ 4796 /* End of VSX instructions */ 4797 4798 case AMADDHD: 4799 return OPVX(4, 48, 0, 0) /* maddhd - v3.00 */ 4800 case AMADDHDU: 4801 return OPVX(4, 49, 0, 0) /* maddhdu - v3.00 */ 4802 case AMADDLD: 4803 return OPVX(4, 51, 0, 0) /* maddld - v3.00 */ 4804 4805 case AXOR: 4806 return OPVCC(31, 316, 0, 0) 4807 case AXORCC: 4808 return OPVCC(31, 316, 0, 1) 4809 } 4810 4811 c.ctxt.Diag("bad r/r, r/r/r or r/r/r/r opcode %v", a) 4812 return 0 4813} 4814 4815func (c *ctxt9) opirrr(a obj.As) uint32 { 4816 switch a { 4817 /* Vector (VMX/Altivec) instructions */ 4818 /* ISA 2.03 enables these for PPC970. For POWERx processors, these */ 4819 /* are enabled starting at POWER6 (ISA 2.05). */ 4820 case AVSLDOI: 4821 return OPVX(4, 44, 0, 0) /* vsldoi - v2.03 */ 4822 } 4823 4824 c.ctxt.Diag("bad i/r/r/r opcode %v", a) 4825 return 0 4826} 4827 4828func (c *ctxt9) opiirr(a obj.As) uint32 { 4829 switch a { 4830 /* Vector (VMX/Altivec) instructions */ 4831 /* ISA 2.07 enables these for POWER8 and beyond. */ 4832 case AVSHASIGMAW: 4833 return OPVX(4, 1666, 0, 0) /* vshasigmaw - v2.07 */ 4834 case AVSHASIGMAD: 4835 return OPVX(4, 1730, 0, 0) /* vshasigmad - v2.07 */ 4836 } 4837 4838 c.ctxt.Diag("bad i/i/r/r opcode %v", a) 4839 return 0 4840} 4841 4842func (c *ctxt9) opirr(a obj.As) uint32 { 4843 switch a { 4844 case AADD: 4845 return OPVCC(14, 0, 0, 0) 4846 case AADDC: 4847 return OPVCC(12, 0, 0, 0) 4848 case AADDCCC: 4849 return OPVCC(13, 0, 0, 0) 4850 case AADDIS: 4851 return OPVCC(15, 0, 0, 0) /* ADDIS */ 4852 4853 case AANDCC: 4854 return OPVCC(28, 0, 0, 0) 4855 case AANDISCC: 4856 return OPVCC(29, 0, 0, 0) /* ANDIS. */ 4857 4858 case ABR: 4859 return OPVCC(18, 0, 0, 0) 4860 case ABL: 4861 return OPVCC(18, 0, 0, 0) | 1 4862 case obj.ADUFFZERO: 4863 return OPVCC(18, 0, 0, 0) | 1 4864 case obj.ADUFFCOPY: 4865 return OPVCC(18, 0, 0, 0) | 1 4866 case ABC: 4867 return OPVCC(16, 0, 0, 0) 4868 case ABCL: 4869 return OPVCC(16, 0, 0, 0) | 1 4870 4871 case ABEQ: 4872 return AOP_RRR(16<<26, 12, 2, 0) 4873 case ABGE: 4874 return AOP_RRR(16<<26, 4, 0, 0) 4875 case ABGT: 4876 return AOP_RRR(16<<26, 12, 1, 0) 4877 case ABLE: 4878 return AOP_RRR(16<<26, 4, 1, 0) 4879 case ABLT: 4880 return AOP_RRR(16<<26, 12, 0, 0) 4881 case ABNE: 4882 return AOP_RRR(16<<26, 4, 2, 0) 4883 case ABVC: 4884 return AOP_RRR(16<<26, 4, 3, 0) // apparently unordered-clear 4885 case ABVS: 4886 return AOP_RRR(16<<26, 12, 3, 0) // apparently unordered-set 4887 4888 case ACMP: 4889 return OPVCC(11, 0, 0, 0) | 1<<21 /* L=1 */ 4890 case ACMPU: 4891 return OPVCC(10, 0, 0, 0) | 1<<21 4892 case ACMPW: 4893 return OPVCC(11, 0, 0, 0) /* L=0 */ 4894 case ACMPWU: 4895 return OPVCC(10, 0, 0, 0) 4896 case ACMPEQB: 4897 return OPVCC(31, 224, 0, 0) /* cmpeqb - v3.00 */ 4898 4899 case ALSW: 4900 return OPVCC(31, 597, 0, 0) 4901 4902 case ACOPY: 4903 return OPVCC(31, 774, 0, 0) /* copy - v3.00 */ 4904 case APASTECC: 4905 return OPVCC(31, 902, 0, 1) /* paste. - v3.00 */ 4906 case ADARN: 4907 return OPVCC(31, 755, 0, 0) /* darn - v3.00 */ 4908 4909 case AMULLW, AMULLD: 4910 return OPVCC(7, 0, 0, 0) /* mulli works with MULLW or MULLD */ 4911 4912 case AOR: 4913 return OPVCC(24, 0, 0, 0) 4914 case AORIS: 4915 return OPVCC(25, 0, 0, 0) /* ORIS */ 4916 4917 case ARLWMI: 4918 return OPVCC(20, 0, 0, 0) /* rlwimi */ 4919 case ARLWMICC: 4920 return OPVCC(20, 0, 0, 1) 4921 case ARLDMI: 4922 return OPMD(30, 3, 0) /* rldimi */ 4923 case ARLDMICC: 4924 return OPMD(30, 3, 1) /* rldimi. */ 4925 case ARLDIMI: 4926 return OPMD(30, 3, 0) /* rldimi */ 4927 case ARLDIMICC: 4928 return OPMD(30, 3, 1) /* rldimi. */ 4929 case ARLWNM: 4930 return OPVCC(21, 0, 0, 0) /* rlwinm */ 4931 case ARLWNMCC: 4932 return OPVCC(21, 0, 0, 1) 4933 4934 case ARLDCL: 4935 return OPMD(30, 0, 0) /* rldicl */ 4936 case ARLDCLCC: 4937 return OPMD(30, 0, 1) /* rldicl. */ 4938 case ARLDCR: 4939 return OPMD(30, 1, 0) /* rldicr */ 4940 case ARLDCRCC: 4941 return OPMD(30, 1, 1) /* rldicr. */ 4942 case ARLDC: 4943 return OPMD(30, 2, 0) /* rldic */ 4944 case ARLDCCC: 4945 return OPMD(30, 2, 1) /* rldic. */ 4946 4947 case ASRAW: 4948 return OPVCC(31, 824, 0, 0) 4949 case ASRAWCC: 4950 return OPVCC(31, 824, 0, 1) 4951 case ASRAD: 4952 return OPVCC(31, (413 << 1), 0, 0) 4953 case ASRADCC: 4954 return OPVCC(31, (413 << 1), 0, 1) 4955 case AEXTSWSLI: 4956 return OPVCC(31, 445, 0, 0) 4957 case AEXTSWSLICC: 4958 return OPVCC(31, 445, 0, 1) 4959 4960 case ASTSW: 4961 return OPVCC(31, 725, 0, 0) 4962 4963 case ASUBC: 4964 return OPVCC(8, 0, 0, 0) 4965 4966 case ATW: 4967 return OPVCC(3, 0, 0, 0) 4968 case ATD: 4969 return OPVCC(2, 0, 0, 0) 4970 4971 /* Vector (VMX/Altivec) instructions */ 4972 /* ISA 2.03 enables these for PPC970. For POWERx processors, these */ 4973 /* are enabled starting at POWER6 (ISA 2.05). */ 4974 case AVSPLTB: 4975 return OPVX(4, 524, 0, 0) /* vspltb - v2.03 */ 4976 case AVSPLTH: 4977 return OPVX(4, 588, 0, 0) /* vsplth - v2.03 */ 4978 case AVSPLTW: 4979 return OPVX(4, 652, 0, 0) /* vspltw - v2.03 */ 4980 4981 case AVSPLTISB: 4982 return OPVX(4, 780, 0, 0) /* vspltisb - v2.03 */ 4983 case AVSPLTISH: 4984 return OPVX(4, 844, 0, 0) /* vspltish - v2.03 */ 4985 case AVSPLTISW: 4986 return OPVX(4, 908, 0, 0) /* vspltisw - v2.03 */ 4987 /* End of vector instructions */ 4988 4989 case AFTDIV: 4990 return OPVCC(63, 128, 0, 0) /* ftdiv - v2.06 */ 4991 case AFTSQRT: 4992 return OPVCC(63, 160, 0, 0) /* ftsqrt - v2.06 */ 4993 4994 case AXOR: 4995 return OPVCC(26, 0, 0, 0) /* XORIL */ 4996 case AXORIS: 4997 return OPVCC(27, 0, 0, 0) /* XORIS */ 4998 } 4999 5000 c.ctxt.Diag("bad opcode i/r or i/r/r %v", a) 5001 return 0 5002} 5003 5004/* 5005 * load o(a),d 5006 */ 5007func (c *ctxt9) opload(a obj.As) uint32 { 5008 switch a { 5009 case AMOVD: 5010 return OPVCC(58, 0, 0, 0) /* ld */ 5011 case AMOVDU: 5012 return OPVCC(58, 0, 0, 1) /* ldu */ 5013 case AMOVWZ: 5014 return OPVCC(32, 0, 0, 0) /* lwz */ 5015 case AMOVWZU: 5016 return OPVCC(33, 0, 0, 0) /* lwzu */ 5017 case AMOVW: 5018 return OPVCC(58, 0, 0, 0) | 1<<1 /* lwa */ 5019 case ALXV: 5020 return OPDQ(61, 1, 0) /* lxv - ISA v3.0 */ 5021 case ALXVL: 5022 return OPVXX1(31, 269, 0) /* lxvl - ISA v3.0 */ 5023 case ALXVLL: 5024 return OPVXX1(31, 301, 0) /* lxvll - ISA v3.0 */ 5025 case ALXVX: 5026 return OPVXX1(31, 268, 0) /* lxvx - ISA v3.0 */ 5027 5028 /* no AMOVWU */ 5029 case AMOVB, AMOVBZ: 5030 return OPVCC(34, 0, 0, 0) 5031 /* load */ 5032 5033 case AMOVBU, AMOVBZU: 5034 return OPVCC(35, 0, 0, 0) 5035 case AFMOVD: 5036 return OPVCC(50, 0, 0, 0) 5037 case AFMOVDU: 5038 return OPVCC(51, 0, 0, 0) 5039 case AFMOVS: 5040 return OPVCC(48, 0, 0, 0) 5041 case AFMOVSU: 5042 return OPVCC(49, 0, 0, 0) 5043 case AMOVH: 5044 return OPVCC(42, 0, 0, 0) 5045 case AMOVHU: 5046 return OPVCC(43, 0, 0, 0) 5047 case AMOVHZ: 5048 return OPVCC(40, 0, 0, 0) 5049 case AMOVHZU: 5050 return OPVCC(41, 0, 0, 0) 5051 case AMOVMW: 5052 return OPVCC(46, 0, 0, 0) /* lmw */ 5053 } 5054 5055 c.ctxt.Diag("bad load opcode %v", a) 5056 return 0 5057} 5058 5059/* 5060 * indexed load a(b),d 5061 */ 5062func (c *ctxt9) oploadx(a obj.As) uint32 { 5063 switch a { 5064 case AMOVWZ: 5065 return OPVCC(31, 23, 0, 0) /* lwzx */ 5066 case AMOVWZU: 5067 return OPVCC(31, 55, 0, 0) /* lwzux */ 5068 case AMOVW: 5069 return OPVCC(31, 341, 0, 0) /* lwax */ 5070 case AMOVWU: 5071 return OPVCC(31, 373, 0, 0) /* lwaux */ 5072 5073 case AMOVB, AMOVBZ: 5074 return OPVCC(31, 87, 0, 0) /* lbzx */ 5075 5076 case AMOVBU, AMOVBZU: 5077 return OPVCC(31, 119, 0, 0) /* lbzux */ 5078 case AFMOVD: 5079 return OPVCC(31, 599, 0, 0) /* lfdx */ 5080 case AFMOVDU: 5081 return OPVCC(31, 631, 0, 0) /* lfdux */ 5082 case AFMOVS: 5083 return OPVCC(31, 535, 0, 0) /* lfsx */ 5084 case AFMOVSU: 5085 return OPVCC(31, 567, 0, 0) /* lfsux */ 5086 case AFMOVSX: 5087 return OPVCC(31, 855, 0, 0) /* lfiwax - power6, isa 2.05 */ 5088 case AFMOVSZ: 5089 return OPVCC(31, 887, 0, 0) /* lfiwzx - power7, isa 2.06 */ 5090 case AMOVH: 5091 return OPVCC(31, 343, 0, 0) /* lhax */ 5092 case AMOVHU: 5093 return OPVCC(31, 375, 0, 0) /* lhaux */ 5094 case AMOVHBR: 5095 return OPVCC(31, 790, 0, 0) /* lhbrx */ 5096 case AMOVWBR: 5097 return OPVCC(31, 534, 0, 0) /* lwbrx */ 5098 case AMOVDBR: 5099 return OPVCC(31, 532, 0, 0) /* ldbrx */ 5100 case AMOVHZ: 5101 return OPVCC(31, 279, 0, 0) /* lhzx */ 5102 case AMOVHZU: 5103 return OPVCC(31, 311, 0, 0) /* lhzux */ 5104 case AECIWX: 5105 return OPVCC(31, 310, 0, 0) /* eciwx */ 5106 case ALBAR: 5107 return OPVCC(31, 52, 0, 0) /* lbarx */ 5108 case ALHAR: 5109 return OPVCC(31, 116, 0, 0) /* lharx */ 5110 case ALWAR: 5111 return OPVCC(31, 20, 0, 0) /* lwarx */ 5112 case ALDAR: 5113 return OPVCC(31, 84, 0, 0) /* ldarx */ 5114 case ALSW: 5115 return OPVCC(31, 533, 0, 0) /* lswx */ 5116 case AMOVD: 5117 return OPVCC(31, 21, 0, 0) /* ldx */ 5118 case AMOVDU: 5119 return OPVCC(31, 53, 0, 0) /* ldux */ 5120 case ALDMX: 5121 return OPVCC(31, 309, 0, 0) /* ldmx */ 5122 5123 /* Vector (VMX/Altivec) instructions */ 5124 case ALVEBX: 5125 return OPVCC(31, 7, 0, 0) /* lvebx - v2.03 */ 5126 case ALVEHX: 5127 return OPVCC(31, 39, 0, 0) /* lvehx - v2.03 */ 5128 case ALVEWX: 5129 return OPVCC(31, 71, 0, 0) /* lvewx - v2.03 */ 5130 case ALVX: 5131 return OPVCC(31, 103, 0, 0) /* lvx - v2.03 */ 5132 case ALVXL: 5133 return OPVCC(31, 359, 0, 0) /* lvxl - v2.03 */ 5134 case ALVSL: 5135 return OPVCC(31, 6, 0, 0) /* lvsl - v2.03 */ 5136 case ALVSR: 5137 return OPVCC(31, 38, 0, 0) /* lvsr - v2.03 */ 5138 /* End of vector instructions */ 5139 5140 /* Vector scalar (VSX) instructions */ 5141 case ALXVX: 5142 return OPVXX1(31, 268, 0) /* lxvx - ISA v3.0 */ 5143 case ALXVD2X: 5144 return OPVXX1(31, 844, 0) /* lxvd2x - v2.06 */ 5145 case ALXVW4X: 5146 return OPVXX1(31, 780, 0) /* lxvw4x - v2.06 */ 5147 case ALXVH8X: 5148 return OPVXX1(31, 812, 0) /* lxvh8x - v3.00 */ 5149 case ALXVB16X: 5150 return OPVXX1(31, 876, 0) /* lxvb16x - v3.00 */ 5151 case ALXVDSX: 5152 return OPVXX1(31, 332, 0) /* lxvdsx - v2.06 */ 5153 case ALXSDX: 5154 return OPVXX1(31, 588, 0) /* lxsdx - v2.06 */ 5155 case ALXSIWAX: 5156 return OPVXX1(31, 76, 0) /* lxsiwax - v2.07 */ 5157 case ALXSIWZX: 5158 return OPVXX1(31, 12, 0) /* lxsiwzx - v2.07 */ 5159 } 5160 5161 c.ctxt.Diag("bad loadx opcode %v", a) 5162 return 0 5163} 5164 5165/* 5166 * store s,o(d) 5167 */ 5168func (c *ctxt9) opstore(a obj.As) uint32 { 5169 switch a { 5170 case AMOVB, AMOVBZ: 5171 return OPVCC(38, 0, 0, 0) /* stb */ 5172 5173 case AMOVBU, AMOVBZU: 5174 return OPVCC(39, 0, 0, 0) /* stbu */ 5175 case AFMOVD: 5176 return OPVCC(54, 0, 0, 0) /* stfd */ 5177 case AFMOVDU: 5178 return OPVCC(55, 0, 0, 0) /* stfdu */ 5179 case AFMOVS: 5180 return OPVCC(52, 0, 0, 0) /* stfs */ 5181 case AFMOVSU: 5182 return OPVCC(53, 0, 0, 0) /* stfsu */ 5183 5184 case AMOVHZ, AMOVH: 5185 return OPVCC(44, 0, 0, 0) /* sth */ 5186 5187 case AMOVHZU, AMOVHU: 5188 return OPVCC(45, 0, 0, 0) /* sthu */ 5189 case AMOVMW: 5190 return OPVCC(47, 0, 0, 0) /* stmw */ 5191 case ASTSW: 5192 return OPVCC(31, 725, 0, 0) /* stswi */ 5193 5194 case AMOVWZ, AMOVW: 5195 return OPVCC(36, 0, 0, 0) /* stw */ 5196 5197 case AMOVWZU, AMOVWU: 5198 return OPVCC(37, 0, 0, 0) /* stwu */ 5199 case AMOVD: 5200 return OPVCC(62, 0, 0, 0) /* std */ 5201 case AMOVDU: 5202 return OPVCC(62, 0, 0, 1) /* stdu */ 5203 case ASTXV: 5204 return OPDQ(61, 5, 0) /* stxv ISA 3.0 */ 5205 case ASTXVL: 5206 return OPVXX1(31, 397, 0) /* stxvl ISA 3.0 */ 5207 case ASTXVLL: 5208 return OPVXX1(31, 429, 0) /* stxvll ISA 3.0 */ 5209 case ASTXVX: 5210 return OPVXX1(31, 396, 0) /* stxvx - ISA v3.0 */ 5211 5212 } 5213 5214 c.ctxt.Diag("unknown store opcode %v", a) 5215 return 0 5216} 5217 5218/* 5219 * indexed store s,a(b) 5220 */ 5221func (c *ctxt9) opstorex(a obj.As) uint32 { 5222 switch a { 5223 case AMOVB, AMOVBZ: 5224 return OPVCC(31, 215, 0, 0) /* stbx */ 5225 5226 case AMOVBU, AMOVBZU: 5227 return OPVCC(31, 247, 0, 0) /* stbux */ 5228 case AFMOVD: 5229 return OPVCC(31, 727, 0, 0) /* stfdx */ 5230 case AFMOVDU: 5231 return OPVCC(31, 759, 0, 0) /* stfdux */ 5232 case AFMOVS: 5233 return OPVCC(31, 663, 0, 0) /* stfsx */ 5234 case AFMOVSU: 5235 return OPVCC(31, 695, 0, 0) /* stfsux */ 5236 case AFMOVSX: 5237 return OPVCC(31, 983, 0, 0) /* stfiwx */ 5238 5239 case AMOVHZ, AMOVH: 5240 return OPVCC(31, 407, 0, 0) /* sthx */ 5241 case AMOVHBR: 5242 return OPVCC(31, 918, 0, 0) /* sthbrx */ 5243 5244 case AMOVHZU, AMOVHU: 5245 return OPVCC(31, 439, 0, 0) /* sthux */ 5246 5247 case AMOVWZ, AMOVW: 5248 return OPVCC(31, 151, 0, 0) /* stwx */ 5249 5250 case AMOVWZU, AMOVWU: 5251 return OPVCC(31, 183, 0, 0) /* stwux */ 5252 case ASTSW: 5253 return OPVCC(31, 661, 0, 0) /* stswx */ 5254 case AMOVWBR: 5255 return OPVCC(31, 662, 0, 0) /* stwbrx */ 5256 case AMOVDBR: 5257 return OPVCC(31, 660, 0, 0) /* stdbrx */ 5258 case ASTBCCC: 5259 return OPVCC(31, 694, 0, 1) /* stbcx. */ 5260 case ASTHCCC: 5261 return OPVCC(31, 726, 0, 1) /* sthcx. */ 5262 case ASTWCCC: 5263 return OPVCC(31, 150, 0, 1) /* stwcx. */ 5264 case ASTDCCC: 5265 return OPVCC(31, 214, 0, 1) /* stwdx. */ 5266 case AECOWX: 5267 return OPVCC(31, 438, 0, 0) /* ecowx */ 5268 case AMOVD: 5269 return OPVCC(31, 149, 0, 0) /* stdx */ 5270 case AMOVDU: 5271 return OPVCC(31, 181, 0, 0) /* stdux */ 5272 5273 /* Vector (VMX/Altivec) instructions */ 5274 case ASTVEBX: 5275 return OPVCC(31, 135, 0, 0) /* stvebx - v2.03 */ 5276 case ASTVEHX: 5277 return OPVCC(31, 167, 0, 0) /* stvehx - v2.03 */ 5278 case ASTVEWX: 5279 return OPVCC(31, 199, 0, 0) /* stvewx - v2.03 */ 5280 case ASTVX: 5281 return OPVCC(31, 231, 0, 0) /* stvx - v2.03 */ 5282 case ASTVXL: 5283 return OPVCC(31, 487, 0, 0) /* stvxl - v2.03 */ 5284 /* End of vector instructions */ 5285 5286 /* Vector scalar (VSX) instructions */ 5287 case ASTXVX: 5288 return OPVXX1(31, 396, 0) /* stxvx - v3.0 */ 5289 case ASTXVD2X: 5290 return OPVXX1(31, 972, 0) /* stxvd2x - v2.06 */ 5291 case ASTXVW4X: 5292 return OPVXX1(31, 908, 0) /* stxvw4x - v2.06 */ 5293 case ASTXVH8X: 5294 return OPVXX1(31, 940, 0) /* stxvh8x - v3.0 */ 5295 case ASTXVB16X: 5296 return OPVXX1(31, 1004, 0) /* stxvb16x - v3.0 */ 5297 5298 case ASTXSDX: 5299 return OPVXX1(31, 716, 0) /* stxsdx - v2.06 */ 5300 5301 case ASTXSIWX: 5302 return OPVXX1(31, 140, 0) /* stxsiwx - v2.07 */ 5303 5304 /* End of vector scalar instructions */ 5305 5306 } 5307 5308 c.ctxt.Diag("unknown storex opcode %v", a) 5309 return 0 5310} 5311