1 ;; Machine description for the TMS320C[34]x for GCC
2 ;; Copyright (C) 1994, 1995, 1996, 1997, 1998,
3 ;; 1999, 2000, 2002, 2004, 2005, 2007 Free Software Foundation, Inc.
5 ;; Contributed by Michael Hayes (m.hayes@elec.canterbury.ac.nz)
6 ;; and Herman Ten Brugge (Haj.Ten.Brugge@net.HCC.nl)
8 ;; This file is part of GCC.
10 ;; GCC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 3, or (at your option)
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING3. If not see
22 ;; <http://www.gnu.org/licenses/>.
26 ; Try using PQImode again for addresses since C30 only uses
27 ; 24-bit addresses. Ideally GCC would emit different insns
28 ; for QImode and Pmode, whether Pmode was QImode or PQImode.
29 ; For addresses we wouldn't have to have a clobber of the CC
30 ; associated with each insn and we could use MPYI in address
31 ; calculations without having to synthesize a proper 32-bit multiply.
33 ; Additional C30/C40 instructions not coded:
34 ; CALLcond, IACK, IDLE, LDE, LDFI, LDII, LDM, NORM, RETIcond
35 ; ROLC, RORC, SIGI, STFI, STII, SUBC, SWI
37 ; Additional C40 instructions not coded:
38 ; LDEP, LDPE, LWRct, LAJcond, RETIcondD
43 ; QImode char, short, int, long (32-bits)
44 ; HImode long long (64-bits)
45 ; QFmode float, double (32-bits)
46 ; HFmode long double (40-bits)
53 ; comparison_operator LT, GT, LE, GE, LTU, GTU, LEU, GEU, EQ, NE
54 ; memory_operand memory [m]
55 ; immediate_operand immediate constant [IKN]
56 ; register_operand register [rf]
57 ; general_operand register, memory, constant [rfmI]
59 ; addr_reg_operand AR0-AR7, pseudo reg [a]
60 ; sp_reg_operand SP [b]
61 ; std_reg_operand AR0-AR7, IR0-IR1, RC, RS, RE, SP, pseudo [c]
62 ; ext_reg_operand R0-R11, pseudo reg [f]
63 ; ext_low_reg_operand R0-R7, pseudo reg [q]
64 ; index_reg_operand IR0-IR1, pseudo reg [x]
65 ; st_reg_operand ST [y]
66 ; dp_reg_operand DP [z]
67 ; stik_const_operand 5-bit const [K]
68 ; src_operand general operand [rfHmI]
69 ; par_ind_operand indirect S mode (ARx + 0, 1, IRx) [S<>]
70 ; parallel_operand par_ind_operand or ext_low_reg_operand
71 ; symbolic_address_operand
72 ; call_address_operand
74 ; ADDI src2, src1, dst three operand op
75 ; ADDI src, dst two operand op
77 ; Note that the predicates are only used when selecting a pattern
78 ; to determine if an operand is valid.
80 ; The constraints then select which of the possible valid operands
81 ; is present (and guide register selection). The actual assembly
82 ; instruction is then selected on the basis of the constraints.
84 ; The extra constraint (valid_operands) is used to determine if
85 ; the combination of operands is legitimate for the pattern.
90 ; a address reg AR0-AR7
92 ; c other int reg AR0-AR7, IR0-IR1, RC, RS, RE
93 ; d fp reg R0-R11 (sets CC when dst)
95 ; f fp reg R0-R11 (sets CC when dst)
96 ; g general reg, memory, constant
97 ; h fp reg (HFmode) R0-R11 (sets CC when dst)
98 ; i immediate int constant
103 ; n immediate int constant with known numeric value
104 ; o offsettable memory
106 ; q low fp reg R0-R7 (sets CC when dst)
107 ; r general reg R0-R11, AR0-AR7, IR0-IR1, RC, RS, RE
108 ; s immediate int constant (value not explicit)
111 ; v repeat count reg RC
113 ; x index reg IR0-IR1
114 ; y status (CC) reg ST
118 ; H fp 16-bit constant
120 ; J signed 8-bit (C4x only)
121 ; K signed 5-bit (C4x only)
123 ; M unsigned 8-bit (C4x only)
124 ; N ones complement of unsigned 16-bit
125 ; O 16-bit high constant
126 ; Q ARx + 9-bit signed disp
127 ; R ARx + 5-bit unsigned disp (C4x only)
128 ; S ARx + 0, 1, IRx disp
129 ; T direct memory operand
130 ; V non offsettable memory
132 ; < memory operand with autodecrement addressing
133 ; > memory operand with autoincrement addressing
134 ; { memory operand with pre-modify addressing
135 ; } memory operand with post-modify addressing
137 ; Note that the 'd', 'f', and 'h' constraints are equivalent.
138 ; The m constraint is equivalent to 'QT<>{}'
140 ; Note we cannot use the 'g' constraint with Pmode (i.e, QImode)
141 ; operations since LEGITIMATE_CONSTANT_P accepts SYMBOL_REF.
142 ; So instead we use 'rIm' for signed operands or 'rLm' for unsigned operands.
144 ; Note that the constraints are used to select the operands
145 ; for a chosen pattern. The constraint that requires the fewest
146 ; instructions to load an operand is chosen.
148 ; Note that the 'r' constraint is mostly only used for src integer register
149 ; operands, while 'c' and 'd' constraints are generally only used for dst
150 ; integer register operands (the 'r' constraint is the union of the 'c' and
151 ; 'd' constraints). When a register satisfying the 'd' constraint
152 ; is used as a dst operand, the CC gets clobbered (except for LDIcond)---but
155 ; The 'f' constraint is only for float register operands---when
156 ; a register satisfying the 'f' constraint is used as a dst operand,
157 ; the CC gets clobbered (except for LDFcond).
159 ; The ! in front of the 'b' constraint says to GCC to disparage the
160 ; use of this constraint. The 'b' constraint applies only to the SP.
162 ; Note that we deal with the condition code CC like some of the RISC
163 ; architectures (arm, sh, sparc) where it is stored in a general register,
164 ; in this case the hard register ST (21). Unlike these other architectures
165 ; that do not set the CC with many instructions, the C[34]x architectures
166 ; sets the CC for many instructions when the destination register is
167 ; an extended precision register. While it would have been easier
168 ; to use the generic cc0 register to store the CC, as with most of
169 ; the other ported architectures, this constrains the setting and testing
170 ; of the CC to be consecutive insns. Thus we would reduce the benefit
171 ; of scheduling instructions to avoid pipeline conflicts and filling of
172 ; delayed branch slots.
174 ; Since the C[34]x has many instructions that set the CC, we pay the
175 ; price of having to explicitly define which insns clobber the CC
176 ; (rather than using the macro NOTICE_UPDATE_CC).
178 ; Note that many patterns say that the CC is clobbered when in fact
179 ; that it may not be (depending on the destination register).
180 ; We have to cover ourselves if an extended precision register
181 ; is allocated to the destination register.
182 ; Unfortunately, it is not easy to tell GCC that the clobbering of CC
183 ; is register dependent. If we could tolerate the ST register being
184 ; copied about, then we could store the CC in a pseudo register and
185 ; use constructs such as (clobber (match_scratch:CC N "&y,X")) to
186 ; indicate that the 'y' class (ST register) is clobbered for the
187 ; first combination of operands but not with the second.
188 ; I tried this approach for a while but reload got unhappy since I
189 ; didn't allow it to move the CC around.
191 ; Note that fundamental operations, such as moves, must not clobber the
192 ; CC. Thus movqi chooses a move instruction that doesn't clobber the CC.
193 ; If GCC wants to combine a move with a compare, it is smart enough to
194 ; chose the move instruction that sets the CC.
196 ; Unfortunately, the C[34]x instruction set does not have arithmetic or
197 ; logical operations that never touch the CC. We thus have to assume
198 ; that the CC may be clobbered at all times. If we define patterns
199 ; such as addqi without the clobber of CC, then GCC will be forced
200 ; to use registers such as the auxiliary registers which can cause
201 ; horrible pipeline conflicts. The tradeoff is that GCC can't now
202 ; sneak in an add instruction between setting and testing of the CC.
204 ; Most of the C[34]x instructions require operands of the following formats,
205 ; where imm represents an immediate constant, dir a direct memory reference,
206 ; ind an indirect memory reference, and reg a register:
208 ; src2 (op2) src1 (op1) dst (op0)
209 ; imm dir ind reg | imm dir ind reg | reg Notes
210 ;---------------------+----------------------+------
211 ; ILH T Q<> r | - - - 0 | r 2 operand
212 ; - - S<> r | - - S<> r | r
213 ; J - R - | - - R r | r C4x
215 ; Arithmetic operations use the I, J constraints for immediate constants,
216 ; while logical operations use the L, J constraints. Floating point
217 ; operations use the H constraint for immediate constants.
219 ; With most instructions the src2 and src1 operands are commutative
220 ; (except for SUB, SUBR, ANDN). The assembler considers
221 ; ADDI 10, R0, R1 and ADDI R0, 10, R1 to be equivalent.
222 ; We thus match src2 and src1 with the src_operand predicate and
223 ; use valid_operands as the extra constraint to reject invalid
224 ; operand combinations. For example, ADDI @foo, @bar, R0.
226 ; Note that we use the ? modifier so that reload doesn't preferentially
227 ; try the alternative where three registers are acceptable as
228 ; operands (whenever an operand requires reloading). Instead it will try
229 ; the 2 operand form which will produce better code since it won't require
230 ; a new spill register.
232 ; Note that the floating point representation of 0.0 on the C4x
233 ; is 0x80000000 (-2147483648). This value produces a warning
234 ; message on 32-bit machines about the decimal constant being so large
235 ; that it is unsigned.
237 ; With two operand instructions patterns having two sets,
238 ; the compare set must come first to keep the combiner happy.
239 ; While the combiner seems to cope most of the time with the
240 ; compare set coming second, it's best to have it first.
243 ; C4x CONSTANT attributes
245 (define_attr "cpu" "c4x,c3x"
247 (cond [(symbol_ref "TARGET_C3X") (const_string "c3x")]
248 (const_string "c4x"))))
251 ; C4x INSN ATTRIBUTES:
253 ; lda load address, non-clobber CC
254 ; store memory store, non-clobber CC
255 ; load_load parallel memory loads, non-clobber CC
256 ; load_store parallel memory load and store, non-clobber CC
257 ; store_load parallel memory store and load, non-clobber CC
258 ; store_store parallel memory stores, non-clobber CC
259 ; unary two operand arithmetic, non-clobber CC
260 ; unarycc two operand arithmetic, clobber CC
261 ; binary three operand arithmetic, non-clobber CC
262 ; binarycc three operand arithmetic, clobber CC
263 ; compare compare, clobber CC
265 ; rets return from subroutine
266 ; jump unconditional branch
267 ; jmpc conditional branch
268 ; db decrement and branch (unconditional)
269 ; dbc decrement and branch (conditional)
273 ; repeat block repeat
274 ; repeat_top block repeat top
276 ; multi multiple instruction
279 ; The only real instructions that affect things are the ones that modify
280 ; address registers and ones that call or jump. Note that the number
281 ; of operands refers to the RTL insn pattern, not the number of explicit
282 ; operands in the machine instruction.
284 (define_attr "type" "lda,store,unary,unarycc,binary,binarycc,compare,call,rets,jump,jmpc,db,dbc,misc,ldp,repeat,repeat_top,laj,load_load,load_store,store_load,store_store,push,pop,multi"
285 (const_string "misc"))
288 ; Some instructions operate on unsigned data constants, some on signed data
289 ; constants, or the ones complement of unsigned constants.
290 ; This differentiates them. Default to signed. This attribute
291 ; is used by the macro SMALL_CONST () (defined in c4x.h) to determine
292 ; whether an immediate integer constant will fit within the instruction,
293 ; or will have to be loaded using direct addressing from memory.
294 ; Note that logical operations assume unsigned integers whereas
295 ; arithmetic operations assume signed integers. Note that the C4x
296 ; small immediate constant (J) used as src2 in three operand instructions
297 ; is always signed. not_uint16 refers to a number that fits into 16-bits
298 ; when one's complemented.
300 (define_attr "data" "int16,uint16,high_16,not_uint16" (const_string "int16"))
302 (define_asm_attributes
303 [(set_attr "type" "multi")])
308 ; Define delay slot scheduling for branch and call instructions.
309 ; The C[34]x has three delay slots. Note that none of the three instructions
310 ; that follow a delayed branch can be a Bcond, BcondD, BR, BRD, DBcond,
311 ; DBcondD, CALL, CALLcond, TRAPcond, RETIcond, RETScond, RPTB, RPTS, or IDLE.
313 ; Annulled branches are a bit difficult because the next instructions
315 ; The table below shows what phase of the c4x is executed.
317 ; op1 fetch, decode and read executed
318 ; op2 fetch and decode executed
320 ; This means that we can allow any instruction in the last delay slot
321 ; and only instructions which modify registers in the first two.
322 ; lda cannot be executed in the first delay slot
323 ; and ldpk cannot be executed in the first two delay slots.
325 (define_attr "onlyreg" "false,true"
326 (cond [(eq_attr "type" "unary,unarycc")
327 (if_then_else (and (match_operand 0 "reg_imm_operand" "")
328 (match_operand 1 "reg_imm_operand" ""))
329 (const_string "true") (const_string "false"))
330 (eq_attr "type" "binary,binarycc")
331 (if_then_else (and (match_operand 0 "reg_imm_operand" "")
332 (and (match_operand 1 "reg_imm_operand" "")
333 (match_operand 2 "reg_imm_operand" "")))
334 (const_string "true") (const_string "false"))]
335 (const_string "false")))
337 (define_attr "onlyreg_nomod" "false,true"
338 (cond [(eq_attr "type" "unary,unarycc,compare,lda,store")
339 (if_then_else (and (match_operand 0 "not_modify_reg" "")
340 (match_operand 1 "not_modify_reg" ""))
341 (const_string "true") (const_string "false"))
342 (eq_attr "type" "binary,binarycc")
343 (if_then_else (and (match_operand 0 "not_modify_reg" "")
344 (and (match_operand 1 "not_modify_reg" "")
345 (match_operand 2 "not_modify_reg" "")))
346 (const_string "true") (const_string "false"))]
347 (const_string "false")))
349 (define_attr "not_repeat_reg" "false,true"
350 (cond [(eq_attr "type" "unary,unarycc,compare,lda,ldp,store")
351 (if_then_else (and (match_operand 0 "not_rc_reg" "")
352 (match_operand 1 "not_rc_reg" ""))
353 (const_string "true") (const_string "false"))
354 (eq_attr "type" "binary,binarycc")
355 (if_then_else (and (match_operand 0 "not_rc_reg" "")
356 (and (match_operand 1 "not_rc_reg" "")
357 (match_operand 2 "not_rc_reg" "")))
358 (const_string "true") (const_string "false"))]
359 (const_string "false")))
361 /* Disable compare because the c4x contains a bug. The cmpi insn sets the CC
362 in the read phase of the pipeline instead of the execution phase when
363 two registers are compared. */
364 (define_attr "in_annul_slot_1" "false,true"
365 (if_then_else (and (and (eq_attr "cpu" "c4x")
366 (eq_attr "type" "!jump,call,rets,jmpc,compare,db,dbc,repeat,repeat_top,laj,push,pop,lda,ldp,multi"))
367 (eq_attr "onlyreg" "true"))
368 (const_string "true")
369 (const_string "false")))
371 (define_attr "in_annul_slot_2" "false,true"
372 (if_then_else (and (and (eq_attr "cpu" "c4x")
373 (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
374 (eq_attr "onlyreg_nomod" "true"))
375 (const_string "true")
376 (const_string "false")))
378 /* Disable ldp because the c4x contains a bug. The ldp insn modifies
379 the dp register when the insn is anulled or not.
380 Also disable autoincrement insns because of a silicon bug. */
381 (define_attr "in_annul_slot_3" "false,true"
382 (if_then_else (and (and (eq_attr "cpu" "c4x")
383 (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
384 (eq_attr "onlyreg_nomod" "true"))
385 (const_string "true")
386 (const_string "false")))
388 (define_attr "in_delay_slot" "false,true"
389 (if_then_else (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
390 (const_string "true")
391 (const_string "false")))
393 (define_attr "in_repeat_slot" "false,true"
394 (if_then_else (and (eq_attr "cpu" "c4x")
395 (and (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
396 (eq_attr "not_repeat_reg" "true")))
397 (const_string "true")
398 (const_string "false")))
400 (define_attr "in_dbc_slot" "false,true"
401 (if_then_else (eq_attr "type" "!jump,call,rets,jmpc,unarycc,binarycc,compare,db,dbc,repeat,repeat_top,laj,multi")
402 (const_string "true")
403 (const_string "false")))
405 (define_delay (eq_attr "type" "jmpc")
406 [(eq_attr "in_delay_slot" "true")
407 (eq_attr "in_annul_slot_1" "true")
408 (eq_attr "in_annul_slot_1" "true")
410 (eq_attr "in_delay_slot" "true")
411 (eq_attr "in_annul_slot_2" "true")
412 (eq_attr "in_annul_slot_2" "true")
414 (eq_attr "in_delay_slot" "true")
415 (eq_attr "in_annul_slot_3" "true")
416 (eq_attr "in_annul_slot_3" "true") ])
419 (define_delay (eq_attr "type" "repeat_top")
420 [(eq_attr "in_repeat_slot" "true") (nil) (nil)
421 (eq_attr "in_repeat_slot" "true") (nil) (nil)
422 (eq_attr "in_repeat_slot" "true") (nil) (nil)])
424 (define_delay (eq_attr "type" "jump,db")
425 [(eq_attr "in_delay_slot" "true") (nil) (nil)
426 (eq_attr "in_delay_slot" "true") (nil) (nil)
427 (eq_attr "in_delay_slot" "true") (nil) (nil)])
430 ; Decrement and branch conditional instructions cannot modify the
431 ; condition codes for the cycles in the delay slots.
433 (define_delay (eq_attr "type" "dbc")
434 [(eq_attr "in_dbc_slot" "true") (nil) (nil)
435 (eq_attr "in_dbc_slot" "true") (nil) (nil)
436 (eq_attr "in_dbc_slot" "true") (nil) (nil)])
438 ; The LAJ instruction has three delay slots but the last slot is
439 ; used for pushing the return address. Thus we can only use two slots.
441 (define_delay (eq_attr "type" "laj")
442 [(eq_attr "in_delay_slot" "true") (nil) (nil)
443 (eq_attr "in_delay_slot" "true") (nil) (nil)])
457 (UNSPEC_LOADHF_INT 8)
458 (UNSPEC_STOREHF_INT 9)
460 (UNSPEC_LOADQF_INT 11)
461 (UNSPEC_STOREQF_INT 12)
470 (UNSPEC_RPTB_INIT 22)
478 ; With the C3x, an external memory write (with no wait states) takes
479 ; two cycles and an external memory read (with no wait states) takes
480 ; one cycle. However, an external read following an external write
481 ; takes two cycles. With internal memory, reads and writes take
483 ; When a C4x address register is loaded it will not be available for
484 ; an extra machine cycle. Calculating with a C4x address register
485 ; makes it unavailable for 2 machine cycles.
487 ; Just some dummy definitions. The real work is done in c4x_adjust_cost.
488 ; These are needed so the min/max READY_DELAY is known.
490 (define_insn_reservation "any_insn" 1 (const_int 1) "nothing")
491 (define_insn_reservation "slowest_insn" 3 (const_int 0) "nothing")
493 ; The attribute setar0 is set to 1 for insns where ar0 is a dst operand.
494 ; Note that the attributes unarycc and binarycc do not apply
495 ; if ar0 is a dst operand (only loading an ext. prec. reg. sets CC)
496 (define_attr "setar0" ""
497 (cond [(eq_attr "type" "unary,binary")
498 (if_then_else (match_operand 0 "ar0_reg_operand" "")
499 (const_int 1) (const_int 0))]
502 (define_attr "setlda_ar0" ""
503 (cond [(eq_attr "type" "lda")
504 (if_then_else (match_operand 0 "ar0_reg_operand" "")
505 (const_int 1) (const_int 0))]
508 ; The attribute usear0 is set to 1 for insns where ar0 is used
509 ; for addressing, as a src operand, or as a dst operand.
510 (define_attr "usear0" ""
511 (cond [(eq_attr "type" "compare,store")
512 (if_then_else (match_operand 0 "ar0_mem_operand" "")
513 (const_int 1) (const_int 0))
514 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
515 (if_then_else (match_operand 1 "ar0_mem_operand" "")
516 (const_int 1) (const_int 0))
517 (eq_attr "type" "binary,binarycc")
518 (if_then_else (match_operand 2 "ar0_mem_operand" "")
519 (const_int 1) (const_int 0))
520 (eq_attr "type" "db,dbc")
521 (if_then_else (match_operand 0 "ar0_reg_operand" "")
522 (const_int 1) (const_int 0))]
525 ; The attribute readar0 is set to 1 for insns where ar0 is a src operand.
526 (define_attr "readar0" ""
527 (cond [(eq_attr "type" "compare")
528 (if_then_else (match_operand 0 "ar0_reg_operand" "")
529 (const_int 1) (const_int 0))
530 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
531 (if_then_else (match_operand 1 "ar0_reg_operand" "")
532 (const_int 1) (const_int 0))
533 (eq_attr "type" "binary,binarycc")
534 (if_then_else (match_operand 2 "ar0_reg_operand" "")
535 (const_int 1) (const_int 0))]
538 (define_attr "setar1" ""
539 (cond [(eq_attr "type" "unary,binary")
540 (if_then_else (match_operand 0 "ar1_reg_operand" "")
541 (const_int 1) (const_int 0))]
544 (define_attr "setlda_ar1" ""
545 (cond [(eq_attr "type" "lda")
546 (if_then_else (match_operand 0 "ar1_reg_operand" "")
547 (const_int 1) (const_int 0))]
550 (define_attr "usear1" ""
551 (cond [(eq_attr "type" "compare,store")
552 (if_then_else (match_operand 0 "ar1_mem_operand" "")
553 (const_int 1) (const_int 0))
554 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
555 (if_then_else (match_operand 1 "ar1_mem_operand" "")
556 (const_int 1) (const_int 0))
557 (eq_attr "type" "binary,binarycc")
558 (if_then_else (match_operand 2 "ar1_mem_operand" "")
559 (const_int 1) (const_int 0))
560 (eq_attr "type" "db,dbc")
561 (if_then_else (match_operand 0 "ar1_reg_operand" "")
562 (const_int 1) (const_int 0))]
565 (define_attr "readar1" ""
566 (cond [(eq_attr "type" "compare")
567 (if_then_else (match_operand 0 "ar1_reg_operand" "")
568 (const_int 1) (const_int 0))
569 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
570 (if_then_else (match_operand 1 "ar1_reg_operand" "")
571 (const_int 1) (const_int 0))
572 (eq_attr "type" "binary,binarycc")
573 (if_then_else (match_operand 2 "ar1_reg_operand" "")
574 (const_int 1) (const_int 0))]
577 (define_attr "setar2" ""
578 (cond [(eq_attr "type" "unary,binary")
579 (if_then_else (match_operand 0 "ar2_reg_operand" "")
580 (const_int 1) (const_int 0))]
583 (define_attr "setlda_ar2" ""
584 (cond [(eq_attr "type" "lda")
585 (if_then_else (match_operand 0 "ar2_reg_operand" "")
586 (const_int 1) (const_int 0))]
589 (define_attr "usear2" ""
590 (cond [(eq_attr "type" "compare,store")
591 (if_then_else (match_operand 0 "ar2_mem_operand" "")
592 (const_int 1) (const_int 0))
593 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
594 (if_then_else (match_operand 1 "ar2_mem_operand" "")
595 (const_int 1) (const_int 0))
596 (eq_attr "type" "binary,binarycc")
597 (if_then_else (match_operand 2 "ar2_mem_operand" "")
598 (const_int 1) (const_int 0))
599 (eq_attr "type" "db,dbc")
600 (if_then_else (match_operand 0 "ar2_reg_operand" "")
601 (const_int 1) (const_int 0))]
604 (define_attr "readar2" ""
605 (cond [(eq_attr "type" "compare")
606 (if_then_else (match_operand 0 "ar2_reg_operand" "")
607 (const_int 1) (const_int 0))
608 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
609 (if_then_else (match_operand 1 "ar2_reg_operand" "")
610 (const_int 1) (const_int 0))
611 (eq_attr "type" "binary,binarycc")
612 (if_then_else (match_operand 2 "ar2_reg_operand" "")
613 (const_int 1) (const_int 0))]
616 (define_attr "setar3" ""
617 (cond [(eq_attr "type" "unary,binary")
618 (if_then_else (match_operand 0 "ar3_reg_operand" "")
619 (const_int 1) (const_int 0))]
622 (define_attr "setlda_ar3" ""
623 (cond [(eq_attr "type" "lda")
624 (if_then_else (match_operand 0 "ar3_reg_operand" "")
625 (const_int 1) (const_int 0))]
628 (define_attr "usear3" ""
629 (cond [(eq_attr "type" "compare,store")
630 (if_then_else (match_operand 0 "ar3_mem_operand" "")
631 (const_int 1) (const_int 0))
632 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
633 (if_then_else (match_operand 1 "ar3_mem_operand" "")
634 (const_int 1) (const_int 0))
635 (eq_attr "type" "binary,binarycc")
636 (if_then_else (match_operand 2 "ar3_mem_operand" "")
637 (const_int 1) (const_int 0))
638 (eq_attr "type" "db,dbc")
639 (if_then_else (match_operand 0 "ar3_reg_operand" "")
640 (const_int 1) (const_int 0))]
643 (define_attr "readar3" ""
644 (cond [(eq_attr "type" "compare")
645 (if_then_else (match_operand 0 "ar3_reg_operand" "")
646 (const_int 1) (const_int 0))
647 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
648 (if_then_else (match_operand 1 "ar3_reg_operand" "")
649 (const_int 1) (const_int 0))
650 (eq_attr "type" "binary,binarycc")
651 (if_then_else (match_operand 2 "ar3_reg_operand" "")
652 (const_int 1) (const_int 0))]
655 (define_attr "setar4" ""
656 (cond [(eq_attr "type" "unary,binary")
657 (if_then_else (match_operand 0 "ar4_reg_operand" "")
658 (const_int 1) (const_int 0))]
661 (define_attr "setlda_ar4" ""
662 (cond [(eq_attr "type" "lda")
663 (if_then_else (match_operand 0 "ar4_reg_operand" "")
664 (const_int 1) (const_int 0))]
667 (define_attr "usear4" ""
668 (cond [(eq_attr "type" "compare,store")
669 (if_then_else (match_operand 0 "ar4_mem_operand" "")
670 (const_int 1) (const_int 0))
671 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
672 (if_then_else (match_operand 1 "ar4_mem_operand" "")
673 (const_int 1) (const_int 0))
674 (eq_attr "type" "binary,binarycc")
675 (if_then_else (match_operand 2 "ar4_mem_operand" "")
676 (const_int 1) (const_int 0))
677 (eq_attr "type" "db,dbc")
678 (if_then_else (match_operand 0 "ar4_reg_operand" "")
679 (const_int 1) (const_int 0))]
682 (define_attr "readar4" ""
683 (cond [(eq_attr "type" "compare")
684 (if_then_else (match_operand 0 "ar4_reg_operand" "")
685 (const_int 1) (const_int 0))
686 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
687 (if_then_else (match_operand 1 "ar4_reg_operand" "")
688 (const_int 1) (const_int 0))
689 (eq_attr "type" "binary,binarycc")
690 (if_then_else (match_operand 2 "ar4_reg_operand" "")
691 (const_int 1) (const_int 0))]
694 (define_attr "setar5" ""
695 (cond [(eq_attr "type" "unary,binary")
696 (if_then_else (match_operand 0 "ar5_reg_operand" "")
697 (const_int 1) (const_int 0))]
700 (define_attr "setlda_ar5" ""
701 (cond [(eq_attr "type" "lda")
702 (if_then_else (match_operand 0 "ar5_reg_operand" "")
703 (const_int 1) (const_int 0))]
706 (define_attr "usear5" ""
707 (cond [(eq_attr "type" "compare,store")
708 (if_then_else (match_operand 0 "ar5_mem_operand" "")
709 (const_int 1) (const_int 0))
710 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
711 (if_then_else (match_operand 1 "ar5_mem_operand" "")
712 (const_int 1) (const_int 0))
713 (eq_attr "type" "binary,binarycc")
714 (if_then_else (match_operand 2 "ar5_mem_operand" "")
715 (const_int 1) (const_int 0))
716 (eq_attr "type" "db,dbc")
717 (if_then_else (match_operand 0 "ar5_reg_operand" "")
718 (const_int 1) (const_int 0))]
721 (define_attr "readar5" ""
722 (cond [(eq_attr "type" "compare")
723 (if_then_else (match_operand 0 "ar5_reg_operand" "")
724 (const_int 1) (const_int 0))
725 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
726 (if_then_else (match_operand 1 "ar5_reg_operand" "")
727 (const_int 1) (const_int 0))
728 (eq_attr "type" "binary,binarycc")
729 (if_then_else (match_operand 2 "ar5_reg_operand" "")
730 (const_int 1) (const_int 0))]
733 (define_attr "setar6" ""
734 (cond [(eq_attr "type" "unary,binary")
735 (if_then_else (match_operand 0 "ar6_reg_operand" "")
736 (const_int 1) (const_int 0))]
739 (define_attr "setlda_ar6" ""
740 (cond [(eq_attr "type" "lda")
741 (if_then_else (match_operand 0 "ar6_reg_operand" "")
742 (const_int 1) (const_int 0))]
745 (define_attr "usear6" ""
746 (cond [(eq_attr "type" "compare,store")
747 (if_then_else (match_operand 0 "ar6_mem_operand" "")
748 (const_int 1) (const_int 0))
749 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
750 (if_then_else (match_operand 1 "ar6_mem_operand" "")
751 (const_int 1) (const_int 0))
752 (eq_attr "type" "binary,binarycc")
753 (if_then_else (match_operand 2 "ar6_mem_operand" "")
754 (const_int 1) (const_int 0))
755 (eq_attr "type" "db,dbc")
756 (if_then_else (match_operand 0 "ar6_reg_operand" "")
757 (const_int 1) (const_int 0))]
760 (define_attr "readar6" ""
761 (cond [(eq_attr "type" "compare")
762 (if_then_else (match_operand 0 "ar6_reg_operand" "")
763 (const_int 1) (const_int 0))
764 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
765 (if_then_else (match_operand 1 "ar6_reg_operand" "")
766 (const_int 1) (const_int 0))
767 (eq_attr "type" "binary,binarycc")
768 (if_then_else (match_operand 2 "ar6_reg_operand" "")
769 (const_int 1) (const_int 0))]
772 (define_attr "setar7" ""
773 (cond [(eq_attr "type" "unary,binary")
774 (if_then_else (match_operand 0 "ar7_reg_operand" "")
775 (const_int 1) (const_int 0))]
778 (define_attr "setlda_ar7" ""
779 (cond [(eq_attr "type" "lda")
780 (if_then_else (match_operand 0 "ar7_reg_operand" "")
781 (const_int 1) (const_int 0))]
784 (define_attr "usear7" ""
785 (cond [(eq_attr "type" "compare,store")
786 (if_then_else (match_operand 0 "ar7_mem_operand" "")
787 (const_int 1) (const_int 0))
788 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
789 (if_then_else (match_operand 1 "ar7_mem_operand" "")
790 (const_int 1) (const_int 0))
791 (eq_attr "type" "binary,binarycc")
792 (if_then_else (match_operand 2 "ar7_mem_operand" "")
793 (const_int 1) (const_int 0))
794 (eq_attr "type" "db,dbc")
795 (if_then_else (match_operand 0 "ar7_reg_operand" "")
796 (const_int 1) (const_int 0))]
799 (define_attr "readar7" ""
800 (cond [(eq_attr "type" "compare")
801 (if_then_else (match_operand 0 "ar7_reg_operand" "")
802 (const_int 1) (const_int 0))
803 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
804 (if_then_else (match_operand 1 "ar7_reg_operand" "")
805 (const_int 1) (const_int 0))
806 (eq_attr "type" "binary,binarycc")
807 (if_then_else (match_operand 2 "ar7_reg_operand" "")
808 (const_int 1) (const_int 0))]
811 (define_attr "setir0" ""
812 (cond [(eq_attr "type" "unary,binary")
813 (if_then_else (match_operand 0 "ir0_reg_operand" "")
814 (const_int 1) (const_int 0))]
817 (define_attr "setlda_ir0" ""
818 (cond [(eq_attr "type" "lda")
819 (if_then_else (match_operand 0 "ir0_reg_operand" "")
820 (const_int 1) (const_int 0))]
823 (define_attr "useir0" ""
824 (cond [(eq_attr "type" "compare,store")
825 (if_then_else (match_operand 0 "ir0_mem_operand" "")
826 (const_int 1) (const_int 0))
827 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
828 (if_then_else (match_operand 1 "ir0_mem_operand" "")
829 (const_int 1) (const_int 0))
830 (eq_attr "type" "binary,binarycc")
831 (if_then_else (match_operand 2 "ir0_mem_operand" "")
832 (const_int 1) (const_int 0))]
835 (define_attr "setir1" ""
836 (cond [(eq_attr "type" "unary,binary")
837 (if_then_else (match_operand 0 "ir1_reg_operand" "")
838 (const_int 1) (const_int 0))]
841 (define_attr "setlda_ir1" ""
842 (cond [(eq_attr "type" "lda")
843 (if_then_else (match_operand 0 "ir1_reg_operand" "")
844 (const_int 1) (const_int 0))]
847 (define_attr "useir1" ""
848 (cond [(eq_attr "type" "compare,store")
849 (if_then_else (match_operand 0 "ir1_mem_operand" "")
850 (const_int 1) (const_int 0))
851 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
852 (if_then_else (match_operand 1 "ir1_mem_operand" "")
853 (const_int 1) (const_int 0))
854 (eq_attr "type" "binary,binarycc")
855 (if_then_else (match_operand 2 "ir1_mem_operand" "")
856 (const_int 1) (const_int 0))]
859 ; With the C3x, things are simpler but slower, i.e. more pipeline conflicts :(
860 ; There are three functional groups:
861 ; (1) AR0-AR7, IR0-IR1, BK
865 ; When a register in one of these functional groups is loaded,
866 ; the contents of that or any other register in its group
867 ; will not be available to the next instruction for 2 machine cycles.
868 ; Similarly, when a register in one of the functional groups is read
869 ; excepting (IR0-IR1, BK, DP) the contents of that or any other register
870 ; in its group will not be available to the next instruction for
873 ; Let's ignore functional groups 2 and 3 for now, since they are not
876 (define_attr "setgroup1" ""
877 (cond [(eq_attr "type" "lda,unary,binary")
878 (if_then_else (match_operand 0 "group1_reg_operand" "")
879 (const_int 1) (const_int 0))]
882 (define_attr "usegroup1" ""
883 (cond [(eq_attr "type" "compare,store,store_store,store_load")
884 (if_then_else (match_operand 0 "group1_mem_operand" "")
885 (const_int 1) (const_int 0))
886 (eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc,load_load,load_store")
887 (if_then_else (match_operand 1 "group1_mem_operand" "")
888 (const_int 1) (const_int 0))
889 (eq_attr "type" "store_store,load_store")
890 (if_then_else (match_operand 2 "group1_mem_operand" "")
891 (const_int 1) (const_int 0))
892 (eq_attr "type" "load_load,store_load")
893 (if_then_else (match_operand 3 "group1_mem_operand" "")
894 (const_int 1) (const_int 0))]
897 (define_attr "readarx" ""
898 (cond [(eq_attr "type" "compare")
899 (if_then_else (match_operand 0 "arx_reg_operand" "")
900 (const_int 1) (const_int 0))
901 (eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
902 (if_then_else (match_operand 1 "arx_reg_operand" "")
903 (const_int 1) (const_int 0))
904 (eq_attr "type" "binary,binarycc")
905 (if_then_else (match_operand 2 "arx_reg_operand" "")
906 (const_int 1) (const_int 0))]
909 (include "predicates.md")
914 ; Note that the movMM and addP patterns can be called during reload
915 ; so we need to take special care with theses patterns since
916 ; we cannot blindly clobber CC or generate new pseudo registers.
919 ; TWO OPERAND INTEGER INSTRUCTIONS
925 (define_insn "set_ldp"
926 [(set (match_operand:QI 0 "dp_reg_operand" "=z")
927 (high:QI (match_operand:QI 1 "" "")))]
929 "* return (TARGET_C3X) ? \"ldp\\t%A1\" : \"ldpk\\t%A1\";"
930 [(set_attr "type" "ldp")])
932 (define_insn "set_ldp_prologue"
933 [(set (match_operand:QI 0 "dp_reg_operand" "=z")
934 (high:QI (match_operand:QI 1 "" "")))]
935 "TARGET_SMALL && TARGET_PARANOID"
936 "* return (TARGET_C3X) ? \"ldp\\t@data_sec\" : \"ldpk\\t@data_sec\";"
937 [(set_attr "type" "ldp")])
939 (define_insn "set_high"
940 [(set (match_operand:QI 0 "std_reg_operand" "=c")
941 (high:QI (match_operand:QI 1 "symbolic_address_operand" "")))]
942 "! TARGET_C3X && ! TARGET_TI"
944 [(set_attr "type" "unary")])
946 (define_insn "set_lo_sum"
947 [(set (match_operand:QI 0 "std_reg_operand" "+c")
948 (lo_sum:QI (match_dup 0)
949 (match_operand:QI 1 "symbolic_address_operand" "")))]
952 [(set_attr "type" "unary")])
955 [(set (match_operand:QI 0 "std_reg_operand" "")
956 (match_operand:QI 1 "symbolic_address_operand" ""))]
957 "reload_completed && ! TARGET_C3X && ! TARGET_TI"
958 [(set (match_dup 0) (high:QI (match_dup 1)))
959 (set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
963 [(set (match_operand:QI 0 "reg_operand" "")
964 (match_operand:QI 1 "const_int_operand" ""))
965 (clobber (reg:QI 16))]
967 && ! IS_INT16_CONST (INTVAL (operands[1]))
968 && ! IS_HIGH_CONST (INTVAL (operands[1]))
970 && std_reg_operand (operands[0], QImode)"
971 [(set (match_dup 0) (match_dup 2))
972 (set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
975 operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
976 operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
980 [(set (match_operand:QI 0 "reg_operand" "")
981 (match_operand:QI 1 "const_int_operand" ""))]
983 && ! IS_INT16_CONST (INTVAL (operands[1]))
984 && ! IS_HIGH_CONST (INTVAL (operands[1]))
986 && std_reg_operand (operands[0], QImode)"
987 [(set (match_dup 0) (match_dup 2))
988 (set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
991 operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
992 operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
996 [(set (match_operand:QI 0 "reg_operand" "")
997 (match_operand:QI 1 "const_int_operand" ""))
998 (clobber (reg:QI 16))]
999 "TARGET_C3X && ! TARGET_SMALL
1000 && ! IS_INT16_CONST (INTVAL (operands[1]))
1002 && std_reg_operand (operands[0], QImode)
1003 && c4x_shiftable_constant (operands[1]) < 0"
1004 [(set (match_dup 0) (match_dup 2))
1005 (set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
1006 (set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
1009 /* Generate two's complement value of 16 MSBs. */
1010 operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
1011 - 0x8000) ^ ~0x7fff);
1012 operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
1013 operands[4] = GEN_INT (16);
1017 [(set (match_operand:QI 0 "reg_operand" "")
1018 (match_operand:QI 1 "const_int_operand" ""))]
1019 "TARGET_C3X && ! TARGET_SMALL
1020 && ! IS_INT16_CONST (INTVAL (operands[1]))
1022 && std_reg_operand (operands[0], QImode)
1023 && c4x_shiftable_constant (operands[1]) < 0"
1024 [(set (match_dup 0) (match_dup 2))
1025 (set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
1026 (set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
1029 /* Generate two's complement value of 16 MSBs. */
1030 operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
1031 - 0x8000) ^ ~0x7fff);
1032 operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
1033 operands[4] = GEN_INT (16);
1037 [(set (match_operand:QI 0 "reg_operand" "")
1038 (match_operand:QI 1 "const_int_operand" ""))
1039 (clobber (reg:QI 16))]
1041 && ! IS_INT16_CONST (INTVAL (operands[1]))
1043 && std_reg_operand (operands[0], QImode)
1044 && c4x_shiftable_constant (operands[1]) >= 0"
1045 [(set (match_dup 0) (match_dup 2))
1046 (set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
1049 /* Generate two's complement value of MSBs. */
1050 int shift = c4x_shiftable_constant (operands[1]);
1052 operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
1053 - 0x8000) ^ ~0x7fff);
1054 operands[3] = GEN_INT (shift);
1058 [(set (match_operand:QI 0 "reg_operand" "")
1059 (match_operand:QI 1 "const_int_operand" ""))]
1061 && ! IS_INT16_CONST (INTVAL (operands[1]))
1063 && std_reg_operand (operands[0], QImode)
1064 && c4x_shiftable_constant (operands[1]) >= 0"
1065 [(set (match_dup 0) (match_dup 2))
1066 (set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
1069 /* Generate two's complement value of MSBs. */
1070 int shift = c4x_shiftable_constant (operands[1]);
1072 operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
1073 - 0x8000) ^ ~0x7fff);
1074 operands[3] = GEN_INT (shift);
1078 [(set (match_operand:QI 0 "reg_operand" "")
1079 (match_operand:QI 1 "const_int_operand" ""))
1080 (clobber (reg:QI 16))]
1082 && ! IS_INT16_CONST (INTVAL (operands[1]))
1083 && ! IS_HIGH_CONST (INTVAL (operands[1]))
1085 && ! std_reg_operand (operands[0], QImode)"
1086 [(set (match_dup 2) (high:QI (match_dup 3)))
1087 (set (match_dup 0) (match_dup 4))
1088 (use (match_dup 1))]
1091 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1092 operands[2] = dp_reg;
1093 operands[3] = force_const_mem (Pmode, operands[1]);
1094 operands[4] = change_address (operands[3], QImode,
1095 gen_rtx_LO_SUM (Pmode, dp_reg,
1096 XEXP (operands[3], 0)));
1097 operands[3] = XEXP (operands[3], 0);
1101 [(set (match_operand:QI 0 "reg_operand" "")
1102 (match_operand:QI 1 "const_int_operand" ""))]
1104 && ! IS_INT16_CONST (INTVAL (operands[1]))
1105 && ! IS_HIGH_CONST (INTVAL (operands[1]))
1107 && ! std_reg_operand (operands[0], QImode)"
1108 [(set (match_dup 2) (high:QI (match_dup 3)))
1109 (set (match_dup 0) (match_dup 4))
1110 (use (match_dup 1))]
1113 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1114 operands[2] = dp_reg;
1115 operands[3] = force_const_mem (Pmode, operands[1]);
1116 operands[4] = change_address (operands[3], QImode,
1117 gen_rtx_LO_SUM (Pmode, dp_reg,
1118 XEXP (operands[3], 0)));
1119 operands[3] = XEXP (operands[3], 0);
1123 [(set (match_operand:QI 0 "reg_operand" "")
1124 (match_operand:QI 1 "const_int_operand" ""))
1125 (clobber (reg:QI 16))]
1127 && ! IS_INT16_CONST (INTVAL (operands[1]))
1128 && ! IS_HIGH_CONST (INTVAL (operands[1]))
1130 && ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
1131 || ! std_reg_operand (operands[0], QImode))"
1132 [(set (match_dup 0) (match_dup 2))
1133 (use (match_dup 1))]
1136 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1137 operands[2] = force_const_mem (Pmode, operands[1]);
1138 operands[2] = change_address (operands[2], QImode,
1139 gen_rtx_LO_SUM (Pmode, dp_reg,
1140 XEXP (operands[2], 0)));
1144 [(set (match_operand:QI 0 "reg_operand" "")
1145 (match_operand:QI 1 "const_int_operand" ""))]
1147 && ! IS_INT16_CONST (INTVAL (operands[1]))
1148 && ! IS_HIGH_CONST (INTVAL (operands[1]))
1150 && ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
1151 || ! std_reg_operand (operands[0], QImode))"
1152 [(set (match_dup 0) (match_dup 2))
1153 (use (match_dup 1))]
1156 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1157 operands[2] = force_const_mem (Pmode, operands[1]);
1158 operands[2] = change_address (operands[2], QImode,
1159 gen_rtx_LO_SUM (Pmode, dp_reg,
1160 XEXP (operands[2], 0)));
1164 [(set (match_operand:HI 0 "reg_operand" "")
1165 (match_operand:HI 1 "const_int_operand" ""))
1166 (clobber (reg:QI 16))]
1168 [(set (match_dup 2) (match_dup 4))
1169 (set (match_dup 3) (match_dup 5))]
1172 operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
1173 operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
1174 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
1175 operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
1179 ; We need to clobber the DP reg to be safe in case we
1180 ; need to load this address from memory
1181 (define_insn "load_immed_address"
1182 [(set (match_operand:QI 0 "reg_operand" "=a?x?c*r")
1183 (match_operand:QI 1 "symbolic_address_operand" ""))
1184 (clobber (reg:QI 16))]
1185 "TARGET_LOAD_ADDRESS"
1187 [(set_attr "type" "multi")])
1191 [(set (match_operand:QI 0 "std_reg_operand" "")
1192 (match_operand:QI 1 "symbolic_address_operand" ""))
1193 (clobber (reg:QI 16))]
1194 "reload_completed && ! TARGET_C3X && ! TARGET_TI"
1195 [(set (match_dup 0) (high:QI (match_dup 1)))
1196 (set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
1199 ; CC has been selected to load a symbolic address. We force the address
1200 ; into memory and then generate LDP and LDIU insns.
1201 ; This is also required for the C30 if we pretend that we can
1202 ; easily load symbolic addresses into a register.
1204 [(set (match_operand:QI 0 "reg_operand" "")
1205 (match_operand:QI 1 "symbolic_address_operand" ""))
1206 (clobber (reg:QI 16))]
1209 && (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
1210 [(set (match_dup 2) (high:QI (match_dup 3)))
1211 (set (match_dup 0) (match_dup 4))
1212 (use (match_dup 1))]
1215 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1216 operands[2] = dp_reg;
1217 operands[3] = force_const_mem (Pmode, operands[1]);
1218 operands[4] = change_address (operands[3], QImode,
1219 gen_rtx_LO_SUM (Pmode, dp_reg,
1220 XEXP (operands[3], 0)));
1221 operands[3] = XEXP (operands[3], 0);
1224 ; This pattern is similar to the above but does not emit a LDP
1225 ; for the small memory model.
1227 [(set (match_operand:QI 0 "reg_operand" "")
1228 (match_operand:QI 1 "symbolic_address_operand" ""))
1229 (clobber (reg:QI 16))]
1232 && (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
1233 [(set (match_dup 0) (match_dup 2))
1234 (use (match_dup 1))]
1237 rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
1238 operands[2] = force_const_mem (Pmode, operands[1]);
1239 operands[2] = change_address (operands[2], QImode,
1240 gen_rtx_LO_SUM (Pmode, dp_reg,
1241 XEXP (operands[2], 0)));
1244 (define_insn "loadhi_big_constant"
1245 [(set (match_operand:HI 0 "reg_operand" "=c*d")
1246 (match_operand:HI 1 "const_int_operand" ""))
1247 (clobber (reg:QI 16))]
1250 [(set_attr "type" "multi")])
1255 ; The following moves will not set the condition codes register.
1258 ; This must come before the general case
1259 (define_insn "*movqi_stik"
1260 [(set (match_operand:QI 0 "memory_operand" "=m")
1261 (match_operand:QI 1 "stik_const_operand" "K"))]
1264 [(set_attr "type" "store")])
1266 (define_insn "loadqi_big_constant"
1267 [(set (match_operand:QI 0 "reg_operand" "=c*d")
1268 (match_operand:QI 1 "const_int_operand" ""))
1269 (clobber (reg:QI 16))]
1270 "! IS_INT16_CONST (INTVAL (operands[1]))
1271 && ! IS_HIGH_CONST (INTVAL (operands[1]))"
1273 [(set_attr "type" "multi")])
1275 ; We must provide an alternative to store to memory in case we have to
1277 (define_insn "movqi_noclobber"
1278 [(set (match_operand:QI 0 "dst_operand" "=d,*c,m,r")
1279 (match_operand:QI 1 "src_hi_operand" "rIm,rIm,r,O"))]
1280 "(REG_P (operands[0]) || REG_P (operands[1])
1281 || GET_CODE (operands[0]) == SUBREG
1282 || GET_CODE (operands[1]) == SUBREG)
1283 && ! symbolic_address_operand (operands[1], QImode)"
1285 if (which_alternative == 2)
1286 return \"sti\\t%1,%0\";
1288 if (! TARGET_C3X && which_alternative == 3)
1290 operands[1] = GEN_INT ((INTVAL (operands[1]) >> 16) & 0xffff);
1291 return \"ldhi\\t%1,%0\";
1294 /* The lda instruction cannot use the same register as source
1296 if (! TARGET_C3X && which_alternative == 1
1297 && ( IS_ADDR_REG (operands[0])
1298 || IS_INDEX_REG (operands[0])
1299 || IS_SP_REG (operands[0]))
1300 && (REGNO (operands[0]) != REGNO (operands[1])))
1301 return \"lda\\t%1,%0\";
1302 return \"ldiu\\t%1,%0\";
1304 [(set_attr "type" "unary,lda,store,unary")
1305 (set_attr "data" "int16,int16,int16,high_16")])
1311 ; We shouldn't need these peepholes, but the combiner seems to miss them...
1313 [(set (match_operand:QI 0 "ext_reg_operand" "=d")
1314 (match_operand:QI 1 "src_operand" "rIm"))
1316 (compare:CC (match_dup 0) (const_int 0)))]
1319 [(set_attr "type" "unarycc")
1320 (set_attr "data" "int16")])
1322 (define_insn "*movqi_set"
1324 (compare:CC (match_operand:QI 1 "src_operand" "rIm")
1326 (set (match_operand:QI 0 "ext_reg_operand" "=d")
1330 [(set_attr "type" "unarycc")
1331 (set_attr "data" "int16")])
1333 ; This pattern probably gets in the way and requires a scratch register
1334 ; when a simple compare with zero will suffice.
1335 ;(define_insn "*movqi_test"
1337 ; (compare:CC (match_operand:QI 1 "src_operand" "rIm")
1339 ; (clobber (match_scratch:QI 0 "=d"))]
1343 ; [(set_attr "type" "unarycc")
1344 ; (set_attr "data" "int16")])
1346 ; If one of the operands is not a register, then we should
1347 ; emit two insns, using a scratch register. This will produce
1348 ; better code in loops if the source operand is invariant, since
1349 ; the source reload can be optimized out. During reload we cannot
1350 ; use change_address or force_reg which will allocate new pseudo regs.
1352 ; Unlike most other insns, the move insns can't be split with
1353 ; different predicates, because register spilling and other parts of
1354 ; the compiler, have memoized the insn number already.
1356 (define_expand "movqi"
1357 [(set (match_operand:QI 0 "general_operand" "")
1358 (match_operand:QI 1 "general_operand" ""))]
1362 if (c4x_emit_move_sequence (operands, QImode))
1367 ; As far as GCC is concerned, the moves are performed in parallel
1368 ; thus it must be convinced that there is no aliasing.
1369 ; It also assumes that the input operands are simultaneously loaded
1370 ; and then the output operands are simultaneously stored.
1371 ; With the C4x, if there are parallel stores to the same address
1372 ; both stores are executed.
1373 ; If there is a parallel load and store to the same address,
1374 ; the load is performed first.
1375 ; The problem with this pattern is that reload can spoil
1376 ; the show when it eliminates a reference to the frame pointer.
1377 ; This can invalidate the memory addressing mode, i.e., when
1378 ; the displacement is greater than 1.
1379 (define_insn "movqi_parallel"
1380 [(set (match_operand:QI 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
1381 (match_operand:QI 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
1382 (set (match_operand:QI 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
1383 (match_operand:QI 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
1384 "TARGET_PARALLEL && valid_parallel_load_store (operands, QImode)"
1386 ldi1\\t%1,%0\\n||\\tldi2\\t%3,%2
1387 sti1\\t%1,%0\\n||\\tsti2\\t%3,%2
1388 ldi\\t%1,%0\\n||\\tsti\\t%3,%2
1389 ldi\\t%3,%2\\n||\\tsti\\t%1,%0"
1390 [(set_attr "type" "load_load,store_store,load_store,store_load")])
1395 (define_insn "pushqi"
1396 [(set (mem:QI (pre_inc:QI (reg:QI 20)))
1397 (match_operand:QI 0 "reg_operand" "r"))]
1400 [(set_attr "type" "push")])
1402 (define_insn "push_st"
1403 [(set (mem:QI (pre_inc:QI (reg:QI 20)))
1404 (unspec:QI [(reg:QI 21)] UNSPEC_PUSH_ST))
1408 [(set_attr "type" "push")])
1410 (define_insn "push_dp"
1411 [(set (mem:QI (pre_inc:QI (reg:QI 20)))
1412 (unspec:QI [(reg:QI 16)] UNSPEC_PUSH_DP))
1416 [(set_attr "type" "push")])
1418 (define_insn "popqi"
1419 [(set (match_operand:QI 0 "reg_operand" "=r")
1420 (mem:QI (post_dec:QI (reg:QI 20))))
1421 (clobber (reg:CC 21))]
1424 [(set_attr "type" "pop")])
1426 (define_insn "pop_st"
1427 [(set (unspec:QI [(reg:QI 21)] UNSPEC_POP_ST)
1428 (mem:QI (post_dec:QI (reg:QI 20))))
1429 (clobber (reg:CC 21))]
1432 [(set_attr "type" "pop")])
1434 (define_insn "pop_dp"
1435 [(set (unspec:QI [(reg:QI 16)] UNSPEC_POP_DP)
1436 (mem:QI (post_dec:QI (reg:QI 20))))
1437 (clobber (reg:CC 16))]
1440 [(set_attr "type" "pop")])
1442 (define_insn "popqi_unspec"
1443 [(set (unspec:QI [(match_operand:QI 0 "reg_operand" "=r")] UNSPEC_POPQI)
1444 (mem:QI (post_dec:QI (reg:QI 20))))
1445 (clobber (match_dup 0))
1446 (clobber (reg:CC 21))]
1449 [(set_attr "type" "pop")])
1454 (define_expand "absqi2"
1455 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1456 (abs:QI (match_operand:QI 1 "src_operand" "")))
1457 (clobber (reg:CC_NOOV 21))])]
1461 (define_insn "*absqi2_clobber"
1462 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1463 (abs:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
1464 (clobber (reg:CC_NOOV 21))]
1467 [(set_attr "type" "unarycc,unary")
1468 (set_attr "data" "int16,int16")])
1470 (define_insn "*absqi2_noclobber"
1471 [(set (match_operand:QI 0 "std_reg_operand" "=c")
1472 (abs:QI (match_operand:QI 1 "src_operand" "rIm")))]
1475 [(set_attr "type" "unary")
1476 (set_attr "data" "int16")])
1479 [(set (match_operand:QI 0 "std_reg_operand" "")
1480 (abs:QI (match_operand:QI 1 "src_operand" "")))
1481 (clobber (reg:CC_NOOV 21))]
1484 (abs:QI (match_dup 1)))]
1487 (define_insn "*absqi2_test"
1488 [(set (reg:CC_NOOV 21)
1489 (compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
1491 (clobber (match_scratch:QI 0 "=d"))]
1494 [(set_attr "type" "unarycc")
1495 (set_attr "data" "int16")])
1497 (define_insn "*absqi2_set"
1498 [(set (reg:CC_NOOV 21)
1499 (compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
1501 (set (match_operand:QI 0 "ext_reg_operand" "=d")
1502 (abs:QI (match_dup 1)))]
1505 [(set_attr "type" "unarycc")
1506 (set_attr "data" "int16")])
1511 (define_expand "negqi2"
1512 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1513 (neg:QI (match_operand:QI 1 "src_operand" "")))
1514 (clobber (reg:CC_NOOV 21))])]
1518 (define_insn "*negqi2_clobber"
1519 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1520 (neg:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
1521 (clobber (reg:CC_NOOV 21))]
1524 [(set_attr "type" "unarycc,unary")
1525 (set_attr "data" "int16,int16")])
1527 (define_insn "*negqi2_noclobber"
1528 [(set (match_operand:QI 0 "std_reg_operand" "=c")
1529 (neg:QI (match_operand:QI 1 "src_operand" "rIm")))]
1532 [(set_attr "type" "unary")
1533 (set_attr "data" "int16")])
1536 [(set (match_operand:QI 0 "std_reg_operand" "")
1537 (neg:QI (match_operand:QI 1 "src_operand" "")))
1538 (clobber (reg:CC_NOOV 21))]
1541 (neg:QI (match_dup 1)))]
1544 (define_insn "*negqi2_test"
1545 [(set (reg:CC_NOOV 21)
1546 (compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
1548 (clobber (match_scratch:QI 0 "=d"))]
1551 [(set_attr "type" "unarycc")
1552 (set_attr "data" "int16")])
1554 (define_insn "*negqi2_set"
1555 [(set (reg:CC_NOOV 21)
1556 (compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
1558 (set (match_operand:QI 0 "ext_reg_operand" "=d")
1559 (neg:QI (match_dup 1)))]
1562 [(set_attr "type" "unarycc")
1563 (set_attr "data" "int16")])
1565 (define_insn "*negbqi2_clobber"
1566 [(set (match_operand:QI 0 "ext_reg_operand" "=d")
1567 (neg:QI (match_operand:QI 1 "src_operand" "rIm")))
1568 (use (reg:CC_NOOV 21))
1569 (clobber (reg:CC_NOOV 21))]
1572 [(set_attr "type" "unarycc")
1573 (set_attr "data" "int16")])
1578 (define_expand "one_cmplqi2"
1579 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1580 (not:QI (match_operand:QI 1 "lsrc_operand" "")))
1581 (clobber (reg:CC 21))])]
1585 (define_insn "*one_cmplqi2_clobber"
1586 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1587 (not:QI (match_operand:QI 1 "lsrc_operand" "rLm,rLm")))
1588 (clobber (reg:CC 21))]
1591 [(set_attr "type" "unarycc,unary")
1592 (set_attr "data" "uint16,uint16")])
1594 (define_insn "*one_cmplqi2_noclobber"
1595 [(set (match_operand:QI 0 "std_reg_operand" "=c")
1596 (not:QI (match_operand:QI 1 "lsrc_operand" "rLm")))]
1599 [(set_attr "type" "unary")
1600 (set_attr "data" "uint16")])
1603 [(set (match_operand:QI 0 "std_reg_operand" "")
1604 (not:QI (match_operand:QI 1 "lsrc_operand" "")))
1605 (clobber (reg:CC 21))]
1608 (not:QI (match_dup 1)))]
1611 (define_insn "*one_cmplqi2_test"
1613 (compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
1615 (clobber (match_scratch:QI 0 "=d"))]
1618 [(set_attr "type" "unarycc")
1619 (set_attr "data" "uint16")])
1621 (define_insn "*one_cmplqi2_set"
1623 (compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
1625 (set (match_operand:QI 0 "ext_reg_operand" "=d")
1626 (not:QI (match_dup 1)))]
1629 [(set_attr "type" "unarycc")
1630 (set_attr "data" "uint16")])
1632 (define_insn "*one_cmplqi2_const_clobber"
1633 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1634 (match_operand:QI 1 "not_const_operand" "N,N"))
1635 (clobber (reg:CC 21))]
1640 [(set_attr "type" "unarycc,unary")
1641 (set_attr "data" "not_uint16,not_uint16")])
1643 ; movqi can use this for loading an integer that can't normally
1644 ; fit into a 16-bit signed integer. The drawback is that it cannot
1645 ; go into R0-R11 since that will clobber the CC and movqi shouldn't
1646 ; do that. This can cause additional reloading but in most cases
1647 ; this will cause only an additional register move. With the large
1648 ; memory model we require an extra instruction to load DP anyway,
1649 ; if we're loading the constant from memory. The big advantage of
1650 ; allowing constants that satisfy not_const_operand in movqi, is that
1651 ; it allows andn to be generated more often.
1652 ; However, there is a problem if GCC has decided that it wants
1653 ; to use R0-R11, since we won't have a matching pattern...
1654 ; In interim, we prevent immed_const allowing `N' constants.
1655 (define_insn "*one_cmplqi2_const_noclobber"
1656 [(set (match_operand:QI 0 "std_reg_operand" "=c")
1657 (match_operand:QI 1 "not_const_operand" "N"))]
1660 [(set_attr "type" "unary")
1661 (set_attr "data" "not_uint16")])
1666 (define_expand "rotlqi3"
1667 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1668 (rotate:QI (match_operand:QI 1 "reg_operand" "")
1669 (match_operand:QI 2 "const_int_operand" "")))
1670 (clobber (reg:CC 21))])]
1672 "if (INTVAL (operands[2]) > 4)
1673 FAIL; /* Open code as two shifts and an or */
1674 if (INTVAL (operands[2]) > 1)
1679 /* If we have 4 or fewer shifts, then it is probably faster
1680 to emit separate ROL instructions. A C3x requires
1681 at least 4 instructions (a C4x requires at least 3), to
1682 perform a rotation by shifts. */
1685 for (i = 0; i < INTVAL (operands[2]) - 1; i++)
1687 tmp = gen_reg_rtx (QImode);
1688 emit_insn (gen_rotl_1_clobber (tmp, operands[1]));
1691 emit_insn (gen_rotl_1_clobber (operands[0], tmp));
1695 (define_insn "rotl_1_clobber"
1696 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1697 (rotate:QI (match_operand:QI 1 "reg_operand" "0,0")
1699 (clobber (reg:CC 21))]
1702 [(set_attr "type" "unarycc,unary")])
1703 ; Default to int16 data attr.
1708 (define_expand "rotrqi3"
1709 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1710 (rotatert:QI (match_operand:QI 1 "reg_operand" "")
1711 (match_operand:QI 2 "const_int_operand" "")))
1712 (clobber (reg:CC 21))])]
1714 "if (INTVAL (operands[2]) > 4)
1715 FAIL; /* Open code as two shifts and an or */
1716 if (INTVAL (operands[2]) > 1)
1721 /* If we have 4 or fewer shifts, then it is probably faster
1722 to emit separate ROL instructions. A C3x requires
1723 at least 4 instructions (a C4x requires at least 3), to
1724 perform a rotation by shifts. */
1727 for (i = 0; i < INTVAL (operands[2]) - 1; i++)
1729 tmp = gen_reg_rtx (QImode);
1730 emit_insn (gen_rotr_1_clobber (tmp, operands[1]));
1733 emit_insn (gen_rotr_1_clobber (operands[0], tmp));
1737 (define_insn "rotr_1_clobber"
1738 [(set (match_operand:QI 0 "reg_operand" "=d,c")
1739 (rotatert:QI (match_operand:QI 1 "reg_operand" "0,0")
1741 (clobber (reg:CC 21))]
1744 [(set_attr "type" "unarycc,unary")])
1745 ; Default to int16 data attr.
1749 ; THREE OPERAND INTEGER INSTRUCTIONS
1755 ; This is used by reload when it calls gen_add2_insn for address arithmetic
1756 ; so we must emit the pattern that doesn't clobber CC.
1758 (define_expand "addqi3"
1759 [(parallel [(set (match_operand:QI 0 "std_or_reg_operand" "")
1760 (plus:QI (match_operand:QI 1 "src_operand" "")
1761 (match_operand:QI 2 "src_operand" "")))
1762 (clobber (reg:CC_NOOV 21))])]
1764 "legitimize_operands (PLUS, operands, QImode);
1765 if (reload_in_progress
1766 || (! IS_PSEUDO_REG (operands[0])
1767 && ! IS_EXT_REG (operands[0])))
1769 emit_insn (gen_addqi3_noclobber (operands[0], operands[1], operands[2]));
1773 ; This pattern is required primarily for manipulating the stack pointer
1774 ; where GCC doesn't expect CC to be clobbered or for calculating
1775 ; addresses during reload. Since this is a more specific pattern
1776 ; it needs to go first (otherwise we get into problems trying to decide
1778 (define_insn "addqi3_noclobber"
1779 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
1780 (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1781 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
1782 "valid_operands (PLUS, operands, QImode)"
1787 [(set_attr "type" "binary,binary,binary")])
1788 ; Default to int16 data attr.
1790 (define_insn "*addqi3_clobber"
1791 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
1792 (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
1793 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
1794 (clobber (reg:CC_NOOV 21))]
1795 "valid_operands (PLUS, operands, QImode)"
1803 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
1804 ; Default to int16 data attr.
1807 [(set (match_operand:QI 0 "std_reg_operand" "")
1808 (plus:QI (match_operand:QI 1 "src_operand" "")
1809 (match_operand:QI 2 "src_operand" "")))
1810 (clobber (reg:CC_NOOV 21))]
1813 (plus:QI (match_dup 1)
1817 (define_insn "*addqi3_test"
1818 [(set (reg:CC_NOOV 21)
1819 (compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1820 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
1822 (clobber (match_scratch:QI 0 "=d,d,d"))]
1823 "valid_operands (PLUS, operands, QImode)"
1828 [(set_attr "type" "binarycc,binarycc,binarycc")])
1829 ; Default to int16 data attr.
1831 ; gcc does this in combine.c we just reverse it here
1832 (define_insn "*cmp_neg"
1833 [(set (reg:CC_NOOV 21)
1834 (compare:CC_NOOV (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1835 (neg: QI (match_operand:QI 2 "src_operand" "g,JR,rS<>"))))
1836 (clobber (match_scratch:QI 0 "=d,d,d"))]
1837 "valid_operands (PLUS, operands, QImode)"
1842 [(set_attr "type" "binarycc,binarycc,binarycc")])
1845 [(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
1846 (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1847 (match_operand:QI 2 "src_operand" "g,JR,rS<>")))
1848 (clobber (reg:CC_NOOV 21))])
1849 (set (reg:CC_NOOV 21)
1850 (compare:CC_NOOV (match_dup 0) (const_int 0)))]
1851 "valid_operands (PLUS, operands, QImode)"
1856 [(set_attr "type" "binarycc,binarycc,binarycc")])
1858 (define_insn "*addqi3_set"
1859 [(set (reg:CC_NOOV 21)
1860 (compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1861 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
1863 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
1864 (plus:QI (match_dup 1) (match_dup 2)))]
1865 "valid_operands (PLUS, operands, QImode)"
1870 [(set_attr "type" "binarycc,binarycc,binarycc")])
1871 ; Default to int16 data attr.
1874 ; This pattern is required during reload when eliminate_regs_in_insn
1875 ; effectively converts a move insn into an add insn when the src
1876 ; operand is the frame pointer plus a constant. Without this
1877 ; pattern, gen_addqi3 can be called with a register for operand0
1878 ; that can clobber CC.
1879 ; For example, we may have (set (mem (reg ar0)) (reg 99))
1880 ; with (set (reg 99) (plus (reg ar3) (const_int 8)))
1881 ; Now since ar3, the frame pointer, is unchanging within the function,
1882 ; (plus (reg ar3) (const_int 8)) is considered a constant.
1883 ; eliminate_regs_in_insn substitutes this constant to give
1884 ; (set (mem (reg ar0)) (plus (reg ar3) (const_int 8))).
1885 ; This is an invalid C4x insn but if we don't provide a pattern
1886 ; for it, it will be considered to be a move insn for reloading.
1887 (define_insn "*addqi3_noclobber_reload"
1888 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
1889 (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
1890 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
1891 "reload_in_progress"
1896 [(set_attr "type" "binary,binary,binary")])
1897 ; Default to int16 data attr.
1900 (define_insn "*addqi3_carry_clobber"
1901 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
1902 (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
1903 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
1904 (use (reg:CC_NOOV 21))
1905 (clobber (reg:CC_NOOV 21))]
1906 "valid_operands (PLUS, operands, QImode)"
1914 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
1915 ; Default to int16 data attr.
1921 (define_expand "subqi3"
1922 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
1923 (minus:QI (match_operand:QI 1 "src_operand" "")
1924 (match_operand:QI 2 "src_operand" "")))
1925 (clobber (reg:CC_NOOV 21))])]
1927 "legitimize_operands (MINUS, operands, QImode);")
1929 (define_insn "*subqi3_clobber"
1930 [(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
1931 (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
1932 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
1933 (clobber (reg:CC_NOOV 21))]
1934 "valid_operands (MINUS, operands, QImode)"
1944 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
1945 ; Default to int16 data attr.
1948 [(set (match_operand:QI 0 "std_reg_operand" "")
1949 (minus:QI (match_operand:QI 1 "src_operand" "")
1950 (match_operand:QI 2 "src_operand" "")))
1951 (clobber (reg:CC_NOOV 21))]
1954 (minus:QI (match_dup 1)
1958 (define_insn "*subqi3_test"
1959 [(set (reg:CC_NOOV 21)
1960 (compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
1961 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
1963 (clobber (match_scratch:QI 0 "=d,d,d,?d"))]
1964 "valid_operands (MINUS, operands, QImode)"
1970 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
1971 ; Default to int16 data attr.
1974 [(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
1975 (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
1976 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))
1977 (clobber (reg:CC_NOOV 21))])
1978 (set (reg:CC_NOOV 21)
1979 (compare:CC_NOOV (match_dup 0) (const_int 0)))]
1980 "valid_operands (MINUS, operands, QImode)"
1986 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
1988 (define_insn "*subqi3_set"
1989 [(set (reg:CC_NOOV 21)
1990 (compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
1991 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
1993 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
1994 (minus:QI (match_dup 1)
1996 "valid_operands (MINUS, operands, QImode)"
2002 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
2003 ; Default to int16 data attr.
2005 (define_insn "*subqi3_noclobber"
2006 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
2007 (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
2008 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))]
2009 "valid_operands (MINUS, operands, QImode)"
2015 [(set_attr "type" "binary,binary,binary,binary")])
2016 ; Default to int16 data attr.
2018 (define_insn "*subqi3_carry_clobber"
2019 [(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
2020 (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
2021 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
2022 (use (reg:CC_NOOV 21))
2023 (clobber (reg:CC_NOOV 21))]
2024 "valid_operands (MINUS, operands, QImode)"
2034 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
2035 ; Default to int16 data attr.
2037 (define_insn "*subqi3_carry_set"
2038 [(set (reg:CC_NOOV 21)
2039 (compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
2040 (match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
2042 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
2043 (minus:QI (match_dup 1)
2045 (use (reg:CC_NOOV 21))]
2046 "valid_operands (MINUS, operands, QImode)"
2052 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
2053 ; Default to int16 data attr.
2058 (define_expand "mulqi3"
2059 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2060 (mult:QI (match_operand:QI 1 "src_operand" "")
2061 (match_operand:QI 2 "src_operand" "")))
2062 (clobber (reg:CC_NOOV 21))])]
2064 "if (TARGET_MPYI || (GET_CODE (operands[2]) == CONST_INT
2065 && exact_log2 (INTVAL (operands[2])) >= 0))
2066 legitimize_operands (MULT, operands, QImode);
2069 if (GET_CODE (operands[2]) == CONST_INT)
2071 /* Let GCC try to synthesize the multiplication using shifts
2072 and adds. In most cases this will be more profitable than
2073 using the C3x MPYI. */
2076 if (operands[1] == operands[2])
2078 /* Do the squaring operation in-line. */
2079 emit_insn (gen_sqrqi2_inline (operands[0], operands[1]));
2084 emit_insn (gen_mulqi3_inline (operands[0], operands[1],
2088 c4x_emit_libcall3 (smul_optab->handlers[(int) QImode].libfunc,
2089 MULT, QImode, operands);
2094 (define_insn "*mulqi3_clobber"
2095 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2096 (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
2097 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
2098 (clobber (reg:CC_NOOV 21))]
2099 "valid_operands (MULT, operands, QImode)"
2101 if (which_alternative == 0 || which_alternative == 3)
2104 && GET_CODE (operands[2]) == CONST_INT
2105 && exact_log2 (INTVAL (operands[2])) >= 0)
2106 return \"ash\\t%L2,%0\";
2108 return \"mpyi\\t%2,%0\";
2111 return \"mpyi3\\t%2,%1,%0\";"
2112 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
2113 ; Default to int16 data attr.
2115 (define_insn "*mulqi3_test"
2116 [(set (reg:CC_NOOV 21)
2117 (compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2118 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
2120 (clobber (match_scratch:QI 0 "=d,d,d"))]
2121 "valid_operands (MULT, operands, QImode)"
2123 if (which_alternative == 0)
2126 && GET_CODE (operands[2]) == CONST_INT
2127 && exact_log2 (INTVAL (operands[2])) >= 0)
2128 return \"ash\\t%L2,%0\";
2130 return \"mpyi\\t%2,%0\";
2133 return \"mpyi3\\t%2,%1,%0\";"
2134 [(set_attr "type" "binarycc,binarycc,binarycc")])
2135 ; Default to int16 data attr.
2137 (define_insn "*mulqi3_set"
2138 [(set (reg:CC_NOOV 21)
2139 (compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2140 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
2142 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
2143 (mult:QI (match_dup 1)
2145 "valid_operands (MULT, operands, QImode)"
2147 if (which_alternative == 0)
2150 && GET_CODE (operands[2]) == CONST_INT
2151 && exact_log2 (INTVAL (operands[2])) >= 0)
2152 return \"ash\\t%L2,%0\";
2154 return \"mpyi\\t%2,%0\";
2157 return \"mpyi3\\t%2,%1,%0\";"
2158 [(set_attr "type" "binarycc,binarycc,binarycc")])
2159 ; Default to int16 data attr.
2161 ; The C3x multiply instruction assumes 24-bit signed integer operands
2162 ; and the 48-bit result is truncated to 32-bits.
2163 (define_insn "mulqi3_24_clobber"
2164 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2167 (and:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
2168 (const_int 16777215)))
2170 (and:QI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")
2171 (const_int 16777215)))))
2172 (clobber (reg:CC_NOOV 21))]
2173 "TARGET_C3X && valid_operands (MULT, operands, QImode)"
2181 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
2182 ; Default to int16 data attr.
2185 ; Fast square function for C3x where TARGET_MPYI not asserted
2186 (define_expand "sqrqi2_inline"
2187 [(set (match_dup 7) (match_operand:QI 1 "src_operand" ""))
2188 (parallel [(set (match_dup 3)
2189 (lshiftrt:QI (match_dup 7) (const_int 16)))
2190 (clobber (reg:CC 21))])
2191 (parallel [(set (match_dup 2)
2192 (and:QI (match_dup 7) (const_int 65535)))
2193 (clobber (reg:CC 21))])
2194 (parallel [(set (match_dup 4)
2195 (mult:QI (sign_extend:QI (and:QI (match_dup 2)
2196 (const_int 16777215)))
2197 (sign_extend:QI (and:QI (match_dup 2)
2198 (const_int 16777215)))))
2199 (clobber (reg:CC_NOOV 21))])
2200 (parallel [(set (match_dup 5)
2201 (mult:QI (sign_extend:QI (and:QI (match_dup 2)
2202 (const_int 16777215)))
2203 (sign_extend:QI (and:QI (match_dup 3)
2204 (const_int 16777215)))))
2205 (clobber (reg:CC_NOOV 21))])
2206 (parallel [(set (match_dup 6)
2207 (ashift:QI (match_dup 5) (const_int 17)))
2208 (clobber (reg:CC 21))])
2209 (parallel [(set (match_operand:QI 0 "reg_operand" "")
2210 (plus:QI (match_dup 4) (match_dup 6)))
2211 (clobber (reg:CC_NOOV 21))])]
2214 operands[2] = gen_reg_rtx (QImode); /* a = val & 0xffff */
2215 operands[3] = gen_reg_rtx (QImode); /* b = val >> 16 */
2216 operands[4] = gen_reg_rtx (QImode); /* a * a */
2217 operands[5] = gen_reg_rtx (QImode); /* a * b */
2218 operands[6] = gen_reg_rtx (QImode); /* (a * b) << 17 */
2219 operands[7] = gen_reg_rtx (QImode); /* val */
2222 ; Inlined integer multiply for C3x
2223 (define_expand "mulqi3_inline"
2224 [(set (match_dup 12) (const_int -16))
2225 (set (match_dup 13) (match_operand:QI 1 "src_operand" ""))
2226 (set (match_dup 14) (match_operand:QI 2 "src_operand" ""))
2227 (parallel [(set (match_dup 4)
2228 (lshiftrt:QI (match_dup 13) (neg:QI (match_dup 12))))
2229 (clobber (reg:CC 21))])
2230 (parallel [(set (match_dup 6)
2231 (lshiftrt:QI (match_dup 14) (neg:QI (match_dup 12))))
2232 (clobber (reg:CC 21))])
2233 (parallel [(set (match_dup 3)
2234 (and:QI (match_dup 13)
2236 (clobber (reg:CC 21))])
2237 (parallel [(set (match_dup 5)
2238 (and:QI (match_dup 14)
2240 (clobber (reg:CC 21))])
2241 (parallel [(set (match_dup 7)
2242 (mult:QI (sign_extend:QI (and:QI (match_dup 4)
2243 (const_int 16777215)))
2244 (sign_extend:QI (and:QI (match_dup 5)
2245 (const_int 16777215)))))
2246 (clobber (reg:CC_NOOV 21))])
2247 (parallel [(set (match_dup 8)
2248 (mult:QI (sign_extend:QI (and:QI (match_dup 3)
2249 (const_int 16777215)))
2250 (sign_extend:QI (and:QI (match_dup 5)
2251 (const_int 16777215)))))
2252 (clobber (reg:CC_NOOV 21))])
2253 (parallel [(set (match_dup 9)
2254 (mult:QI (sign_extend:QI (and:QI (match_dup 3)
2255 (const_int 16777215)))
2256 (sign_extend:QI (and:QI (match_dup 6)
2257 (const_int 16777215)))))
2258 (clobber (reg:CC_NOOV 21))])
2259 (parallel [(set (match_dup 10)
2260 (plus:QI (match_dup 7) (match_dup 9)))
2261 (clobber (reg:CC_NOOV 21))])
2262 (parallel [(set (match_dup 11)
2263 (ashift:QI (match_dup 10) (const_int 16)))
2264 (clobber (reg:CC 21))])
2265 (parallel [(set (match_operand:QI 0 "reg_operand" "")
2266 (plus:QI (match_dup 8) (match_dup 11)))
2267 (clobber (reg:CC_NOOV 21))])]
2270 operands[3] = gen_reg_rtx (QImode); /* a = arg1 & 0xffff */
2271 operands[4] = gen_reg_rtx (QImode); /* b = arg1 >> 16 */
2272 operands[5] = gen_reg_rtx (QImode); /* a = arg2 & 0xffff */
2273 operands[6] = gen_reg_rtx (QImode); /* b = arg2 >> 16 */
2274 operands[7] = gen_reg_rtx (QImode); /* b * c */
2275 operands[8] = gen_reg_rtx (QImode); /* a * c */
2276 operands[9] = gen_reg_rtx (QImode); /* a * d */
2277 operands[10] = gen_reg_rtx (QImode); /* b * c + a * d */
2278 operands[11] = gen_reg_rtx (QImode); /* (b *c + a * d) << 16 */
2279 operands[12] = gen_reg_rtx (QImode); /* -16 */
2280 operands[13] = gen_reg_rtx (QImode); /* arg1 */
2281 operands[14] = gen_reg_rtx (QImode); /* arg2 */
2287 (define_expand "smulqi3_highpart"
2288 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2292 (sign_extend:HI (match_operand:QI 1 "src_operand" ""))
2293 (sign_extend:HI (match_operand:QI 2 "src_operand" "")))
2295 (clobber (reg:CC_NOOV 21))])]
2297 "legitimize_operands (MULT, operands, QImode);
2300 c4x_emit_libcall_mulhi (smulhi3_libfunc, SIGN_EXTEND, QImode, operands);
2305 (define_insn "*smulqi3_highpart_clobber"
2306 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2310 (sign_extend:HI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>"))
2311 (sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
2313 (clobber (reg:CC_NOOV 21))]
2314 "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
2322 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
2323 (set_attr "data" "int16,int16,int16,int16,int16,int16")])
2325 (define_insn "*smulqi3_highpart_noclobber"
2326 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
2330 (sign_extend:HI (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
2331 (sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))
2333 "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
2338 [(set_attr "type" "binary,binary,binary")
2339 (set_attr "data" "int16,int16,int16")])
2344 (define_expand "umulqi3_highpart"
2345 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2349 (zero_extend:HI (match_operand:QI 1
2350 "nonimmediate_src_operand" ""))
2351 (zero_extend:HI (match_operand:QI 2
2352 "nonimmediate_lsrc_operand" "")))
2354 (clobber (reg:CC_NOOV 21))])]
2356 "legitimize_operands (MULT, operands, QImode);
2359 c4x_emit_libcall_mulhi (umulhi3_libfunc, ZERO_EXTEND, QImode, operands);
2364 (define_insn "*umulqi3_highpart_clobber"
2365 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2369 (zero_extend:HI (match_operand:QI 1
2370 "nonimmediate_src_operand" "%0,rR,rS<>,0,rR,rS<>"))
2371 (zero_extend:HI (match_operand:QI 2
2372 "nonimmediate_lsrc_operand" "rm,R,rS<>,rm,R,rS<>")))
2374 (clobber (reg:CC_NOOV 21))]
2375 "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
2383 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
2384 (set_attr "data" "uint16,uint16,uint16,uint16,uint16,uint16")])
2386 (define_insn "*umulqi3_highpart_noclobber"
2387 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
2391 (zero_extend:HI (match_operand:QI 1
2392 "nonimmediate_src_operand" "0,rR,rS<>"))
2393 (zero_extend:HI (match_operand:QI 2
2394 "nonimmediate_lsrc_operand" "rm,R,rS<>")))
2396 "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
2401 [(set_attr "type" "binary,binary,binary")
2402 (set_attr "data" "uint16,uint16,uint16")])
2407 (define_expand "andqi3"
2408 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2409 (and:QI (match_operand:QI 1 "src_operand" "")
2410 (match_operand:QI 2 "tsrc_operand" "")))
2411 (clobber (reg:CC 21))])]
2413 "legitimize_operands (AND, operands, QImode);")
2416 (define_insn "*andqi3_255_clobber"
2417 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2418 (and:QI (match_operand:QI 1 "src_operand" "mr,mr")
2420 (clobber (reg:CC 21))]
2423 [(set_attr "type" "unarycc,unary")])
2425 (define_insn "*andqi3_255_noclobber"
2426 [(set (match_operand:QI 0 "reg_operand" "=c")
2427 (and:QI (match_operand:QI 1 "src_operand" "mr")
2431 [(set_attr "type" "unary")])
2434 (define_insn "*andqi3_65535_clobber"
2435 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2436 (and:QI (match_operand:QI 1 "src_operand" "mr,mr")
2438 (clobber (reg:CC 21))]
2441 [(set_attr "type" "unarycc,unary")])
2443 (define_insn "*andqi3_65535_noclobber"
2444 [(set (match_operand:QI 0 "reg_operand" "=c")
2445 (and:QI (match_operand:QI 1 "src_operand" "mr")
2446 (const_int 65535)))]
2449 [(set_attr "type" "unary")])
2451 (define_insn "*andqi3_clobber"
2452 [(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
2453 (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>,0,0,rR,rS<>")
2454 (match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>,N,rLm,JR,rS<>")))
2455 (clobber (reg:CC 21))]
2456 "valid_operands (AND, operands, QImode)"
2466 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")
2467 (set_attr "data" "not_uint16,uint16,int16,uint16,not_uint16,uint16,int16,uint16")])
2469 (define_insn "*andqi3_noclobber"
2470 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
2471 (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
2472 (match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))]
2473 "valid_operands (AND, operands, QImode)"
2479 [(set_attr "type" "binary,binary,binary,binary")
2480 (set_attr "data" "not_uint16,uint16,int16,uint16")])
2482 (define_insn "andn_st"
2483 [(set (unspec:QI [(reg:QI 21)] 20)
2484 (and:QI (unspec:QI [(reg:QI 21)] UNSPEC_ANDN_ST)
2485 (match_operand:QI 0 "" "N")))
2488 (clobber (reg:CC 21))]
2491 [(set_attr "type" "misc")
2492 (set_attr "data" "not_uint16")])
2495 [(set (match_operand:QI 0 "std_reg_operand" "")
2496 (and:QI (match_operand:QI 1 "src_operand" "")
2497 (match_operand:QI 2 "tsrc_operand" "")))
2498 (clobber (reg:CC 21))]
2501 (and:QI (match_dup 1)
2505 (define_insn "*andqi3_test"
2507 (compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,r,rR,rS<>")
2508 (match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
2510 (clobber (match_scratch:QI 0 "=d,X,X,?X"))]
2511 "valid_operands (AND, operands, QImode)"
2517 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
2518 (set_attr "data" "not_uint16,uint16,int16,uint16")])
2521 [(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
2522 (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
2523 (match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))
2524 (clobber (reg:CC 21))])
2526 (compare:CC (match_dup 0) (const_int 0)))]
2527 "valid_operands (AND, operands, QImode)"
2533 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
2534 (set_attr "data" "not_uint16,uint16,int16,uint16")])
2536 (define_insn "*andqi3_set"
2538 (compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
2539 (match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
2541 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
2542 (and:QI (match_dup 1)
2544 "valid_operands (AND, operands, QImode)"
2550 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
2551 (set_attr "data" "not_uint16,uint16,int16,uint16")])
2556 ; NB, this insn doesn't have commutative operands, but valid_operands
2557 ; assumes that the code AND does. We might have to kludge this if
2558 ; we make valid_operands stricter.
2559 (define_insn "*andnqi3_clobber"
2560 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2561 (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>"))
2562 (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")))
2563 (clobber (reg:CC 21))]
2564 "valid_operands (AND, operands, QImode)"
2572 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
2573 (set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
2575 (define_insn "*andnqi3_noclobber"
2576 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
2577 (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2578 (match_operand:QI 1 "src_operand" "0,rR,rS<>")))]
2579 "valid_operands (AND, operands, QImode)"
2584 [(set_attr "type" "binary,binary,binary")
2585 (set_attr "data" "uint16,int16,uint16")])
2588 [(set (match_operand:QI 0 "std_reg_operand" "")
2589 (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" ""))
2590 (match_operand:QI 1 "src_operand" "")))
2591 (clobber (reg:CC 21))]
2594 (and:QI (not:QI (match_dup 2))
2598 (define_insn "*andnqi3_test"
2600 (compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2601 (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
2603 (clobber (match_scratch:QI 0 "=d,d,d"))]
2604 "valid_operands (AND, operands, QImode)"
2609 [(set_attr "type" "binarycc,binarycc,binarycc")
2610 (set_attr "data" "uint16,int16,uint16")])
2612 (define_insn "*andnqi3_set"
2614 (compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2615 (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
2617 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
2618 (and:QI (not:QI (match_dup 2))
2620 "valid_operands (AND, operands, QImode)"
2625 [(set_attr "type" "binarycc,binarycc,binarycc")
2626 (set_attr "data" "uint16,int16,uint16")])
2631 (define_expand "iorqi3"
2632 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2633 (ior:QI (match_operand:QI 1 "src_operand" "")
2634 (match_operand:QI 2 "lsrc_operand" "")))
2635 (clobber (reg:CC 21))])]
2637 "legitimize_operands (IOR, operands, QImode);")
2639 (define_insn "*iorqi3_clobber"
2640 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2641 (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
2642 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
2643 (clobber (reg:CC 21))]
2644 "valid_operands (IOR, operands, QImode)"
2652 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
2653 (set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
2656 [(set (match_operand:QI 0 "std_reg_operand" "")
2657 (ior:QI (match_operand:QI 1 "src_operand" "")
2658 (match_operand:QI 2 "lsrc_operand" "")))
2659 (clobber (reg:CC 21))]
2662 (ior:QI (match_dup 1)
2666 (define_insn "*iorqi3_test"
2668 (compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2669 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2671 (clobber (match_scratch:QI 0 "=d,d,d"))]
2672 "valid_operands (IOR, operands, QImode)"
2677 [(set_attr "type" "binarycc,binarycc,binarycc")
2678 (set_attr "data" "uint16,int16,uint16")])
2681 [(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
2682 (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2683 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))
2684 (clobber (reg:CC 21))])
2686 (compare:CC (match_dup 0) (const_int 0)))]
2687 "valid_operands (IOR, operands, QImode)"
2692 [(set_attr "type" "binarycc,binarycc,binarycc")
2693 (set_attr "data" "uint16,int16,uint16")])
2695 (define_insn "*iorqi3_set"
2697 (compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2698 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2700 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
2701 (ior:QI (match_dup 1)
2703 "valid_operands (IOR, operands, QImode)"
2708 [(set_attr "type" "binarycc,binarycc,binarycc")
2709 (set_attr "data" "uint16,int16,uint16")])
2711 ; This pattern is used for loading symbol references in several parts.
2712 (define_insn "iorqi3_noclobber"
2713 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
2714 (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2715 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
2716 "valid_operands (IOR, operands, QImode)"
2721 [(set_attr "type" "binary,binary,binary")
2722 (set_attr "data" "uint16,int16,uint16")])
2727 (define_expand "xorqi3"
2728 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2729 (xor:QI (match_operand:QI 1 "src_operand" "")
2730 (match_operand:QI 2 "lsrc_operand" "")))
2731 (clobber (reg:CC 21))])]
2733 "legitimize_operands (XOR, operands, QImode);")
2735 (define_insn "*xorqi3_clobber"
2736 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2737 (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
2738 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
2739 (clobber (reg:CC 21))]
2740 "valid_operands (XOR, operands, QImode)"
2748 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
2749 (set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
2751 (define_insn "*xorqi3_noclobber"
2752 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
2753 (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2754 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
2755 "valid_operands (XOR, operands, QImode)"
2760 [(set_attr "type" "binary,binary,binary")
2761 (set_attr "data" "uint16,int16,uint16")])
2764 [(set (match_operand:QI 0 "std_reg_operand" "")
2765 (xor:QI (match_operand:QI 1 "src_operand" "")
2766 (match_operand:QI 2 "lsrc_operand" "")))
2767 (clobber (reg:CC 21))]
2770 (xor:QI (match_dup 1)
2774 (define_insn "*xorqi3_test"
2776 (compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2777 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2779 (clobber (match_scratch:QI 0 "=d,d,d"))]
2780 "valid_operands (XOR, operands, QImode)"
2785 [(set_attr "type" "binarycc,binarycc,binarycc")
2786 (set_attr "data" "uint16,int16,uint16")])
2788 (define_insn "*xorqi3_set"
2790 (compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
2791 (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
2793 (set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
2794 (xor:QI (match_dup 1)
2796 "valid_operands (XOR, operands, QImode)"
2801 [(set_attr "type" "binarycc,binarycc,binarycc")
2802 (set_attr "data" "uint16,int16,uint16")])
2807 ; The C3x and C4x have two shift instructions ASH and LSH
2808 ; If the shift count is positive, a left shift is performed
2809 ; otherwise a right shift is performed. The number of bits
2810 ; shifted is determined by the seven LSBs of the shift count.
2811 ; If the absolute value of the count is 32 or greater, the result
2812 ; using the LSH instruction is zero; with the ASH insn the result
2813 ; is zero or negative 1. Note that the ISO C standard allows
2814 ; the result to be machine dependent whenever the shift count
2815 ; exceeds the size of the object.
2816 (define_expand "ashlqi3"
2817 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2818 (ashift:QI (match_operand:QI 1 "src_operand" "")
2819 (match_operand:QI 2 "src_operand" "")))
2820 (clobber (reg:CC 21))])]
2822 "legitimize_operands (ASHIFT, operands, QImode);")
2824 (define_insn "*ashlqi3_clobber"
2825 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2826 (ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
2827 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
2828 (clobber (reg:CC 21))]
2829 "valid_operands (ASHIFT, operands, QImode)"
2837 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
2838 ; Default to int16 data attr.
2840 (define_insn "*ashlqi3_set"
2843 (ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
2844 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
2846 (set (match_operand:QI 0 "reg_operand" "=d,d,d")
2847 (ashift:QI (match_dup 1)
2849 "valid_operands (ASHIFT, operands, QImode)"
2854 [(set_attr "type" "binarycc,binarycc,binarycc")])
2855 ; Default to int16 data attr.
2857 (define_insn "ashlqi3_noclobber"
2858 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
2859 (ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
2860 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
2861 "valid_operands (ASHIFT, operands, QImode)"
2866 [(set_attr "type" "binary,binary,binary")])
2867 ; Default to int16 data attr.
2870 [(set (match_operand:QI 0 "std_reg_operand" "")
2871 (ashift:QI (match_operand:QI 1 "src_operand" "")
2872 (match_operand:QI 2 "src_operand" "")))
2873 (clobber (reg:CC 21))]
2876 (ashift:QI (match_dup 1)
2880 ; This is only used by lshrhi3_reg where we need a LSH insn that will
2882 (define_insn "*lshlqi3_clobber"
2883 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2884 (ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
2885 (unspec:QI [(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")] UNSPEC_LSH)))
2886 (clobber (reg:CC 21))]
2887 "valid_operands (ASHIFT, operands, QImode)"
2895 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
2896 ; Default to int16 data attr.
2901 ; Logical right shift on the C[34]x works by negating the shift count,
2902 ; then emitting a right shift with the shift count negated. This means
2903 ; that all actual shift counts in the RTL will be positive.
2905 (define_expand "lshrqi3"
2906 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
2907 (lshiftrt:QI (match_operand:QI 1 "src_operand" "")
2908 (match_operand:QI 2 "src_operand" "")))
2909 (clobber (reg:CC 21))])]
2911 "legitimize_operands (LSHIFTRT, operands, QImode);")
2914 (define_insn "*lshrqi3_24_clobber"
2915 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2916 (lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
2918 (clobber (reg:CC 21))]
2921 [(set_attr "type" "unarycc")])
2924 (define_insn "*ashrqi3_24_clobber"
2925 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2926 (ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
2928 (clobber (reg:CC 21))]
2931 [(set_attr "type" "unarycc")])
2934 (define_insn "lshrqi3_16_clobber"
2935 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2936 (lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
2938 (clobber (reg:CC 21))]
2941 [(set_attr "type" "unarycc")])
2944 (define_insn "*ashrqi3_16_clobber"
2945 [(set (match_operand:QI 0 "reg_operand" "=d,c")
2946 (ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
2948 (clobber (reg:CC 21))]
2951 [(set_attr "type" "unarycc")])
2954 ; When the shift count is greater than the size of the word
2955 ; the result can be implementation specific
2956 (define_insn "*lshrqi3_const_clobber"
2957 [(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
2958 (lshiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
2959 (match_operand:QI 2 "const_int_operand" "n,n,J,J")))
2960 (clobber (reg:CC 21))]
2961 "valid_operands (LSHIFTRT, operands, QImode)"
2967 [(set_attr "type" "binarycc,binary,binarycc,binary")])
2969 (define_insn "*lshrqi3_const_noclobber"
2970 [(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
2971 (lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
2972 (match_operand:QI 2 "const_int_operand" "n,J")))]
2973 "valid_operands (LSHIFTRT, operands, QImode)"
2977 [(set_attr "type" "binary,binary")])
2979 ; When the shift count is greater than the size of the word
2980 ; the result can be implementation specific
2981 (define_insn "*lshrqi3_const_set"
2984 (lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
2985 (match_operand:QI 2 "const_int_operand" "n,J"))
2987 (set (match_operand:QI 0 "reg_operand" "=?d,d")
2988 (lshiftrt:QI (match_dup 1)
2990 "valid_operands (LSHIFTRT, operands, QImode)"
2994 [(set_attr "type" "binarycc,binarycc")])
2996 (define_insn "*lshrqi3_nonconst_clobber"
2997 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
2998 (lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
2999 (neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
3000 (clobber (reg:CC 21))]
3001 "valid_operands (LSHIFTRT, operands, QImode)"
3009 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
3010 ; Default to int16 data attr.
3012 (define_insn "*lshrqi3_nonconst_noclobber"
3013 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
3014 (lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
3015 (neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
3016 "valid_operands (LSHIFTRT, operands, QImode)"
3021 [(set_attr "type" "binary,binary,binary")])
3022 ; Default to int16 data attr.
3027 ; Arithmetic right shift on the C[34]x works by negating the shift count,
3028 ; then emitting a right shift with the shift count negated. This means
3029 ; that all actual shift counts in the RTL will be positive.
3031 (define_expand "ashrqi3"
3032 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
3033 (ashiftrt:QI (match_operand:QI 1 "src_operand" "")
3034 (match_operand:QI 2 "src_operand" "")))
3035 (clobber (reg:CC 21))])]
3037 "legitimize_operands (ASHIFTRT, operands, QImode);")
3039 ; When the shift count is greater than the size of the word
3040 ; the result can be implementation specific
3041 (define_insn "*ashrqi3_const_clobber"
3042 [(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
3043 (ashiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
3044 (match_operand:QI 2 "const_int_operand" "n,n,J,J")))
3045 (clobber (reg:CC 21))]
3046 "valid_operands (ASHIFTRT, operands, QImode)"
3052 [(set_attr "type" "binarycc,binary,binarycc,binary")])
3054 (define_insn "*ashrqi3_const_noclobber"
3055 [(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
3056 (ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
3057 (match_operand:QI 2 "const_int_operand" "n,J")))]
3058 "valid_operands (ASHIFTRT, operands, QImode)"
3062 [(set_attr "type" "binarycc,binarycc")])
3064 ; When the shift count is greater than the size of the word
3065 ; the result can be implementation specific
3066 (define_insn "*ashrqi3_const_set"
3069 (ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
3070 (match_operand:QI 2 "const_int_operand" "n,J"))
3072 (set (match_operand:QI 0 "reg_operand" "=?d,d")
3073 (ashiftrt:QI (match_dup 1)
3075 "valid_operands (ASHIFTRT, operands, QImode)"
3079 [(set_attr "type" "binarycc,binarycc")])
3081 (define_insn "*ashrqi3_nonconst_clobber"
3082 [(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
3083 (ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
3084 (neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
3085 (clobber (reg:CC 21))]
3086 "valid_operands (ASHIFTRT, operands, QImode)"
3094 [(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
3095 ; Default to int16 data attr.
3097 (define_insn "*ashrqi3_nonconst_noclobber"
3098 [(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
3099 (ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
3100 (neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
3101 "valid_operands (ASHIFTRT, operands, QImode)"
3106 [(set_attr "type" "binary,binary,binary")])
3107 ; Default to int16 data attr.
3112 ; Unfortunately the C40 doesn't allow cmpi3 7, *ar0++ so the next best
3113 ; thing would be to get the small constant loaded into a register (say r0)
3114 ; so that it could be hoisted out of the loop so that we only
3115 ; would need to do cmpi3 *ar0++, r0. Now the loop optimization pass
3116 ; comes before the flow pass (which finds autoincrements) so we're stuck.
3117 ; Ideally, GCC requires another loop optimization pass (preferably after
3118 ; reload) so that it can hoist invariants out of loops.
3119 ; The current solution modifies legitimize_operands () so that small
3120 ; constants are forced into a pseudo register.
3122 (define_expand "cmpqi"
3124 (compare:CC (match_operand:QI 0 "src_operand" "")
3125 (match_operand:QI 1 "src_operand" "")))]
3127 "legitimize_operands (COMPARE, operands, QImode);
3128 c4x_compare_op0 = operands[0];
3129 c4x_compare_op1 = operands[1];
3132 (define_insn "*cmpqi_test"
3134 (compare:CC (match_operand:QI 0 "src_operand" "r,rR,rS<>")
3135 (match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
3136 "valid_operands (COMPARE, operands, QImode)"
3141 [(set_attr "type" "compare,compare,compare")])
3143 (define_insn "*cmpqi_test_noov"
3144 [(set (reg:CC_NOOV 21)
3145 (compare:CC_NOOV (match_operand:QI 0 "src_operand" "r,rR,rS<>")
3146 (match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
3147 "valid_operands (COMPARE, operands, QImode)"
3152 [(set_attr "type" "compare,compare,compare")])
3156 ; BIT-FIELD INSTRUCTIONS
3160 ; LBx/LHw (C4x only)
3162 (define_expand "extv"
3163 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
3164 (sign_extract:QI (match_operand:QI 1 "src_operand" "")
3165 (match_operand:QI 2 "const_int_operand" "")
3166 (match_operand:QI 3 "const_int_operand" "")))
3167 (clobber (reg:CC 21))])]
3169 "if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
3170 || (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
3174 (define_insn "*extv_clobber"
3175 [(set (match_operand:QI 0 "reg_operand" "=d,c")
3176 (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
3177 (match_operand:QI 2 "const_int_operand" "n,n")
3178 (match_operand:QI 3 "const_int_operand" "n,n")))
3179 (clobber (reg:CC 21))]
3181 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3182 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3184 if (INTVAL (operands[2]) == 8)
3186 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3187 return \"lb%3\\t%1,%0\";
3189 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3190 return \"lh%3\\t%1,%0\";
3192 [(set_attr "type" "binarycc,binary")
3193 (set_attr "data" "int16,int16")])
3195 (define_insn "*extv_clobber_test"
3197 (compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
3198 (match_operand:QI 2 "const_int_operand" "n")
3199 (match_operand:QI 3 "const_int_operand" "n"))
3201 (clobber (match_scratch:QI 0 "=d"))]
3203 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3204 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3206 if (INTVAL (operands[2]) == 8)
3208 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3209 return \"lb%3\\t%1,%0\";
3211 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3212 return \"lh%3\\t%1,%0\";
3214 [(set_attr "type" "binarycc")
3215 (set_attr "data" "int16")])
3217 (define_insn "*extv_clobber_set"
3219 (compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
3220 (match_operand:QI 2 "const_int_operand" "n")
3221 (match_operand:QI 3 "const_int_operand" "n"))
3223 (set (match_operand:QI 0 "reg_operand" "=d")
3224 (sign_extract:QI (match_dup 1)
3228 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3229 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3231 if (INTVAL (operands[2]) == 8)
3233 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3234 return \"lb%3\\t%1,%0\";
3236 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3237 return \"lh%3\\t%1,%0\";
3239 [(set_attr "type" "binarycc")
3240 (set_attr "data" "int16")])
3243 ; LBUx/LHUw (C4x only)
3245 (define_expand "extzv"
3246 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
3247 (zero_extract:QI (match_operand:QI 1 "src_operand" "")
3248 (match_operand:QI 2 "const_int_operand" "")
3249 (match_operand:QI 3 "const_int_operand" "")))
3250 (clobber (reg:CC 21))])]
3252 "if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
3253 || (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
3257 (define_insn "*extzv_clobber"
3258 [(set (match_operand:QI 0 "reg_operand" "=d,c")
3259 (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
3260 (match_operand:QI 2 "const_int_operand" "n,n")
3261 (match_operand:QI 3 "const_int_operand" "n,n")))
3262 (clobber (reg:CC 21))]
3264 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3265 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3267 if (INTVAL (operands[2]) == 8)
3269 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3270 return \"lbu%3\\t%1,%0\";
3272 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3273 return \"lhu%3\\t%1,%0\";
3275 [(set_attr "type" "binarycc,binary")
3276 (set_attr "data" "uint16,uint16")])
3278 (define_insn "*extzv_test"
3280 (compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
3281 (match_operand:QI 2 "const_int_operand" "n")
3282 (match_operand:QI 3 "const_int_operand" "n"))
3284 (clobber (match_scratch:QI 0 "=d"))]
3286 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3287 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3289 if (INTVAL (operands[2]) == 8)
3291 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3292 return \"lbu%3\\t%1,%0\";
3294 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3295 return \"lhu%3\\t%1,%0\";
3297 [(set_attr "type" "binarycc")
3298 (set_attr "data" "uint16")])
3300 (define_insn "*extzv_set"
3302 (compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
3303 (match_operand:QI 2 "const_int_operand" "n")
3304 (match_operand:QI 3 "const_int_operand" "n"))
3306 (set (match_operand:QI 0 "ext_reg_operand" "=d")
3307 (zero_extract:QI (match_dup 1)
3311 && (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
3312 && (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
3314 if (INTVAL (operands[2]) == 8)
3316 /* 8 bit extract. */
3317 operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
3318 return \"lbu%3\\t%1,%0\";
3320 /* 16 bit extract. */
3321 operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
3322 return \"lhu%3\\t%1,%0\";
3324 [(set_attr "type" "binarycc")
3325 (set_attr "data" "uint16")])
3328 ; MBx/MHw (C4x only)
3330 (define_expand "insv"
3331 [(parallel [(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "")
3332 (match_operand:QI 1 "const_int_operand" "")
3333 (match_operand:QI 2 "const_int_operand" ""))
3334 (match_operand:QI 3 "src_operand" ""))
3335 (clobber (reg:CC 21))])]
3337 "if (! (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
3338 && (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
3339 || (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8)))
3343 (define_insn "*insv_clobber"
3344 [(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "+d,c")
3345 (match_operand:QI 1 "const_int_operand" "n,n")
3346 (match_operand:QI 2 "const_int_operand" "n,n"))
3347 (match_operand:QI 3 "src_operand" "rLm,rLm"))
3348 (clobber (reg:CC 21))]
3350 && (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
3351 && (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
3352 || (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8))"
3354 if (INTVAL (operands[1]) == 8)
3357 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
3358 return \"mb%2\\t%3,%0\";
3360 else if (INTVAL (operands[1]) == 16)
3362 /* 16 bit insert. */
3363 operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
3364 return \"mh%2\\t%3,%0\";
3366 /* 24 bit insert. */
3367 return \"lwl1\\t%3,%0\";
3369 [(set_attr "type" "binarycc,binary")
3370 (set_attr "data" "uint16,uint16")])
3373 [(parallel [(set (zero_extract:QI (match_operand:QI 0 "ext_reg_operand" "+d")
3374 (match_operand:QI 1 "const_int_operand" "n")
3375 (match_operand:QI 2 "const_int_operand" "n"))
3376 (match_operand:QI 3 "src_operand" "rLm"))
3377 (clobber (reg:CC 21))])
3379 (compare:CC (match_dup 0) (const_int 0)))]
3381 && (INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
3382 && (INTVAL (operands[2]) % INTVAL (operands[1]) == 0)"
3384 if (INTVAL (operands[1]) == 8)
3386 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
3387 return \"mb%2\\t%3,%0\";
3389 operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
3390 return \"mh%2\\t%3,%0\";
3392 [(set_attr "type" "binarycc")
3393 (set_attr "data" "uint16")])
3396 ; TWO OPERAND FLOAT INSTRUCTIONS
3402 ; If one of the operands is not a register, then we should
3403 ; emit two insns, using a scratch register. This will produce
3404 ; better code in loops if the source operand is invariant, since
3405 ; the source reload can be optimized out. During reload we cannot
3406 ; use change_address or force_reg.
3407 (define_expand "movqf"
3408 [(set (match_operand:QF 0 "src_operand" "")
3409 (match_operand:QF 1 "src_operand" ""))]
3413 if (c4x_emit_move_sequence (operands, QFmode))
3417 ; This can generate invalid stack slot displacements
3419 [(set (match_operand:QI 0 "reg_operand" "")
3420 (unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))]
3422 [(set (match_dup 3) (match_dup 1))
3423 (set (match_dup 0) (match_dup 2))]
3424 "operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
3425 operands[3] = copy_rtx (operands[2]);
3426 PUT_MODE (operands[3], QFmode);")
3429 (define_insn "storeqf_int"
3430 [(set (match_operand:QI 0 "reg_operand" "=r")
3431 (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))]
3434 [(set_attr "type" "multi")])
3437 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
3438 (unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))
3439 (clobber (reg:CC 21))])]
3441 [(set (mem:QF (pre_inc:QI (reg:QI 20)))
3443 (parallel [(set (match_dup 0)
3444 (mem:QI (post_dec:QI (reg:QI 20))))
3445 (clobber (reg:CC 21))])]
3449 ; We need accurate death notes for this...
3451 ; [(set (match_operand:QF 0 "reg_operand" "=f")
3452 ; (match_operand:QF 1 "memory_operand" "m"))
3453 ; (set (mem:QF (pre_inc:QI (reg:QI 20)))
3455 ; (parallel [(set (match_operand:QI 2 "reg_operand" "r")
3456 ; (mem:QI (post_dec:QI (reg:QI 20))))
3457 ; (clobber (reg:CC 21))])]
3461 (define_insn "storeqf_int_clobber"
3462 [(parallel [(set (match_operand:QI 0 "reg_operand" "=r")
3463 (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))
3464 (clobber (reg:CC 21))])]
3467 [(set_attr "type" "multi")])
3470 ; This can generate invalid stack slot displacements
3472 [(set (match_operand:QF 0 "reg_operand" "")
3473 (unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))]
3475 [(set (match_dup 2) (match_dup 1))
3476 (set (match_dup 0) (match_dup 3))]
3477 "operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
3478 operands[3] = copy_rtx (operands[2]);
3479 PUT_MODE (operands[3], QFmode);")
3482 (define_insn "loadqf_int"
3483 [(set (match_operand:QF 0 "reg_operand" "=f")
3484 (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))]
3487 [(set_attr "type" "multi")])
3490 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3491 (unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))
3492 (clobber (reg:CC 21))])]
3494 [(set (mem:QI (pre_inc:QI (reg:QI 20)))
3496 (parallel [(set (match_dup 0)
3497 (mem:QF (post_dec:QI (reg:QI 20))))
3498 (clobber (reg:CC 21))])]
3501 (define_insn "loadqf_int_clobber"
3502 [(parallel [(set (match_operand:QF 0 "reg_operand" "=f")
3503 (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))
3504 (clobber (reg:CC 21))])]
3507 [(set_attr "type" "multi")])
3509 ; We must provide an alternative to store to memory in case we have to
3511 (define_insn "movqf_noclobber"
3512 [(set (match_operand:QF 0 "dst_operand" "=f,m")
3513 (match_operand:QF 1 "src_operand" "fHm,f"))]
3514 "REG_P (operands[0]) || REG_P (operands[1])"
3518 [(set_attr "type" "unary,store")])
3520 ;(define_insn "*movqf_clobber"
3521 ; [(set (match_operand:QF 0 "reg_operand" "=f")
3522 ; (match_operand:QF 1 "src_operand" "fHm"))
3523 ; (clobber (reg:CC 21))]
3526 ; [(set_attr "type" "unarycc")])
3528 (define_insn "*movqf_test"
3530 (compare:CC (match_operand:QF 1 "src_operand" "fHm")
3532 (clobber (match_scratch:QF 0 "=f"))]
3535 [(set_attr "type" "unarycc")])
3537 (define_insn "*movqf_set"
3539 (compare:CC (match_operand:QF 1 "src_operand" "fHm")
3540 (match_operand:QF 2 "fp_zero_operand" "G")))
3541 (set (match_operand:QF 0 "reg_operand" "=f")
3545 [(set_attr "type" "unarycc")])
3548 (define_insn "*movqf_parallel"
3549 [(set (match_operand:QF 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
3550 (match_operand:QF 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
3551 (set (match_operand:QF 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
3552 (match_operand:QF 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
3553 "TARGET_PARALLEL && valid_parallel_load_store (operands, QFmode)"
3555 ldf1\\t%1,%0\\n||\\tldf2\\t%3,%2
3556 stf1\\t%1,%0\\n||\\tstf2\\t%3,%2
3557 ldf\\t%1,%0\\n||\\tstf\\t%3,%2
3558 ldf\\t%3,%2\\n||\\tstf\\t%1,%0"
3559 [(set_attr "type" "load_load,store_store,load_store,store_load")])
3565 (define_insn "pushqf"
3566 [(set (mem:QF (pre_inc:QI (reg:QI 20)))
3567 (match_operand:QF 0 "reg_operand" "f"))]
3570 [(set_attr "type" "push")])
3572 (define_insn "popqf"
3573 [(set (match_operand:QF 0 "reg_operand" "=f")
3574 (mem:QF (post_dec:QI (reg:QI 20))))
3575 (clobber (reg:CC 21))]
3578 [(set_attr "type" "pop")])
3580 (define_insn "popqf_unspec"
3581 [(set (unspec:QF [(match_operand:QF 0 "reg_operand" "=f")] UNSPEC_POPQF)
3582 (mem:QF (post_dec:QI (reg:QI 20))))
3583 (clobber (match_dup 0))
3584 (clobber (reg:CC 21))]
3587 [(set_attr "type" "pop")])
3592 (define_expand "absqf2"
3593 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3594 (abs:QF (match_operand:QF 1 "src_operand" "")))
3595 (clobber (reg:CC_NOOV 21))])]
3599 (define_insn "*absqf2_clobber"
3600 [(set (match_operand:QF 0 "reg_operand" "=f")
3601 (abs:QF (match_operand:QF 1 "src_operand" "fHm")))
3602 (clobber (reg:CC_NOOV 21))]
3605 [(set_attr "type" "unarycc")])
3607 (define_insn "*absqf2_test"
3608 [(set (reg:CC_NOOV 21)
3609 (compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
3610 (match_operand:QF 2 "fp_zero_operand" "G")))
3611 (clobber (match_scratch:QF 0 "=f"))]
3614 [(set_attr "type" "unarycc")])
3616 (define_insn "*absqf2_set"
3617 [(set (reg:CC_NOOV 21)
3618 (compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
3619 (match_operand:QF 2 "fp_zero_operand" "G")))
3620 (set (match_operand:QF 0 "reg_operand" "=f")
3621 (abs:QF (match_dup 1)))]
3625 [(set_attr "type" "unarycc")])
3630 (define_expand "negqf2"
3631 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3632 (neg:QF (match_operand:QF 1 "src_operand" "")))
3633 (clobber (reg:CC_NOOV 21))])]
3637 (define_insn "*negqf2_clobber"
3638 [(set (match_operand:QF 0 "reg_operand" "=f")
3639 (neg:QF (match_operand:QF 1 "src_operand" "fHm")))
3640 (clobber (reg:CC_NOOV 21))]
3643 [(set_attr "type" "unarycc")])
3645 (define_insn "*negqf2_test"
3646 [(set (reg:CC_NOOV 21)
3647 (compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
3648 (match_operand:QF 2 "fp_zero_operand" "G")))
3649 (clobber (match_scratch:QF 0 "=f"))]
3652 [(set_attr "type" "unarycc")])
3654 (define_insn "*negqf2_set"
3655 [(set (reg:CC_NOOV 21)
3656 (compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
3657 (match_operand:QF 2 "fp_zero_operand" "G")))
3658 (set (match_operand:QF 0 "reg_operand" "=f")
3659 (neg:QF (match_dup 1)))]
3662 [(set_attr "type" "unarycc")])
3667 (define_insn "floatqiqf2"
3668 [(set (match_operand:QF 0 "reg_operand" "=f")
3669 (float:QF (match_operand:QI 1 "src_operand" "rIm")))
3670 (clobber (reg:CC 21))]
3673 [(set_attr "type" "unarycc")])
3675 (define_insn "*floatqiqf2_set"
3677 (compare:CC (float:QF (match_operand:QI 1 "src_operand" "rIm"))
3678 (match_operand:QF 2 "fp_zero_operand" "G")))
3679 (set (match_operand:QF 0 "reg_operand" "=f")
3680 (float:QF (match_dup 1)))]
3683 [(set_attr "type" "unarycc")])
3685 ; Unsigned conversions are a little tricky because we need to
3686 ; add the value for the high bit if necessary.
3689 (define_expand "floatunsqiqf2"
3690 [(set (match_dup 2) (match_dup 3))
3691 (parallel [(set (reg:CC 21)
3692 (compare:CC (float:QF (match_operand:QI 1 "src_operand" ""))
3695 (float:QF (match_dup 1)))])
3697 (if_then_else:QF (lt (reg:CC 21) (const_int 0))
3700 (parallel [(set (match_operand:QF 0 "reg_operand" "")
3701 (plus:QF (match_dup 2) (match_dup 4)))
3702 (clobber (reg:CC_NOOV 21))])]
3704 "operands[2] = gen_reg_rtx (QFmode);
3705 operands[3] = CONST0_RTX (QFmode);
3706 operands[4] = gen_reg_rtx (QFmode);
3707 operands[5] = gen_reg_rtx (QFmode);
3708 emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
3710 (define_expand "floatunsqihf2"
3711 [(set (match_dup 2) (match_dup 3))
3712 (parallel [(set (reg:CC 21)
3713 (compare:CC (float:HF (match_operand:QI 1 "src_operand" ""))
3716 (float:HF (match_dup 1)))])
3718 (if_then_else:HF (lt (reg:CC 21) (const_int 0))
3721 (parallel [(set (match_operand:HF 0 "reg_operand" "")
3722 (plus:HF (match_dup 2) (match_dup 4)))
3723 (clobber (reg:CC_NOOV 21))])]
3725 "operands[2] = gen_reg_rtx (HFmode);
3726 operands[3] = CONST0_RTX (HFmode);
3727 operands[4] = gen_reg_rtx (HFmode);
3728 operands[5] = gen_reg_rtx (HFmode);
3729 emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
3731 (define_insn "floatqihf2"
3732 [(set (match_operand:HF 0 "reg_operand" "=h")
3733 (float:HF (match_operand:QI 1 "src_operand" "rIm")))
3734 (clobber (reg:CC 21))]
3737 [(set_attr "type" "unarycc")])
3739 (define_insn "*floatqihf2_set"
3741 (compare:CC (float:HF (match_operand:QI 1 "src_operand" "rIm"))
3742 (match_operand:QF 2 "fp_zero_operand" "G")))
3743 (set (match_operand:HF 0 "reg_operand" "=h")
3744 (float:HF (match_dup 1)))]
3747 [(set_attr "type" "unarycc")])
3752 (define_insn "fixqfqi_clobber"
3753 [(set (match_operand:QI 0 "reg_operand" "=d,c")
3754 (fix:QI (match_operand:QF 1 "src_operand" "fHm,fHm")))
3755 (clobber (reg:CC 21))]
3758 [(set_attr "type" "unarycc")])
3760 (define_insn "*fixqfqi_set"
3762 (compare:CC (fix:QI (match_operand:QF 1 "src_operand" "fHm"))
3764 (set (match_operand:QI 0 "ext_reg_operand" "=d")
3765 (fix:QI (match_dup 1)))]
3768 [(set_attr "type" "unarycc")])
3771 ; The C[34]x fix instruction implements a floor, not a straight trunc,
3772 ; so we have to invert the number, fix it, and reinvert it if negative
3774 (define_expand "fix_truncqfqi2"
3775 [(parallel [(set (match_dup 2)
3776 (fix:QI (match_operand:QF 1 "src_operand" "")))
3777 (clobber (reg:CC 21))])
3778 (parallel [(set (match_dup 3) (neg:QF (match_dup 1)))
3779 (clobber (reg:CC_NOOV 21))])
3780 (parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
3781 (clobber (reg:CC 21))])
3782 (parallel [(set (reg:CC_NOOV 21)
3783 (compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
3784 (set (match_dup 5) (neg:QI (match_dup 4)))])
3786 (if_then_else:QI (le (reg:CC 21) (const_int 0))
3789 (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
3791 "if (TARGET_FAST_FIX)
3793 emit_insn (gen_fixqfqi_clobber (operands[0], operands[1]));
3796 operands[2] = gen_reg_rtx (QImode);
3797 operands[3] = gen_reg_rtx (QFmode);
3798 operands[4] = gen_reg_rtx (QImode);
3799 operands[5] = gen_reg_rtx (QImode);
3802 (define_expand "fix_truncqfhi2"
3803 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
3804 (fix:HI (match_operand:QF 1 "src_operand" "")))
3805 (clobber (reg:CC 21))])]
3807 "c4x_emit_libcall (fix_truncqfhi2_libfunc, FIX, HImode, QFmode, 2, operands);
3810 (define_expand "fixuns_truncqfqi2"
3811 [(parallel [(set (match_dup 2)
3812 (fix:QI (match_operand:QF 1 "src_operand" "fHm")))
3813 (clobber (reg:CC 21))])
3814 (parallel [(set (match_dup 3)
3815 (minus:QF (match_dup 1) (match_dup 5)))
3816 (clobber (reg:CC_NOOV 21))])
3817 (parallel [(set (reg:CC 21)
3818 (compare:CC (fix:QI (match_dup 3))
3821 (fix:QI (match_dup 3)))])
3822 (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
3824 (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
3826 "operands[2] = gen_reg_rtx (QImode);
3827 operands[3] = gen_reg_rtx (QFmode);
3828 operands[4] = gen_reg_rtx (QImode);
3829 operands[5] = gen_reg_rtx (QFmode);
3830 emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
3832 (define_expand "fixuns_truncqfhi2"
3833 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
3834 (unsigned_fix:HI (match_operand:QF 1 "src_operand" "")))
3835 (clobber (reg:CC 21))])]
3837 "c4x_emit_libcall (fixuns_truncqfhi2_libfunc, UNSIGNED_FIX,
3838 HImode, QFmode, 2, operands);
3844 (define_insn "rcpfqf_clobber"
3845 [(set (match_operand:QF 0 "reg_operand" "=f")
3846 (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RCPF))
3847 (clobber (reg:CC_NOOV 21))]
3850 [(set_attr "type" "unarycc")])
3855 (define_insn "*rsqrfqf_clobber"
3856 [(set (match_operand:QF 0 "reg_operand" "=f")
3857 (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RSQRF))
3858 (clobber (reg:CC_NOOV 21))]
3861 [(set_attr "type" "unarycc")])
3866 (define_insn "*rndqf_clobber"
3867 [(set (match_operand:QF 0 "reg_operand" "=f")
3868 (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RND))
3869 (clobber (reg:CC_NOOV 21))]
3872 [(set_attr "type" "unarycc")])
3875 ; Inlined float square root for C4x
3876 (define_expand "sqrtqf2_inline"
3877 [(parallel [(set (match_dup 2)
3878 (unspec:QF [(match_operand:QF 1 "src_operand" "")] UNSPEC_RSQRF))
3879 (clobber (reg:CC_NOOV 21))])
3880 (parallel [(set (match_dup 3) (mult:QF (match_dup 5) (match_dup 1)))
3881 (clobber (reg:CC_NOOV 21))])
3882 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
3883 (clobber (reg:CC_NOOV 21))])
3884 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
3885 (clobber (reg:CC_NOOV 21))])
3886 (parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
3887 (clobber (reg:CC_NOOV 21))])
3888 (parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
3889 (clobber (reg:CC_NOOV 21))])
3890 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
3891 (clobber (reg:CC_NOOV 21))])
3892 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
3893 (clobber (reg:CC_NOOV 21))])
3894 (parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
3895 (clobber (reg:CC_NOOV 21))])
3896 (parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
3897 (clobber (reg:CC_NOOV 21))])
3898 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 1)))
3899 (clobber (reg:CC_NOOV 21))])
3900 (parallel [(set (match_operand:QF 0 "reg_operand" "")
3901 (unspec:QF [(match_dup 4)] UNSPEC_RND))
3902 (clobber (reg:CC_NOOV 21))])]
3904 "if (! reload_in_progress
3905 && ! reg_operand (operands[1], QFmode))
3906 operands[1] = force_reg (QFmode, operands[1]);
3907 operands[2] = gen_reg_rtx (QFmode);
3908 operands[3] = gen_reg_rtx (QFmode);
3909 operands[4] = gen_reg_rtx (QFmode);
3910 operands[5] = CONST_DOUBLE_ATOF (\"0.5\", QFmode);
3911 operands[6] = CONST_DOUBLE_ATOF (\"1.5\", QFmode);")
3913 (define_expand "sqrtqf2"
3914 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3915 (sqrt:QF (match_operand:QF 1 "src_operand" "")))
3916 (clobber (reg:CC 21))])]
3917 "! TARGET_C3X && TARGET_INLINE"
3918 "emit_insn (gen_sqrtqf2_inline (operands[0], operands[1]));
3924 (define_insn "toieee"
3925 [(set (match_operand:QF 0 "reg_operand" "=f")
3926 (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_TOIEEE))
3927 (clobber (reg:CC 21))]
3931 (define_insn "frieee"
3932 [(set (match_operand:QF 0 "reg_operand" "=f")
3933 (unspec:QF [(match_operand:QF 1 "memory_operand" "m")] UNSPEC_FRIEEE))
3934 (clobber (reg:CC 21))]
3939 ; THREE OPERAND FLOAT INSTRUCTIONS
3945 (define_expand "addqf3"
3946 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3947 (plus:QF (match_operand:QF 1 "src_operand" "")
3948 (match_operand:QF 2 "src_operand" "")))
3949 (clobber (reg:CC_NOOV 21))])]
3951 "legitimize_operands (PLUS, operands, QFmode);")
3953 (define_insn "*addqf3_clobber"
3954 [(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
3955 (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
3956 (match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
3957 (clobber (reg:CC_NOOV 21))]
3958 "valid_operands (PLUS, operands, QFmode)"
3963 [(set_attr "type" "binarycc,binarycc,binarycc")])
3965 (define_insn "*addqf3_test"
3966 [(set (reg:CC_NOOV 21)
3967 (compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
3968 (match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
3969 (match_operand:QF 3 "fp_zero_operand" "G,G,G")))
3970 (clobber (match_scratch:QF 0 "=f,f,?f"))]
3971 "valid_operands (PLUS, operands, QFmode)"
3976 [(set_attr "type" "binarycc,binarycc,binarycc")])
3978 (define_insn "*addqf3_set"
3979 [(set (reg:CC_NOOV 21)
3980 (compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
3981 (match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
3982 (match_operand:QF 3 "fp_zero_operand" "G,G,G")))
3983 (set (match_operand:QF 0 "reg_operand" "=f,f,?f")
3984 (plus:QF (match_dup 1)
3986 "valid_operands (PLUS, operands, QFmode)"
3991 [(set_attr "type" "binarycc,binarycc,binarycc")])
3996 (define_expand "subqf3"
3997 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
3998 (minus:QF (match_operand:QF 1 "src_operand" "")
3999 (match_operand:QF 2 "src_operand" "")))
4000 (clobber (reg:CC_NOOV 21))])]
4002 "legitimize_operands (MINUS, operands, QFmode);")
4004 (define_insn "*subqf3_clobber"
4005 [(set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
4006 (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
4007 (match_operand:QF 2 "src_operand" "fHm,0,R,fS<>")))
4008 (clobber (reg:CC_NOOV 21))]
4009 "valid_operands (MINUS, operands, QFmode)"
4015 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
4017 (define_insn "*subqf3_test"
4018 [(set (reg:CC_NOOV 21)
4019 (compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
4020 (match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
4021 (match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
4022 (clobber (match_scratch:QF 0 "=f,f,f,?f"))]
4023 "valid_operands (MINUS, operands, QFmode)"
4029 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
4031 (define_insn "*subqf3_set"
4032 [(set (reg:CC_NOOV 21)
4033 (compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
4034 (match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
4035 (match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
4036 (set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
4037 (minus:QF (match_dup 1)
4039 "valid_operands (MINUS, operands, QFmode)"
4045 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
4050 (define_expand "mulqf3"
4051 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
4052 (mult:QF (match_operand:QF 1 "src_operand" "")
4053 (match_operand:QF 2 "src_operand" "")))
4054 (clobber (reg:CC_NOOV 21))])]
4056 "legitimize_operands (MULT, operands, QFmode);")
4058 (define_insn "*mulqf3_clobber"
4059 [(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
4060 (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
4061 (match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
4062 (clobber (reg:CC_NOOV 21))]
4063 "valid_operands (MULT, operands, QFmode)"
4068 [(set_attr "type" "binarycc,binarycc,binarycc")])
4070 (define_insn "*mulqf3_test"
4071 [(set (reg:CC_NOOV 21)
4072 (compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
4073 (match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
4074 (match_operand:QF 3 "fp_zero_operand" "G,G,G")))
4075 (clobber (match_scratch:QF 0 "=f,f,?f"))]
4076 "valid_operands (MULT, operands, QFmode)"
4081 [(set_attr "type" "binarycc,binarycc,binarycc")])
4083 (define_insn "*mulqf3_set"
4084 [(set (reg:CC_NOOV 21)
4085 (compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
4086 (match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
4087 (match_operand:QF 3 "fp_zero_operand" "G,G,G")))
4088 (set (match_operand:QF 0 "reg_operand" "=f,f,?f")
4089 (mult:QF (match_dup 1)
4091 "valid_operands (MULT, operands, QFmode)"
4096 [(set_attr "type" "binarycc,binarycc,binarycc")])
4101 (define_expand "cmpqf"
4103 (compare:CC (match_operand:QF 0 "src_operand" "")
4104 (match_operand:QF 1 "src_operand" "")))]
4106 "legitimize_operands (COMPARE, operands, QFmode);
4107 c4x_compare_op0 = operands[0];
4108 c4x_compare_op1 = operands[1];
4111 (define_insn "*cmpqf"
4113 (compare:CC (match_operand:QF 0 "src_operand" "f,fR,fS<>")
4114 (match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
4115 "valid_operands (COMPARE, operands, QFmode)"
4120 [(set_attr "type" "compare,compare,compare")])
4122 (define_insn "*cmpqf_noov"
4123 [(set (reg:CC_NOOV 21)
4124 (compare:CC_NOOV (match_operand:QF 0 "src_operand" "f,fR,fS<>")
4125 (match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
4126 "valid_operands (COMPARE, operands, QFmode)"
4131 [(set_attr "type" "compare,compare,compare")])
4133 ; Inlined float divide for C4x
4134 (define_expand "divqf3_inline"
4135 [(parallel [(set (match_dup 3)
4136 (unspec:QF [(match_operand:QF 2 "src_operand" "")] UNSPEC_RCPF))
4137 (clobber (reg:CC_NOOV 21))])
4138 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
4139 (clobber (reg:CC_NOOV 21))])
4140 (parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
4141 (clobber (reg:CC_NOOV 21))])
4142 (parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
4143 (clobber (reg:CC_NOOV 21))])
4144 (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
4145 (clobber (reg:CC_NOOV 21))])
4146 (parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
4147 (clobber (reg:CC_NOOV 21))])
4148 (parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
4149 (clobber (reg:CC_NOOV 21))])
4150 (parallel [(set (match_dup 3)
4151 (mult:QF (match_operand:QF 1 "src_operand" "")
4153 (clobber (reg:CC_NOOV 21))])
4154 (parallel [(set (match_operand:QF 0 "reg_operand" "")
4155 (unspec:QF [(match_dup 3)] UNSPEC_RND))
4156 (clobber (reg:CC_NOOV 21))])]
4158 "if (! reload_in_progress
4159 && ! reg_operand (operands[2], QFmode))
4160 operands[2] = force_reg (QFmode, operands[2]);
4161 operands[3] = gen_reg_rtx (QFmode);
4162 operands[4] = gen_reg_rtx (QFmode);
4163 operands[5] = CONST2_RTX (QFmode);")
4165 (define_expand "divqf3"
4166 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
4167 (div:QF (match_operand:QF 1 "src_operand" "")
4168 (match_operand:QF 2 "src_operand" "")))
4169 (clobber (reg:CC 21))])]
4170 "! TARGET_C3X && TARGET_INLINE"
4171 "emit_insn (gen_divqf3_inline (operands[0], operands[1], operands[2]));
4178 ; ??? We should make these pattern fail if the src operand combination
4179 ; is not valid. Although reload will fix things up, it will introduce
4180 ; extra load instructions that won't be hoisted out of a loop.
4182 (define_insn "*ldi_conditional"
4183 [(set (match_operand:QI 0 "reg_operand" "=r,r")
4184 (if_then_else:QI (match_operator 1 "comparison_operator"
4185 [(reg:CC 21) (const_int 0)])
4186 (match_operand:QI 2 "src_operand" "rIm,0")
4187 (match_operand:QI 3 "src_operand" "0,rIm")))]
4188 "valid_operands (IF_THEN_ELSE, operands, QImode)"
4192 [(set_attr "type" "binary")])
4194 (define_insn "*ldi_conditional_noov"
4195 [(set (match_operand:QI 0 "reg_operand" "=r,r")
4196 (if_then_else:QI (match_operator 1 "comparison_operator"
4197 [(reg:CC_NOOV 21) (const_int 0)])
4198 (match_operand:QI 2 "src_operand" "rIm,0")
4199 (match_operand:QI 3 "src_operand" "0,rIm")))]
4200 "GET_CODE (operands[1]) != LE
4201 && GET_CODE (operands[1]) != GE
4202 && GET_CODE (operands[1]) != LT
4203 && GET_CODE (operands[1]) != GT
4204 && valid_operands (IF_THEN_ELSE, operands, QImode)"
4208 [(set_attr "type" "binary")])
4210 (define_insn "*ldi_on_overflow"
4211 [(set (match_operand:QI 0 "reg_operand" "=r")
4212 (unspec:QI [(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LDIV))
4216 [(set_attr "type" "unary")])
4218 ; Move operand 2 to operand 0 if condition (operand 1) is true
4219 ; else move operand 3 to operand 0.
4220 ; The temporary register is required below because some of the operands
4221 ; might be identical (namely 0 and 2).
4223 (define_expand "movqicc"
4224 [(set (match_operand:QI 0 "reg_operand" "")
4225 (if_then_else:QI (match_operand 1 "comparison_operator" "")
4226 (match_operand:QI 2 "src_operand" "")
4227 (match_operand:QI 3 "src_operand" "")))]
4230 enum rtx_code code = GET_CODE (operands[1]);
4231 rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
4232 if (ccreg == NULL_RTX) FAIL;
4233 emit_insn (gen_rtx_SET (QImode, operands[0],
4234 gen_rtx_IF_THEN_ELSE (QImode,
4235 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
4236 operands[2], operands[3])));
4239 (define_insn "*ldf_conditional"
4240 [(set (match_operand:QF 0 "reg_operand" "=f,f")
4241 (if_then_else:QF (match_operator 1 "comparison_operator"
4242 [(reg:CC 21) (const_int 0)])
4243 (match_operand:QF 2 "src_operand" "fHm,0")
4244 (match_operand:QF 3 "src_operand" "0,fHm")))]
4245 "valid_operands (IF_THEN_ELSE, operands, QFmode)"
4249 [(set_attr "type" "binary")])
4251 (define_insn "*ldf_conditional_noov"
4252 [(set (match_operand:QF 0 "reg_operand" "=f,f")
4253 (if_then_else:QF (match_operator 1 "comparison_operator"
4254 [(reg:CC_NOOV 21) (const_int 0)])
4255 (match_operand:QF 2 "src_operand" "fHm,0")
4256 (match_operand:QF 3 "src_operand" "0,fHm")))]
4257 "GET_CODE (operands[1]) != LE
4258 && GET_CODE (operands[1]) != GE
4259 && GET_CODE (operands[1]) != LT
4260 && GET_CODE (operands[1]) != GT
4261 && valid_operands (IF_THEN_ELSE, operands, QFmode)"
4265 [(set_attr "type" "binary")])
4267 (define_expand "movqfcc"
4268 [(set (match_operand:QF 0 "reg_operand" "")
4269 (if_then_else:QF (match_operand 1 "comparison_operator" "")
4270 (match_operand:QF 2 "src_operand" "")
4271 (match_operand:QF 3 "src_operand" "")))]
4274 enum rtx_code code = GET_CODE (operands[1]);
4275 rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
4276 if (ccreg == NULL_RTX) FAIL;
4277 emit_insn (gen_rtx_SET (QFmode, operands[0],
4278 gen_rtx_IF_THEN_ELSE (QFmode,
4279 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
4280 operands[2], operands[3])));
4283 (define_insn "*ldhf_conditional"
4284 [(set (match_operand:HF 0 "reg_operand" "=h,h")
4285 (if_then_else:HF (match_operator 1 "comparison_operator"
4286 [(reg:CC 21) (const_int 0)])
4287 (match_operand:HF 2 "src_operand" "hH,0")
4288 (match_operand:HF 3 "src_operand" "0,hH")))]
4293 [(set_attr "type" "binary")])
4295 (define_insn "*ldhf_conditional_noov"
4296 [(set (match_operand:HF 0 "reg_operand" "=h,h")
4297 (if_then_else:HF (match_operator 1 "comparison_operator"
4298 [(reg:CC_NOOV 21) (const_int 0)])
4299 (match_operand:HF 2 "src_operand" "hH,0")
4300 (match_operand:HF 3 "src_operand" "0,hH")))]
4301 "GET_CODE (operands[1]) != LE
4302 && GET_CODE (operands[1]) != GE
4303 && GET_CODE (operands[1]) != LT
4304 && GET_CODE (operands[1]) != GT"
4308 [(set_attr "type" "binary")])
4310 (define_expand "movhfcc"
4311 [(set (match_operand:HF 0 "reg_operand" "")
4312 (if_then_else:HF (match_operand 1 "comparison_operator" "")
4313 (match_operand:HF 2 "src_operand" "")
4314 (match_operand:HF 3 "src_operand" "")))]
4317 enum rtx_code code = GET_CODE (operands[1]);
4318 rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
4319 if (ccreg == NULL_RTX) FAIL;
4320 emit_insn (gen_rtx_SET (HFmode, operands[0],
4321 gen_rtx_IF_THEN_ELSE (HFmode,
4322 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
4323 operands[2], operands[3])));
4326 (define_expand "seq"
4327 [(set (match_operand:QI 0 "reg_operand" "")
4330 (if_then_else:QI (eq (match_dup 1) (const_int 0))
4334 "operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
4336 (define_expand "sne"
4337 [(set (match_operand:QI 0 "reg_operand" "")
4340 (if_then_else:QI (ne (match_dup 1) (const_int 0))
4344 "operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
4346 (define_expand "slt"
4347 [(set (match_operand:QI 0 "reg_operand" "")
4350 (if_then_else:QI (lt (match_dup 1) (const_int 0))
4354 "operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
4355 if (operands[1] == NULL_RTX) FAIL;")
4357 (define_expand "sltu"
4358 [(set (match_operand:QI 0 "reg_operand" "")
4361 (if_then_else:QI (ltu (match_dup 1) (const_int 0))
4365 "operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
4367 (define_expand "sgt"
4368 [(set (match_operand:QI 0 "reg_operand" "")
4371 (if_then_else:QI (gt (match_dup 1) (const_int 0))
4375 "operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
4376 if (operands[1] == NULL_RTX) FAIL;")
4378 (define_expand "sgtu"
4379 [(set (match_operand:QI 0 "reg_operand" "")
4382 (if_then_else:QI (gtu (match_dup 1) (const_int 0))
4386 "operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
4388 (define_expand "sle"
4389 [(set (match_operand:QI 0 "reg_operand" "")
4392 (if_then_else:QI (le (match_dup 1) (const_int 0))
4396 "operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
4397 if (operands[1] == NULL_RTX) FAIL;")
4399 (define_expand "sleu"
4400 [(set (match_operand:QI 0 "reg_operand" "")
4403 (if_then_else:QI (leu (match_dup 1) (const_int 0))
4407 "operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
4409 (define_expand "sge"
4410 [(set (match_operand:QI 0 "reg_operand" "")
4413 (if_then_else:QI (ge (match_dup 1) (const_int 0))
4417 "operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
4418 if (operands[1] == NULL_RTX) FAIL;")
4420 (define_expand "sgeu"
4421 [(set (match_operand:QI 0 "reg_operand" "")
4424 (if_then_else:QI (geu (match_dup 1) (const_int 0))
4428 "operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
4431 [(set (match_operand:QI 0 "reg_operand" "")
4432 (match_operator:QI 1 "comparison_operator" [(reg:CC 21) (const_int 0)]))]
4434 [(set (match_dup 0) (const_int 0))
4436 (if_then_else:QI (match_op_dup 1 [(reg:CC 21) (const_int 0)])
4442 [(set (match_operand:QI 0 "reg_operand" "")
4443 (match_operator:QI 1 "comparison_operator" [(reg:CC_NOOV 21) (const_int 0)]))]
4445 [(set (match_dup 0) (const_int 0))
4447 (if_then_else:QI (match_op_dup 1 [(reg:CC_NOOV 21) (const_int 0)])
4454 (unspec [(match_operand:QI 0 "reg_operand" "r")] UNSPEC_BU))]
4457 [(set_attr "type" "jump")])
4459 (define_expand "caseqi"
4460 [(parallel [(set (match_dup 5)
4461 (minus:QI (match_operand:QI 0 "reg_operand" "")
4462 (match_operand:QI 1 "src_operand" "")))
4463 (clobber (reg:CC_NOOV 21))])
4465 (compare:CC (match_dup 5)
4466 (match_operand:QI 2 "src_operand" "")))
4468 (if_then_else (gtu (reg:CC 21)
4470 (label_ref (match_operand 4 "" ""))
4472 (parallel [(set (match_dup 6)
4473 (plus:QI (match_dup 5)
4474 (label_ref:QI (match_operand 3 "" ""))))
4475 (clobber (reg:CC_NOOV 21))])
4477 (mem:QI (match_dup 6)))
4478 (set (pc) (match_dup 7))]
4480 "operands[5] = gen_reg_rtx (QImode);
4481 operands[6] = gen_reg_rtx (QImode);
4482 operands[7] = gen_reg_rtx (QImode);")
4485 ; PARALLEL FLOAT INSTRUCTIONS
4487 ; This patterns are under development
4493 (define_insn "*absqf2_movqf_clobber"
4494 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4495 (abs:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
4496 (set (match_operand:QF 2 "par_ind_operand" "=S<>")
4497 (match_operand:QF 3 "ext_low_reg_operand" "q"))
4498 (clobber (reg:CC_NOOV 21))]
4499 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
4500 "absf\\t%1,%0\\n||\\tstf\\t%3,%2"
4501 [(set_attr "type" "binarycc")])
4507 (define_insn "*addqf3_movqf_clobber"
4508 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
4509 (plus:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
4510 (match_operand:QF 2 "parallel_operand" "S<>,q")))
4511 (set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
4512 (match_operand:QF 4 "ext_low_reg_operand" "q,q"))
4513 (clobber (reg:CC 21))]
4514 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
4515 "addf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
4516 [(set_attr "type" "binarycc,binarycc")])
4522 (define_insn "*floatqiqf2_movqf_clobber"
4523 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4524 (float:QF (match_operand:QI 1 "par_ind_operand" "S<>")))
4525 (set (match_operand:QF 2 "par_ind_operand" "=S<>")
4526 (match_operand:QF 3 "ext_low_reg_operand" "q"))
4527 (clobber (reg:CC 21))]
4528 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
4529 "float\\t%1,%0\\n||\\tstf\\t%3,%2"
4530 [(set_attr "type" "binarycc")])
4536 (define_insn "*mulqf3_addqf3_clobber"
4537 [(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t,t,t")
4538 (mult:QF (match_operand:QF 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
4539 (match_operand:QF 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
4540 (set (match_operand:QF 3 "r2r3_reg_operand" "=u,u,u,u")
4541 (plus:QF (match_operand:QF 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
4542 (match_operand:QF 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
4543 (clobber (reg:CC_NOOV 21))]
4544 "TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
4545 "mpyf3\\t%2,%1,%0\\n||\\taddf3\\t%5,%4,%3"
4546 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
4553 (define_insn "*mulqf3_movqf_clobber"
4554 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
4555 (mult:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
4556 (match_operand:QF 2 "parallel_operand" "S<>,q")))
4557 (set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
4558 (match_operand:QF 4 "ext_low_reg_operand" "q,q"))
4559 (clobber (reg:CC 21))]
4560 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
4561 "mpyf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
4562 [(set_attr "type" "binarycc,binarycc")])
4568 (define_insn "*mulqf3_subqf3_clobber"
4569 [(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t")
4570 (mult:QF (match_operand:QF 1 "parallel_operand" "S<>,q")
4571 (match_operand:QF 2 "parallel_operand" "q,S<>")))
4572 (set (match_operand:QF 3 "r2r3_reg_operand" "=u,u")
4573 (minus:QF (match_operand:QF 4 "parallel_operand" "S<>,q")
4574 (match_operand:QF 5 "parallel_operand" "q,S<>")))
4575 (clobber (reg:CC 21))]
4576 "TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
4577 "mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%5,%4,%3"
4578 [(set_attr "type" "binarycc,binarycc")])
4584 (define_insn "*mulqf3_clrqf_clobber"
4585 [(set (match_operand:QF 0 "r0r1_reg_operand" "=t")
4586 (mult:QF (match_operand:QF 1 "par_ind_operand" "%S<>")
4587 (match_operand:QF 2 "par_ind_operand" "S<>")))
4588 (set (match_operand:QF 3 "r2r3_reg_operand" "=u")
4589 (match_operand:QF 4 "fp_zero_operand" "G"))
4590 (clobber (reg:CC 21))]
4591 "TARGET_PARALLEL_MPY"
4592 "mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%3,%3,%3"
4593 [(set_attr "type" "binarycc")])
4599 (define_insn "*negqf2_movqf_clobber"
4600 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4601 (neg:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
4602 (set (match_operand:QF 2 "par_ind_operand" "=S<>")
4603 (match_operand:QF 3 "ext_low_reg_operand" "q"))
4604 (clobber (reg:CC 21))]
4605 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
4606 "negf\\t%1,%0\\n||\\tstf\\t%3,%2"
4607 [(set_attr "type" "binarycc")])
4613 (define_insn "*subqf3_movqf_clobber"
4614 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4615 (minus:QF (match_operand:QF 1 "ext_low_reg_operand" "q")
4616 (match_operand:QF 2 "par_ind_operand" "S<>")))
4617 (set (match_operand:QF 3 "par_ind_operand" "=S<>")
4618 (match_operand:QF 4 "ext_low_reg_operand" "q"))
4619 (clobber (reg:CC 21))]
4620 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
4621 "subf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
4622 [(set_attr "type" "binarycc")])
4628 (define_insn "*toieee_movqf_clobber"
4629 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4630 (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_TOIEEE))
4631 (set (match_operand:QF 2 "par_ind_operand" "=S<>")
4632 (match_operand:QF 3 "ext_low_reg_operand" "q"))
4633 (clobber (reg:CC 21))]
4634 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
4635 "toieee\\t%1,%0\\n||\\tstf\\t%3,%2"
4636 [(set_attr "type" "binarycc")])
4642 (define_insn "*frieee_movqf_clobber"
4643 [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
4644 (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_FRIEEE))
4645 (set (match_operand:QF 2 "par_ind_operand" "=S<>")
4646 (match_operand:QF 3 "ext_low_reg_operand" "q"))
4647 (clobber (reg:CC 21))]
4648 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
4649 "frieee\\t%1,%0\\n||\\tstf\\t%3,%2"
4650 [(set_attr "type" "binarycc")])
4653 ; PARALLEL INTEGER INSTRUCTIONS
4660 (define_insn "*absqi2_movqi_clobber"
4661 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4662 (abs:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
4663 (set (match_operand:QI 2 "par_ind_operand" "=S<>")
4664 (match_operand:QI 3 "ext_low_reg_operand" "q"))
4665 (clobber (reg:CC_NOOV 21))]
4666 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
4667 "absi\\t%1,%0\\n||\\tsti\\t%3,%2"
4668 [(set_attr "type" "binarycc")])
4674 (define_insn "*addqi3_movqi_clobber"
4675 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
4676 (plus:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
4677 (match_operand:QI 2 "parallel_operand" "S<>,q")))
4678 (set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
4679 (match_operand:QI 4 "ext_low_reg_operand" "q,q"))
4680 (clobber (reg:CC 21))]
4681 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4682 "addi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4683 [(set_attr "type" "binarycc,binarycc")])
4689 (define_insn "*andqi3_movqi_clobber"
4690 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
4691 (and:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
4692 (match_operand:QI 2 "parallel_operand" "S<>,q")))
4693 (set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
4694 (match_operand:QI 4 "ext_low_reg_operand" "q,q"))
4695 (clobber (reg:CC 21))]
4696 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4697 "and3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4698 [(set_attr "type" "binarycc,binarycc")])
4704 (define_insn "*ashlqi3_movqi_clobber"
4705 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4706 (ashift:QI (match_operand:QI 1 "par_ind_operand" "S<>")
4707 (match_operand:QI 2 "ext_low_reg_operand" "q")))
4708 (set (match_operand:QI 3 "par_ind_operand" "=S<>")
4709 (match_operand:QI 4 "ext_low_reg_operand" "q"))
4710 (clobber (reg:CC 21))]
4711 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4712 "ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4713 [(set_attr "type" "binarycc")])
4719 (define_insn "*ashrqi3_movqi_clobber"
4720 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4721 (ashiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
4722 (neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
4723 (set (match_operand:QI 3 "par_ind_operand" "=S<>")
4724 (match_operand:QI 4 "ext_low_reg_operand" "q"))
4725 (clobber (reg:CC 21))]
4726 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4727 "ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4728 [(set_attr "type" "binarycc")])
4734 (define_insn "*fixqfqi2_movqi_clobber"
4735 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4736 (fix:QI (match_operand:QF 1 "par_ind_operand" "S<>")))
4737 (set (match_operand:QI 2 "par_ind_operand" "=S<>")
4738 (match_operand:QI 3 "ext_low_reg_operand" "q"))
4739 (clobber (reg:CC 21))]
4740 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
4741 "fix\\t%1,%0\\n||\\tsti\\t%3,%2"
4742 [(set_attr "type" "binarycc")])
4748 (define_insn "*lshrqi3_movqi_clobber"
4749 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4750 (lshiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
4751 (neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
4752 (set (match_operand:QI 3 "par_ind_operand" "=S<>")
4753 (match_operand:QI 4 "ext_low_reg_operand" "q"))
4754 (clobber (reg:CC 21))]
4755 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4756 "lsh3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4757 [(set_attr "type" "binarycc")])
4763 (define_insn "*mulqi3_addqi3_clobber"
4764 [(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t,t,t")
4765 (mult:QI (match_operand:QI 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
4766 (match_operand:QI 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
4767 (set (match_operand:QI 3 "r2r3_reg_operand" "=u,u,u,u")
4768 (plus:QI (match_operand:QI 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
4769 (match_operand:QI 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
4770 (clobber (reg:CC 21))]
4771 "TARGET_PARALLEL_MPY && TARGET_MPYI
4772 && valid_parallel_operands_6 (operands, QImode)"
4773 "mpyi3\\t%2,%1,%0\\n||\\taddi3\\t%5,%4,%3"
4774 [(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
4781 (define_insn "*mulqi3_movqi_clobber"
4782 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
4783 (mult:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
4784 (match_operand:QI 2 "parallel_operand" "S<>,q")))
4785 (set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
4786 (match_operand:QI 4 "ext_low_reg_operand" "q,q"))
4787 (clobber (reg:CC 21))]
4788 "TARGET_PARALLEL && TARGET_MPYI
4789 && valid_parallel_operands_5 (operands, QImode)"
4790 "mpyi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4791 [(set_attr "type" "binarycc,binarycc")])
4797 (define_insn "*mulqi3_subqi3_clobber"
4798 [(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t")
4799 (mult:QI (match_operand:QI 1 "parallel_operand" "S<>,q")
4800 (match_operand:QI 2 "parallel_operand" "q,S<>")))
4801 (set (match_operand:QI 3 "r2r3_reg_operand" "=u,u")
4802 (minus:QI (match_operand:QI 4 "parallel_operand" "S<>,q")
4803 (match_operand:QI 5 "parallel_operand" "q,S<>")))
4804 (clobber (reg:CC 21))]
4805 "TARGET_PARALLEL_MPY && TARGET_MPYI
4806 && valid_parallel_operands_6 (operands, QImode)"
4807 "mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%5,%4,%3"
4808 [(set_attr "type" "binarycc,binarycc")])
4814 (define_insn "*mulqi3_clrqi_clobber"
4815 [(set (match_operand:QI 0 "r0r1_reg_operand" "=t")
4816 (mult:QI (match_operand:QI 1 "par_ind_operand" "%S<>")
4817 (match_operand:QI 2 "par_ind_operand" "S<>")))
4818 (set (match_operand:QI 3 "r2r3_reg_operand" "=u")
4820 (clobber (reg:CC 21))]
4821 "TARGET_PARALLEL_MPY && TARGET_MPYI"
4822 "mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%3,%3,%3"
4823 [(set_attr "type" "binarycc")])
4829 (define_insn "*negqi2_movqi_clobber"
4830 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4831 (neg:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
4832 (set (match_operand:QI 2 "par_ind_operand" "=S<>")
4833 (match_operand:QI 3 "ext_low_reg_operand" "q"))
4834 (clobber (reg:CC 21))]
4835 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
4836 "negi\\t%1,%0\\n||\\tsti\\t%3,%2"
4837 [(set_attr "type" "binarycc")])
4843 (define_insn "*notqi2_movqi_clobber"
4844 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4845 (not:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
4846 (set (match_operand:QI 2 "par_ind_operand" "=S<>")
4847 (match_operand:QI 3 "ext_low_reg_operand" "q"))
4848 (clobber (reg:CC 21))]
4849 "TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
4850 "not\\t%1,%0\\n||\\tsti\\t%3,%2"
4851 [(set_attr "type" "binarycc")])
4857 (define_insn "*iorqi3_movqi_clobber"
4858 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
4859 (ior:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
4860 (match_operand:QI 2 "parallel_operand" "S<>,q")))
4861 (set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
4862 (match_operand:QI 4 "ext_low_reg_operand" "q,q"))
4863 (clobber (reg:CC 21))]
4864 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4865 "or3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4866 [(set_attr "type" "binarycc,binarycc")])
4872 (define_insn "*subqi3_movqi_clobber"
4873 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
4874 (minus:QI (match_operand:QI 1 "par_ind_operand" "S<>")
4875 (match_operand:QI 2 "ext_low_reg_operand" "q")))
4876 (set (match_operand:QI 3 "par_ind_operand" "=S<>")
4877 (match_operand:QI 4 "ext_low_reg_operand" "q"))
4878 (clobber (reg:CC 21))]
4879 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4880 "subi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4881 [(set_attr "type" "binarycc")])
4887 (define_insn "*xorqi3_movqi_clobber"
4888 [(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
4889 (xor:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
4890 (match_operand:QI 2 "parallel_operand" "S<>,q")))
4891 (set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
4892 (match_operand:QI 4 "ext_low_reg_operand" "q,q"))
4893 (clobber (reg:CC 21))]
4894 "TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
4895 "xor3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
4896 [(set_attr "type" "binarycc,binarycc")])
4899 ; BRANCH/CALL INSTRUCTIONS
4903 ; Branch instructions
4906 [(set (pc) (if_then_else (match_operator 0 "comparison_operator"
4907 [(reg:CC 21) (const_int 0)])
4908 (label_ref (match_operand 1 "" ""))
4912 return c4x_output_cbranch (\"b%0\", insn);"
4913 [(set_attr "type" "jmpc")])
4915 (define_insn "*b_rev"
4916 [(set (pc) (if_then_else (match_operator 0 "comparison_operator"
4917 [(reg:CC 21) (const_int 0)])
4919 (label_ref (match_operand 1 "" ""))))]
4922 return c4x_output_cbranch (\"b%I0\", insn);"
4923 [(set_attr "type" "jmpc")])
4925 (define_insn "*b_noov"
4926 [(set (pc) (if_then_else (match_operator 0 "comparison_operator"
4927 [(reg:CC_NOOV 21) (const_int 0)])
4928 (label_ref (match_operand 1 "" ""))
4930 "GET_CODE (operands[0]) != LE
4931 && GET_CODE (operands[0]) != GE
4932 && GET_CODE (operands[0]) != LT
4933 && GET_CODE (operands[0]) != GT"
4935 return c4x_output_cbranch (\"b%0\", insn);"
4936 [(set_attr "type" "jmpc")])
4938 (define_insn "*b_noov_rev"
4939 [(set (pc) (if_then_else (match_operator 0 "comparison_operator"
4940 [(reg:CC_NOOV 21) (const_int 0)])
4942 (label_ref (match_operand 1 "" ""))))]
4943 "GET_CODE (operands[0]) != LE
4944 && GET_CODE (operands[0]) != GE
4945 && GET_CODE (operands[0]) != LT
4946 && GET_CODE (operands[0]) != GT"
4948 return c4x_output_cbranch (\"b%I0\", insn);"
4949 [(set_attr "type" "jmpc")])
4951 (define_expand "beq"
4952 [(set (pc) (if_then_else (eq (match_dup 1) (const_int 0))
4953 (label_ref (match_operand 0 "" ""))
4956 "operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
4958 (define_expand "bne"
4959 [(set (pc) (if_then_else (ne (match_dup 1) (const_int 0))
4960 (label_ref (match_operand 0 "" ""))
4963 "operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
4965 (define_expand "blt"
4966 [(set (pc) (if_then_else (lt (match_dup 1) (const_int 0))
4967 (label_ref (match_operand 0 "" ""))
4970 "operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
4971 if (operands[1] == NULL_RTX) FAIL;")
4973 (define_expand "bltu"
4974 [(set (pc) (if_then_else (ltu (match_dup 1) (const_int 0))
4975 (label_ref (match_operand 0 "" ""))
4978 "operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
4980 (define_expand "bgt"
4981 [(set (pc) (if_then_else (gt (match_dup 1) (const_int 0))
4982 (label_ref (match_operand 0 "" ""))
4985 "operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
4986 if (operands[1] == NULL_RTX) FAIL;")
4988 (define_expand "bgtu"
4989 [(set (pc) (if_then_else (gtu (match_dup 1) (const_int 0))
4990 (label_ref (match_operand 0 "" ""))
4993 "operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
4995 (define_expand "ble"
4996 [(set (pc) (if_then_else (le (match_dup 1) (const_int 0))
4997 (label_ref (match_operand 0 "" ""))
5000 "operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
5001 if (operands[1] == NULL_RTX) FAIL;")
5003 (define_expand "bleu"
5004 [(set (pc) (if_then_else (leu (match_dup 1) (const_int 0))
5005 (label_ref (match_operand 0 "" ""))
5008 "operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
5010 (define_expand "bge"
5011 [(set (pc) (if_then_else (ge (match_dup 1) (const_int 0))
5012 (label_ref (match_operand 0 "" ""))
5015 "operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
5016 if (operands[1] == NULL_RTX) FAIL;")
5018 (define_expand "bgeu"
5019 [(set (pc) (if_then_else (geu (match_dup 1) (const_int 0))
5020 (label_ref (match_operand 0 "" ""))
5023 "operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
5025 (define_insn "*b_reg"
5026 [(set (pc) (match_operand:QI 0 "reg_operand" "r"))]
5029 [(set_attr "type" "jump")])
5031 (define_expand "indirect_jump"
5032 [(set (pc) (match_operand:QI 0 "reg_operand" ""))]
5036 (define_insn "tablejump"
5037 [(set (pc) (match_operand:QI 0 "src_operand" "r"))
5038 (use (label_ref (match_operand 1 "" "")))]
5041 [(set_attr "type" "jump")])
5046 (define_insn "*call_c3x"
5047 [(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
5048 (match_operand:QI 1 "general_operand" ""))
5049 (clobber (reg:QI 31))]
5050 ;; Operand 1 not really used on the C4x. The C30 doesn't have reg 31.
5054 [(set_attr "type" "call")])
5056 ; LAJ requires R11 (31) for the return address
5058 [(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
5059 (match_operand:QI 1 "general_operand" ""))
5060 (clobber (reg:QI 31))]
5061 ;; Operand 1 not really used on the C4x.
5066 return c4x_check_laj_p (insn)
5067 ? \"nop\\n\\tlaj%U0\\t%C0\" : \"laj%U0\\t%C0\";
5069 return \"call%U0\\t%C0\";"
5070 [(set_attr "type" "laj")])
5072 (define_expand "call"
5073 [(parallel [(call (match_operand:QI 0 "" "")
5074 (match_operand:QI 1 "general_operand" ""))
5075 (clobber (reg:QI 31))])]
5079 if (GET_CODE (operands[0]) == MEM
5080 && ! call_address_operand (XEXP (operands[0], 0), Pmode))
5081 operands[0] = gen_rtx_MEM (GET_MODE (operands[0]),
5082 force_reg (Pmode, XEXP (operands[0], 0)));
5085 (define_insn "nodb_call"
5086 [(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
5090 [(set_attr "type" "call")])
5092 (define_insn "*callv_c3x"
5093 [(set (match_operand 0 "" "=r")
5094 (call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
5095 (match_operand:QI 2 "general_operand" "")))
5096 (clobber (reg:QI 31))]
5097 ;; Operand 0 and 2 not really used for the C4x.
5098 ;; The C30 doesn't have reg 31.
5102 [(set_attr "type" "call")])
5104 ; LAJ requires R11 (31) for the return address
5105 (define_insn "*lajv"
5106 [(set (match_operand 0 "" "=r")
5107 (call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
5108 (match_operand:QI 2 "general_operand" "")))
5109 (clobber (reg:QI 31))]
5110 ;; Operand 0 and 2 not really used in the C30 instruction.
5115 return c4x_check_laj_p (insn)
5116 ? \"nop\\n\\tlaj%U1\\t%C1\" : \"laj%U1\\t%C1\";
5118 return \"call%U1\\t%C1\";"
5119 [(set_attr "type" "laj")])
5121 (define_expand "call_value"
5122 [(parallel [(set (match_operand 0 "" "")
5123 (call (match_operand:QI 1 "" "")
5124 (match_operand:QI 2 "general_operand" "")))
5125 (clobber (reg:QI 31))])]
5129 if (GET_CODE (operands[0]) == MEM
5130 && ! call_address_operand (XEXP (operands[1], 0), Pmode))
5131 operands[0] = gen_rtx_MEM (GET_MODE (operands[1]),
5132 force_reg (Pmode, XEXP (operands[1], 0)));
5135 (define_insn "return"
5137 "! c4x_null_epilogue_p ()"
5139 [(set_attr "type" "rets")])
5141 (define_insn "return_from_epilogue"
5143 "reload_completed && ! c4x_interrupt_function_p ()"
5145 [(set_attr "type" "rets")])
5147 (define_insn "return_from_interrupt_epilogue"
5149 "reload_completed && c4x_interrupt_function_p ()"
5151 [(set_attr "type" "rets")])
5153 (define_insn "*return_cc"
5155 (if_then_else (match_operator 0 "comparison_operator"
5156 [(reg:CC 21) (const_int 0)])
5159 "! c4x_null_epilogue_p ()"
5161 [(set_attr "type" "rets")])
5163 (define_insn "*return_cc_noov"
5165 (if_then_else (match_operator 0 "comparison_operator"
5166 [(reg:CC_NOOV 21) (const_int 0)])
5169 "GET_CODE (operands[0]) != LE
5170 && GET_CODE (operands[0]) != GE
5171 && GET_CODE (operands[0]) != LT
5172 && GET_CODE (operands[0]) != GT
5173 && ! c4x_null_epilogue_p ()"
5175 [(set_attr "type" "rets")])
5177 (define_insn "*return_cc_inverse"
5179 (if_then_else (match_operator 0 "comparison_operator"
5180 [(reg:CC 21) (const_int 0)])
5183 "! c4x_null_epilogue_p ()"
5185 [(set_attr "type" "rets")])
5187 (define_insn "*return_cc_noov_inverse"
5189 (if_then_else (match_operator 0 "comparison_operator"
5190 [(reg:CC_NOOV 21) (const_int 0)])
5193 "GET_CODE (operands[0]) != LE
5194 && GET_CODE (operands[0]) != GE
5195 && GET_CODE (operands[0]) != LT
5196 && GET_CODE (operands[0]) != GT
5197 && ! c4x_null_epilogue_p ()"
5199 [(set_attr "type" "rets")])
5202 [(set (pc) (label_ref (match_operand 0 "" "")))]
5205 [(set_attr "type" "jump")])
5208 [(trap_if (const_int 1) (const_int 31))]
5211 [(set_attr "type" "call")])
5213 (define_expand "conditional_trap"
5214 [(trap_if (match_operand 0 "comparison_operator" "")
5215 (match_operand 1 "const_int_operand" ""))]
5218 enum rtx_code code = GET_CODE (operands[1]);
5219 rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
5220 if (ccreg == NULL_RTX) FAIL;
5221 if (GET_MODE (ccreg) == CCmode)
5222 emit_insn (gen_cond_trap_cc (operands[0], operands[1]));
5224 emit_insn (gen_cond_trap_cc_noov (operands[0], operands[1]));
5227 (define_insn "cond_trap_cc"
5228 [(trap_if (match_operator 0 "comparison_operator"
5229 [(reg:CC 21) (const_int 0)])
5230 (match_operand 1 "const_int_operand" ""))]
5233 [(set_attr "type" "call")])
5235 (define_insn "cond_trap_cc_noov"
5236 [(trap_if (match_operator 0 "comparison_operator"
5237 [(reg:CC_NOOV 21) (const_int 0)])
5238 (match_operand 1 "const_int_operand" ""))]
5239 "GET_CODE (operands[0]) != LE
5240 && GET_CODE (operands[0]) != GE
5241 && GET_CODE (operands[0]) != LT
5242 && GET_CODE (operands[0]) != GT"
5244 [(set_attr "type" "call")])
5249 ; Note we have to emit a dbu instruction if there are no delay slots
5251 ; Also note that GCC will try to reverse a loop to see if it can
5252 ; utilize this instruction. However, if there are more than one
5253 ; memory reference in the loop, it cannot guarantee that reversing
5254 ; the loop will work :( (see check_dbra_loop() in loop.c)
5255 ; Note that the C3x only decrements the 24 LSBs of the address register
5256 ; and the 8 MSBs are untouched. The C4x uses all 32-bits. We thus
5257 ; have an option to disable this instruction.
5260 (if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
5262 (label_ref (match_operand 1 "" ""))
5265 (plus:QI (match_dup 0)
5268 (clobber (reg:CC_NOOV 21))]
5269 "TARGET_DB && TARGET_LOOP_UNSIGNED"
5271 if (which_alternative == 0)
5272 return \"dbu%#\\t%0,%l1\";
5273 else if (which_alternative == 1)
5274 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
5275 else if (which_alternative == 2)
5276 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
5278 return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
5280 [(set_attr "type" "db,jmpc,jmpc,jmpc")])
5282 (define_insn "*db_noclobber"
5284 (if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a")
5286 (label_ref (match_operand 1 "" ""))
5289 (plus:QI (match_dup 0)
5291 "reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
5293 [(set_attr "type" "db")])
5297 (if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "")
5299 (label_ref (match_operand 1 "" ""))
5302 (plus:QI (match_dup 0)
5305 (clobber (reg:CC_NOOV 21))]
5306 "reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
5307 [(parallel [(set (pc)
5308 (if_then_else (ne (match_dup 0)
5310 (label_ref (match_dup 1))
5313 (plus:QI (match_dup 0)
5318 ; This insn is used for some loop tests, typically loops reversed when
5319 ; strength reduction is used. It is actually created when the instruction
5320 ; combination phase combines the special loop test. Since this insn
5321 ; is both a jump insn and has an output, it must deal with its own
5322 ; reloads, hence the `m' constraints.
5324 ; The C4x does the decrement and then compares the result against zero.
5325 ; It branches if the result was greater than or equal to zero.
5326 ; In the RTL the comparison and decrement are assumed to happen
5327 ; at the same time so we bias the iteration counter with by -1
5328 ; when we make the test.
5329 (define_insn "decrement_and_branch_until_zero"
5331 (if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
5334 (label_ref (match_operand 1 "" ""))
5337 (plus:QI (match_dup 0)
5340 (clobber (reg:CC_NOOV 21))]
5341 "TARGET_DB && (find_reg_note (insn, REG_NONNEG, 0) || TARGET_LOOP_UNSIGNED)"
5343 if (which_alternative == 0)
5344 return \"dbu%#\\t%0,%l1\";
5345 else if (which_alternative == 1)
5346 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
5347 else if (which_alternative == 2)
5348 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
5350 return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
5352 [(set_attr "type" "db,jmpc,jmpc,jmpc")])
5354 (define_insn "*decrement_and_branch_until_zero_noclobber"
5356 (if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
5359 (label_ref (match_operand 1 "" ""))
5362 (plus:QI (match_dup 0)
5364 "reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
5366 [(set_attr "type" "db")])
5370 (if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "")
5373 (label_ref (match_operand 1 "" ""))
5376 (plus:QI (match_dup 0)
5379 (clobber (reg:CC_NOOV 21))]
5380 "reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
5381 [(parallel [(set (pc)
5382 (if_then_else (ge (plus:QI (match_dup 0)
5385 (label_ref (match_dup 1))
5388 (plus:QI (match_dup 0)
5403 ; Default to misc type attr.
5405 (define_insn "return_indirect_internal"
5407 (use (match_operand:QI 0 "reg_operand" ""))]
5410 [(set_attr "type" "jump")])
5412 (define_expand "prologue"
5415 "c4x_expand_prologue (); DONE;")
5417 (define_expand "epilogue"
5420 "c4x_expand_epilogue (); DONE;")
5425 (define_insn "rptb_top"
5426 [(use (label_ref (match_operand 0 "" "")))
5427 (use (label_ref (match_operand 1 "" "")))
5428 (clobber (reg:QI 25))
5429 (clobber (reg:QI 26))]
5432 return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
5433 ? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
5435 [(set_attr "type" "repeat_top")])
5437 (define_insn "rpts_top"
5438 [(unspec [(use (label_ref (match_operand 0 "" "")))
5439 (use (label_ref (match_operand 1 "" "")))] UNSPEC_RPTS)
5440 (clobber (reg:QI 25))
5441 (clobber (reg:QI 26))]
5444 return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
5445 ? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
5447 [(set_attr "type" "repeat")])
5449 ; This pattern needs to be emitted at the start of the loop to
5450 ; say that RS and RE are loaded.
5451 (define_insn "rptb_init"
5452 [(unspec [(match_operand:QI 0 "register_operand" "va")] UNSPEC_RPTB_INIT)
5453 (clobber (reg:QI 25))
5454 (clobber (reg:QI 26))]
5457 [(set_attr "type" "repeat")])
5460 ; operand 0 is the loop count pseudo register
5461 ; operand 1 is the number of loop iterations or 0 if it is unknown
5462 ; operand 2 is the maximum number of loop iterations
5463 ; operand 3 is the number of levels of enclosed loops
5464 (define_expand "doloop_begin"
5465 [(use (match_operand 0 "register_operand" ""))
5466 (use (match_operand:QI 1 "const_int_operand" ""))
5467 (use (match_operand:QI 2 "const_int_operand" ""))
5468 (use (match_operand:QI 3 "const_int_operand" ""))]
5470 "if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
5472 emit_insn (gen_rptb_init (operands[0]));
5477 ; The RS (25) and RE (26) registers must be unviolate from the top of the loop
5479 (define_insn "rptb_end"
5481 (if_then_else (ge (match_operand:QI 0 "register_operand" "+v,?a,!*d,!*x*k,!m")
5483 (label_ref (match_operand 1 "" ""))
5486 (plus:QI (match_dup 0)
5491 (clobber (reg:CC_NOOV 21))]
5494 if (which_alternative == 0)
5495 return c4x_rptb_nop_p (insn) ? \"nop\" : \"\";
5496 else if (which_alternative == 1 && TARGET_DB)
5497 return \"dbu%#\\t%0,%l1\";
5498 else if (which_alternative == 2)
5499 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
5500 else if (which_alternative == 3 || (which_alternative == 1 && ! TARGET_DB))
5501 return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
5503 return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
5505 [(set_attr "type" "repeat,db,jmpc,jmpc,jmpc")])
5509 (if_then_else (ge (match_operand:QI 0 "addr_reg_operand" "")
5511 (label_ref (match_operand 1 "" ""))
5514 (plus:QI (match_dup 0)
5516 (use (match_operand:QI 2 "const_int_operand" ""))
5517 (use (match_operand:QI 3 "const_int_operand" ""))
5518 (use (match_operand:QI 4 "const_int_operand" ""))
5522 (clobber (reg:CC_NOOV 21))]
5524 [(parallel [(set (pc)
5525 (if_then_else (ge (match_dup 0)
5527 (label_ref (match_dup 1))
5530 (plus:QI (match_dup 0)
5534 ; operand 0 is the loop count pseudo register
5535 ; operand 1 is the number of loop iterations or 0 if it is unknown
5536 ; operand 2 is the maximum number of loop iterations
5537 ; operand 3 is the number of levels of enclosed loops
5538 ; operand 4 is the label to jump to at the top of the loop
5539 (define_expand "doloop_end"
5540 [(use (match_operand 0 "register_operand" ""))
5541 (use (match_operand:QI 1 "const_int_operand" ""))
5542 (use (match_operand:QI 2 "const_int_operand" ""))
5543 (use (match_operand:QI 3 "const_int_operand" ""))
5544 (use (label_ref (match_operand 4 "" "")))]
5546 "if (! TARGET_LOOP_UNSIGNED
5547 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > ((unsigned) 1 << 31))
5549 if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
5551 /* The C30 maximum iteration count for DB is 2^24. */
5554 emit_jump_insn (gen_decrement_and_branch_until_zero (operands[0],
5558 emit_jump_insn (gen_rptb_end (operands[0], operands[4]));
5562 (define_expand "decrement_and_branch_on_count"
5563 [(parallel [(set (pc)
5564 (if_then_else (ge (match_operand:QI 0 "register_operand" "")
5566 (label_ref (match_operand 1 "" ""))
5569 (plus:QI (match_dup 0)
5573 (clobber (reg:CC_NOOV 21))])]
5577 (define_expand "movmemqi_small"
5578 [(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
5579 (mem:BLK (match_operand:BLK 1 "src_operand" "")))
5580 (use (match_operand:QI 2 "immediate_operand" ""))
5581 (use (match_operand:QI 3 "immediate_operand" ""))
5582 (clobber (match_operand:QI 4 "ext_low_reg_operand" ""))])]
5587 rtx src_mem, dst_mem;
5593 len = INTVAL (operands[2]);
5596 src_mem = gen_rtx_MEM (QImode, src);
5597 dst_mem = gen_rtx_MEM (QImode, dst);
5599 if (TARGET_PARALLEL)
5601 emit_insn (gen_movqi (tmp, src_mem));
5602 emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
5603 for (i = 1; i < len; i++)
5605 emit_insn (gen_movqi_parallel (tmp, src_mem, dst_mem, tmp));
5606 emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
5607 emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
5609 emit_insn (gen_movqi (dst_mem, tmp));
5610 emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
5614 for (i = 0; i < len; i++)
5616 emit_insn (gen_movqi (tmp, src_mem));
5617 emit_insn (gen_movqi (dst_mem, tmp));
5618 emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
5619 emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
5629 ; We should probably get RC loaded when using RPTB automagically...
5630 ; There's probably no need to call _memcpy() if we don't get
5631 ; an immediate operand for the size. We could do a better job here
5632 ; than most memcpy() implementations.
5633 ; operand 2 is the number of bytes
5634 ; operand 3 is the shared alignment
5635 ; operand 4 is a scratch register
5637 (define_insn "movmemqi_large"
5638 [(set (mem:BLK (match_operand:QI 0 "addr_reg_operand" "a"))
5639 (mem:BLK (match_operand:QI 1 "addr_reg_operand" "a")))
5640 (use (match_operand:QI 2 "immediate_operand" "i"))
5641 (use (match_operand:QI 3 "immediate_operand" ""))
5642 (clobber (match_operand:QI 4 "ext_low_reg_operand" "=&q"))
5643 (clobber (match_scratch:QI 5 "=0"))
5644 (clobber (match_scratch:QI 6 "=1"))
5645 (clobber (reg:QI 25))
5646 (clobber (reg:QI 26))
5647 (clobber (reg:QI 27))]
5652 int len = INTVAL (operands[2]);
5654 output_asm_insn (\"ldiu\\t*%1++,%4\", operands);
5657 for (i = 1; i < len; i++)
5659 output_asm_insn (\"sti\\t%4,*%0++\", operands);
5660 output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
5665 if (TARGET_RPTS_CYCLES (len))
5667 output_asm_insn (\"rpts\\t%2-2\", operands);
5668 output_asm_insn (\"sti\\t%4,*%0++\", operands);
5669 output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
5673 output_asm_insn (\"ldiu\\t%2-2,rc\", operands);
5674 output_asm_insn (\"rptb\\t$+1\", operands);
5675 output_asm_insn (\"sti\\t%4,*%0++\", operands);
5676 output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
5679 return \"sti\\t%4,*%0++\";
5681 [(set_attr "type" "multi")])
5683 ; Operand 2 is the count, operand 3 is the alignment.
5684 (define_expand "movmemqi"
5685 [(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
5686 (mem:BLK (match_operand:BLK 1 "src_operand" "")))
5687 (use (match_operand:QI 2 "immediate_operand" ""))
5688 (use (match_operand:QI 3 "immediate_operand" ""))])]
5693 if (GET_CODE (operands[2]) != CONST_INT
5694 || INTVAL (operands[2]) > 32767
5695 || INTVAL (operands[2]) <= 0)
5697 FAIL; /* Try to call _memcpy */
5700 operands[0] = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
5701 operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
5702 tmp = gen_reg_rtx (QImode);
5703 /* Disabled because of reload problems. */
5704 if (0 && INTVAL (operands[2]) < 8)
5705 emit_insn (gen_movmemqi_small (operands[0], operands[1], operands[2],
5709 emit_insn (gen_movmemqi_large (operands[0], operands[1], operands[2],
5716 (define_insn "*cmpstrnqi"
5717 [(set (match_operand:QI 0 "ext_reg_operand" "=d")
5718 (compare:QI (mem:BLK (match_operand:QI 1 "addr_reg_operand" "+a"))
5719 (mem:BLK (match_operand:QI 2 "addr_reg_operand" "+a"))))
5720 (use (match_operand:QI 3 "immediate_operand" "i"))
5721 (use (match_operand:QI 4 "immediate_operand" ""))
5722 (clobber (match_operand:QI 5 "std_reg_operand" "=&c"))
5723 (clobber (reg:QI 21))]
5727 output_asm_insn (\"ldi\\t%3-1,%5\", operands);
5728 output_asm_insn (\"$1:\tsubi3\\t*%1++,*%2++,%0\", operands);
5729 output_asm_insn (\"dbeq\\t%5,$1\", operands);
5733 (define_expand "cmpstrnqi"
5734 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
5735 (compare:QI (match_operand:BLK 1 "general_operand" "")
5736 (match_operand:BLK 2 "general_operand" "")))
5737 (use (match_operand:QI 3 "immediate_operand" ""))
5738 (use (match_operand:QI 4 "immediate_operand" ""))
5739 (clobber (match_dup 5))
5740 (clobber (reg:QI 21))])]
5744 if (GET_CODE (operands[3]) != CONST_INT
5745 || INTVAL (operands[3]) > 32767
5746 || INTVAL (operands[3]) <= 0)
5750 operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
5751 operands[2] = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
5752 operands[5] = gen_reg_rtx (QImode);
5756 ; TWO OPERAND LONG DOUBLE INSTRUCTIONS
5759 (define_expand "movhf"
5760 [(set (match_operand:HF 0 "src_operand" "")
5761 (match_operand:HF 1 "src_operand" ""))]
5763 "if (c4x_emit_move_sequence (operands, HFmode))
5766 (define_insn "*movhf_noclobber_reg"
5767 [(set (match_operand:HF 0 "reg_operand" "=h")
5768 (match_operand:HF 1 "src_operand" "Hh"))]
5769 "GET_CODE (operands[1]) != MEM"
5771 [(set_attr "type" "unary")])
5773 (define_insn "*movhf_noclobber"
5774 [(set (match_operand:HF 0 "dst_operand" "=h,m")
5775 (match_operand:HF 1 "src_operand" "Hm,h"))]
5776 "reg_operand (operands[0], HFmode) ^ reg_operand (operands[1], HFmode)"
5778 [(set_attr "type" "multi,multi")])
5780 (define_insn "*movhf_test"
5782 (compare:CC (match_operand:HF 1 "reg_operand" "h")
5784 (clobber (match_scratch:HF 0 "=h"))]
5787 [(set_attr "type" "unarycc")])
5789 (define_insn "*movhf_set"
5791 (compare:CC (match_operand:HF 1 "reg_operand" "h")
5792 (match_operand:HF 2 "fp_zero_operand" "G")))
5793 (set (match_operand:HF 0 "reg_operand" "=h")
5797 [(set_attr "type" "unarycc")])
5800 [(set (match_operand:HF 0 "reg_operand" "")
5801 (match_operand:HF 1 "memory_operand" ""))]
5803 [(set (match_dup 0) (float_extend:HF (match_dup 2)))
5804 (set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
5805 (match_dup 3)] UNSPEC_LOADHF_INT))]
5806 "operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
5807 operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
5808 PUT_MODE (operands[2], QFmode);
5809 PUT_MODE (operands[3], QImode);")
5812 [(set (match_operand:HF 0 "reg_operand" "")
5813 (match_operand:HF 1 "const_operand" ""))]
5814 "reload_completed && 0"
5815 [(set (match_dup 0) (float_extend:HF (match_dup 2)))
5816 (set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
5817 (match_dup 3)] UNSPEC_LOADHF_INT))]
5818 "operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
5819 operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
5820 PUT_MODE (operands[2], QFmode);
5821 PUT_MODE (operands[3], QImode);")
5824 [(set (match_operand:HF 0 "memory_operand" "")
5825 (match_operand:HF 1 "reg_operand" ""))]
5827 [(set (match_dup 2) (float_truncate:QF (match_dup 1)))
5828 (set (match_dup 3) (unspec:QI [(match_dup 1)] UNSPEC_STOREHF_INT))]
5829 "operands[2] = c4x_operand_subword (operands[0], 0, 1, HFmode);
5830 operands[3] = c4x_operand_subword (operands[0], 1, 1, HFmode);
5831 PUT_MODE (operands[2], QFmode);
5832 PUT_MODE (operands[3], QImode);")
5834 (define_insn "*loadhf_float"
5835 [(set (match_operand:HF 0 "reg_operand" "=h")
5836 (float_extend:HF (match_operand:QF 1 "src_operand" "fHm")))]
5839 [(set_attr "type" "unary")])
5841 (define_insn "*loadhf_int"
5842 [(set (match_operand:HF 0 "reg_operand" "+h")
5843 (unspec:HF [(subreg:QI (match_dup 0) 0)
5844 (match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LOADHF_INT))]
5847 [(set_attr "type" "unary")])
5849 (define_insn "*storehf_float"
5850 [(set (match_operand:QF 0 "memory_operand" "=m")
5851 (float_truncate:QF (match_operand:HF 1 "reg_operand" "h")))]
5854 [(set_attr "type" "store")])
5856 (define_insn "*storehf_int"
5857 [(set (match_operand:QI 0 "memory_operand" "=m")
5858 (unspec:QI [(match_operand:HF 1 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
5861 [(set_attr "type" "store")])
5863 (define_insn "extendqfhf2"
5864 [(set (match_operand:HF 0 "reg_operand" "=h")
5865 (float_extend:HF (match_operand:QF 1 "reg_operand" "h")))]
5868 [(set_attr "type" "unarycc")])
5870 (define_insn "trunchfqf2"
5871 [(set (match_operand:QF 0 "reg_operand" "=h")
5872 (float_truncate:QF (match_operand:HF 1 "reg_operand" "0")))
5873 (clobber (reg:CC 21))]
5876 [(set_attr "type" "unarycc")])
5881 (define_insn "pushhf"
5882 [(set (mem:HF (pre_inc:QI (reg:QI 20)))
5883 (match_operand:HF 0 "reg_operand" "h"))]
5886 [(set_attr "type" "multi")])
5889 [(set (mem:HF (pre_inc:QI (reg:QI 20)))
5890 (match_operand:HF 0 "reg_operand" ""))]
5892 [(set (mem:QF (pre_inc:QI (reg:QI 20)))
5893 (float_truncate:QF (match_dup 0)))
5894 (set (mem:QI (pre_inc:QI (reg:QI 20)))
5895 (unspec:QI [(match_dup 0)] UNSPEC_STOREHF_INT))]
5898 (define_insn "pushhf_trunc"
5899 [(set (mem:QF (pre_inc:QI (reg:QI 20)))
5900 (float_truncate:QF (match_operand:HF 0 "reg_operand" "h")))]
5903 [(set_attr "type" "push")])
5905 (define_insn "pushhf_int"
5906 [(set (mem:QI (pre_inc:QI (reg:QI 20)))
5907 (unspec:QI [(match_operand:HF 0 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
5910 [(set_attr "type" "push")])
5912 ; we cannot use this because the popf will destroy the low 8 bits
5913 ;(define_insn "pophf"
5914 ; [(set (match_operand:HF 0 "reg_operand" "=h")
5915 ; (mem:HF (post_dec:QI (reg:QI 20))))
5916 ; (clobber (reg:CC 21))]
5919 ; [(set_attr "type" "multi")])
5922 [(set (match_operand:HF 0 "reg_operand" "")
5923 (mem:HF (post_dec:QI (reg:QI 20))))
5924 (clobber (reg:CC 21))]
5926 [(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
5927 (float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
5928 (clobber (reg:CC 21))])
5929 (parallel [(set (match_dup 0)
5930 (unspec:HF [(subreg:QI (match_dup 0) 0)
5931 (mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
5932 (clobber (reg:CC 21))])]
5935 (define_insn "*pophf_int"
5936 [(set (match_operand:HF 0 "reg_operand" "+h")
5937 (unspec:HF [(subreg:QI (match_dup 0) 0)
5938 (mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
5939 (clobber (reg:CC 21))]
5942 [(set_attr "type" "pop")])
5944 (define_insn "*pophf_float"
5945 [(set (match_operand:HF 0 "reg_operand" "=h")
5946 (float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
5947 (clobber (reg:CC 21))]
5950 [(set_attr "type" "pop")])
5955 (define_expand "fixuns_trunchfqi2"
5956 [(parallel [(set (match_dup 2)
5957 (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
5958 (clobber (reg:CC 21))])
5959 (parallel [(set (match_dup 3)
5960 (minus:HF (match_dup 1) (match_dup 5)))
5961 (clobber (reg:CC_NOOV 21))])
5962 (parallel [(set (reg:CC 21)
5963 (compare:CC (fix:QI (match_dup 3))
5966 (fix:QI (match_dup 3)))])
5967 (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
5969 (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
5971 "operands[2] = gen_reg_rtx (QImode);
5972 operands[3] = gen_reg_rtx (HFmode);
5973 operands[4] = gen_reg_rtx (QImode);
5974 operands[5] = gen_reg_rtx (HFmode);
5975 emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
5977 (define_expand "fix_trunchfqi2"
5978 [(parallel [(set (match_dup 2)
5979 (fix:QI (match_operand:HF 1 "reg_or_const_operand" "")))
5980 (clobber (reg:CC 21))])
5981 (parallel [(set (match_dup 3) (neg:HF (match_dup 1)))
5982 (clobber (reg:CC_NOOV 21))])
5983 (parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
5984 (clobber (reg:CC 21))])
5985 (parallel [(set (reg:CC_NOOV 21)
5986 (compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
5987 (set (match_dup 5) (neg:QI (match_dup 4)))])
5989 (if_then_else:QI (le (reg:CC 21) (const_int 0))
5992 (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
5994 "if (TARGET_FAST_FIX)
5996 emit_insn (gen_fixhfqi_clobber (operands[0], operands[1]));
5999 operands[2] = gen_reg_rtx (QImode);
6000 operands[3] = gen_reg_rtx (HFmode);
6001 operands[4] = gen_reg_rtx (QImode);
6002 operands[5] = gen_reg_rtx (QImode);
6005 (define_insn "*fixhfqi_set"
6007 (compare:CC (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH"))
6009 (set (match_operand:QI 0 "ext_reg_operand" "=d")
6010 (fix:QI (match_dup 1)))]
6013 [(set_attr "type" "unarycc")])
6015 (define_insn "fixhfqi_clobber"
6016 [(set (match_operand:QI 0 "reg_operand" "=dc")
6017 (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
6018 (clobber (reg:CC 21))]
6021 [(set_attr "type" "unarycc")])
6023 (define_expand "fix_trunchfhi2"
6024 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6025 (fix:HI (match_operand:HF 1 "reg_operand" "")))
6026 (clobber (reg:CC 21))])]
6028 "c4x_emit_libcall (fix_trunchfhi2_libfunc, FIX, HImode, HFmode, 2, operands);
6031 (define_expand "fixuns_trunchfhi2"
6032 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6033 (unsigned_fix:HI (match_operand:HF 1 "reg_operand" "")))
6034 (clobber (reg:CC 21))])]
6036 "c4x_emit_libcall (fixuns_trunchfhi2_libfunc, UNSIGNED_FIX,
6037 HImode, HFmode, 2, operands);
6043 (define_expand "abshf2"
6044 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6045 (abs:HF (match_operand:HF 1 "reg_or_const_operand" "")))
6046 (clobber (reg:CC_NOOV 21))])]
6050 (define_insn "*abshf2_clobber"
6051 [(set (match_operand:HF 0 "reg_operand" "=h")
6052 (abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
6053 (clobber (reg:CC_NOOV 21))]
6056 [(set_attr "type" "unarycc")])
6058 (define_insn "*abshf2_test"
6059 [(set (reg:CC_NOOV 21)
6060 (compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_operand" "h"))
6061 (match_operand:HF 2 "fp_zero_operand" "G")))
6062 (clobber (match_scratch:HF 0 "=h"))]
6065 [(set_attr "type" "unarycc")])
6067 (define_insn "*abshf2_set"
6068 [(set (reg:CC_NOOV 21)
6069 (compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
6070 (match_operand:HF 2 "fp_zero_operand" "G")))
6071 (set (match_operand:HF 0 "reg_operand" "=h")
6072 (abs:HF (match_dup 1)))]
6076 [(set_attr "type" "unarycc")])
6081 (define_expand "neghf2"
6082 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6083 (neg:HF (match_operand:HF 1 "reg_or_const_operand" "")))
6084 (clobber (reg:CC_NOOV 21))])]
6088 (define_insn "*neghf2_clobber"
6089 [(set (match_operand:HF 0 "reg_operand" "=h")
6090 (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
6091 (clobber (reg:CC_NOOV 21))]
6094 [(set_attr "type" "unarycc")])
6096 (define_insn "*neghf2_test"
6097 [(set (reg:CC_NOOV 21)
6098 (compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
6099 (match_operand:HF 2 "fp_zero_operand" "G")))
6100 (clobber (match_scratch:HF 0 "=h"))]
6103 [(set_attr "type" "unarycc")])
6105 (define_insn "*neghf2_set"
6106 [(set (reg:CC_NOOV 21)
6107 (compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
6108 (match_operand:HF 2 "fp_zero_operand" "G")))
6109 (set (match_operand:HF 0 "reg_operand" "=h")
6110 (neg:HF (match_dup 1)))]
6113 [(set_attr "type" "unarycc")])
6118 (define_insn "*rcpfhf_clobber"
6119 [(set (match_operand:HF 0 "reg_operand" "=h")
6120 (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RCPF))
6121 (clobber (reg:CC_NOOV 21))]
6124 [(set_attr "type" "unarycc")])
6129 (define_insn "*rsqrfhf_clobber"
6130 [(set (match_operand:HF 0 "reg_operand" "=h")
6131 (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RSQRF))
6132 (clobber (reg:CC_NOOV 21))]
6135 [(set_attr "type" "unarycc")])
6140 (define_insn "*rndhf_clobber"
6141 [(set (match_operand:HF 0 "reg_operand" "=h")
6142 (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RND))
6143 (clobber (reg:CC_NOOV 21))]
6146 [(set_attr "type" "unarycc")])
6149 ; Inlined float square root for C4x
6150 (define_expand "sqrthf2_inline"
6151 [(parallel [(set (match_dup 2)
6152 (unspec:HF [(match_operand:HF 1 "reg_operand" "")] UNSPEC_RSQRF))
6153 (clobber (reg:CC_NOOV 21))])
6154 (parallel [(set (match_dup 3) (mult:HF (match_dup 5) (match_dup 1)))
6155 (clobber (reg:CC_NOOV 21))])
6156 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
6157 (clobber (reg:CC_NOOV 21))])
6158 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
6159 (clobber (reg:CC_NOOV 21))])
6160 (parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
6161 (clobber (reg:CC_NOOV 21))])
6162 (parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
6163 (clobber (reg:CC_NOOV 21))])
6164 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
6165 (clobber (reg:CC_NOOV 21))])
6166 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
6167 (clobber (reg:CC_NOOV 21))])
6168 (parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
6169 (clobber (reg:CC_NOOV 21))])
6170 (parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
6171 (clobber (reg:CC_NOOV 21))])
6172 (parallel [(set (match_operand:HF 0 "reg_operand" "")
6173 (mult:HF (match_dup 2) (match_dup 1)))
6174 (clobber (reg:CC_NOOV 21))])]
6177 operands[2] = gen_reg_rtx (HFmode);
6178 operands[3] = gen_reg_rtx (HFmode);
6179 operands[4] = gen_reg_rtx (HFmode);
6180 operands[5] = CONST_DOUBLE_ATOF (\"0.5\", HFmode);
6181 operands[6] = CONST_DOUBLE_ATOF (\"1.5\", HFmode);
6185 (define_expand "sqrthf2"
6186 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6187 (sqrt:HF (match_operand:HF 1 "reg_operand" "")))
6188 (clobber (reg:CC 21))])]
6189 "! TARGET_C3X && TARGET_INLINE"
6190 "emit_insn (gen_sqrthf2_inline (operands[0], operands[1]));
6194 ; THREE OPERAND LONG DOUBLE INSTRUCTIONS
6200 (define_insn "addhf3"
6201 [(set (match_operand:HF 0 "reg_operand" "=h,?h")
6202 (plus:HF (match_operand:HF 1 "reg_operand" "%0,h")
6203 (match_operand:HF 2 "reg_or_const_operand" "H,h")))
6204 (clobber (reg:CC_NOOV 21))]
6209 [(set_attr "type" "binarycc,binarycc")])
6214 (define_insn "subhf3"
6215 [(set (match_operand:HF 0 "reg_operand" "=h,h,?h")
6216 (minus:HF (match_operand:HF 1 "reg_or_const_operand" "0,H,h")
6217 (match_operand:HF 2 "reg_or_const_operand" "H,0,h")))
6218 (clobber (reg:CC_NOOV 21))]
6224 [(set_attr "type" "binarycc,binarycc,binarycc")])
6229 ; The C3x MPYF only uses 24-bit precision while the C4x uses 32-bit precision.
6231 (define_expand "mulhf3"
6232 [(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
6233 (mult:HF (match_operand:HF 1 "reg_operand" "h")
6234 (match_operand:HF 2 "reg_operand" "h")))
6235 (clobber (reg:CC_NOOV 21))])]
6239 (define_insn "*mulhf3_c40"
6240 [(set (match_operand:HF 0 "reg_operand" "=h,?h")
6241 (mult:HF (match_operand:HF 1 "reg_operand" "%0,h")
6242 (match_operand:HF 2 "reg_or_const_operand" "hH,h")))
6243 (clobber (reg:CC_NOOV 21))]
6248 [(set_attr "type" "binarycc,binarycc")])
6253 (define_expand "cmphf"
6255 (compare:CC (match_operand:HF 0 "reg_operand" "")
6256 (match_operand:HF 1 "reg_or_const_operand" "")))]
6258 "c4x_compare_op0 = operands[0];
6259 c4x_compare_op1 = operands[1];
6262 (define_insn "*cmphf"
6264 (compare:CC (match_operand:HF 0 "reg_operand" "h")
6265 (match_operand:HF 1 "reg_or_const_operand" "hH")))]
6268 [(set_attr "type" "compare")])
6270 (define_insn "*cmphf_noov"
6271 [(set (reg:CC_NOOV 21)
6272 (compare:CC_NOOV (match_operand:HF 0 "reg_operand" "h")
6273 (match_operand:HF 1 "reg_or_const_operand" "hH")))]
6276 [(set_attr "type" "compare")])
6278 ; Inlined float divide for C4x
6279 (define_expand "divhf3_inline"
6280 [(parallel [(set (match_dup 3)
6281 (unspec:HF [(match_operand:HF 2 "reg_operand" "")] UNSPEC_RCPF))
6282 (clobber (reg:CC_NOOV 21))])
6283 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
6284 (clobber (reg:CC_NOOV 21))])
6285 (parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
6286 (clobber (reg:CC_NOOV 21))])
6287 (parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
6288 (clobber (reg:CC_NOOV 21))])
6289 (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
6290 (clobber (reg:CC_NOOV 21))])
6291 (parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
6292 (clobber (reg:CC_NOOV 21))])
6293 (parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
6294 (clobber (reg:CC_NOOV 21))])
6295 (parallel [(set (match_operand:HF 0 "reg_operand" "")
6296 (mult:HF (match_operand:HF 1 "reg_operand" "")
6298 (clobber (reg:CC_NOOV 21))])]
6301 operands[3] = gen_reg_rtx (HFmode);
6302 operands[4] = gen_reg_rtx (HFmode);
6303 operands[5] = CONST2_RTX (HFmode);
6306 (define_expand "divhf3"
6307 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6308 (div:HF (match_operand:HF 1 "reg_operand" "")
6309 (match_operand:HF 2 "reg_operand" "")))
6310 (clobber (reg:CC 21))])]
6311 "! TARGET_C3X && TARGET_INLINE"
6312 "emit_insn (gen_divhf3_inline (operands[0], operands[1], operands[2]));
6317 ; TWO OPERAND LONG LONG INSTRUCTIONS
6320 (define_insn "*movhi_stik"
6321 [(set (match_operand:HI 0 "memory_operand" "=m")
6322 (match_operand:HI 1 "stik_const_operand" "K"))]
6325 [(set_attr "type" "multi")])
6327 ; We could load some constants using define_splits for the C30
6328 ; in the large memory model---these would emit shift and or insns.
6329 (define_expand "movhi"
6330 [(set (match_operand:HI 0 "src_operand" "")
6331 (match_operand:HI 1 "src_operand" ""))]
6333 "if (c4x_emit_move_sequence (operands, HImode))
6336 ; The constraints for movhi must include 'r' if we don't
6337 ; restrict HImode regnos to start on an even number, since
6338 ; we can get RC, R8 allocated as a pair. We want more
6339 ; votes for FP_REGS so we use dr as the constraints.
6340 (define_insn "*movhi_noclobber"
6341 [(set (match_operand:HI 0 "dst_operand" "=dr,m")
6342 (match_operand:HI 1 "src_operand" "drIm,r"))]
6343 "reg_operand (operands[0], HImode)
6344 || reg_operand (operands[1], HImode)"
6346 [(set_attr "type" "multi,multi")])
6348 ; This will fail miserably if the destination register is used in the
6349 ; source memory address.
6350 ; The usual strategy in this case is to swap the order of insns we emit,
6351 ; however, this will fail if we have an autoincrement memory address.
6356 ; We could convert this to
6360 ; However, things are likely to be very screwed up if we get this.
6363 [(set (match_operand:HI 0 "dst_operand" "")
6364 (match_operand:HI 1 "src_operand" ""))]
6366 && (reg_operand (operands[0], HImode)
6367 || reg_operand (operands[1], HImode)
6368 || stik_const_operand (operands[1], HImode))"
6369 [(set (match_dup 2) (match_dup 4))
6370 (set (match_dup 3) (match_dup 5))]
6371 "operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
6372 operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
6373 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6374 operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
6375 if (reg_overlap_mentioned_p (operands[2], operands[5]))
6377 /* Swap order of move insns. */
6380 operands[2] =operands[3];
6383 operands[4] =operands[5];
6388 (define_insn "extendqihi2"
6389 [(set (match_operand:HI 0 "reg_operand" "=dc")
6390 (sign_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
6391 (clobber (reg:CC 21))]
6394 [(set_attr "type" "multi")])
6397 [(set (match_operand:HI 0 "reg_operand" "")
6398 (sign_extend:HI (match_operand:QI 1 "src_operand" "")))
6399 (clobber (reg:CC 21))]
6400 "reload_completed && TARGET_C3X"
6401 [(set (match_dup 2) (match_dup 1))
6402 (set (match_dup 3) (match_dup 2))
6403 (parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 3) (const_int 31)))
6404 (clobber (reg:CC 21))])]
6405 "operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
6406 operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
6409 [(set (match_operand:HI 0 "reg_operand" "")
6410 (sign_extend:HI (match_operand:QI 1 "src_operand" "")))
6411 (clobber (reg:CC 21))]
6412 "reload_completed && ! TARGET_C3X"
6413 [(set (match_dup 2) (match_dup 1))
6414 (parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 2) (const_int 31)))
6415 (clobber (reg:CC 21))])]
6416 "operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
6417 operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
6419 (define_insn "zero_extendqihi2"
6420 [(set (match_operand:HI 0 "reg_operand" "=?dc")
6421 (zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "rm")))
6422 (clobber (reg:CC 21))]
6425 [(set_attr "type" "multi")])
6427 ; If operand0 and operand1 are the same register we don't need
6430 [(set (match_operand:HI 0 "reg_operand" "")
6431 (zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "")))
6432 (clobber (reg:CC 21))]
6434 [(set (match_dup 2) (match_dup 1))
6435 (set (match_dup 3) (const_int 0))]
6436 "operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
6437 operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
6442 (define_insn "*pushhi"
6443 [(set (mem:HI (pre_inc:QI (reg:QI 20)))
6444 (match_operand:HI 0 "reg_operand" "r"))]
6447 [(set_attr "type" "multi")])
6450 [(set (mem:HI (pre_inc:QI (reg:QI 20)))
6451 (match_operand:HI 0 "reg_operand" ""))]
6453 [(set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 2))
6454 (set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 3))]
6455 "operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
6456 operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
6458 (define_insn "*pophi"
6459 [(set (match_operand:HI 0 "reg_operand" "=r")
6460 (mem:HI (post_dec:QI (reg:QI 20))))
6461 (clobber (reg:CC 21))]
6464 [(set_attr "type" "multi")])
6467 [(set (match_operand:HI 0 "reg_operand" "")
6468 (mem:HI (pre_inc:QI (reg:QI 20))))]
6470 [(set (match_dup 2) (mem:QI (pre_inc:QI (reg:QI 20))))
6471 (set (match_dup 3) (mem:QI (pre_inc:QI (reg:QI 20))))]
6472 "operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
6473 operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
6478 (define_insn "neghi2"
6479 [(set (match_operand:HI 0 "ext_reg_operand" "=d")
6480 (neg:HI (match_operand:HI 1 "src_operand" "rm")))
6481 (clobber (reg:CC_NOOV 21))]
6484 [(set_attr "type" "multi")])
6487 [(set (match_operand:HI 0 "ext_reg_operand" "")
6488 (neg:HI (match_operand:HI 1 "src_operand" "")))
6489 (clobber (reg:CC_NOOV 21))]
6491 [(parallel [(set (reg:CC_NOOV 21)
6492 (compare:CC_NOOV (neg:QI (match_dup 3))
6494 (set (match_dup 2) (neg:QI (match_dup 3)))])
6495 (parallel [(set (match_dup 4) (neg:QI (match_dup 5)))
6496 (use (reg:CC_NOOV 21))
6497 (clobber (reg:CC_NOOV 21))])]
6498 "operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
6499 operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
6500 operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
6501 operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
6503 (define_insn "one_cmplhi2"
6504 [(set (match_operand:HI 0 "reg_operand" "=r")
6505 (not:HI (match_operand:HI 1 "src_operand" "rm")))
6506 (clobber (reg:CC 21))]
6509 [(set_attr "type" "multi")])
6512 [(set (match_operand:HI 0 "reg_operand" "")
6513 (not:HI (match_operand:HI 1 "src_operand" "")))
6514 (clobber (reg:CC 21))]
6516 [(parallel [(set (match_dup 2) (not:QI (match_dup 3)))
6517 (clobber (reg:CC 21))])
6518 (parallel [(set (match_dup 4) (not:QI (match_dup 5)))
6519 (clobber (reg:CC 21))])]
6520 "operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
6521 operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
6522 operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
6523 operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
6525 (define_expand "floathiqf2"
6526 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
6527 (float:QF (match_operand:HI 1 "src_operand" "")))
6528 (clobber (reg:CC 21))])]
6530 "c4x_emit_libcall (floathiqf2_libfunc, FLOAT, QFmode, HImode, 2, operands);
6533 (define_expand "floatunshiqf2"
6534 [(parallel [(set (match_operand:QF 0 "reg_operand" "")
6535 (unsigned_float:QF (match_operand:HI 1 "src_operand" "")))
6536 (clobber (reg:CC 21))])]
6538 "c4x_emit_libcall (floatunshiqf2_libfunc, UNSIGNED_FLOAT,
6539 QFmode, HImode, 2, operands);
6542 (define_expand "floathihf2"
6543 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6544 (float:HF (match_operand:HI 1 "src_operand" "")))
6545 (clobber (reg:CC 21))])]
6547 "c4x_emit_libcall (floathihf2_libfunc, FLOAT, HFmode, HImode, 2, operands);
6550 (define_expand "floatunshihf2"
6551 [(parallel [(set (match_operand:HF 0 "reg_operand" "")
6552 (unsigned_float:HF (match_operand:HI 1 "src_operand" "")))
6553 (clobber (reg:CC 21))])]
6555 "c4x_emit_libcall (floatunshihf2_libfunc, UNSIGNED_FLOAT,
6556 HFmode, HImode, 2, operands);
6561 ; THREE OPERAND LONG LONG INSTRUCTIONS
6564 (define_expand "addhi3"
6565 [(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
6566 (plus:HI (match_operand:HI 1 "src_operand" "")
6567 (match_operand:HI 2 "src_operand" "")))
6568 (clobber (reg:CC_NOOV 21))])]
6570 "legitimize_operands (PLUS, operands, HImode);")
6572 (define_insn "*addhi3_clobber"
6573 [(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
6574 (plus:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
6575 (match_operand:HI 2 "src_operand" "rm,R,rS<>")))
6576 (clobber (reg:CC_NOOV 21))]
6577 "valid_operands (PLUS, operands, HImode)"
6579 [(set_attr "type" "multi,multi,multi")])
6582 [(set (match_operand:HI 0 "ext_reg_operand" "")
6583 (plus:HI (match_operand:HI 1 "src_operand" "")
6584 (match_operand:HI 2 "src_operand" "")))
6585 (clobber (reg:CC_NOOV 21))]
6587 [(parallel [(set (reg:CC_NOOV 21)
6588 (compare:CC_NOOV (plus:QI (match_dup 4) (match_dup 5))
6590 (set (match_dup 3) (plus:QI (match_dup 4) (match_dup 5)))])
6591 (parallel [(set (match_dup 6) (plus:QI (match_dup 7) (match_dup 8)))
6592 (use (reg:CC_NOOV 21))
6593 (clobber (reg:CC_NOOV 21))])]
6594 "operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
6595 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6596 operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
6597 operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
6598 operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
6599 operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
6601 (define_expand "subhi3"
6602 [(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
6603 (minus:HI (match_operand:HI 1 "src_operand" "")
6604 (match_operand:HI 2 "src_operand" "")))
6605 (clobber (reg:CC_NOOV 21))])]
6607 "legitimize_operands (MINUS, operands, HImode);")
6610 (define_insn "*subhi3_clobber"
6611 [(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
6612 (minus:HI (match_operand:HI 1 "src_operand" "0,rR,rS<>")
6613 (match_operand:HI 2 "src_operand" "rm,R,rS<>")))
6614 (clobber (reg:CC_NOOV 21))]
6615 "valid_operands (MINUS, operands, HImode)"
6617 [(set_attr "type" "multi,multi,multi")])
6620 [(set (match_operand:HI 0 "ext_reg_operand" "")
6621 (minus:HI (match_operand:HI 1 "src_operand" "")
6622 (match_operand:HI 2 "src_operand" "")))
6623 (clobber (reg:CC_NOOV 21))]
6625 [(parallel [(set (reg:CC_NOOV 21)
6626 (compare:CC_NOOV (minus:QI (match_dup 4) (match_dup 5))
6628 (set (match_dup 3) (minus:QI (match_dup 4) (match_dup 5)))])
6629 (parallel [(set (match_dup 6) (minus:QI (match_dup 7) (match_dup 8)))
6630 (use (reg:CC_NOOV 21))
6631 (clobber (reg:CC_NOOV 21))])]
6632 "operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
6633 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6634 operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
6635 operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
6636 operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
6637 operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
6639 (define_expand "iorhi3"
6640 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6641 (ior:HI (match_operand:HI 1 "src_operand" "")
6642 (match_operand:HI 2 "src_operand" "")))
6643 (clobber (reg:CC 21))])]
6645 "legitimize_operands (IOR, operands, HImode);")
6647 (define_insn "*iorhi3_clobber"
6648 [(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
6649 (ior:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
6650 (match_operand:HI 2 "src_operand" "rm,R,rS<>")))
6651 (clobber (reg:CC 21))]
6652 "valid_operands (IOR, operands, HImode)"
6654 [(set_attr "type" "multi,multi,multi")])
6657 [(set (match_operand:HI 0 "reg_operand" "")
6658 (ior:HI (match_operand:HI 1 "src_operand" "")
6659 (match_operand:HI 2 "src_operand" "")))
6660 (clobber (reg:CC 21))]
6662 [(parallel [(set (match_dup 3) (ior:QI (match_dup 4) (match_dup 5)))
6663 (clobber (reg:CC 21))])
6664 (parallel [(set (match_dup 6) (ior:QI (match_dup 7) (match_dup 8)))
6665 (clobber (reg:CC 21))])]
6666 "operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
6667 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6668 operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
6669 operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
6670 operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
6671 operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
6673 (define_expand "andhi3"
6674 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6675 (and:HI (match_operand:HI 1 "src_operand" "")
6676 (match_operand:HI 2 "src_operand" "")))
6677 (clobber (reg:CC 21))])]
6679 "legitimize_operands (AND, operands, HImode);")
6681 (define_insn "*andhi3_clobber"
6682 [(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
6683 (and:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
6684 (match_operand:HI 2 "src_operand" "rm,R,rS<>")))
6685 (clobber (reg:CC 21))]
6686 "valid_operands (AND, operands, HImode)"
6688 [(set_attr "type" "multi,multi,multi")])
6691 [(set (match_operand:HI 0 "reg_operand" "")
6692 (and:HI (match_operand:HI 1 "src_operand" "")
6693 (match_operand:HI 2 "src_operand" "")))
6694 (clobber (reg:CC 21))]
6696 [(parallel [(set (match_dup 3) (and:QI (match_dup 4) (match_dup 5)))
6697 (clobber (reg:CC 21))])
6698 (parallel [(set (match_dup 6) (and:QI (match_dup 7) (match_dup 8)))
6699 (clobber (reg:CC 21))])]
6700 "operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
6701 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6702 operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
6703 operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
6704 operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
6705 operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
6707 (define_expand "xorhi3"
6708 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6709 (xor:HI (match_operand:HI 1 "src_operand" "")
6710 (match_operand:HI 2 "src_operand" "")))
6711 (clobber (reg:CC 21))])]
6713 "legitimize_operands (XOR, operands, HImode);")
6716 (define_insn "*xorhi3_clobber"
6717 [(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
6718 (xor:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
6719 (match_operand:HI 2 "src_operand" "rm,R,rS<>")))
6720 (clobber (reg:CC 21))]
6721 "valid_operands (XOR, operands, HImode)"
6723 [(set_attr "type" "multi,multi,multi")])
6726 [(set (match_operand:HI 0 "reg_operand" "")
6727 (xor:HI (match_operand:HI 1 "src_operand" "")
6728 (match_operand:HI 2 "src_operand" "")))
6729 (clobber (reg:CC 21))]
6731 [(parallel [(set (match_dup 3) (xor:QI (match_dup 4) (match_dup 5)))
6732 (clobber (reg:CC 21))])
6733 (parallel [(set (match_dup 6) (xor:QI (match_dup 7) (match_dup 8)))
6734 (clobber (reg:CC 21))])]
6735 "operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
6736 operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
6737 operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
6738 operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
6739 operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
6740 operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
6742 (define_expand "ashlhi3"
6743 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6744 (ashift:HI (match_operand:HI 1 "src_operand" "")
6745 (match_operand:QI 2 "src_operand" "")))
6746 (clobber (reg:CC 21))])]
6748 "if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
6750 rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
6751 rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
6752 rtx op1lo = operand_subword (operands[1], 0, 0, HImode);
6753 rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
6756 emit_insn (gen_ashlqi3 (op0hi, op1lo, count));
6758 emit_insn (gen_movqi (op0hi, op1lo));
6759 emit_insn (gen_movqi (op0lo, const0_rtx));
6762 if (! REG_P (operands[1]))
6763 operands[1] = force_reg (HImode, operands[1]);
6764 emit_insn (gen_ashlhi3_reg (operands[0], operands[1], operands[2]));
6768 ; %0.lo = %1.lo << %2
6769 ; %0.hi = (%1.hi << %2 ) | (%1.lo >> (32 - %2))
6770 ; This algorithm should work for shift counts greater than 32
6771 (define_expand "ashlhi3_reg"
6772 [(use (match_operand:HI 1 "reg_operand" ""))
6773 (use (match_operand:HI 0 "reg_operand" ""))
6774 /* If the shift count is greater than 32 this will give zero. */
6775 (parallel [(set (match_dup 7)
6776 (ashift:QI (match_dup 3)
6777 (match_operand:QI 2 "reg_operand" "")))
6778 (clobber (reg:CC 21))])
6779 /* If the shift count is greater than 32 this will give zero. */
6780 (parallel [(set (match_dup 8)
6781 (ashift:QI (match_dup 4) (match_dup 2)))
6782 (clobber (reg:CC 21))])
6783 (parallel [(set (match_dup 10)
6784 (plus:QI (match_dup 2) (const_int -32)))
6785 (clobber (reg:CC_NOOV 21))])
6786 /* If the shift count is greater than 32 this will do a left shift. */
6787 (parallel [(set (match_dup 9)
6788 (lshiftrt:QI (match_dup 3) (neg:QI (match_dup 10))))
6789 (clobber (reg:CC 21))])
6790 (set (match_dup 5) (match_dup 7))
6791 (parallel [(set (match_dup 6)
6792 (ior:QI (match_dup 8) (match_dup 9)))
6793 (clobber (reg:CC 21))])]
6796 operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
6797 operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
6798 operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
6799 operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
6800 operands[7] = gen_reg_rtx (QImode); /* lo << count */
6801 operands[8] = gen_reg_rtx (QImode); /* hi << count */
6802 operands[9] = gen_reg_rtx (QImode); /* lo >> (32 - count) */
6803 operands[10] = gen_reg_rtx (QImode); /* 32 - count */
6806 ; This should do all the dirty work with define_split
6807 (define_expand "lshrhi3"
6808 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6809 (lshiftrt:HI (match_operand:HI 1 "src_operand" "")
6810 (match_operand:QI 2 "src_operand" "")))
6811 (clobber (reg:CC 21))])]
6813 "if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
6815 rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
6816 rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
6817 rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
6818 rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
6821 emit_insn (gen_lshrqi3 (op0lo, op1hi, count));
6823 emit_insn (gen_movqi (op0lo, op1hi));
6824 emit_insn (gen_movqi (op0hi, const0_rtx));
6827 if (! REG_P (operands[1]))
6828 operands[1] = force_reg (HImode, operands[1]);
6829 emit_insn (gen_lshrhi3_reg (operands[0], operands[1], operands[2]));
6832 ; %0.hi = %1.hi >> %2
6833 ; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
6834 ; This algorithm should work for shift counts greater than 32
6835 (define_expand "lshrhi3_reg"
6836 [(use (match_operand:HI 1 "reg_operand" ""))
6837 (use (match_operand:HI 0 "reg_operand" ""))
6838 (parallel [(set (match_dup 11)
6839 (neg:QI (match_operand:QI 2 "reg_operand" "")))
6840 (clobber (reg:CC_NOOV 21))])
6841 /* If the shift count is greater than 32 this will give zero. */
6842 (parallel [(set (match_dup 7)
6843 (lshiftrt:QI (match_dup 3)
6844 (neg:QI (match_dup 11))))
6845 (clobber (reg:CC 21))])
6846 /* If the shift count is greater than 32 this will give zero. */
6847 (parallel [(set (match_dup 8)
6848 (lshiftrt:QI (match_dup 4)
6849 (neg:QI (match_dup 11))))
6850 (clobber (reg:CC 21))])
6851 (parallel [(set (match_dup 10)
6852 (plus:QI (match_dup 11) (const_int 32)))
6853 (clobber (reg:CC_NOOV 21))])
6854 /* If the shift count is greater than 32 this will do an arithmetic
6855 right shift. However, we need a logical right shift. */
6856 (parallel [(set (match_dup 9)
6857 (ashift:QI (match_dup 4) (unspec:QI [(match_dup 10)] UNSPEC_LSH)))
6858 (clobber (reg:CC 21))])
6859 (set (match_dup 6) (match_dup 8))
6860 (parallel [(set (match_dup 5)
6861 (ior:QI (match_dup 7) (match_dup 9)))
6862 (clobber (reg:CC 21))])]
6865 operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
6866 operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
6867 operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
6868 operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
6869 operands[7] = gen_reg_rtx (QImode); /* lo >> count */
6870 operands[8] = gen_reg_rtx (QImode); /* hi >> count */
6871 operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
6872 operands[10] = gen_reg_rtx (QImode); /* 32 - count */
6873 operands[11] = gen_reg_rtx (QImode); /* -count */
6876 ; This should do all the dirty work with define_split
6877 (define_expand "ashrhi3"
6878 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
6879 (ashiftrt:HI (match_operand:HI 1 "src_operand" "")
6880 (match_operand:QI 2 "src_operand" "")))
6881 (clobber (reg:CC 21))])]
6883 "if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
6885 rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
6886 rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
6887 rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
6888 rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
6891 emit_insn (gen_ashrqi3 (op0lo, op1hi, count));
6893 emit_insn (gen_movqi (op0lo, op1hi));
6894 emit_insn (gen_ashrqi3 (op0hi, op1hi, GEN_INT (31)));
6897 if (! REG_P (operands[1]))
6898 operands[1] = force_reg (HImode, operands[1]);
6899 emit_insn (gen_ashrhi3_reg (operands[0], operands[1], operands[2]));
6902 ; %0.hi = %1.hi >> %2
6903 ; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
6904 ; This algorithm should work for shift counts greater than 32
6905 (define_expand "ashrhi3_reg"
6906 [(use (match_operand:HI 1 "reg_operand" ""))
6907 (use (match_operand:HI 0 "reg_operand" ""))
6908 (parallel [(set (match_dup 11)
6909 (neg:QI (match_operand:QI 2 "reg_operand" "")))
6910 (clobber (reg:CC_NOOV 21))])
6911 /* If the shift count is greater than 32 this will give zero. */
6912 (parallel [(set (match_dup 7)
6913 (lshiftrt:QI (match_dup 3)
6914 (neg:QI (match_dup 11))))
6915 (clobber (reg:CC 21))])
6916 /* If the shift count is greater than 32 this will give zero. */
6917 (parallel [(set (match_dup 8)
6918 (ashiftrt:QI (match_dup 4)
6919 (neg:QI (match_dup 11))))
6920 (clobber (reg:CC 21))])
6921 (parallel [(set (match_dup 10)
6922 (plus:QI (match_dup 11) (const_int 32)))
6923 (clobber (reg:CC_NOOV 21))])
6924 /* If the shift count is greater than 32 this will do an arithmetic
6926 (parallel [(set (match_dup 9)
6927 (ashift:QI (match_dup 4) (match_dup 10)))
6928 (clobber (reg:CC 21))])
6929 (set (match_dup 6) (match_dup 8))
6930 (parallel [(set (match_dup 5)
6931 (ior:QI (match_dup 7) (match_dup 9)))
6932 (clobber (reg:CC 21))])]
6935 operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
6936 operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
6937 operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
6938 operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
6939 operands[7] = gen_reg_rtx (QImode); /* lo >> count */
6940 operands[8] = gen_reg_rtx (QImode); /* hi >> count */
6941 operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
6942 operands[10] = gen_reg_rtx (QImode); /* 32 - count */
6943 operands[11] = gen_reg_rtx (QImode); /* -count */
6946 (define_expand "cmphi"
6948 (compare:CC (match_operand:HI 0 "src_operand" "")
6949 (match_operand:HI 1 "src_operand" "")))]
6951 "legitimize_operands (COMPARE, operands, HImode);
6952 c4x_compare_op0 = operands[0];
6953 c4x_compare_op1 = operands[1];
6956 (define_insn "*cmphi_cc"
6958 (compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
6959 (match_operand:HI 1 "src_operand" "R,rS<>")))]
6960 "valid_operands (COMPARE, operands, HImode)"
6962 [(set_attr "type" "multi")])
6964 (define_insn "*cmphi_cc_noov"
6965 [(set (reg:CC_NOOV 21)
6966 (compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
6967 (match_operand:HI 1 "src_operand" "R,rS<>")))]
6968 "valid_operands (COMPARE, operands, HImode)"
6970 [(set_attr "type" "multi")])
6972 ; This works only before reload because we need 2 extra registers.
6973 ; Use unspec to avoid recursive split.
6976 (compare:CC (match_operand:HI 0 "src_operand" "")
6977 (match_operand:HI 1 "src_operand" "")))]
6978 "! reload_completed"
6979 [(parallel [(set (reg:CC 21)
6980 (unspec:CC [(compare:CC (match_dup 0)
6981 (match_dup 1))] UNSPEC_CMPHI))
6982 (clobber (match_scratch:QI 2 ""))
6983 (clobber (match_scratch:QI 3 ""))])]
6987 [(set (reg:CC_NOOV 21)
6988 (compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
6989 (match_operand:HI 1 "src_operand" "")))]
6990 "! reload_completed"
6991 [(parallel [(set (reg:CC_NOOV 21)
6992 (unspec:CC_NOOV [(compare:CC_NOOV (match_dup 0)
6993 (match_dup 1))] UNSPEC_CMPHI))
6994 (clobber (match_scratch:QI 2 ""))
6995 (clobber (match_scratch:QI 3 ""))])]
6998 ; This is normally not used. The define splits above are used first.
7001 (compare:CC (match_operand:HI 0 "src_operand" "")
7002 (match_operand:HI 1 "src_operand" "")))]
7004 [(parallel [(set (reg:CC 21)
7005 (compare:CC (match_dup 0) (match_dup 1)))
7006 (use (reg:QI 20))])]
7010 [(set (reg:CC_NOOV 21)
7011 (compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
7012 (match_operand:HI 1 "src_operand" "")))]
7014 [(parallel [(set (reg:CC_NOOV 21)
7015 (compare:CC_NOOV (match_dup 0) (match_dup 1)))
7016 (use (reg:QI 20))])]
7019 (define_insn "*cmphi"
7021 (compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
7022 (match_operand:HI 1 "src_operand" "R,rS<>")))
7024 "valid_operands (COMPARE, operands, HImode)"
7027 int use_ir1 = (reg_operand (operands[0], HImode)
7028 && REG_P (operands[0])
7029 && REGNO (operands[0]) == IR1_REGNO)
7030 || (reg_operand (operands[1], HImode)
7031 && REG_P (operands[1])
7032 && REGNO (operands[1]) == IR1_REGNO);
7035 output_asm_insn (\"push\\tir1\", operands);
7037 output_asm_insn (\"push\\tbk\", operands);
7038 output_asm_insn (\"push\\tr0\", operands);
7039 output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
7042 output_asm_insn (\"ldiu\\tst,ir1\", operands);
7043 output_asm_insn (\"or\\t07bh,ir1\", operands);
7047 output_asm_insn (\"ldiu\\tst,bk\", operands);
7048 output_asm_insn (\"or\\t07bh,bk\", operands);
7050 output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
7052 output_asm_insn (\"and3\\tir1,st,ir1\", operands);
7054 output_asm_insn (\"and3\\tbk,st,bk\", operands);
7055 output_asm_insn (\"pop\\tr0\", operands);
7058 output_asm_insn (\"ldiu\\tir1,st\", operands);
7059 output_asm_insn (\"pop\\tir1\", operands);
7063 output_asm_insn (\"ldiu\\tbk,st\", operands);
7064 output_asm_insn (\"pop\\tbk\", operands);
7068 [(set_attr "type" "multi")])
7070 (define_insn "*cmphi_noov"
7071 [(set (reg:CC_NOOV 21)
7072 (compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
7073 (match_operand:HI 1 "src_operand" "R,rS<>")))
7075 "valid_operands (COMPARE, operands, HImode)"
7078 int use_ir1 = (reg_operand (operands[0], HImode)
7079 && REG_P (operands[0])
7080 && REGNO (operands[0]) == IR1_REGNO)
7081 || (reg_operand (operands[1], HImode)
7082 && REG_P (operands[1])
7083 && REGNO (operands[1]) == IR1_REGNO);
7086 output_asm_insn (\"push\\tir1\", operands);
7088 output_asm_insn (\"push\\tbk\", operands);
7089 output_asm_insn (\"push\\tr0\", operands);
7090 output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
7093 output_asm_insn (\"ldiu\\tst,ir1\", operands);
7094 output_asm_insn (\"or\\t07bh,ir1\", operands);
7098 output_asm_insn (\"ldiu\\tst,bk\", operands);
7099 output_asm_insn (\"or\\t07bh,bk\", operands);
7101 output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
7103 output_asm_insn (\"and3\\tir1,st,ir1\", operands);
7105 output_asm_insn (\"and3\\tbk,st,bk\", operands);
7106 output_asm_insn (\"pop\\tr0\", operands);
7109 output_asm_insn (\"ldiu\\tir1,st\", operands);
7110 output_asm_insn (\"pop\\tir1\", operands);
7114 output_asm_insn (\"ldiu\\tbk,st\", operands);
7115 output_asm_insn (\"pop\\tbk\", operands);
7119 [(set_attr "type" "multi")])
7122 (define_insn "cmphi_cc"
7124 (unspec:CC [(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
7125 (match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
7126 (clobber (match_scratch:QI 2 "=&d,&d"))
7127 (clobber (match_scratch:QI 3 "=&c,&c"))]
7128 "valid_operands (COMPARE, operands, HImode)"
7130 output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
7131 output_asm_insn (\"ldiu\\tst,%3\", operands);
7132 output_asm_insn (\"or\\t07bh,%3\", operands);
7133 output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
7134 output_asm_insn (\"and\\t%3,st\", operands);
7136 [(set_attr "type" "multi")])
7138 (define_insn "cmphi_cc_noov"
7139 [(set (reg:CC_NOOV 21)
7140 (unspec:CC_NOOV [(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
7141 (match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
7142 (clobber (match_scratch:QI 2 "=&d,&d"))
7143 (clobber (match_scratch:QI 3 "=&c,&c"))]
7144 "valid_operands (COMPARE, operands, HImode)"
7146 output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
7147 output_asm_insn (\"ldiu\\tst,%3\", operands);
7148 output_asm_insn (\"or\\t07bh,%3\", operands);
7149 output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
7150 output_asm_insn (\"and\\t%3,st\", operands);
7152 [(set_attr "type" "multi")])
7154 (define_expand "mulhi3"
7155 [(parallel [(set (match_operand:HI 0 "reg_operand" "")
7156 (mult:HI (match_operand:HI 1 "src_operand" "")
7157 (match_operand:HI 2 "src_operand" "")))
7158 (clobber (reg:CC 21))])]
7160 "c4x_emit_libcall3 (smul_optab->handlers[(int) HImode].libfunc,
7161 MULT, HImode, operands);
7174 ; bCC label ; abnormal loop termination
7175 ; dbu aN, loop ; normal loop termination
7183 ; Which moves the bCC condition outside the inner loop for free.
7186 [(set (pc) (if_then_else (match_operator 3 "comparison_operator"
7187 [(reg:CC 21) (const_int 0)])
7188 (label_ref (match_operand 2 "" ""))
7193 (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
7196 (label_ref (match_operand 1 "" ""))
7199 (plus:QI (match_dup 0)
7202 (clobber (reg:CC_NOOV 21))])]
7203 "! c4x_label_conflict (insn, operands[2], operands[1])"
7204 "db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
7205 [(set_attr "type" "multi")])
7208 [(set (pc) (if_then_else (match_operator 3 "comparison_operator"
7209 [(reg:CC 21) (const_int 0)])
7210 (label_ref (match_operand 2 "" ""))
7215 (ne (match_operand:QI 0 "addr_reg_operand" "+a")
7217 (label_ref (match_operand 1 "" ""))
7220 (plus:QI (match_dup 0)
7222 "! c4x_label_conflict (insn, operands[2], operands[1])"
7223 "db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
7224 [(set_attr "type" "multi")])
7227 ; Peepholes to convert 'call label; rets' into jump label
7231 [(parallel [(call (mem:QI (match_operand:QI 0 "call_address_operand" ""))
7232 (match_operand:QI 1 "general_operand" ""))
7233 (clobber (reg:QI 31))])
7235 "! c4x_null_epilogue_p ()"
7237 if (REG_P (operands[0]))
7238 return \"bu%#\\t%C0\";
7240 return \"br%#\\t%C0\";"
7241 [(set_attr "type" "jump")])
7244 [(parallel [(set (match_operand 0 "" "")
7245 (call (mem:QI (match_operand:QI 1 "call_address_operand" ""))
7246 (match_operand:QI 2 "general_operand" "")))
7247 (clobber (reg:QI 31))])
7249 "! c4x_null_epilogue_p ()"
7251 if (REG_P (operands[1]))
7252 return \"bu%#\\t%C1\";
7254 return \"br%#\\t%C1\";"
7255 [(set_attr "type" "jump")])
7258 ; This peephole should be unnecessary with my patches to flow.c
7259 ; for better autoincrement detection
7261 [(set (match_operand:QF 0 "ext_low_reg_operand" "")
7262 (mem:QF (match_operand:QI 1 "addr_reg_operand" "")))
7263 (set (match_operand:QF 2 "ext_low_reg_operand" "")
7264 (mem:QF (plus:QI (match_dup 1) (const_int 1))))
7265 (parallel [(set (match_dup 1) (plus:QI (match_dup 1) (const_int 2)))
7266 (clobber (reg:CC_NOOV 21))])]
7268 "ldf\\t*%1++,%0\\n\\tldf\\t*%1++,%2")
7271 ; This peephole should be unnecessary with my patches to flow.c
7272 ; for better autoincrement detection
7274 [(set (mem:QF (match_operand:QI 0 "addr_reg_operand" ""))
7275 (match_operand:QF 1 "ext_low_reg_operand" ""))
7276 (set (mem:QF (plus:QI (match_dup 0) (const_int 1)))
7277 (match_operand:QF 2 "ext_low_reg_operand" ""))
7278 (parallel [(set (match_dup 0) (plus:QI (match_dup 0) (const_int 2)))
7279 (clobber (reg:CC_NOOV 21))])]
7281 "stf\\t%1,*%0++\\n\\tstf\\t%2,*%0++")
7284 ; The following two peepholes remove an unnecessary load
7285 ; often found at the end of a function. These peepholes
7286 ; could be generalized to other binary operators. They shouldn't
7287 ; be required if we run a post reload mop-up pass.
7289 [(parallel [(set (match_operand:QF 0 "ext_reg_operand" "")
7290 (plus:QF (match_operand:QF 1 "ext_reg_operand" "")
7291 (match_operand:QF 2 "ext_reg_operand" "")))
7292 (clobber (reg:CC_NOOV 21))])
7293 (set (match_operand:QF 3 "ext_reg_operand" "")
7295 "dead_or_set_p (insn, operands[0])"
7299 [(parallel [(set (match_operand:QI 0 "reg_operand" "")
7300 (plus:QI (match_operand:QI 1 "reg_operand" "")
7301 (match_operand:QI 2 "reg_operand" "")))
7302 (clobber (reg:CC_NOOV 21))])
7303 (set (match_operand:QI 3 "reg_operand" "")
7305 "dead_or_set_p (insn, operands[0])"