2 % (c) The AQUA Project, Glasgow University, 1993-1998
4 \section[MachMisc]{Description of various machine-specific things}
7 #include "nativeGen/NCG.h"
15 volatileSaves, volatileRestores,
17 targetMaxDouble, targetMaxInt, targetMinDouble, targetMinInt,
23 Instr(..), IF_ARCH_i386(Operand(..) COMMA,)
26 IF_ARCH_i386(i386_insert_ffrees COMMA,)
34 RI(..), riZero, fpRelEA, moveSp, fPair
36 #if powerpc_TARGET_ARCH
38 , condUnsigned, condToSigned
42 #include "HsVersions.h"
43 #include "../includes/config.h"
45 import AbsCSyn ( MagicId(..) )
46 import AbsCUtils ( magicIdPrimRep )
47 import CLabel ( CLabel, isAsmTemp )
48 import Literal ( mkMachInt, Literal(..) )
49 import MachRegs ( callerSaves,
50 get_MagicId_addr, get_MagicId_reg_or_addr,
51 Imm(..), Reg(..), MachRegsAddr(..)
52 # if sparc_TARGET_ARCH
56 import PrimRep ( PrimRep(..) )
57 import Stix ( StixStmt(..), StixExpr(..), StixReg(..),
58 CodeSegment, DestInfo(..) )
59 import Panic ( panic )
60 import Outputable ( pprPanic, ppr, showSDoc )
61 import Config ( cLeadingUnderscore )
66 import TRACE ( trace )
68 import Maybes ( mapCatMaybes )
72 underscorePrefix :: Bool -- leading underscore on assembler labels?
73 underscorePrefix = (cLeadingUnderscore == "YES")
75 ---------------------------
76 fmtAsmLbl :: String -> String -- for formatting labels
79 {- The alpha assembler likes temporary labels to look like $L123
80 instead of L123. (Don't toss the L, because then Lf28
90 % ----------------------------------------------------------------
92 We (allegedly) put the first six C-call arguments in registers;
93 where do we start putting the rest of them?
95 eXTRA_STK_ARGS_HERE :: Int
97 = IF_ARCH_alpha(0, IF_ARCH_i386(23{-6x4bytes-}, IF_ARCH_sparc(23,
98 IF_ARCH_powerpc( IF_OS_darwin(24,8{-SVR4 ABI: Linux-}), ???))))
101 % - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
103 Now the volatile saves and restores. We add the basic guys to the
104 list of ``user'' registers provided. Note that there are more basic
105 registers on the restore list, because some are reloaded from
108 (@volatileRestores@ used only for wrapper-hungry PrimOps.)
111 volatileSaves, volatileRestores :: [MagicId] -> [StixStmt]
113 volatileSaves = volatileSavesOrRestores True
114 volatileRestores = volatileSavesOrRestores False
116 save_cands = [BaseReg,Sp,SpLim,Hp,HpLim]
117 restore_cands = save_cands
119 volatileSavesOrRestores do_saves vols
120 = mapCatMaybes mkCode vols
123 | case mid of { BaseReg -> True; _ -> False }
124 = panic "volatileSavesOrRestores:BaseReg"
125 | not (callerSaves mid)
127 | otherwise -- must be callee-saves ...
128 = case get_MagicId_reg_or_addr mid of
129 -- If stored in BaseReg, we ain't interested
133 -- OK, it's callee-saves, and in a real reg (rrno).
134 -- We have to cook up some transfer code.
135 {- Note that the use of (StixMagicId mid) here is a bit subtle.
136 Here, we only create those for MagicIds which are stored in
137 a real reg on this arch -- the preceding case on the result
138 of get_MagicId_reg_or_addr guarantees this. Later, when
139 selecting insns, that means these assignments are sure to turn
140 into real reg-to-mem or mem-to-reg moves, rather than being
141 pointless moves from some address in the reg-table
144 -> Just (StAssignMem rep addr
145 (StReg (StixMagicId mid)))
147 -> Just (StAssignReg rep (StixMagicId mid)
150 rep = magicIdPrimRep mid
151 addr = get_MagicId_addr mid
154 % - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
156 Obviously slightly weedy
157 (Note that the floating point values aren't terribly important.)
160 targetMinDouble = MachDouble (-1.7976931348623157e+308)
161 targetMaxDouble = MachDouble (1.7976931348623157e+308)
162 targetMinInt = mkMachInt (-2147483648)
163 targetMaxInt = mkMachInt 2147483647
166 % - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
168 This algorithm for determining the $\log_2$ of exact powers of 2 comes
169 from GCC. It requires bit manipulation primitives, and we use GHC
176 exactLog2 :: Integer -> Maybe Integer
178 = if (x <= 0 || x >= 2147483648) then
181 case iUnbox (fromInteger x) of { x# ->
182 if (w2i ((i2w x#) `and#` (i2w (0# -# x#))) /=# x#) then
185 Just (toInteger (iBox (pow2 x#)))
188 pow2 x# | x# ==# 1# = 0#
189 | otherwise = 1# +# pow2 (w2i (i2w x# `shiftRL#` 1#))
192 % - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
196 #if alpha_TARGET_ARCH
197 = ALWAYS -- For BI (same as BR)
198 | EQQ -- For CMP and BI (NB: "EQ" is a 1.3 Prelude name)
200 | GTT -- For BI only (NB: "GT" is a 1.3 Prelude name)
201 | LE -- For CMP and BI
202 | LTT -- For CMP and BI (NB: "LT" is a 1.3 Prelude name)
204 | NEVER -- For BI (null instruction)
205 | ULE -- For CMP only
206 | ULT -- For CMP only
209 = ALWAYS -- What's really used? ToDo
225 #if sparc_TARGET_ARCH
226 = ALWAYS -- What's really used? ToDo
243 #if powerpc_TARGET_ARCH
256 deriving Eq -- to make an assertion work
261 #if alpha_TARGET_ARCH
264 -- | W -- word (2 bytes): UNUSED
266 | L -- longword (4 bytes)
267 | Q -- quadword (8 bytes)
268 -- | FF -- VAX F-style floating pt: UNUSED
269 -- | GF -- VAX G-style floating pt: UNUSED
270 -- | DF -- VAX D-style floating pt: UNUSED
271 -- | SF -- IEEE single-precision floating pt: UNUSED
272 | TF -- IEEE double-precision floating pt
276 | Bu -- byte (unsigned)
278 | Wu -- word (unsigned)
279 | L -- longword (signed)
280 | Lu -- longword (unsigned)
281 | F -- IEEE single-precision floating pt
282 | DF -- IEEE single-precision floating pt
283 | F80 -- Intel 80-bit internal FP format; only used for spilling
285 #if sparc_TARGET_ARCH || powerpc_TARGET_ARCH
287 | Bu -- byte (unsigned)
288 | H -- halfword (signed, 2 bytes)
289 | Hu -- halfword (unsigned, 2 bytes)
290 | W -- word (4 bytes)
291 | F -- IEEE single-precision floating pt
292 | DF -- IEEE single-precision floating pt
295 primRepToSize :: PrimRep -> Size
297 primRepToSize PtrRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
298 primRepToSize CodePtrRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
299 primRepToSize DataPtrRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
300 primRepToSize RetRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
301 primRepToSize CostCentreRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
302 primRepToSize CharRep = IF_ARCH_alpha(L, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
304 primRepToSize Int8Rep = IF_ARCH_alpha(B, IF_ARCH_i386(B, IF_ARCH_sparc(B, IF_ARCH_powerpc(B, ))))
305 primRepToSize Int16Rep = IF_ARCH_alpha(err,IF_ARCH_i386(W, IF_ARCH_sparc(H, IF_ARCH_powerpc(H, ))))
306 where err = primRepToSize_fail "Int16Rep"
307 primRepToSize Int32Rep = IF_ARCH_alpha(L, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
308 primRepToSize Word8Rep = IF_ARCH_alpha(Bu, IF_ARCH_i386(Bu, IF_ARCH_sparc(Bu, IF_ARCH_powerpc(Bu, ))))
309 primRepToSize Word16Rep = IF_ARCH_alpha(err,IF_ARCH_i386(Wu, IF_ARCH_sparc(Hu, IF_ARCH_powerpc(Hu, ))))
310 where err = primRepToSize_fail "Word16Rep"
311 primRepToSize Word32Rep = IF_ARCH_alpha(L, IF_ARCH_i386(Lu, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
313 primRepToSize IntRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
314 primRepToSize WordRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
315 primRepToSize AddrRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
316 primRepToSize FloatRep = IF_ARCH_alpha(TF, IF_ARCH_i386(F, IF_ARCH_sparc(F, IF_ARCH_powerpc(F, ))))
317 primRepToSize DoubleRep = IF_ARCH_alpha(TF, IF_ARCH_i386(DF, IF_ARCH_sparc(DF, IF_ARCH_powerpc(DF, ))))
318 primRepToSize StablePtrRep = IF_ARCH_alpha(Q, IF_ARCH_i386(L, IF_ARCH_sparc(W, IF_ARCH_powerpc(W, ))))
320 primRepToSize Word64Rep = primRepToSize_fail "Word64Rep"
321 primRepToSize Int64Rep = primRepToSize_fail "Int64Rep"
322 primRepToSize other = primRepToSize_fail (showSDoc (ppr other))
324 primRepToSize_fail str
325 = error ("ERROR: MachMisc.primRepToSize: cannot handle `" ++ str ++ "'.\n\t"
326 ++ "Workaround: use -fvia-C.\n\t"
327 ++ "Perhaps you should report it as a GHC bug,\n\t"
328 ++ "to glasgow-haskell-bugs@haskell.org.")
331 %************************************************************************
333 \subsection{Machine's assembly language}
335 %************************************************************************
337 We have a few common ``instructions'' (nearly all the pseudo-ops) but
338 mostly all of @Instr@ is machine-specific.
342 = COMMENT FastString -- comment pseudo-op
343 | SEGMENT CodeSegment -- {data,text} segment pseudo-op
344 | LABEL CLabel -- global label pseudo-op
345 | ASCII Bool -- True <=> needs backslash conversion
346 String -- the literal string
349 | DELTA Int -- specify current stack offset for
350 -- benefit of subsequent passes
354 #if alpha_TARGET_ARCH
356 -- data Instr continues...
360 | LD Size Reg MachRegsAddr -- size, dst, src
361 | LDA Reg MachRegsAddr -- dst, src
362 | LDAH Reg MachRegsAddr -- dst, src
363 | LDGP Reg MachRegsAddr -- dst, src
364 | LDI Size Reg Imm -- size, dst, src
365 | ST Size Reg MachRegsAddr -- size, src, dst
370 | ABS Size RI Reg -- size, src, dst
371 | NEG Size Bool RI Reg -- size, overflow, src, dst
372 | ADD Size Bool Reg RI Reg -- size, overflow, src, src, dst
373 | SADD Size Size Reg RI Reg -- size, scale, src, src, dst
374 | SUB Size Bool Reg RI Reg -- size, overflow, src, src, dst
375 | SSUB Size Size Reg RI Reg -- size, scale, src, src, dst
376 | MUL Size Bool Reg RI Reg -- size, overflow, src, src, dst
377 | DIV Size Bool Reg RI Reg -- size, unsigned, src, src, dst
378 | REM Size Bool Reg RI Reg -- size, unsigned, src, src, dst
380 -- Simple bit-twiddling.
400 | CMP Cond Reg RI Reg
407 | FADD Size Reg Reg Reg
408 | FDIV Size Reg Reg Reg
409 | FMUL Size Reg Reg Reg
410 | FSUB Size Reg Reg Reg
411 | CVTxy Size Size Reg Reg
412 | FCMP Size Cond Reg Reg Reg
420 | JMP Reg MachRegsAddr Int
422 | JSR Reg MachRegsAddr Int
424 -- Alpha-specific pseudo-ops.
433 #endif /* alpha_TARGET_ARCH */
436 Intel, in their infinite wisdom, selected a stack model for floating
437 point registers on x86. That might have made sense back in 1979 --
438 nowadays we can see it for the nonsense it really is. A stack model
439 fits poorly with the existing nativeGen infrastructure, which assumes
440 flat integer and FP register sets. Prior to this commit, nativeGen
441 could not generate correct x86 FP code -- to do so would have meant
442 somehow working the register-stack paradigm into the register
443 allocator and spiller, which sounds very difficult.
445 We have decided to cheat, and go for a simple fix which requires no
446 infrastructure modifications, at the expense of generating ropey but
447 correct FP code. All notions of the x86 FP stack and its insns have
448 been removed. Instead, we pretend (to the instruction selector and
449 register allocator) that x86 has six floating point registers, %fake0
450 .. %fake5, which can be used in the usual flat manner. We further
451 claim that x86 has floating point instructions very similar to SPARC
452 and Alpha, that is, a simple 3-operand register-register arrangement.
453 Code generation and register allocation proceed on this basis.
455 When we come to print out the final assembly, our convenient fiction
456 is converted to dismal reality. Each fake instruction is
457 independently converted to a series of real x86 instructions.
458 %fake0 .. %fake5 are mapped to %st(0) .. %st(5). To do reg-reg
459 arithmetic operations, the two operands are pushed onto the top of the
460 FP stack, the operation done, and the result copied back into the
461 relevant register. There are only six %fake registers because 2 are
462 needed for the translation, and x86 has 8 in total.
464 The translation is inefficient but is simple and it works. A cleverer
465 translation would handle a sequence of insns, simulating the FP stack
466 contents, would not impose a fixed mapping from %fake to %st regs, and
467 hopefully could avoid most of the redundant reg-reg moves of the
470 We might as well make use of whatever unique FP facilities Intel have
471 chosen to bless us with (let's not be churlish, after all).
472 Hence GLDZ and GLD1. Bwahahahahahahaha!
474 LATER (10 Nov 2000): idiv gives problems with the register spiller,
475 because the spiller is simpleminded and because idiv has fixed uses of
476 %eax and %edx. Rather than make the spiller cleverer, we do away with
477 idiv, and instead have iquot and irem fake (integer) insns, which have
478 no operand register constraints -- ie, they behave like add, sub, mul.
479 The printer-outer transforms them to a sequence of real insns which does
480 the Right Thing (tm). As with the FP stuff, this gives ropey code,
481 but we don't care, since it doesn't get used much. We hope.
486 -- data Instr continues...
490 | MOV Size Operand Operand
491 | MOVZxL Size Operand Operand -- size is the size of operand 1
492 | MOVSxL Size Operand Operand -- size is the size of operand 1
494 -- Load effective address (also a very useful three-operand add instruction :-)
496 | LEA Size Operand Operand
500 | ADD Size Operand Operand
501 | SUB Size Operand Operand
502 | IMUL Size Operand Operand -- signed int mul
503 | MUL Size Operand Operand -- unsigned int mul
504 | IMUL64 Reg Reg -- 32 x 32 -> 64 signed mul
505 -- operand1:operand2 := (operand1[31:0] *signed operand2[31:0])
507 -- Quotient and remainder. SEE comment above -- these are not
508 -- real x86 insns; instead they are expanded when printed
509 -- into a sequence of real insns.
511 | IQUOT Size Operand Operand -- signed quotient
512 | IREM Size Operand Operand -- signed remainder
513 | QUOT Size Operand Operand -- unsigned quotient
514 | REM Size Operand Operand -- unsigned remainder
516 -- Simple bit-twiddling.
518 | AND Size Operand Operand
519 | OR Size Operand Operand
520 | XOR Size Operand Operand
522 | NEGI Size Operand -- NEG instruction (name clash with Cond)
523 | SHL Size Imm Operand -- Only immediate shifts allowed
524 | SAR Size Imm Operand -- Only immediate shifts allowed
525 | SHR Size Imm Operand -- Only immediate shifts allowed
526 | BT Size Imm Operand
531 -- Note that we cheat by treating G{ABS,MOV,NEG} of doubles
532 -- as single instructions right up until we spit them out.
534 -- all the 3-operand fake fp insns are src1 src2 dst
535 -- and furthermore are constrained to be fp regs only.
536 -- IMPORTANT: keep is_G_insn up to date with any changes here
537 | GMOV Reg Reg -- src(fpreg), dst(fpreg)
538 | GLD Size MachRegsAddr Reg -- src, dst(fpreg)
539 | GST Size Reg MachRegsAddr -- src(fpreg), dst
541 | GLDZ Reg -- dst(fpreg)
542 | GLD1 Reg -- dst(fpreg)
544 | GFTOI Reg Reg -- src(fpreg), dst(intreg)
545 | GDTOI Reg Reg -- src(fpreg), dst(intreg)
547 | GITOF Reg Reg -- src(intreg), dst(fpreg)
548 | GITOD Reg Reg -- src(intreg), dst(fpreg)
550 | GADD Size Reg Reg Reg -- src1, src2, dst
551 | GDIV Size Reg Reg Reg -- src1, src2, dst
552 | GSUB Size Reg Reg Reg -- src1, src2, dst
553 | GMUL Size Reg Reg Reg -- src1, src2, dst
555 -- FP compare. Cond must be `elem` [EQQ, NE, LE, LTT, GE, GTT]
556 -- Compare src1 with src2; set the Zero flag iff the numbers are
557 -- comparable and the comparison is True. Subsequent code must
558 -- test the %eflags zero flag regardless of the supplied Cond.
559 | GCMP Cond Reg Reg -- src1, src2
561 | GABS Size Reg Reg -- src, dst
562 | GNEG Size Reg Reg -- src, dst
563 | GSQRT Size Reg Reg -- src, dst
564 | GSIN Size Reg Reg -- src, dst
565 | GCOS Size Reg Reg -- src, dst
566 | GTAN Size Reg Reg -- src, dst
568 | GFREE -- do ffree on all x86 regs; an ugly hack
571 | TEST Size Operand Operand
572 | CMP Size Operand Operand
584 | JMP DestInfo Operand -- possible dests, target
585 | JXX Cond CLabel -- target
586 | CALL (Either Imm Reg)
590 | CLTD -- sign extend %eax into %edx:%eax
593 = OpReg Reg -- register
594 | OpImm Imm -- immediate value
595 | OpAddr MachRegsAddr -- memory reference
598 i386_insert_ffrees :: [Instr] -> [Instr]
599 i386_insert_ffrees insns
600 | any is_G_instr insns
601 = concatMap ffree_before_nonlocal_transfers insns
605 ffree_before_nonlocal_transfers insn
607 CALL _ -> [GFREE, insn]
608 -- Jumps to immediate labels are local
609 JMP _ (OpImm (ImmCLbl clbl)) | isAsmTemp clbl -> [insn]
610 -- If a jump mentions dests, it is a local jump thru
612 JMP (DestInfo _) _ -> [insn]
613 JMP _ _ -> [GFREE, insn]
617 -- if you ever add a new FP insn to the fake x86 FP insn set,
618 -- you must update this too
619 is_G_instr :: Instr -> Bool
622 GMOV _ _ -> True; GLD _ _ _ -> True; GST _ _ _ -> True;
623 GLDZ _ -> True; GLD1 _ -> True;
624 GFTOI _ _ -> True; GDTOI _ _ -> True;
625 GITOF _ _ -> True; GITOD _ _ -> True;
626 GADD _ _ _ _ -> True; GDIV _ _ _ _ -> True
627 GSUB _ _ _ _ -> True; GMUL _ _ _ _ -> True
628 GCMP _ _ _ -> True; GABS _ _ _ -> True
629 GNEG _ _ _ -> True; GSQRT _ _ _ -> True
630 GSIN _ _ _ -> True; GCOS _ _ _ -> True; GTAN _ _ _ -> True;
631 GFREE -> panic "is_G_instr: GFREE (!)"
634 #endif /* i386_TARGET_ARCH */
638 #if sparc_TARGET_ARCH
640 -- data Instr continues...
644 | LD Size MachRegsAddr Reg -- size, src, dst
645 | ST Size Reg MachRegsAddr -- size, src, dst
649 | ADD Bool Bool Reg RI Reg -- x?, cc?, src1, src2, dst
650 | SUB Bool Bool Reg RI Reg -- x?, cc?, src1, src2, dst
651 | UMUL Bool Reg RI Reg -- cc?, src1, src2, dst
652 | SMUL Bool Reg RI Reg -- cc?, src1, src2, dst
653 | RDY Reg -- move contents of Y register to reg
655 -- Simple bit-twiddling.
657 | AND Bool Reg RI Reg -- cc?, src1, src2, dst
658 | ANDN Bool Reg RI Reg -- cc?, src1, src2, dst
659 | OR Bool Reg RI Reg -- cc?, src1, src2, dst
660 | ORN Bool Reg RI Reg -- cc?, src1, src2, dst
661 | XOR Bool Reg RI Reg -- cc?, src1, src2, dst
662 | XNOR Bool Reg RI Reg -- cc?, src1, src2, dst
663 | SLL Reg RI Reg -- src1, src2, dst
664 | SRL Reg RI Reg -- src1, src2, dst
665 | SRA Reg RI Reg -- src1, src2, dst
666 | SETHI Imm Reg -- src, dst
667 | NOP -- Really SETHI 0, %g0, but worth an alias
671 -- Note that we cheat by treating F{ABS,MOV,NEG} of doubles as single instructions
672 -- right up until we spit them out.
674 | FABS Size Reg Reg -- src dst
675 | FADD Size Reg Reg Reg -- src1, src2, dst
676 | FCMP Bool Size Reg Reg -- exception?, src1, src2, dst
677 | FDIV Size Reg Reg Reg -- src1, src2, dst
678 | FMOV Size Reg Reg -- src, dst
679 | FMUL Size Reg Reg Reg -- src1, src2, dst
680 | FNEG Size Reg Reg -- src, dst
681 | FSQRT Size Reg Reg -- src, dst
682 | FSUB Size Reg Reg Reg -- src1, src2, dst
683 | FxTOy Size Size Reg Reg -- src, dst
687 | BI Cond Bool Imm -- cond, annul?, target
688 | BF Cond Bool Imm -- cond, annul?, target
690 | JMP DestInfo MachRegsAddr -- target
691 | CALL (Either Imm Reg) Int Bool -- target, args, terminal
698 riZero (RIImm (ImmInt 0)) = True
699 riZero (RIImm (ImmInteger 0)) = True
700 riZero (RIReg (RealReg 0)) = True
703 -- Calculate the effective address which would be used by the
704 -- corresponding fpRel sequence. fpRel is in MachRegs.lhs,
705 -- alas -- can't have fpRelEA here because of module dependencies.
706 fpRelEA :: Int -> Reg -> Instr
708 = ADD False False fp (RIImm (ImmInt (n * BYTES_PER_WORD))) dst
710 -- Code to shift the stack pointer by n words.
711 moveSp :: Int -> Instr
713 = ADD False False sp (RIImm (ImmInt (n * BYTES_PER_WORD))) sp
715 -- Produce the second-half-of-a-double register given the first half.
717 fPair (RealReg n) | n >= 32 && n `mod` 2 == 0 = RealReg (n+1)
718 fPair other = pprPanic "fPair(sparc NCG)" (ppr other)
719 #endif /* sparc_TARGET_ARCH */
723 #ifdef powerpc_TARGET_ARCH
724 -- data Instr continues...
728 | LD Size Reg MachRegsAddr -- Load size, dst, src
729 | ST Size Reg MachRegsAddr -- Store size, src, dst
730 | STU Size Reg MachRegsAddr -- Store with Update size, src, dst
731 | LIS Reg Imm -- Load Immediate Shifted dst, src
732 | LI Reg Imm -- Load Immediate dst, src
733 | MR Reg Reg -- Move Register dst, src -- also for fmr
735 | CMP Size Reg RI --- size, src1, src2
736 | CMPL Size Reg RI --- size, src1, src2
741 | BL Imm [Reg] -- with list of argument regs
744 | ADD Reg Reg RI -- dst, src1, src2
745 | SUBF Reg Reg Reg -- dst, src1, src2 ; dst = src2 - src1
750 | AND Reg Reg RI -- dst, src1, src2
751 | OR Reg Reg RI -- dst, src1, src2
752 | XOR Reg Reg RI -- dst, src1, src2
753 | XORIS Reg Reg Imm -- XOR Immediate Shifted dst, src1, src2
758 | SLW Reg Reg RI -- shift left word
759 | SRW Reg Reg RI -- shift right word
760 | SRAW Reg Reg RI -- shift right arithmetic word
762 | FADD Size Reg Reg Reg
763 | FSUB Size Reg Reg Reg
764 | FMUL Size Reg Reg Reg
765 | FDIV Size Reg Reg Reg
766 | FNEG Reg Reg -- negate is the same for single and double prec.
770 | FCTIWZ Reg Reg -- convert to integer word
771 -- (but destination is a FP register)
776 condUnsigned GU = True
777 condUnsigned LU = True
778 condUnsigned GEU = True
779 condUnsigned LEU = True
780 condUnsigned _ = False
782 condToSigned GU = GTT
783 condToSigned LU = LTT
784 condToSigned GEU = GE
785 condToSigned LEU = LE
787 #endif /* powerpc_TARGET_ARCH */