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