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