ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/cebix/mon/src/mon_ppc.cpp
Revision: 1.11
Committed: 2010-02-21T11:58:33Z (14 years, 2 months ago) by cebix
Branch: MAIN
CVS Tags: HEAD
Changes since 1.10: +7 -7 lines
Log Message:
fixed const-correctness

File Contents

# User Rev Content
1 cebix 1.1 /*
2     * mon_ppc.cpp - PowerPC disassembler
3     *
4 cebix 1.11 * cxmon (C) Christian Bauer, Marc Hellwig
5 cebix 1.2 *
6     * This program is free software; you can redistribute it and/or modify
7     * it under the terms of the GNU General Public License as published by
8     * the Free Software Foundation; either version 2 of the License, or
9     * (at your option) any later version.
10     *
11     * This program is distributed in the hope that it will be useful,
12     * but WITHOUT ANY WARRANTY; without even the implied warranty of
13     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14     * GNU General Public License for more details.
15     *
16     * You should have received a copy of the GNU General Public License
17     * along with this program; if not, write to the Free Software
18     * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 cebix 1.1 */
20    
21 cebix 1.2 #include "sysdeps.h"
22 cebix 1.1
23     #include "mon.h"
24 cebix 1.4 #include "mon_disass.h"
25 cebix 1.1
26    
27     // Instruction fields
28 gbeauche 1.9 static int primop, exop, vxop, ra, rb, rc, rd;
29 cebix 1.1 static unsigned short imm;
30    
31    
32     // Codes for trap instructions
33 cebix 1.11 static const char *to_code[32] = {
34 cebix 1.1 NULL, "lgt", "llt", NULL, "eq", "lge", "lle", NULL,
35     "gt", NULL, NULL, NULL, "ge", NULL, NULL, NULL,
36     "lt", NULL, NULL, NULL, "le", NULL, NULL, NULL,
37     "ne", NULL, NULL, NULL, NULL, NULL, NULL, ""
38     };
39    
40    
41     // Macros for instruction forms
42     #define iform(s, t) fprintf(f, "%s\t$%08x\n", s, t)
43    
44     #define bform(s, t) \
45     if (rd == 0) \
46     fprintf(f, "bdnzf%s\t%d,$%08x\n", s, ra, t); \
47     else if (rd == 2) \
48     fprintf(f, "bdzf%s\t%d,$%08x\n", s, ra, t); \
49     else if (rd == 4) { \
50     if (ra == 0) \
51     fprintf(f, "bge%s\t$%08x\n", s, t); \
52     else if (ra == 1) \
53     fprintf(f, "ble%s\t$%08x\n", s, t); \
54     else if (ra == 2) \
55     fprintf(f, "bne%s\t$%08x\n", s, t); \
56     else \
57     fprintf(f, "bf%s\t%d,$%08x\n", s, ra, t); \
58     } else if (rd == 8) \
59     fprintf(f, "bdnzt%s\t%d,$%08x\n", s, ra, t); \
60     else if (rd == 10) \
61     fprintf(f, "bdzt%s\t%d,$%08x\n", s, ra, t); \
62     else if (rd == 12) { \
63     if (ra == 0) \
64     fprintf(f, "blt%s\t$%08x\n", s, t); \
65     else if (ra == 1) \
66     fprintf(f, "bgt%s\t$%08x\n", s, t); \
67     else if (ra == 2) \
68     fprintf(f, "beq%s\t$%08x\n", s, t); \
69     else \
70     fprintf(f, "bt%s\t%d,$%08x\n", s, ra, t); \
71     } else if (rd == 16) \
72     fprintf(f, "bdnz%s\t$%08x\n", s, t); \
73     else if (rd == 18) \
74     fprintf(f, "bdz%s\t$%08x\n", s, t); \
75     else \
76     fprintf(f, "bc%s\t%d,%d,$%08x\n", s, rd, ra, t)
77    
78     #define scform(s) fprintf(f, s "\n")
79    
80     #define dform_ls(s) \
81     if (ra == 0) \
82     fprintf(f, "%s\tr%d,$%08x\n", s, rd, short(imm)); \
83     else \
84     fprintf(f, "%s\tr%d,$%04x(r%d)\n", s, rd, short(imm), ra)
85     #define dform_fls(s) \
86     if (ra == 0) \
87     fprintf(f, "%s\tfr%d,$%08x\n", s, rd, short(imm)); \
88     else \
89     fprintf(f, "%s\tfr%d,$%04x(r%d)\n", s, rd, short(imm), ra)
90     #define dform_simm(s) fprintf(f, "%s\tr%d,r%d,$%04x\n", s, rd, ra, short(imm))
91     #define dform_simmn(s) fprintf(f, "%s\tr%d,r%d,$%04x\n", s, rd, ra, (-imm) & 0xffff)
92     #define dform_uimm(s) fprintf(f, "%s\tr%d,r%d,$%04x\n", s, ra, rd, imm)
93     #define dform_crs(s) fprintf(f, "%s\tcrf%d,r%d,$%04x\n", s, rd >> 2, ra, short(imm))
94     #define dform_cru(s) fprintf(f, "%s\tcrf%d,r%d,$%04x\n", s, rd >> 2, ra, imm)
95     #define dform_to(s) fprintf(f, "%s\t%d,r%d,$%04x\n", s, rd, ra, short(imm))
96    
97     #define dsform(s) fprintf(f, "%s\tr%d,$%04x(r%d)\n", s, rd, short(imm & 0xfffc), ra)
98    
99 gbeauche 1.9 #define xform_vls(s) \
100     if (ra == 0) \
101     fprintf(f, "%s\tv%d,r%d\n", s, rd, rb); \
102     else \
103     fprintf(f, "%s\tv%d,r%d,r%d\n", s, rd, ra, rb)
104 cebix 1.1 #define xform_ls(s) \
105     if (ra == 0) \
106     fprintf(f, "%s\tr%d,r%d\n", s, rd, rb); \
107     else \
108     fprintf(f, "%s\tr%d,r%d,r%d\n", s, rd, ra, rb)
109     #define xform_fls(s) \
110     if (ra == 0) \
111     fprintf(f, "%s\tfr%d,r%d\n", s, rd, rb); \
112     else \
113     fprintf(f, "%s\tfr%d,r%d,r%d\n", s, rd, ra, rb)
114     #define xform_lsswi(s) \
115     if (ra == 0) \
116     fprintf(f, "%s\tr%d,%d\n", s, rd, rb ? rb : 32); \
117     else \
118     fprintf(f, "%s\tr%d,r%d,%d\n", s, rd, ra, rb ? rb : 32)
119     #define xform_db(s) fprintf(f, "%s\tr%d,r%d\n", s, rd, rb)
120     #define xform_d(s) fprintf(f, "%s\tr%d\n", s, rd)
121     #define xform_fsr(s) fprintf(f, s "\tr%d,%d\n", rd, ra & 0xf)
122     #define xform_sabc(s) fprintf(f, "%s%s\tr%d,r%d,r%d\n", s, w & 1 ? "." : "", ra, rd, rb)
123     #define xform_sac(s) fprintf(f, "%s%s\tr%d,r%d\n", s, w & 1 ? "." : "", ra, rd)
124     #define xform_tsr(s) fprintf(f, s "\t%d,r%d\n", ra & 0xf, rd)
125     #define xform_sash(s) fprintf(f, s "%s\tr%d,r%d,%d\n", w & 1 ? "." : "", ra, rd, rb)
126     #define xform_crlab(s) fprintf(f, "%s\tcrf%d,r%d,r%d\n", s, rd >> 2, ra, rb)
127     #define xform_fcrab(s) fprintf(f, "%s\tcrf%d,fr%d,fr%d\n", s, rd >> 2, ra, rb)
128     #define xform_crcr(s) fprintf(f, "%s\tcrf%d,crf%d\n", s, rd >> 2, ra >> 2)
129     #define xform_cr(s) fprintf(f, "%s\tcrf%d\n", s, rd >> 2)
130     #define xform_cri(s) fprintf(f, s "%s\tcrf%d,%d\n", w & 1 ? "." : "", rd >> 2, rb >> 1)
131     #define xform_to(s) fprintf(f, "%s\t%d,r%d,r%d\n", s, rd, ra, rb)
132     #define xform_fdb(s) fprintf(f, "%s%s\tfr%d,fr%d\n", s, w & 1 ? "." : "", rd, rb)
133     #define xform_fd(s) fprintf(f, "%s%s\tfr%d\n", s, w & 1 ? "." : "", rd)
134     #define xform_crb(s) fprintf(f, "%s%s\tcrb%d\n", s, w & 1 ? "." : "", rd)
135     #define xform_ab(s) fprintf(f, "%s\tr%d,r%d\n", s, ra, rb)
136     #define xform_b(s) fprintf(f, "%s\tr%d\n", s, rb)
137     #define xform(s) fprintf(f, s "\n")
138    
139     #define xlform_b(s) fprintf(f, "%s\t%d,%d\n", s, rd, ra)
140     #define xlform_cr(s) fprintf(f, "%s\tcrb%d,crb%d,crb%d\n", s, rd, ra, rb)
141     #define xlform_crcr(s) fprintf(f, "%s\tcrf%d,crf%d\n", s, rd >> 2, ra >> 2)
142     #define xlform(s) fprintf(f, s "\n")
143    
144     #define xfxform_fspr(s) fprintf(f, "%s\tr%d,SPR%d\n", s, rd, ra | (rb << 5))
145     #define xfxform_crm(s) fprintf(f, s "\t$%02x,r%d\n", w >> 12 & 0xff, rd)
146     #define xfxform_tspr(s) fprintf(f, "%s\tSPR%d,r%d\n", s, ra | (rb << 5), rd)
147     #define xfxform_tb(s) fprintf(f, "%s\tr%d\n", s, rd)
148    
149     #define xflform(s) fprintf(f, s "%s\t$%02x,fr%d\n", w & 1 ? "." : "", w >> 17 & 0xff, rb)
150    
151     #define xsform(s) fprintf(f, s "%s\tr%d,r%d,%d\n", w & 1 ? "." : "", ra, rd, rb | (w & 2 ? 32 : 0))
152    
153     #define xoform_dab(s) fprintf(f, "%s%s\tr%d,r%d,r%d\n", s, w & 1 ? "." : "", rd, ra, rb)
154     #define xoform_da(s) fprintf(f, "%s%s\tr%d,r%d\n", s, w & 1 ? "." : "", rd, ra)
155    
156     #define aform_dab(s) fprintf(f, "%s%s\tfr%d,fr%d,fr%d\n", s, w & 1 ? "." : "", rd, ra, rb)
157     #define aform_db(s) fprintf(f, "%s%s\tfr%d,fr%d\n", s, w & 1 ? "." : "", rd, rb)
158     #define aform_dac(s) fprintf(f, "%s%s\tfr%d,fr%d,fr%d\n", s, w & 1 ? "." : "", rd, ra, rc)
159     #define aform_dacb(s) fprintf(f, "%s%s\tfr%d,fr%d,fr%d,fr%d\n", s, w & 1 ? "." : "", rd, ra, rc, rb)
160    
161     #define mform(s) fprintf(f, "%s%s\tr%d,r%d,r%d,$%08x\n", s, w & 1 ? "." : "", ra, rd, rb, mbme2mask(w >> 6 & 31, w >>1 & 31))
162     #define mform_i(s) fprintf(f, "%s%s\tr%d,r%d,%d,$%08x\n", s, w & 1 ? "." : "", ra, rd, rb, mbme2mask(w >> 6 & 31, w >>1 & 31))
163    
164     #define mdform(s) fprintf(f, "%s%s\tr%d,r%d,%d,%d\n", s, w & 1 ? "." : "", ra, rd, rb | (w & 2 ? 32 : 0), rc | (w & 32 ? 32 : 0))
165    
166     #define mdsform(s) fprintf(f, "%s%s\tr%d,r%d,r%d,%d\n", s, w & 1 ? "." : "", ra, rd, rb, rc | (w & 32 ? 32 : 0))
167    
168 gbeauche 1.10 #define va_form(s) fprintf(f, "%s\tv%d,v%d,v%d,v%d\n", s, rd, ra, rb, rc)
169 gbeauche 1.9 #define vx_form(s) fprintf(f, "%s\tv%d,v%d,v%d\n", s, rd, ra, rb)
170 gbeauche 1.10 #define vxr_form(s) fprintf(f, "%s%s\tv%d,v%d,v%d\n", s, w & (1 << 10) ? "." : "", rd, ra, rb)
171     #define vxi_ra_form(s) fprintf(f, "%s\tv%d,v%d,%d\n", s, rd, rb, ra)
172     #define vx_raz_form(s) \
173     if (ra == 0) \
174     fprintf(f, "%s\tv%d,v%d\n", s, rd, rb); \
175     else \
176     fprintf(f, "?\n")
177     #define vxi_ras_rbz_form(s) \
178     if (rb == 0) \
179     fprintf(f, "%s\tv%d,%d\n", s, rd, ra - (ra & 0x10 ? 0x20 : 0)); \
180     else \
181     fprintf(f, "?\n")
182 cebix 1.1
183     // Prototypes
184 gbeauche 1.9 static void disass4(FILE *f, unsigned int adr, unsigned int w);
185 cebix 1.1 static void disass19(FILE *f, unsigned int adr, unsigned int w);
186     static void disass31(FILE *f, unsigned int adr, unsigned int w);
187     static void disass59(FILE *f, unsigned int adr, unsigned int w);
188     static void disass63(FILE *f, unsigned int adr, unsigned int w);
189     static unsigned int mbme2mask(int mb, int me);
190 cebix 1.11 static const char *get_spr(int reg);
191 cebix 1.1
192    
193     /*
194     * Disassemble one instruction
195     */
196    
197     void disass_ppc(FILE *f, unsigned int adr, unsigned int w)
198     {
199     // Divide instruction into fields
200     primop = w >> 26;
201     rd = w >> 21 & 0x1f;
202     ra = w >> 16 & 0x1f;
203     rb = w >> 11 & 0x1f;
204     rc = w >> 6 & 0x1f;
205     exop = w >> 1 & 0x3ff;
206 gbeauche 1.9 vxop = w & 0x7ff;
207 cebix 1.1 imm = w & 0xffff;
208    
209     // Decode primary opcode
210     switch (primop) {
211     case 2: // 64 bit
212     if (to_code[rd] != NULL)
213     fprintf(f, "td%si\tr%d,$%04x\n", to_code[rd], ra, short(imm));
214     else
215     dform_to("tdi");
216     break;
217    
218     case 3:
219     if (to_code[rd] != NULL)
220     fprintf(f, "tw%si\tr%d,$%04x\n", to_code[rd], ra, short(imm));
221     else
222     dform_to("twi");
223     break;
224    
225 gbeauche 1.9 case 4: // AltiVec
226     disass4(f, adr, w);
227     break;
228 cebix 1.1
229     case 7: dform_simm("mulli"); break;
230     case 8: dform_simm("subfic"); break;
231    
232     case 10:
233     if (rd & 1)
234     dform_cru("cmpldi"); // 64 bit
235     else
236     dform_cru("cmplwi");
237     break;
238    
239     case 11:
240     if (rd & 1)
241     dform_crs("cmpdi"); // 64 bit
242     else
243     dform_crs("cmpwi");
244     break;
245    
246     case 12:
247     if (imm < 0x8000)
248     dform_simm("addic");
249     else
250     dform_simmn("subic");
251     break;
252    
253     case 13:
254     if (imm < 0x8000)
255     dform_simm("addic.");
256     else
257     dform_simmn("subic.");
258     break;
259    
260     case 14:
261     if (ra == 0)
262     fprintf(f, "li\tr%d,$%04x\n", rd, short(imm));
263     else
264     if (imm < 0x8000)
265     dform_simm("addi");
266     else
267     dform_simmn("subi");
268     break;
269    
270     case 15:
271     if (ra == 0)
272     fprintf(f, "lis\tr%d,$%04x\n", rd, imm);
273     else
274     if (imm < 0x8000)
275     dform_simm("addis");
276     else
277     dform_simmn("subis");
278     break;
279    
280     case 16: {
281     int target = short(imm & 0xfffc);
282 cebix 1.11 const char *form;
283 cebix 1.1 if (w & 1)
284     if (w & 2)
285     form = "la";
286     else {
287     form = "l";
288     target += adr;
289     }
290     else
291     if (w & 2)
292     form = "a";
293     else {
294     form = "";
295     target += adr;
296     }
297     bform(form, target);
298     break;
299     }
300    
301     case 17:
302     if (w & 2)
303     scform("sc");
304     else
305     fprintf(f, "?\n");
306     break;
307    
308     case 18: {
309     int target = w & 0x03fffffc;
310     if (target & 0x02000000)
311     target |= 0xfc000000;
312     if (w & 1)
313     if (w & 2)
314     iform("bla", target);
315     else
316     iform("bl", adr + target);
317     else
318     if (w & 2)
319     iform("ba", target);
320     else
321     iform("b", adr + target);
322     break;
323     }
324    
325     case 19: disass19(f, adr, w); break;
326     case 20: mform_i("rlwimi"); break;
327     case 21: mform_i("rlwinm"); break;
328     case 23: mform("rlwnm"); break;
329    
330     case 24:
331     if (rd == 0 && ra == 0 && imm == 0)
332     fprintf(f, "nop\n");
333     else
334     dform_uimm("ori");
335     break;
336    
337     case 25: dform_uimm("oris"); break;
338     case 26: dform_uimm("xori"); break;
339     case 27: dform_uimm("xoris"); break;
340     case 28: dform_uimm("andi."); break;
341     case 29: dform_uimm("andis."); break;
342    
343     case 30: // 64 bit
344     switch (w >> 1 & 0xf) {
345     case 0: case 1: mdform("rldicl"); break;
346     case 2: case 3: mdform("rldicr"); break;
347     case 4: case 5: mdform("rldic"); break;
348     case 6: case 7: mdform("rldimi"); break;
349     case 8: mdsform("rldcl"); break;
350     case 9: mdsform("rldcr"); break;
351     default:
352     fprintf(f, "?\n");
353     break;
354     };
355     break;
356    
357     case 31: disass31(f, adr, w); break;
358     case 32: dform_ls("lwz"); break;
359     case 33: dform_ls("lwzu"); break;
360     case 34: dform_ls("lbz"); break;
361     case 35: dform_ls("lbzu"); break;
362     case 36: dform_ls("stw"); break;
363     case 37: dform_ls("stwu"); break;
364     case 38: dform_ls("stb"); break;
365     case 39: dform_ls("stbu"); break;
366     case 40: dform_ls("lhz"); break;
367     case 41: dform_ls("lhzu"); break;
368     case 42: dform_ls("lha"); break;
369     case 43: dform_ls("lhau"); break;
370     case 44: dform_ls("sth"); break;
371     case 45: dform_ls("sthu"); break;
372     case 46: dform_ls("lmw"); break;
373     case 47: dform_ls("stmw"); break;
374     case 48: dform_fls("lfs"); break;
375     case 49: dform_fls("lfsu"); break;
376     case 50: dform_fls("lfd"); break;
377     case 51: dform_fls("lfdu"); break;
378     case 52: dform_fls("stfs"); break;
379     case 53: dform_fls("stfsu"); break;
380     case 54: dform_fls("stfd"); break;
381     case 55: dform_fls("stfdu"); break;
382    
383     case 58: // 64 bit
384     switch (w & 3) {
385     case 0: dsform("ld"); break;
386     case 1: dsform("ldu"); break;
387     case 2: dsform("lwa"); break;
388     default:
389     fprintf(f, "?\n");
390     break;
391     }
392     break;
393    
394     case 59: disass59(f, adr, w); break;
395    
396     case 62: // 64 bit
397     switch (w & 3) {
398     case 0: dsform("std"); break;
399     case 1: dsform("stdu"); break;
400     default:
401     fprintf(f, "?\n");
402     break;
403     }
404     break;
405    
406     case 63: disass63(f, adr, w); break;
407    
408     default:
409     if (!w)
410     fprintf(f, "illegal\n");
411     else
412     fprintf(f, "?\n");
413     break;
414     }
415     }
416    
417    
418     /*
419 gbeauche 1.9 * Disassemble instruction with primary opcode = 4 (VX-Form)
420     */
421    
422     static void disass4(FILE *f, unsigned int adr, unsigned int w)
423     {
424     switch (vxop) {
425 gbeauche 1.10 case 1540:
426     if (ra == 0 && rb == 0)
427     fprintf(f, "mfvscr\tv%d\n", rd);
428     else
429     fprintf(f, "?\n");
430     break;
431     case 1604:
432     if (rd == 0 && ra == 0)
433     fprintf(f, "mtvscr\tv%d\n", rb);
434     else
435     fprintf(f, "?\n");
436     break;
437 gbeauche 1.9 case 384: vx_form("vaddcuw"); break;
438     case 10: vx_form("vaddfp"); break;
439     case 768: vx_form("vaddsbs"); break;
440     case 832: vx_form("vaddshs"); break;
441     case 896: vx_form("vaddsws"); break;
442     case 0: vx_form("vaddubm"); break;
443     case 512: vx_form("vaddubs"); break;
444     case 64: vx_form("vadduhm"); break;
445     case 576: vx_form("vadduhs"); break;
446     case 128: vx_form("vadduwm"); break;
447     case 640: vx_form("vadduws"); break;
448     case 1028: vx_form("vand"); break;
449     case 1092: vx_form("vandc"); break;
450     case 1282: vx_form("vavgsb"); break;
451     case 1346: vx_form("vavgsh"); break;
452     case 1410: vx_form("vavgsw"); break;
453     case 1026: vx_form("vavgub"); break;
454     case 1090: vx_form("vavguh"); break;
455     case 1154: vx_form("vavguw"); break;
456 gbeauche 1.10 case 842: vxi_ra_form("vcfsx"); break;
457     case 778: vxi_ra_form("vcfux"); break;
458     case 966: case 966+1024: vxr_form("vcmpbfp"); break;
459     case 198: case 198+1024: vxr_form("vcmpeqfp"); break;
460     case 6: case 6+1024: vxr_form("vcmpequb"); break;
461     case 70: case 70+1024: vxr_form("vcmpequh"); break;
462     case 134: case 134+1024: vxr_form("vcmpequw"); break;
463     case 454: case 454+1024: vxr_form("vcmpgefp"); break;
464     case 710: case 710+1024: vxr_form("vcmpgtfp"); break;
465     case 774: case 774+1024: vxr_form("vcmpgtsb"); break;
466     case 838: case 838+1024: vxr_form("vcmpgtsh"); break;
467     case 902: case 902+1024: vxr_form("vcmpgtsw"); break;
468     case 518: case 518+1024: vxr_form("vcmpgtub"); break;
469     case 582: case 582+1024: vxr_form("vcmpgtuh"); break;
470     case 646: case 646+1024: vxr_form("vcmpgtuw"); break;
471     case 970: vxi_ra_form("vctsxs"); break;
472     case 906: vxi_ra_form("vctuxs"); break;
473     case 394: vx_raz_form("vexptefp"); break;
474     case 458: vx_raz_form("vlogefp"); break;
475 gbeauche 1.9 case 1034: vx_form("vmaxfp"); break;
476     case 258: vx_form("vmaxsb"); break;
477     case 322: vx_form("vmaxsh"); break;
478     case 386: vx_form("vmaxsw"); break;
479     case 2: vx_form("vmaxub"); break;
480 gbeauche 1.10 case 66: vx_form("vmaxuh"); break;
481 gbeauche 1.9 case 130: vx_form("vmaxuw"); break;
482     case 1098: vx_form("vminfp"); break;
483     case 770: vx_form("vminsb"); break;
484     case 834: vx_form("vminsh"); break;
485     case 898: vx_form("vminsw"); break;
486     case 514: vx_form("vminub"); break;
487     case 578: vx_form("vminuh"); break;
488     case 642: vx_form("vminuw"); break;
489     case 12: vx_form("vmrghb"); break;
490     case 76: vx_form("vmrghh"); break;
491     case 140: vx_form("vmrghw"); break;
492     case 268: vx_form("vmrglb"); break;
493     case 332: vx_form("vmrglh"); break;
494     case 396: vx_form("vmrglw"); break;
495     case 776: vx_form("vmulesb"); break;
496     case 840: vx_form("vmulesh"); break;
497     case 520: vx_form("vmuleub"); break;
498     case 584: vx_form("vmuleuh"); break;
499     case 264: vx_form("vmulosb"); break;
500     case 328: vx_form("vmulosh"); break;
501     case 8: vx_form("vmuloub"); break;
502     case 72: vx_form("vmulouh"); break;
503     case 1284: vx_form("vnor"); break;
504     case 1156: vx_form("vor"); break;
505     case 782: vx_form("vpkpx"); break;
506     case 398: vx_form("vpkshss"); break;
507     case 270: vx_form("vpkshus"); break;
508     case 462: vx_form("vpkswss"); break;
509     case 334: vx_form("vpkswus"); break;
510     case 14: vx_form("vpkuhum"); break;
511     case 142: vx_form("vpkuhus"); break;
512     case 78: vx_form("vpkuwum"); break;
513     case 206: vx_form("vpkuwus"); break;
514 gbeauche 1.10 case 266: vx_raz_form("vrefp"); break;
515     case 714: vx_raz_form("vrfim"); break;
516     case 522: vx_raz_form("vrfin"); break;
517     case 650: vx_raz_form("vrfip"); break;
518     case 586: vx_raz_form("vrfiz"); break;
519 gbeauche 1.9 case 4: vx_form("vrlb"); break;
520     case 68: vx_form("vrlh"); break;
521     case 132: vx_form("vrlw"); break;
522 gbeauche 1.10 case 330: vx_raz_form("vrsqrtefp"); break;
523 gbeauche 1.9 case 452: vx_form("vsl"); break;
524     case 260: vx_form("vslb"); break;
525     case 324: vx_form("vslh"); break;
526     case 1036: vx_form("vslo"); break;
527     case 388: vx_form("vslw"); break;
528 gbeauche 1.10 case 524: vxi_ra_form("vspltb"); break;
529     case 588: vxi_ra_form("vsplth"); break;
530     case 780: vxi_ras_rbz_form("vspltisb"); break;
531     case 844: vxi_ras_rbz_form("vspltish"); break;
532     case 908: vxi_ras_rbz_form("vspltisw"); break;
533     case 652: vxi_ra_form("vspltw"); break;
534 gbeauche 1.9 case 708: vx_form("vsr"); break;
535     case 772: vx_form("vsrab"); break;
536     case 836: vx_form("vsrah"); break;
537     case 900: vx_form("vsraw"); break;
538     case 516: vx_form("vsrb"); break;
539     case 580: vx_form("vsrh"); break;
540     case 1100: vx_form("vsro"); break;
541     case 644: vx_form("vsrw"); break;
542     case 1408: vx_form("vsubcuw"); break;
543     case 74: vx_form("vsubfp"); break;
544     case 1792: vx_form("vsubsbs"); break;
545     case 1856: vx_form("vsubshs"); break;
546     case 1920: vx_form("vsubsws"); break;
547     case 1024: vx_form("vsububm"); break;
548     case 1536: vx_form("vsububs"); break;
549     case 1088: vx_form("vsubuhm"); break;
550     case 1600: vx_form("vsubuhs"); break;
551     case 1152: vx_form("vsubuwm"); break;
552     case 1664: vx_form("vsubuws"); break;
553     case 1928: vx_form("vsumsws"); break;
554     case 1672: vx_form("vsum2sws"); break;
555     case 1800: vx_form("vsum4sbs"); break;
556     case 1608: vx_form("vsum4shs"); break;
557     case 1544: vx_form("vsum4ubs"); break;
558 gbeauche 1.10 case 846: vx_raz_form("vupkhpx"); break;
559     case 526: vx_raz_form("vupkhsb"); break;
560     case 590: vx_raz_form("vupkhsh"); break;
561     case 974: vx_raz_form("vupklpx"); break;
562     case 654: vx_raz_form("vupklsb"); break;
563     case 718: vx_raz_form("vupklsh"); break;
564     case 1220: vx_form("vxor"); break;
565 gbeauche 1.9 default:
566 gbeauche 1.10 if ((vxop & 0x43f) == 44) { // vsldoi vD,vA,vB,SHB
567     fprintf(f, "vsldoi\tv%d,v%d,v%d,%d\n", rd, ra, rb, rc & 15);
568 gbeauche 1.9 break;
569     }
570 gbeauche 1.10 switch (vxop & 0x3f) { // VA-form, must come last
571     case 46: va_form("vmaddfp"); break;
572     case 32: va_form("vmhaddshs"); break;
573     case 33: va_form("vmhraddshs"); break;
574     case 34: va_form("vmladduhm"); break;
575     case 37: va_form("vmsummbm"); break;
576     case 40: va_form("vmsumshm"); break;
577     case 41: va_form("vmsumshs"); break;
578     case 36: va_form("vmsumubm"); break;
579     case 38: va_form("vmsumuhm"); break;
580     case 39: va_form("vmsumuhs"); break;
581     case 47: va_form("vnmsubfp"); break;
582     case 43: va_form("vperm"); break;
583     case 42: va_form("vsel"); break;
584     default: fprintf(f, "?\n"); break;
585     }
586 gbeauche 1.9 break;
587     }
588     }
589    
590    
591     /*
592 cebix 1.1 * Disassemble instruction with primary opcode = 19 (XL-Form)
593     */
594    
595     static void disass19(FILE *f, unsigned int adr, unsigned int w)
596     {
597     switch (exop) {
598     case 0: xlform_crcr("mcrf"); break;
599    
600     case 16:
601     if (w & 1)
602     if (rd == 20)
603     fprintf(f, "blrl\n");
604     else
605     xlform_b("bclrl");
606     else
607     if (rd == 20)
608     fprintf(f, "blr\n");
609     else
610     xlform_b("bclr");
611     break;
612    
613     case 33:
614     if (ra == rb)
615     fprintf(f, "crnot\tcrb%d,crb%d\n", rd, ra);
616     else
617     xlform_cr("crnor");
618     break;
619    
620     case 50: xlform("rfi"); break;
621     case 129: xlform_cr("crandc"); break;
622     case 150: xlform("isync"); break;
623    
624     case 193:
625     if (ra == rd && rb == rd)
626     fprintf(f, "crclr\tcrb%d\n", rd);
627     else
628     xlform_cr("crxor");
629     break;
630    
631     case 225: xlform_cr("crnand"); break;
632     case 257: xlform_cr("crand"); break;
633    
634     case 289:
635     if (ra == rd && rb == rd)
636     fprintf(f, "crset\tcrb%d\n", rd);
637     else
638     xlform_cr("creqv");
639     break;
640    
641     case 417: xlform_cr("crorc"); break;
642    
643     case 449:
644     if (ra == rb)
645     fprintf(f, "crmove\tcrb%d,crb%d\n", rd, ra);
646     else
647     xlform_cr("cror");
648     break;
649    
650     case 528:
651     if (w & 1)
652     if (rd == 20)
653     fprintf(f, "bctrl\n");
654     else
655     xlform_b("bcctrl");
656     else
657     if (rd == 20)
658     fprintf(f, "bctr\n");
659     else
660     xlform_b("bcctr");
661     break;
662    
663     default:
664     fprintf(f, "?\n");
665     break;
666     }
667     }
668    
669    
670     /*
671     * Disassemble instruction with primary opcode = 31 (X-Form/XO-Form/XFX-Form/XS-Form)
672     */
673    
674     static void disass31(FILE *f, unsigned int adr, unsigned int w)
675     {
676     switch (exop) {
677     case 0:
678     if (rd & 1)
679     xform_crlab("cmpd"); // 64 bit
680     else
681     xform_crlab("cmpw");
682     break;
683    
684     case 4:
685     if (rd == 31 && ra == 0 && rb == 0)
686     xform("trap");
687     else if (to_code[rd] != NULL)
688     fprintf(f, "tw%s\tr%d,r%d\n", to_code[rd], ra, rb);
689     else
690     xform_to("tw");
691     break;
692    
693 gbeauche 1.9 case 6: xform_vls("lvsl"); break;
694     case 7: xform_vls("lvebx"); break;
695 cebix 1.1 case 8: xoform_dab("subfc"); break;
696     case 8+512: xoform_dab("subfco"); break;
697     case 9: case 9+512: xoform_dab("mulhdu"); break; // 64 bit
698     case 10: xoform_dab("addc"); break;
699     case 10+512: xoform_dab("addco"); break;
700     case 11: case 11+512: xoform_dab("mulhwu"); break;
701     case 19: xform_d("mfcr"); break;
702     case 20: xform_ls("lwarx"); break;
703     case 21: xform_ls("ldx"); break; // 64 bit
704     case 23: xform_ls("lwzx"); break;
705     case 24: xform_sabc("slw"); break;
706     case 26: xform_sac("cntlzw"); break;
707     case 27: xform_sabc("sld"); break; // 64 bit
708     case 28: xform_sabc("and"); break;
709    
710     case 32:
711     if (rd & 1)
712     xform_crlab("cmpld"); // 64 bit
713     else
714     xform_crlab("cmplw");
715     break;
716    
717 gbeauche 1.9 case 38: xform_vls("lvsr"); break;
718     case 39: xform_vls("lvehx"); break;
719 cebix 1.1 case 40: xoform_dab("subf"); break;
720     case 40+512: xoform_dab("subfo"); break;
721     case 53: xform_ls("ldux"); break; // 64 bit
722     case 54: xform_ab("dcbst"); break;
723     case 55: xform_ls("lwzux"); break;
724     case 58: xform_sac("cntlzd"); break; // 64 bit
725     case 60: xform_sabc("andc"); break;
726    
727     case 68: // 64 bit
728     if (to_code[rd] != NULL)
729     fprintf(f, "td%s\tr%d,r%d\n", to_code[rd], ra, rb);
730     else
731     xform_to("td");
732     break;
733    
734 gbeauche 1.9 case 71: xform_vls("lvewx"); break;
735 cebix 1.1 case 73: case 73+512: xoform_dab("mulhd"); break; // 64 bit
736     case 75: case 75+512: xoform_dab("mulhw"); break;
737     case 83: xform_d("mfmsr"); break;
738     case 84: xform_ls("ldarx"); break; // 64 bit
739     case 86: xform_ab("dcbf"); break;
740     case 87: xform_ls("lbzx"); break;
741 gbeauche 1.9 case 103: xform_vls("lvx"); break;
742 cebix 1.1 case 104: xoform_da("neg"); break;
743     case 104+512: xoform_da("nego"); break;
744     case 119: xform_ls("lbzux"); break;
745    
746     case 124:
747     if (rd == rb)
748     fprintf(f, "not%s\tr%d,r%d\n", w & 1 ? "." : "", ra, rd);
749     else
750     xform_sabc("nor");
751     break;
752    
753 gbeauche 1.9 case 135: xform_vls("stvebx"); break;
754 cebix 1.1 case 136: xoform_dab("subfe"); break;
755     case 136+512: xoform_dab("subfeo"); break;
756     case 138: xoform_dab("adde"); break;
757     case 138+512: xoform_dab("addeo"); break;
758     case 144: xfxform_crm("mtcrf"); break;
759     case 146: xform_d("mtmsr"); break;
760     case 149: xform_ls("stdx"); break; // 64 bit
761    
762     case 150:
763     if (w & 1)
764     xform_ls("stwcx.");
765     else
766     fprintf(f, "?\n");
767     break;
768    
769     case 151: xform_ls("stwx"); break;
770 gbeauche 1.9 case 167: xform_vls("stvehx"); break;
771 cebix 1.1 case 181: xform_ls("stdux"); break; // 64 bit
772     case 183: xform_ls("stwux"); break;
773 gbeauche 1.9 case 199: xform_vls("stvewx"); break;
774 cebix 1.1 case 200: xoform_da("subfze"); break;
775     case 200+512: xoform_da("subfzeo"); break;
776     case 202: xoform_da("addze"); break;
777     case 202+512: xoform_da("addzeo"); break;
778     case 210: xform_tsr("mtsr"); break;
779    
780     case 214: // 64 bit
781     if (w & 1)
782     xform_ls("stdcx");
783     else
784     fprintf(f, "?\n");
785     break;
786    
787     case 215: xform_ls("stbx"); break;
788 gbeauche 1.9 case 231: xform_vls("stvx"); break;
789 cebix 1.1 case 232: xoform_da("subfme"); break;
790     case 232+512: xoform_da("subfmeo"); break;
791     case 233: xoform_dab("mulld"); break; // 64 bit
792     case 233+512: xoform_dab("mulldo"); break; // 64 bit
793     case 234: xoform_da("addme"); break;
794     case 234+512: xoform_da("addmeo"); break;
795     case 235: xoform_dab("mullw"); break;
796     case 235+512: xoform_dab("mullwo"); break;
797     case 242: xform_db("mtsrin"); break;
798     case 246: xform_ab("dcbtst"); break;
799     case 247: xform_ls("stbux"); break;
800     case 266: xoform_dab("add"); break;
801     case 266+512: xoform_dab("addo"); break;
802     case 278: xform_ab("dcbt"); break;
803     case 279: xform_ls("lhzx"); break;
804     case 284: xform_sabc("eqv"); break;
805     case 306: xform_b("tlbie"); break;
806     case 310: xform_ls("eciwx"); break;
807     case 311: xform_ls("lhzux"); break;
808     case 316: xform_sabc("xor"); break;
809    
810     case 339:
811     if ((ra | (rb << 5)) == 1)
812     fprintf(f, "mfxer\tr%d\n", rd);
813     else if ((ra | (rb << 5)) == 8)
814     fprintf(f, "mflr\tr%d\n", rd);
815     else if ((ra | (rb << 5)) == 9)
816     fprintf(f, "mfctr\tr%d\n", rd);
817 gbeauche 1.9 else if ((ra | (rb << 5)) == 256)
818     fprintf(f, "mfvrsave\tr%d\n", rd);
819 cebix 1.1 else {
820 cebix 1.11 const char *spr = get_spr(ra | (rb << 5));
821 cebix 1.1 if (spr)
822     fprintf(f, "mfspr\tr%d,%s\n", rd, spr);
823     else
824     xfxform_fspr("mfspr");
825     }
826     break;
827    
828     case 341: xform_ls("lwax"); break; // 64 bit
829     case 343: xform_ls("lhax"); break;
830 gbeauche 1.9 case 359: xform_vls("lvxl"); break;
831 cebix 1.1 case 370: xform("tlbia"); break;
832    
833 gbeauche 1.10 case 822: // AltiVec
834     if ((rd & 0xc) == 0 && ra == 0 && rb == 0 && (w & 1) == 0) {
835     if (rd & 0x10)
836     fprintf(f, "dssall\n");
837     else
838     fprintf(f, "dss\t%d\n", rd & 3);
839     }
840     else
841     fprintf(f, "?\n");
842     break;
843    
844     case 342: // AltiVec
845     if ((rd & 0xc) == 0 && (w & 1) == 0)
846     fprintf(f, "dst%s\tr%d,r%d,%d\n", rd & 0x10 ? "t" : "", ra, rb, rd & 3);
847     else
848     fprintf(f, "?\n");
849     break;
850    
851     case 374: // AltiVec
852     if ((rd & 0xc) == 0 && (w & 1) == 0)
853     fprintf(f, "dstst%s\tr%d,r%d,%d\n", rd & 0x10 ? "t" : "", ra, rb, rd & 3);
854     else
855     fprintf(f, "?\n");
856     break;
857    
858 cebix 1.1 case 371:
859     if ((ra | (rb << 5)) == 268)
860     xfxform_tb("mftb");
861     else if ((ra | (rb << 5)) == 269)
862     xfxform_tb("mftbu");
863     else
864     fprintf(f, "?\n");
865     break;
866    
867     case 373: xform_ls("lwaux"); break; // 64 bit
868     case 375: xform_ls("lhaux"); break;
869     case 407: xform_ls("sthx"); break;
870     case 412: xform_sabc("orc"); break;
871     case 434: xform_b("slbie"); break; // 64 bit
872     case 438: xform_ls("ecowx"); break;
873     case 439: xform_ls("sthux"); break;
874    
875     case 444:
876     if (rd == rb)
877     fprintf(f, "mr%s\tr%d,r%d\n", w & 1 ? "." : "", ra, rd);
878     else
879     xform_sabc("or");
880     break;
881    
882     case 457: xoform_dab("divdu"); break; // 64 bit
883     case 457+512: xoform_dab("divduo"); break; // 64 bit
884     case 459: xoform_dab("divwu"); break;
885     case 459+512: xoform_dab("divwuo"); break;
886    
887     case 467:
888     if ((ra | (rb << 5)) == 1)
889     fprintf(f, "mtxer\tr%d\n", rd);
890     else if ((ra | (rb << 5)) == 8)
891     fprintf(f, "mtlr\tr%d\n", rd);
892     else if ((ra | (rb << 5)) == 9)
893     fprintf(f, "mtctr\tr%d\n", rd);
894 gbeauche 1.9 else if ((ra | (rb << 5)) == 256)
895     fprintf(f, "mtvrsave\tr%d\n", rd);
896 cebix 1.1 else {
897 cebix 1.11 const char *spr = get_spr(ra | (rb << 5));
898 cebix 1.1 if (spr)
899     fprintf(f, "mtspr\t%s,r%d\n", spr, rd);
900     else
901     xfxform_tspr("mtspr");
902     }
903     break;
904    
905     case 470: xform_ab("dcbi"); break;
906     case 476: xform_sabc("nand"); break;
907 gbeauche 1.9 case 487: xform_vls("stvxl"); break;
908 cebix 1.1 case 489: xoform_dab("divd"); break; // 64 bit
909     case 489+512: xoform_dab("divdo"); break; // 64 bit
910     case 491: xoform_dab("divw"); break;
911     case 491+512: xoform_dab("divwo"); break;
912     case 498: xform("slbia"); break; // 64 bit
913     case 512: xform_cr("mcrxr"); break;
914     case 533: xform_ls("lswx"); break;
915     case 534: xform_ls("lwbrx"); break;
916     case 535: xform_fls("lfsx"); break;
917     case 536: xform_sabc("srw"); break;
918     case 539: xform_sabc("srd"); break; // 64 bit
919     case 566: xform("tlbsync"); break;
920     case 567: xform_fls("lfsux"); break;
921     case 595: xform_fsr("mfsr"); break;
922     case 597: xform_lsswi("lswi"); break;
923     case 598: xform("sync"); break;
924     case 599: xform_fls("lfdx"); break;
925     case 631: xform_fls("lfdux"); break;
926     case 659: xform_db("mfsrin"); break;
927     case 661: xform_ls("stswx"); break;
928     case 662: xform_ls("stwbrx"); break;
929     case 663: xform_fls("stfsx"); break;
930     case 695: xform_fls("stfsux"); break;
931     case 725: xform_lsswi("stswi"); break;
932     case 727: xform_fls("stfdx"); break;
933     case 758: xform_ab("dcba"); break;
934     case 759: xform_fls("stfdux"); break;
935     case 790: xform_ls("lhbrx"); break;
936     case 792: xform_sabc("sraw"); break;
937     case 794: xform_sabc("srad"); break; // 64 bit
938     case 824: xform_sash("srawi"); break;
939     case 826: case 827: xsform("sradi"); break; // 64 bit
940     case 854: xform("eieio"); break;
941     case 918: xform_ls("sthbrx"); break;
942     case 922: xform_sac("extsh"); break;
943     case 954: xform_sac("extsb"); break;
944     case 978: fprintf(f, "tlbld\tr%d\n", rb); break; // 603
945     case 982: xform_ab("icbi"); break;
946     case 983: xform_fls("stfiwx"); break;
947     case 986: xform_sac("extsw"); break; // 64 bit
948     case 1010: fprintf(f, "tlbli\tr%d\n", rb); break; // 603
949     case 1014: xform_ab("dcbz"); break;
950    
951     default:
952     fprintf(f, "?\n");
953     break;
954     }
955     }
956    
957    
958     /*
959     * Disassemble instruction with primary opcode = 59 (A-Form)
960     */
961    
962     static void disass59(FILE *f, unsigned int adr, unsigned int w)
963     {
964     switch (exop & 0x1f) {
965     case 18: aform_dab("fdivs"); break;
966     case 20: aform_dab("fsubs"); break;
967     case 21: aform_dab("fadds"); break;
968     case 22: aform_db("fsqrts"); break;
969     case 24: aform_db("fres"); break;
970     case 25: aform_dac("fmuls"); break;
971     case 28: aform_dacb("fmsubs"); break;
972     case 29: aform_dacb("fmadds"); break;
973     case 30: aform_dacb("fnmsubs"); break;
974     case 31: aform_dacb("fnmadds"); break;
975    
976     default:
977     fprintf(f, "?\n");
978     break;
979     }
980     }
981    
982    
983     /*
984     * Disassemble instruction with primary opcode = 63 (A-Form/X-Form/XFL-Form)
985     */
986    
987     static void disass63(FILE *f, unsigned int adr, unsigned int w)
988     {
989     if (exop & 0x10)
990     switch (exop & 0x1f) {
991     case 18: aform_dab("fdiv"); break;
992     case 20: aform_dab("fsub"); break;
993     case 21: aform_dab("fadd"); break;
994     case 22: aform_db("fsqrt"); break;
995     case 23: aform_dacb("fsel"); break;
996     case 25: aform_dac("fmul"); break;
997     case 26: aform_db("frsqrte"); break;
998     case 28: aform_dacb("fmsub"); break;
999     case 29: aform_dacb("fmadd"); break;
1000     case 30: aform_dacb("fnmsub"); break;
1001     case 31: aform_dacb("fnmadd"); break;
1002    
1003     default:
1004     fprintf(f, "?\n");
1005     break;
1006     }
1007     else
1008     switch (exop) {
1009     case 0: xform_fcrab("fcmpu"); break;
1010     case 12: xform_fdb("frsp"); break;
1011     case 14: xform_fdb("fctiw"); break;
1012     case 15: xform_fdb("fctiwz"); break;
1013     case 32: xform_fcrab("fcmpo"); break;
1014     case 38: xform_crb("mtfsb1"); break;
1015     case 40: xform_fdb("fneg"); break;
1016     case 64: xform_crcr("mcrfs"); break;
1017     case 70: xform_crb("mtfsb0"); break;
1018     case 72: xform_fdb("fmr"); break;
1019     case 134: xform_cri("mtfsfi"); break;
1020     case 136: xform_fdb("fnabs"); break;
1021     case 264: xform_fdb("fabs"); break;
1022     case 583: xform_fd("mffs"); break;
1023     case 711: xflform("mtfsf"); break;
1024     case 814: xform_fdb("fctid"); break; // 64 bit
1025     case 815: xform_fdb("fctidz"); break; // 64 bit
1026     case 846: xform_fdb("fcfid"); break; // 64 bit
1027    
1028     default:
1029     fprintf(f, "?\n");
1030     break;
1031     }
1032     }
1033    
1034    
1035     /*
1036     * Convert mask begin/end to mask
1037     */
1038    
1039     static unsigned int mbme2mask(int mb, int me)
1040     {
1041     unsigned int m = 0;
1042     int i;
1043    
1044     if (mb <= me)
1045     for (i=mb; i<=me; i++)
1046     m |= 1 << (31-i);
1047     else {
1048     for (i=0; i<=me; i++)
1049     m |= 1 << (31-i);
1050     for (i=mb; i<=31; i++)
1051     m |= 1 << (31-i);
1052     }
1053     return m;
1054     }
1055    
1056    
1057     /*
1058     * Convert SPR number to register name
1059     */
1060    
1061 cebix 1.11 const char *get_spr(int reg)
1062 cebix 1.1 {
1063     switch (reg) {
1064     case 1: return "xer";
1065     case 8: return "lr";
1066     case 9: return "ctr";
1067     case 18: return "dsisr";
1068     case 19: return "dar";
1069     case 22: return "dec";
1070     case 25: return "sdr1";
1071     case 26: return "srr0";
1072     case 27: return "srr1";
1073     case 272: return "sprg0";
1074     case 273: return "sprg1";
1075     case 274: return "sprg2";
1076     case 275: return "sprg3";
1077     case 280: return "asr"; // 64 bit
1078     case 282: return "ear";
1079     case 284: return "tbl";
1080     case 285: return "tbu";
1081     case 287: return "pvr";
1082     case 528: return "ibat0u";
1083     case 529: return "ibat0l";
1084     case 530: return "ibat1u";
1085     case 531: return "ibat1l";
1086     case 532: return "ibat2u";
1087     case 533: return "ibat2l";
1088     case 534: return "ibat3u";
1089     case 535: return "ibat3l";
1090     case 536: return "dbat0u";
1091     case 537: return "dbat0l";
1092     case 538: return "dbat1u";
1093     case 539: return "dbat1l";
1094     case 540: return "dbat2u";
1095     case 541: return "dbat2l";
1096     case 542: return "dbat3u";
1097     case 543: return "dbat3l";
1098     case 1013: return "dabr";
1099    
1100     case 0: return "mq"; // 601
1101     case 4: return "rtcu"; // 601
1102     case 5: return "rtcl"; // 601
1103     case 20: return "rtcu"; // 601
1104     case 21: return "rtcl"; // 601
1105     case 952: return "mmcr0"; // 604
1106     case 953: return "pmc1"; // 604
1107     case 954: return "pmc2"; // 604
1108     case 955: return "sia"; // 604
1109     case 956: return "mmcr1"; // 604e
1110     case 957: return "pmc3"; // 604e
1111     case 958: return "pmc4"; // 604e
1112     case 959: return "sda"; // 604
1113     case 976: return "dmiss"; // 603
1114     case 977: return "dcmp"; // 603
1115     case 978: return "hash1"; // 603
1116     case 979: return "hash2"; // 603
1117     case 980: return "imiss"; // 603
1118     case 981: return "icmp"; // 603
1119     case 982: return "rpa"; // 603
1120     case 1008: return "hid0"; // 601/603/604
1121     case 1009: return "hid1"; // 601/603/604e
1122     case 1010: return "iabr"; // 601/603
1123     case 1023: return "pir"; // 601/604
1124    
1125     case 256: return "vrsave"; // AltiVec
1126    
1127     default: return NULL;
1128     }
1129     }