3 // Copyright (c) 2009 The University of Edinburgh
4 // All rights reserved.
6 // Redistribution and use in source and binary forms, with or without
7 // modification, are permitted provided that the following conditions are
8 // met: redistributions of source code must retain the above copyright
9 // notice, this list of conditions and the following disclaimer;
10 // redistributions in binary form must reproduce the above copyright
11 // notice, this list of conditions and the following disclaimer in the
12 // documentation and/or other materials provided with the distribution;
13 // neither the name of the copyright holders nor the names of its
14 // contributors may be used to endorse or promote products derived from
15 // this software without specific prior written permission.
17 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
20 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
21 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 ////////////////////////////////////////////////////////////////////
31 // The actual Power ISA decoder
32 // ------------------------------
34 // I've used the Power ISA Book I v2.06 for instruction formats,
35 // opcode numbers, register names, etc.
37 decode PO default Unknown::unknown() {
39 // Unconditionally branch to a PC-relative or absoulute address.
41 18: b({{ NIA = CIA + disp; }},
45 // Conditionally branch to a PC-relative or absoulute address based
47 format BranchDispCondOp {
48 16: bc({{ NIA = CIA + disp; }},
54 // Conditionally branch to an address in a register based on
55 // either CR only or both CR and CTR.
56 format BranchRegCondOp {
57 16: bclr({{ NIA = LR & -4ULL; }}, true, [ IsReturn ]);
58 528: bcctr({{ NIA = CTR & -4ULL; }});
59 560: bctar({{ NIA = TAR & -4ULL; }}, true);
62 // Condition register manipulation instructions.
65 uint32_t crBa = bits(CR, 31 - ba);
66 uint32_t crBb = bits(CR, 31 - bb);
67 CR = insertBits(CR, 31 - bt, crBa & crBb);
71 uint32_t crBa = bits(CR, 31 - ba);
72 uint32_t crBb = bits(CR, 31 - bb);
73 CR = insertBits(CR, 31 - bt, crBa | crBb);
77 uint32_t crBa = bits(CR, 31 - ba);
78 uint32_t crBb = bits(CR, 31 - bb);
79 CR = insertBits(CR, 31 - bt, !(crBa & crBb));
83 uint32_t crBa = bits(CR, 31 - ba);
84 uint32_t crBb = bits(CR, 31 - bb);
85 CR = insertBits(CR, 31 - bt, crBa ^ crBb);
89 uint32_t crBa = bits(CR, 31 - ba);
90 uint32_t crBb = bits(CR, 31 - bb);
91 CR = insertBits(CR, 31 - bt, !(crBa | crBb));
95 uint32_t crBa = bits(CR, 31 - ba);
96 uint32_t crBb = bits(CR, 31 - bb);
97 CR = insertBits(CR, 31 - bt, crBa == crBb);
101 uint32_t crBa = bits(CR, 31 - ba);
102 uint32_t crBb = bits(CR, 31 - bb);
103 CR = insertBits(CR, 31 - bt, crBa & !crBb);
107 uint32_t crBa = bits(CR, 31 - ba);
108 uint32_t crBb = bits(CR, 31 - bb);
109 CR = insertBits(CR, 31 - bt, crBa | !crBb);
115 uint32_t crBfa = bits(CR, 31 - bfa*4, 28 - bfa*4);
116 CR = insertBits(CR, 31 - bf*4, 28 - bf*4, crBfa);
121 150: isync({{ }}, [ IsSerializeAfter ]);
124 default: decode DX_XO {
125 format IntDispArithOp {
126 2: addpcis({{ Rt = NIA + (disp << 16); }});
131 17: IntOp::sc({{ return std::make_shared<SESyscallFault>(); }});
134 34: lbz({{ Rt = Mem_ub; }});
135 40: lhz({{ Rt = Mem_uh; }});
136 42: lha({{ Rt = Mem_sh; }});
137 32: lwz({{ Rt = Mem_uw; }});
141 format LoadDispShiftOp {
142 2: lwa({{ Rt = Mem_sw; }});
143 0: ld({{ Rt = Mem; }});
146 format LoadDispShiftUpdateOp {
147 1: ldu({{ Rt = Mem; }});
152 format StoreDispShiftOp {
153 0: std({{ Mem = Rs; }});
156 format StoreDispShiftUpdateOp {
157 1: stdu({{ Mem = Rs; }});
161 format LoadDispUpdateOp {
162 35: lbzu({{ Rt = Mem_ub; }});
163 41: lhzu({{ Rt = Mem_uh; }});
164 43: lhau({{ Rt = Mem_sh; }});
165 33: lwzu({{ Rt = Mem_uw; }});
169 38: stb({{ Mem_ub = Rs_ub; }});
170 44: sth({{ Mem_uh = Rs_uh; }});
171 36: stw({{ Mem_uw = Rs_uw; }});
174 format StoreDispUpdateOp {
175 39: stbu({{ Mem_ub = Rs_ub; }});
176 45: sthu({{ Mem_uh = Rs_uh; }});
177 37: stwu({{ Mem_uw = Rs_uw; }});
180 format IntImmArithCheckRaOp {
181 14: addi({{ Rt = Ra + simm; }},
183 15: addis({{ Rt = Ra + (simm << 16); }},
184 {{ Rt = simm << 16; }});
187 format IntImmArithOp {
207 int64_t res = Ra_sd * simm;
214 // Arithmetic instructions that use source registers Ra, Rb and Rc,
215 // with destination register Rt.
219 std::tie(std::ignore, res) = multiplyAdd(Ra_sd, Rb_sd, Rc_sd);
225 std::tie(std::ignore, res) = multiplyAdd(Ra, Rb, Rc);
231 std::tie(res, std::ignore) = multiplyAdd(Ra_sd, Rb_sd, Rc_sd);
237 format IntImmCompOp {
240 cr = makeCRField(Ra_sd, simm, xer.so);
242 cr = makeCRField((int32_t)Ra_sd, simm, xer.so);
247 format IntImmCompLogicOp {
250 cr = makeCRField(Ra, uimm, xer.so);
252 cr = makeCRField((uint32_t)Ra, uimm, xer.so);
257 format IntImmLogicOp {
258 24: ori({{ Ra = Rs | uimm; }});
259 25: oris({{ Ra = Rs | (uimm << 16); }});
260 26: xori({{ Ra = Rs ^ uimm; }});
261 27: xoris({{ Ra = Rs ^ (uimm << 16); }});
262 28: andi_({{ Ra = Rs & uimm; }},
264 29: andis_({{ Ra = Rs & (uimm << 16); }},
271 res = rotate(Rs, shift);
272 res = res & bitmask(maskBeg, maskEnd);
278 res = rotate(Rs, Rb);
279 res = res & bitmask(maskBeg, maskEnd);
285 mask = bitmask(maskBeg, maskEnd);
286 res = rotate(Rs, shift);
287 res = (res & mask) | (Ra & ~mask);
292 // There are a large number of instructions that have the same primary
293 // opcode (PO) of 31. In this case, the instructions are of different
294 // forms. For every form, the XO fields may vary in position and width.
295 // The X, XFL, XFX and XL form instructions use bits 21 - 30 and the
296 // XO form instructions use bits 22 - 30 as extended opcode (XO). To
297 // avoid conflicts, instructions of each form have to be defined under
298 // separate decode blocks. However, only a single decode block can be
299 // associated with a particular PO and it will recognize only one type
300 // of XO field. A solution for associating decode blocks for the other
301 // types of XO fields with the same PO is to have the other blocks as
302 // nested default cases.
305 // All loads with an index register. The non-update versions
306 // all use the value 0 if Ra == R0, not the value contained in
307 // R0. Others update Ra with the effective address. In all cases,
308 // Ra and Rb are source registers, Rt is the destintation.
310 87: lbzx({{ Rt = Mem_ub; }});
311 52: lbarx({{ Rt = Mem_ub; Rsv = 1; RsvLen = 1; RsvAddr = EA; }});
312 279: lhzx({{ Rt = Mem_uh; }});
313 343: lhax({{ Rt = Mem_sh; }});
314 116: lharx({{ Rt = Mem_uh; Rsv = 1; RsvLen = 2; RsvAddr = EA; }});
315 790: lhbrx({{ Rt = swap_byte(Mem_uh); }});
316 23: lwzx({{ Rt = Mem_uw; }});
317 341: lwax({{ Rt = Mem_sw; }});
318 20: lwarx({{ Rt = Mem_uw; Rsv = 1; RsvLen = 4; RsvAddr = EA; }});
319 534: lwbrx({{ Rt = swap_byte(Mem_uw); }});
320 21: ldx({{ Rt = Mem; }});
321 84: ldarx({{ Rt = Mem_ud; Rsv = 1; RsvLen = 8; RsvAddr = EA; }});
322 532: ldbrx({{ Rt = swap_byte(Mem); }});
323 535: lfsx({{ Ft_sf = Mem_sf; }});
324 599: lfdx({{ Ft = Mem_df; }});
325 855: lfiwax({{ Ft_uw = Mem; }});
328 format LoadIndexUpdateOp {
329 119: lbzux({{ Rt = Mem_ub; }});
330 311: lhzux({{ Rt = Mem_uh; }});
331 375: lhaux({{ Rt = Mem_sh; }});
332 55: lwzux({{ Rt = Mem_uw; }});
333 373: lwaux({{ Rt = Mem_sw; }});
334 53: ldux({{ Rt = Mem; }});
335 567: lfsux({{ Ft_sf = Mem_sf; }});
336 631: lfdux({{ Ft = Mem_df; }});
339 format StoreIndexOp {
340 215: stbx({{ Mem_ub = Rs_ub; }});
342 bool store_performed = false;
347 store_performed = true;
353 cr.cr0 = ((store_performed ? 0x2 : 0x0) | xer.so);
357 407: sthx({{ Mem_uh = Rs_uh; }});
359 bool store_performed = false;
364 store_performed = true;
370 cr.cr0 = ((store_performed ? 0x2 : 0x0) | xer.so);
374 918: sthbrx({{ Mem_uh = swap_byte(Rs_uh); }});
375 151: stwx({{ Mem_uw = Rs_uw; }});
377 bool store_performed = false;
382 store_performed = true;
388 cr.cr0 = ((store_performed ? 0x2 : 0x0) | xer.so);
392 662: stwbrx({{ Mem_uw = swap_byte(Rs_uw); }});
393 149: stdx({{ Mem = Rs }});
395 bool store_performed = false;
400 store_performed = true;
406 cr.cr0 = ((store_performed ? 0x2 : 0x0) | xer.so);
410 660: stdbrx({{ Mem = swap_byte(Rs); }});
413 format StoreIndexUpdateOp {
414 247: stbux({{ Mem_ub = Rs_ub; }});
415 439: sthux({{ Mem_uh = Rs_uh; }});
416 183: stwux({{ Mem_uw = Rs_uw; }});
417 181: stdux({{ Mem = Rs; }});
422 int64_t src1 = Ra_sw;
423 int64_t src2 = Rb_sw;
424 if ((src1 != INT32_MIN || src2 != -1) && src2 != 0) {
432 uint64_t src1 = Ra_uw;
433 uint64_t src2 = Rb_uw;
442 int64_t src1 = Ra_sd;
443 int64_t src2 = Rb_sd;
444 if ((src1 != INT64_MIN || src2 != -1) && src2 != 0) {
465 cr = makeCRField(Ra_sd, Rb_sd, xer.so);
467 cr = makeCRField((int32_t)Ra_sd, (int32_t)Rb_sd, xer.so);
473 cr = makeCRField(Ra, Rb, xer.so);
475 cr = makeCRField((uint32_t)Ra, (uint32_t)Rb, xer.so);
480 uint32_t src1 = Ra_ub;
481 uint32_t src2 = Rb_uw;
482 uint8_t src2lo = src2 & 0xff;
483 uint8_t src2hi = (src2 >>= 8) & 0xff;
484 uint32_t res = (src2lo <= src1) & (src1 <= src2hi);
486 src2lo = (src2 >>= 8) & 0xff;
487 src2hi = (src2 >>= 8) & 0xff;
488 res = ((src2lo <= src1) & (src1 <= src2hi)) | res;
494 // Based on "Determine if a word has a byte equal to n"
495 // from https://graphics.stanford.edu/~seander/bithacks.html
496 const uint64_t m1 = 0x0101010101010101;
497 const uint64_t m2 = 0x8080808080808080;
498 uint64_t res = Rb ^ (Ra_ub * m1);
499 res = (res - m1) & ~res & m2;
500 cr = (res != 0) << 2;
504 // Integer logic instructions use source registers Rs and Rb,
505 // with destination register Ra.
507 28: and({{ Ra = Rs & Rb; }}, true);
508 316: xor({{ Ra = Rs ^ Rb; }}, true);
509 476: nand({{ Ra = ~(Rs & Rb); }}, true);
510 444: or({{ Ra = Rs | Rb; }}, true);
511 124: nor({{ Ra = ~(Rs | Rb); }}, true);
512 60: andc({{ Ra = Rs & ~Rb; }}, true);
513 284: eqv({{ Ra = ~(Rs ^ Rb); }}, true);
514 412: orc({{ Ra = Rs | ~Rb; }}, true);
515 954: extsb({{ Ra = Rs_sb; }}, true);
516 922: extsh({{ Ra = Rs_sh; }}, true);
517 986: extsw({{ Ra = Rs_sw; }}, true);
518 26: cntlzw({{ Ra = findLeadingZeros(Rs_uw); }}, true);
519 58: cntlzd({{ Ra = findLeadingZeros(Rs); }}, true);
520 538: cnttzw({{ Ra = findTrailingZeros(Rs_uw); }}, true);
521 570: cnttzd({{ Ra = findTrailingZeros(Rs); }}, true);
524 uint64_t mask = 0xff;
526 for (int i = 0; i < 8; ++i) {
527 if ((Rs & mask) == (Rb & mask)) {
536 // Based on "Counting bits set, in parallel"
537 // from https://graphics.stanford.edu/~seander/bithacks.html
538 const uint64_t m1 = 0x5555555555555555ULL;
539 const uint64_t m2 = 0x3333333333333333ULL;
540 const uint64_t m4 = 0x0f0f0f0f0f0f0f0fULL;
542 res = (res & m1) + ((res >> 1) & m1);
543 res = (res & m2) + ((res >> 2) & m2);
544 res = (res & m4) + ((res >> 4) & m4);
549 #if defined(__GNUC__) || (defined(__clang__) && \
550 __has_builtin(__builtin_popcount))
552 uint64_t res = __builtin_popcount(src >> 32);
553 res = (res << 32) | __builtin_popcount(src);
555 // Based on "Counting bits set, in parallel"
556 // from https://graphics.stanford.edu/~seander/bithacks.html
557 const uint64_t m1 = 0x5555555555555555ULL;
558 const uint64_t m2 = 0x3333333333333333ULL;
559 const uint64_t m4 = 0x0f0f0f0f0f0f0f0fULL;
560 const uint64_t m8 = 0x00ff00ff00ff00ffULL;
561 const uint64_t m16 = 0x0000ffff0000ffffULL;
563 res = (res & m1) + ((res >> 1) & m1);
564 res = (res & m2) + ((res >> 2) & m2);
565 res = (res & m4) + ((res >> 4) & m4);
566 res = (res & m8) + ((res >> 8) & m8);
567 res = (res & m16) + ((res >> 16) & m16);
572 506: popcntd({{ Ra = popCount(Rs); }});
576 res = res ^ (res >> 16);
577 res = res ^ (res >> 8);
578 res = res & 0x100000001;
584 res = res ^ (res >> 32);
585 res = res ^ (res >> 16);
586 res = res ^ (res >> 8);
593 for (int i = 0; i < 8; ++i) {
594 int index = (Rs >> (i * 8)) & 0xff;
596 if (Rb & (1ULL << (63 - index))) {
605 // Integer instructions with a shift value.
608 int32_t shift = Rb_sw;
609 uint32_t res = Rs_uw & ~((shift << 26) >> 31);
611 shift = shift & 0x1f;
618 int32_t shift = Rb_sw;
619 uint32_t res = Rs_uw & ~((shift << 26) >> 31);
621 shift = shift & 0x1f;
629 uint32_t shift = Rb_uw;
631 if ((shift & 0x20) != 0) {
638 shift = shift & 0x1f;
640 if (src < 0 && (src & mask(shift)) != 0) {
656 if (src < 0 && (src & mask(shift)) != 0) {
667 format IntConcatShiftOp {
669 int64_t shift = Rb_sd;
670 uint64_t res = Rs & ~((shift << 57) >> 63);
672 shift = shift & 0x3f;
679 int64_t shift = Rb_sd;
680 uint64_t res = Rs & ~((shift << 57) >> 63);
682 shift = shift & 0x3f;
692 if ((shift & 0x40) != 0) {
699 shift = shift & 0x3f;
701 if (src < 0 && (src & mask(shift)) != 0) {
713 format StoreIndexOp {
714 663: stfsx({{ Mem_sf = Fs_sf; }});
715 727: stfdx({{ Mem_df = Fs; }});
716 983: stfiwx({{ Mem = Fs_uw; }});
719 format StoreIndexUpdateOp {
720 695: stfsux({{ Mem_sf = Fs_sf; }});
721 759: stfdux({{ Mem_df = Fs; }});
724 // These instructions all provide data cache hints
728 598: sync({{ }}, [ IsReadBarrier, IsWriteBarrier ]);
729 854: eieio({{ }}, [ IsReadBarrier, IsWriteBarrier ]);
732 // These instructions are of XO form with bit 21 as the OE bit.
733 default: decode XO_XO {
735 // These instructions can all be reduced to the form
736 // Rt = src1 + src2 [+ CA], therefore we just give src1 and src2
737 // (and, if necessary, CA) definitions and let the python script
738 // deal with setting things up correctly. We also give flags to
739 // say which control registers to set.
741 266: add({{ Ra }}, {{ Rb }});
742 40: subf({{ ~Ra }}, {{ Rb }}, {{ 1 }});
743 10: addc({{ Ra }}, {{ Rb }},
745 8: subfc({{ ~Ra }}, {{ Rb }}, {{ 1 }},
747 104: neg({{ ~Ra }}, {{ 1 }});
748 138: adde({{ Ra }}, {{ Rb }}, {{ xer.ca }},
750 234: addme({{ Ra }}, {{ -1ULL }}, {{ xer.ca }},
752 136: subfe({{ ~Ra }}, {{ Rb }}, {{ xer.ca }},
754 232: subfme({{ ~Ra }}, {{ -1ULL }}, {{ xer.ca }},
756 202: addze({{ Ra }}, {{ xer.ca }},
758 200: subfze({{ ~Ra }}, {{ xer.ca }},
762 // Arithmetic instructions all use source registers Ra and Rb,
763 // with destination register Rt.
764 format IntArithCheckRcOp {
766 uint64_t res = (int64_t)Ra_sw * Rb_sw;
772 uint64_t res = (uint64_t)Ra_uw * Rb_uw;
778 int64_t res = (int64_t)Ra_sw * Rb_sw;
779 if (res != (int32_t)res) {
788 std::tie(std::ignore, res) = multiply(Ra_sd, Rb_sd);
794 std::tie(std::ignore, res) = multiply(Ra, Rb);
799 int64_t src1 = Ra_sd;
800 int64_t src2 = Rb_sd;
801 uint64_t res = src1 * src2;
802 std::tie(res, std::ignore) = multiply(src1, src2);
803 if (src1 != 0 && (int64_t)res / src1 != src2) {
811 int32_t src1 = Ra_sw;
812 int32_t src2 = Rb_sw;
813 if ((src1 != INT32_MIN || src2 != -1) && src2 != 0) {
814 Rt = (uint32_t)(src1 / src2);
823 uint32_t src1 = Ra_uw;
824 uint32_t src2 = Rb_uw;
835 int32_t src1 = Ra_sw;
836 int32_t src2 = Rb_sw;
838 if ((src1 != INT32_MIN || src2 != -1) && src2 != 0) {
839 res = ((int64_t)src1 << 32) / src2;
840 if (res == (int32_t)res) {
854 uint32_t src1 = Ra_ud;
855 uint32_t src2 = Rb_ud;
858 res = ((uint64_t)src1 << 32) / src2;
859 if (res <= UINT32_MAX) {
873 int64_t src1 = Ra_sd;
874 int64_t src2 = Rb_sd;
875 if ((src1 != INT64_MIN || src2 != -1) && src2 != 0) {
897 int64_t src1 = Ra_sd;
898 int64_t src2 = Rb_sd;
900 std::tie(setOV, res, std::ignore) = divide(0, src1, src2);
913 std::tie(setOV, res, std::ignore) = divide(0, src1, src2);
923 // These instructions are of XS form and use bits 21 - 29 as XO.
924 default: decode XS_XO {
925 format IntConcatShiftOp {
930 if (src < 0 && (src & mask(shift))) {
949 default: decode XFX_XO {
952 0x20: mfxer({{ Rt = XER; }});
953 0x100: mflr({{ Rt = LR; }});
954 0x120: mfctr({{ Rt = CTR; }});
955 0x1f9: mftar({{ Rt = TAR; }});
959 0x20: mtxer({{ XER = Rs; }});
960 0x100: mtlr({{ LR = Rs; }});
961 0x120: mtctr({{ CTR = Rs; }});
962 0x1f9: mttar({{ TAR = Rs; }});
967 for (int i = 0; i < 8; ++i) {
968 if (((FXM >> i) & 0x1) == 0x1) {
969 mask |= 0xf << (4 * i);
972 CR = (Rs & mask) | (CR & ~mask);
975 19: mfcr({{ Rt = CR; }});
978 CR = insertCRField(CR, BF, XER<31:28>);
988 48: lfs({{ Ft_sf = Mem_sf; }});
989 50: lfd({{ Ft = Mem_df; }});
992 format LoadDispUpdateOp {
993 49: lfsu({{ Ft_sf = Mem_sf; }});
994 51: lfdu({{ Ft = Mem_df; }});
998 52: stfs({{ Mem_sf = Fs_sf; }});
999 54: stfd({{ Mem_df = Fs; }});
1002 format StoreDispUpdateOp {
1003 53: stfsu({{ Mem_sf = Fs_sf; }});
1004 55: stfdu({{ Mem_df = Fs; }});
1007 format FloatArithOp {
1009 21: fadds({{ Ft = Fa + Fb; }});
1010 20: fsubs({{ Ft = Fa - Fb; }});
1011 25: fmuls({{ Ft = Fa * Fc; }});
1012 18: fdivs({{ Ft = Fa / Fb; }});
1013 29: fmadds({{ Ft = (Fa * Fc) + Fb; }});
1014 28: fmsubs({{ Ft = (Fa * Fc) - Fb; }});
1015 31: fnmadds({{ Ft = -((Fa * Fc) + Fb); }});
1016 30: fnmsubs({{ Ft = -((Fa * Fc) - Fb); }});
1021 format FloatArithOp {
1022 21: fadd({{ Ft = Fa + Fb; }});
1023 20: fsub({{ Ft = Fa - Fb; }});
1024 25: fmul({{ Ft = Fa * Fc; }});
1025 18: fdiv({{ Ft = Fa / Fb; }});
1026 29: fmadd({{ Ft = (Fa * Fc) + Fb; }});
1027 28: fmsub({{ Ft = (Fa * Fc) - Fb; }});
1028 31: fnmadd({{ Ft = -((Fa * Fc) + Fb); }});
1029 30: fnmsub({{ Ft = -((Fa * Fc) - Fb); }});
1032 default: decode X_XO {
1033 format FloatRCCheckOp {
1034 72: fmr({{ Ft = Fb; }});
1037 Ft_ud = insertBits(Ft_ud, 63, 0); }});
1040 Ft_ud = insertBits(Ft_ud, 63, 1); }});
1041 40: fneg({{ Ft = -Fb; }});
1044 Ft_ud = insertBits(Ft_ud, 63, Fa_ud<63:63>);
1048 format FloatConvertOp {
1049 12: frsp({{ Ft_sf = Fb; }});
1050 15: fctiwz({{ Ft_sw = (int32_t)trunc(Fb); }});
1055 uint32_t c = makeCRField(Fa, Fb);
1056 Fpscr fpscr = FPSCR;
1057 fpscr.fprf.fpcc = c;
1059 CR = insertCRField(CR, BF, c);
1063 format FloatRCCheckOp {
1064 583: mffs({{ Ft_ud = FPSCR; }});
1066 FPSCR = insertCRField(FPSCR, BF + (8 * (1 - W_FIELD)),
1069 70: mtfsb0({{ FPSCR = insertBits(FPSCR, 31 - BT, 0); }});
1070 38: mtfsb1({{ FPSCR = insertBits(FPSCR, 31 - BT, 1); }});
1072 default: decode XFL_XO {
1074 if (L_FIELD == 1) { FPSCR = Fb_ud; }
1076 for (int i = 0; i < 8; ++i) {
1077 if (bits(FLM, i) == 1) {
1078 int k = 4 * (i + (8 * (1 - W_FIELD)));
1079 FPSCR = insertBits(FPSCR, k + 3, k,
1080 bits(Fb_ud, k + 3, k));