]> gcc.gnu.org Git - gcc.git/blob - gcc/config/frv/frv.md
Implement FR-V FDPIC ABI support for frv-uclinux and frv-linux.
[gcc.git] / gcc / config / frv / frv.md
1 ;; Frv Machine Description
2 ;; Copyright (C) 1999, 2000, 2001, 2003, 2004 Free Software Foundation, Inc.
3 ;; Contributed by Red Hat, Inc.
4
5 ;; This file is part of GCC.
6
7 ;; GCC is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 2, or (at your option)
10 ;; any later version.
11
12 ;; GCC is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 ;; GNU General Public License for more details.
16
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GCC; see the file COPYING. If not, write to
19 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
20 ;; Boston, MA 02111-1307, USA.
21
22 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
23
24 \f
25 ;; ::::::::::::::::::::
26 ;; ::
27 ;; :: Unspec's used
28 ;; ::
29 ;; ::::::::::::::::::::
30
31 ;; GOT constants must go 12/HI/LO for the splitter to work
32
33 (define_constants
34 [(UNSPEC_BLOCKAGE 0)
35 (UNSPEC_CC_TO_GPR 1)
36 (UNSPEC_GPR_TO_CC 2)
37 (UNSPEC_PIC_PROLOGUE 3)
38 (UNSPEC_CR_LOGIC 4)
39 (UNSPEC_STACK_ADJUST 5)
40 (UNSPEC_EH_RETURN_EPILOGUE 6)
41 (UNSPEC_GOT 7)
42 (UNSPEC_LDD 8)
43
44 (R_FRV_GOT12 11)
45 (R_FRV_GOTHI 12)
46 (R_FRV_GOTLO 13)
47 (R_FRV_FUNCDESC 14)
48 (R_FRV_FUNCDESC_GOT12 15)
49 (R_FRV_FUNCDESC_GOTHI 16)
50 (R_FRV_FUNCDESC_GOTLO 17)
51 (R_FRV_FUNCDESC_VALUE 18)
52 (R_FRV_FUNCDESC_GOTOFF12 19)
53 (R_FRV_FUNCDESC_GOTOFFHI 20)
54 (R_FRV_FUNCDESC_GOTOFFLO 21)
55 (R_FRV_GOTOFF12 22)
56 (R_FRV_GOTOFFHI 23)
57 (R_FRV_GOTOFFLO 24)
58 (R_FRV_GPREL12 25)
59 (R_FRV_GPRELHI 26)
60 (R_FRV_GPRELLO 27)
61
62 (FDPIC_REG 15)
63 ])
64
65
66 \f
67 ;; ::::::::::::::::::::
68 ;; ::
69 ;; :: Constraints
70 ;; ::
71 ;; ::::::::::::::::::::
72
73 ;; Standard Constraints
74 ;;
75 ;; `m' A memory operand is allowed, with any kind of address that the
76 ;; machine supports in general.
77 ;;
78 ;; `o' A memory operand is allowed, but only if the address is
79 ;; "offsettable". This means that adding a small integer (actually, the
80 ;; width in bytes of the operand, as determined by its machine mode) may be
81 ;; added to the address and the result is also a valid memory address.
82 ;;
83 ;; `V' A memory operand that is not offsettable. In other words,
84 ;; anything that would fit the `m' constraint but not the `o' constraint.
85 ;;
86 ;; `<' A memory operand with autodecrement addressing (either
87 ;; predecrement or postdecrement) is allowed.
88 ;;
89 ;; `>' A memory operand with autoincrement addressing (either
90 ;; preincrement or postincrement) is allowed.
91 ;;
92 ;; `r' A register operand is allowed provided that it is in a general
93 ;; register.
94 ;;
95 ;; `d', `a', `f', ...
96 ;; Other letters can be defined in machine-dependent fashion to stand for
97 ;; particular classes of registers. `d', `a' and `f' are defined on the
98 ;; 68000/68020 to stand for data, address and floating point registers.
99 ;;
100 ;; `i' An immediate integer operand (one with constant value) is allowed.
101 ;; This includes symbolic constants whose values will be known only at
102 ;; assembly time.
103 ;;
104 ;; `n' An immediate integer operand with a known numeric value is allowed.
105 ;; Many systems cannot support assembly-time constants for operands less
106 ;; than a word wide. Constraints for these operands should use `n' rather
107 ;; than `i'.
108 ;;
109 ;; 'I' First machine-dependent integer constant (6 bit signed ints).
110 ;; 'J' Second machine-dependent integer constant (10 bit signed ints).
111 ;; 'K' Third machine-dependent integer constant (-2048).
112 ;; 'L' Fourth machine-dependent integer constant (16 bit signed ints).
113 ;; 'M' Fifth machine-dependent integer constant (16 bit unsigned ints).
114 ;; 'N' Sixth machine-dependent integer constant (-2047..-1).
115 ;; 'O' Seventh machine-dependent integer constant (zero).
116 ;; 'P' Eighth machine-dependent integer constant (1..2047).
117 ;;
118 ;; Other letters in the range `I' through `P' may be defined in a
119 ;; machine-dependent fashion to permit immediate integer operands with
120 ;; explicit integer values in specified ranges. For example, on the 68000,
121 ;; `I' is defined to stand for the range of values 1 to 8. This is the
122 ;; range permitted as a shift count in the shift instructions.
123 ;;
124 ;; `E' An immediate floating operand (expression code `const_double') is
125 ;; allowed, but only if the target floating point format is the same as
126 ;; that of the host machine (on which the compiler is running).
127 ;;
128 ;; `F' An immediate floating operand (expression code `const_double') is
129 ;; allowed.
130 ;;
131 ;; 'G' First machine-dependent const_double.
132 ;; 'H' Second machine-dependent const_double.
133 ;;
134 ;; `s' An immediate integer operand whose value is not an explicit
135 ;; integer is allowed.
136 ;;
137 ;; This might appear strange; if an insn allows a constant operand with a
138 ;; value not known at compile time, it certainly must allow any known
139 ;; value. So why use `s' instead of `i'? Sometimes it allows better code
140 ;; to be generated.
141 ;;
142 ;; For example, on the 68000 in a fullword instruction it is possible to
143 ;; use an immediate operand; but if the immediate value is between -128 and
144 ;; 127, better code results from loading the value into a register and
145 ;; using the register. This is because the load into the register can be
146 ;; done with a `moveq' instruction. We arrange for this to happen by
147 ;; defining the letter `K' to mean "any integer outside the range -128 to
148 ;; 127", and then specifying `Ks' in the operand constraints.
149 ;;
150 ;; `g' Any register, memory or immediate integer operand is allowed,
151 ;; except for registers that are not general registers.
152 ;;
153 ;; `X' Any operand whatsoever is allowed, even if it does not satisfy
154 ;; `general_operand'. This is normally used in the constraint of a
155 ;; `match_scratch' when certain alternatives will not actually require a
156 ;; scratch register.
157 ;;
158 ;; `0' Match operand 0.
159 ;; `1' Match operand 1.
160 ;; `2' Match operand 2.
161 ;; `3' Match operand 3.
162 ;; `4' Match operand 4.
163 ;; `5' Match operand 5.
164 ;; `6' Match operand 6.
165 ;; `7' Match operand 7.
166 ;; `8' Match operand 8.
167 ;; `9' Match operand 9.
168 ;;
169 ;; An operand that matches the specified operand number is allowed. If a
170 ;; digit is used together with letters within the same alternative, the
171 ;; digit should come last.
172 ;;
173 ;; This is called a "matching constraint" and what it really means is that
174 ;; the assembler has only a single operand that fills two roles considered
175 ;; separate in the RTL insn. For example, an add insn has two input
176 ;; operands and one output operand in the RTL, but on most CISC machines an
177 ;; add instruction really has only two operands, one of them an
178 ;; input-output operand:
179 ;;
180 ;; addl #35,r12
181 ;;
182 ;; Matching constraints are used in these circumstances. More precisely,
183 ;; the two operands that match must include one input-only operand and one
184 ;; output-only operand. Moreover, the digit must be a smaller number than
185 ;; the number of the operand that uses it in the constraint.
186 ;;
187 ;; For operands to match in a particular case usually means that they are
188 ;; identical-looking RTL expressions. But in a few special cases specific
189 ;; kinds of dissimilarity are allowed. For example, `*x' as an input
190 ;; operand will match `*x++' as an output operand. For proper results in
191 ;; such cases, the output template should always use the output-operand's
192 ;; number when printing the operand.
193 ;;
194 ;; `p' An operand that is a valid memory address is allowed. This is for
195 ;; "load address" and "push address" instructions.
196 ;;
197 ;; `p' in the constraint must be accompanied by `address_operand' as the
198 ;; predicate in the `match_operand'. This predicate interprets the mode
199 ;; specified in the `match_operand' as the mode of the memory reference for
200 ;; which the address would be valid.
201 ;;
202 ;; `Q` First non constant, non register machine-dependent insns
203 ;; `R` Second non constant, non register machine-dependent insns
204 ;; `S` Third non constant, non register machine-dependent insns
205 ;; `T` Fourth non constant, non register machine-dependent insns
206 ;; `U` Fifth non constant, non register machine-dependent insns
207 ;;
208 ;; Letters in the range `Q' through `U' may be defined in a
209 ;; machine-dependent fashion to stand for arbitrary operand types. The
210 ;; machine description macro `EXTRA_CONSTRAINT' is passed the operand as
211 ;; its first argument and the constraint letter as its second operand.
212 ;;
213 ;; A typical use for this would be to distinguish certain types of memory
214 ;; references that affect other insn operands.
215 ;;
216 ;; Do not define these constraint letters to accept register references
217 ;; (`reg'); the reload pass does not expect this and would not handle it
218 ;; properly.
219
220 ;; Multiple Alternative Constraints
221 ;; `?' Disparage slightly the alternative that the `?' appears in, as a
222 ;; choice when no alternative applies exactly. The compiler regards this
223 ;; alternative as one unit more costly for each `?' that appears in it.
224 ;;
225 ;; `!' Disparage severely the alternative that the `!' appears in. This
226 ;; alternative can still be used if it fits without reloading, but if
227 ;; reloading is needed, some other alternative will be used.
228
229 ;; Constraint modifiers
230 ;; `=' Means that this operand is write-only for this instruction: the
231 ;; previous value is discarded and replaced by output data.
232 ;;
233 ;; `+' Means that this operand is both read and written by the
234 ;; instruction.
235 ;;
236 ;; When the compiler fixes up the operands to satisfy the constraints, it
237 ;; needs to know which operands are inputs to the instruction and which are
238 ;; outputs from it. `=' identifies an output; `+' identifies an operand
239 ;; that is both input and output; all other operands are assumed to be
240 ;; input only.
241 ;;
242 ;; `&' Means (in a particular alternative) that this operand is written
243 ;; before the instruction is finished using the input operands. Therefore,
244 ;; this operand may not lie in a register that is used as an input operand
245 ;; or as part of any memory address.
246 ;;
247 ;; `&' applies only to the alternative in which it is written. In
248 ;; constraints with multiple alternatives, sometimes one alternative
249 ;; requires `&' while others do not.
250 ;;
251 ;; `&' does not obviate the need to write `='.
252 ;;
253 ;; `%' Declares the instruction to be commutative for this operand and the
254 ;; following operand. This means that the compiler may interchange the two
255 ;; operands if that is the cheapest way to make all operands fit the
256 ;; constraints. This is often used in patterns for addition instructions
257 ;; that really have only two operands: the result must go in one of the
258 ;; arguments.
259 ;;
260 ;; `#' Says that all following characters, up to the next comma, are to be
261 ;; ignored as a constraint. They are significant only for choosing
262 ;; register preferences.
263 ;;
264 ;; `*' Says that the following character should be ignored when choosing
265 ;; register preferences. `*' has no effect on the meaning of the
266 ;; constraint as a constraint, and no effect on reloading.
267
268 \f
269 ;; ::::::::::::::::::::
270 ;; ::
271 ;; :: Attributes
272 ;; ::
273 ;; ::::::::::::::::::::
274
275 ;; The `define_attr' expression is used to define each attribute required by
276 ;; the target machine. It looks like:
277 ;;
278 ;; (define_attr NAME LIST-OF-VALUES DEFAULT)
279
280 ;; NAME is a string specifying the name of the attribute being defined.
281
282 ;; LIST-OF-VALUES is either a string that specifies a comma-separated list of
283 ;; values that can be assigned to the attribute, or a null string to indicate
284 ;; that the attribute takes numeric values.
285
286 ;; DEFAULT is an attribute expression that gives the value of this attribute
287 ;; for insns that match patterns whose definition does not include an explicit
288 ;; value for this attribute.
289
290 ;; For each defined attribute, a number of definitions are written to the
291 ;; `insn-attr.h' file. For cases where an explicit set of values is specified
292 ;; for an attribute, the following are defined:
293
294 ;; * A `#define' is written for the symbol `HAVE_ATTR_NAME'.
295 ;;
296 ;; * An enumeral class is defined for `attr_NAME' with elements of the
297 ;; form `UPPER-NAME_UPPER-VALUE' where the attribute name and value are first
298 ;; converted to upper case.
299 ;;
300 ;; * A function `get_attr_NAME' is defined that is passed an insn and
301 ;; returns the attribute value for that insn.
302
303 ;; For example, if the following is present in the `md' file:
304 ;;
305 ;; (define_attr "type" "branch,fp,load,store,arith" ...)
306 ;;
307 ;; the following lines will be written to the file `insn-attr.h'.
308 ;;
309 ;; #define HAVE_ATTR_type
310 ;; enum attr_type {TYPE_BRANCH, TYPE_FP, TYPE_LOAD, TYPE_STORE, TYPE_ARITH};
311 ;; extern enum attr_type get_attr_type ();
312
313 ;; If the attribute takes numeric values, no `enum' type will be defined and
314 ;; the function to obtain the attribute's value will return `int'.
315
316 (define_attr "length" "" (const_int 4))
317
318 ;; Processor type -- this attribute must exactly match the processor_type
319 ;; enumeration in frv-protos.h.
320
321 (define_attr "cpu" "generic,fr500,fr400,fr300,simple,tomcat"
322 (const (symbol_ref "frv_cpu_type")))
323
324 ;; Attribute is "yes" for branches and jumps that span too great a distance
325 ;; to be implemented in the most natural way. Such instructions will use
326 ;; a call instruction in some way.
327
328 (define_attr "far_jump" "yes,no" (const_string "no"))
329
330 ;; Instruction type
331
332 ;; The table below summarizes the types of media instruction and their
333 ;; scheduling classification. Headings are:
334
335 ;; Type: the name of the define_attr type
336 ;; Conditions: "yes" if conditional variants are available
337 ;; FR500: Fujitsu's categorization for the FR500
338 ;; FR400: Fujitsu's categorization for the FR400 (but see below).
339
340 ;; On the FR400, media instructions are divided into 2 broad categories.
341 ;; Category 1 instructions can execute in either the M0 or M1 unit and can
342 ;; execute in parallel with other category 1 instructions. Category 2
343 ;; instructions must use the M0 unit, and therefore cannot run in parallel
344 ;; with other media instructions.
345
346 ;; The FR400 documentation also divides media instructions into one of seven
347 ;; categories (m1 to m7). m1 to m4 contain both Category 1 and Category 2
348 ;; instructions, so we use a combination of the categories here.
349
350 ;; Type Conditional FR500 FR400
351 ;; ---- ---------- ----- -----
352 ;; mlogic yes m1 m1:1
353 ;; mrdacc no m2 m4:1
354 ;; mwtacc no m3 m5:1
355 ;; maveh no m1 m1:1
356 ;; msath no m1 m1:1
357 ;; maddh yes m1 m1:1
358 ;; mqaddh yes m1 m1:2
359 ;; mpackh no m2 m3:1
360 ;; munpackh no m2 m3:2
361 ;; mdpackh no m5 m3:2
362 ;; mbhconv yes m2 m3:2
363 ;; mrot no m2 m3:1
364 ;; mshift no m2 m3:1
365 ;; mexpdhw yes m2 m3:1
366 ;; mexpdhd yes m2 m3:2
367 ;; mwcut no m2 m3:2
368 ;; mmulh yes m4 m2:1
369 ;; mmulxh no m4 m2:1
370 ;; mmach yes m4 m2:1
371 ;; mmrdh no m4 m2:1
372 ;; mqmulh yes m4 m2:2
373 ;; mqmulxh no m4 m2:2
374 ;; mqmach yes m4 m2:2
375 ;; mcpx yes m4 m2:1
376 ;; mqcpx yes m4 m2:2
377 ;; mcut no m2 m4:1
378 ;; mclracc no m3 m4:1
379 ;; mclracca no m6 m4:2
380 ;; mdunpackh no m2 n/a
381 ;; mbhconve no m2 n/a
382 ;; maddacc no n/a m2:1
383 ;; mdaddacc no n/a m2:2
384 ;; mabsh no n/a m1:1
385 ;; mdrot no n/a m3:2
386 ;; mcpl no n/a m3:2
387 ;; mdcut no n/a m4:2
388 ;; mqsath no n/a m1:2
389 ;; mset no n/a m1:1
390
391 (define_attr "type"
392 "int,sethi,setlo,mul,div,gload,gstore,fload,fstore,movfg,movgf,branch,jump,jumpl,call,spr,trap,fsconv,fsadd,fsmul,fmas,fsdiv,sqrt_single,fdconv,fdadd,fdmul,fddiv,sqrt_double,mlogic,maveh,msath,maddh,mqaddh,mpackh,munpackh,mdpackh,mbhconv,mrot,mshift,mexpdhw,mexpdhd,mwcut,mmulh,mmulxh,mmach,mmrdh,mqmulh,mqmulxh,mqmach,mcpx,mqcpx,mcut,mclracc,mclracca,mdunpackh,mbhconve,mrdacc,mwtacc,maddacc,mdaddacc,mabsh,mdrot,mcpl,mdcut,mqsath,mset,m7,ccr,multi,unknown"
393 (const_string "unknown"))
394
395 \f
396
397 /* This is description of pipeline hazards based on DFA. The
398 following constructions can be used for this:
399
400 o define_cpu_unit string [string]) describes a cpu functional unit
401 (separated by comma).
402
403 1st operand: Names of cpu function units.
404 2nd operand: Name of automaton (see comments for
405 DEFINE_AUTOMATON).
406
407 All define_reservations and define_cpu_units should have unique
408 names which can not be "nothing".
409
410 o (exclusion_set string string) means that each CPU function unit
411 in the first string can not be reserved simultaneously with each
412 unit whose name is in the second string and vise versa. CPU
413 units in the string are separated by commas. For example, it is
414 useful for description CPU with fully pipelined floating point
415 functional unit which can execute simultaneously only single
416 floating point insns or only double floating point insns.
417
418 o (presence_set string string) means that each CPU function unit in
419 the first string can not be reserved unless at least one of units
420 whose names are in the second string is reserved. This is an
421 asymmetric relation. CPU units in the string are separated by
422 commas. For example, it is useful for description that slot1 is
423 reserved after slot0 reservation for a VLIW processor.
424
425 o (absence_set string string) means that each CPU function unit in
426 the first string can not be reserved only if each unit whose name
427 is in the second string is not reserved. This is an asymmetric
428 relation (actually exclusion set is analogous to this one but it
429 is symmetric). CPU units in the string are separated by commas.
430 For example, it is useful for description that slot0 can not be
431 reserved after slot1 or slot2 reservation for a VLIW processor.
432
433 o (define_bypass number out_insn_names in_insn_names) names bypass with
434 given latency (the first number) from insns given by the first
435 string (see define_insn_reservation) into insns given by the
436 second string. Insn names in the strings are separated by
437 commas.
438
439 o (define_automaton string) describes names of an automaton
440 generated and used for pipeline hazards recognition. The names
441 are separated by comma. Actually it is possibly to generate the
442 single automaton but unfortunately it can be very large. If we
443 use more one automata, the summary size of the automata usually
444 is less than the single one. The automaton name is used in
445 define_cpu_unit. All automata should have unique names.
446
447 o (define_reservation string string) names reservation (the first
448 string) of cpu functional units (the 2nd string). Sometimes unit
449 reservations for different insns contain common parts. In such
450 case, you describe common part and use one its name (the 1st
451 parameter) in regular expression in define_insn_reservation. All
452 define_reservations, define results and define_cpu_units should
453 have unique names which can not be "nothing".
454
455 o (define_insn_reservation name default_latency condition regexpr)
456 describes reservation of cpu functional units (the 3nd operand)
457 for instruction which is selected by the condition (the 2nd
458 parameter). The first parameter is used for output of debugging
459 information. The reservations are described by a regular
460 expression according the following syntax:
461
462 regexp = regexp "," oneof
463 | oneof
464
465 oneof = oneof "|" allof
466 | allof
467
468 allof = allof "+" repeat
469 | repeat
470
471 repeat = element "*" number
472 | element
473
474 element = cpu_function_name
475 | reservation_name
476 | result_name
477 | "nothing"
478 | "(" regexp ")"
479
480 1. "," is used for describing start of the next cycle in
481 reservation.
482
483 2. "|" is used for describing the reservation described by the
484 first regular expression *or* the reservation described by
485 the second regular expression *or* etc.
486
487 3. "+" is used for describing the reservation described by the
488 first regular expression *and* the reservation described by
489 the second regular expression *and* etc.
490
491 4. "*" is used for convenience and simply means sequence in
492 which the regular expression are repeated NUMBER times with
493 cycle advancing (see ",").
494
495 5. cpu function unit name which means reservation.
496
497 6. reservation name -- see define_reservation.
498
499 7. string "nothing" means no units reservation.
500
501 */
502
503 (define_automaton "nodiv, idiv, div")
504
505 ;; An FR500 packet can contain a single control instruction or a sequence
506 ;; of up to four operations matching the regular expression:
507
508 ;; (I FM? I? FM? | FM? FM?) B? B?
509
510 ;; where I denotes an integer operation, FM a floating-point or media
511 ;; operation, and B a branch operation. There are two units for each type
512 ;; of instruction: I0 and I1, FM0 and FM1, and B0 and B1. Units are
513 ;; allocated left-to-right: the first integer instruction uses I0, the
514 ;; second uses I1, and so on.
515
516 ;; The FR400 is similar to the FR500 except that it allows only 2 operations
517 ;; per packet and has only one branch unit. We can use the FR500 conflict
518 ;; description for the FR400, but need to define different cpu_units
519 ;; later.
520
521 ;; Slot/unit combinations available on the FR400 and above:
522 (define_cpu_unit "sl0_i0, sl0_fm0, sl0_b0, sl0_c" "nodiv")
523 (define_cpu_unit "sl1_fm0, sl1_i1, sl1_fm1, sl1_b0" "nodiv")
524
525 ;; These are available on the FR500 and above:
526 (define_cpu_unit "sl1_b1" "nodiv")
527 (define_cpu_unit "sl2_i1, sl2_fm1, sl2_b0, sl2_b1" "nodiv")
528 (define_cpu_unit "sl3_fm1, sl3_b0, sl3_b1" "nodiv")
529
530 ;; The following describes conflicts by slots
531 ;; slot0
532 (exclusion_set "sl0_i0" "sl0_fm0,sl0_b0,sl0_c")
533 (exclusion_set "sl0_fm0" "sl0_b0,sl0_c")
534 (exclusion_set "sl0_b0" "sl0_c")
535
536 ;; slot1
537 (exclusion_set "sl1_fm0" "sl1_i1,sl1_fm1,sl1_b0,sl1_b1")
538 (exclusion_set "sl1_i1" "sl1_fm1,sl1_b0,sl1_b1")
539 (exclusion_set "sl1_fm1" "sl1_b0,sl1_b1")
540 (exclusion_set "sl1_b0" "sl1_b1")
541
542 ;; slot2
543 (exclusion_set "sl2_i1" "sl2_fm1,sl2_b0,sl2_b1")
544 (exclusion_set "sl2_fm1" "sl2_b0,sl2_b1")
545 (exclusion_set "sl2_b0" "sl2_b1")
546
547 ;; slot3
548 (exclusion_set "sl3_fm1" "sl3_b0,sl3_b1")
549 (exclusion_set "sl3_b0" "sl3_b1")
550
551 ;; The following describes conflicts by units
552 ;; fm0
553 (exclusion_set "sl0_fm0" "sl1_fm0")
554
555 ;; b0
556 (exclusion_set "sl0_b0" "sl1_b0,sl2_b0,sl3_b0")
557 (exclusion_set "sl1_b0" "sl2_b0,sl3_b0")
558 (exclusion_set "sl2_b0" "sl3_b0")
559
560 ;; i1
561 (exclusion_set "sl1_i1" "sl2_i1")
562
563 ;; fm1
564 (exclusion_set "sl1_fm1" "sl2_fm1,sl3_fm1")
565 (exclusion_set "sl2_fm1" "sl3_fm1")
566
567 ;; b1
568 (exclusion_set "sl1_b1" "sl2_b1,sl3_b1")
569 (exclusion_set "sl2_b1" "sl3_b1")
570
571 ;; The following describes remaining combinations of conflicts
572 ;; slot0
573 (exclusion_set "sl0_i0" "sl1_fm1,sl1_b1")
574 (exclusion_set "sl0_fm0" "sl1_i1,sl1_b1,sl2_i1,sl2_fm1,sl3_fm1,sl3_b0")
575 (exclusion_set "sl0_b0" "sl1_fm0,sl1_i1,sl1_fm1,sl2_i1,sl2_fm1,sl2_b1,\
576 sl3_fm1,sl3_b1")
577 (exclusion_set "sl0_c" "sl1_fm0,sl1_i1,sl1_fm1,sl1_b0,sl1_b1,sl2_i1,sl2_fm1,\
578 sl2_b0,sl2_b1,sl3_fm1,sl3_b0,sl3_b1")
579
580
581 ;; slot1
582 (exclusion_set "sl1_fm0" "sl2_b1")
583 (exclusion_set "sl1_i1" "sl2_fm1,sl2_b1,sl3_fm1,sl3_b0")
584 (exclusion_set "sl1_fm1" "sl2_i1,sl2_b1,sl3_b0")
585 (exclusion_set "sl1_b0" "sl2_i1,sl2_fm1,sl3_fm1,sl3_b1")
586 (exclusion_set "sl1_b1" "sl2_i1,sl2_fm1,sl2_b0,sl3_fm1,sl3_b0")
587
588 ;; slot2
589 (exclusion_set "sl2_i1" "sl3_b1")
590 (exclusion_set "sl2_fm1" "sl3_b1")
591 (exclusion_set "sl2_b0" "sl3_fm1")
592 (exclusion_set "sl2_b1" "sl3_fm1,sl3_b0")
593
594 ;; slot3
595 (exclusion_set "sl1_fm0" "sl2_i1,sl2_fm1,sl2_b0,sl2_b1,sl3_fm1,sl3_b0,sl3_b1")
596 (exclusion_set "sl3_fm1" "sl2_i1,sl2_fm1,sl2_b0,sl2_b1,sl3_b0,sl3_b1")
597
598 ;; ::::::::::::::::::::
599 ;; ::
600 ;; :: Generic/FR500 scheduler description
601 ;; ::
602 ;; ::::::::::::::::::::
603
604 ;; Define reservation in order to describe only in terms of units.
605
606 (define_reservation "i0" "sl0_i0")
607 (define_reservation "f0" "sl0_fm0|sl1_fm0")
608 (define_reservation "m0" "f0")
609 (define_reservation "b0" "sl0_b0|sl1_b0|sl2_b0|sl3_b0")
610 (define_reservation "c" "sl0_c")
611 (define_reservation "i1" "sl1_i1|sl2_i1")
612 (define_reservation "f1" "sl1_fm1|sl2_fm1|sl3_fm1")
613 (define_reservation "m1" "f1")
614 (define_reservation "b1" "sl1_b1|sl2_b1|sl3_b1")
615
616 ;; Integer insns
617 ;; It is not possibly to issue load & store in one VLIW insn.
618 (define_cpu_unit "idiv1" "idiv")
619 (define_cpu_unit "idiv2" "idiv")
620 (define_cpu_unit "l0" "nodiv")
621 (define_cpu_unit "l1" "nodiv")
622 (define_cpu_unit "s0" "nodiv")
623
624 (exclusion_set "l1,l0" "s0")
625
626 ;; We set the default_latency of sethi to be 0 to allow sethi and setlo to be
627 ;; combined in the same VLIW instruction as allowed by the architecture. This
628 ;; assumes the only use of sethi is always followed by a setlo of the same
629 ;; register.
630 (define_insn_reservation "i1_sethi" 0
631 (and (eq_attr "cpu" "generic,fr500,tomcat")
632 (eq_attr "type" "sethi"))
633 "i0|i1")
634
635 (define_insn_reservation "i1_setlo" 1
636 (and (eq_attr "cpu" "generic,fr500,tomcat")
637 (eq_attr "type" "setlo"))
638 "i0|i1")
639
640 (define_insn_reservation "i1_int" 1
641 (and (eq_attr "cpu" "generic,fr500,tomcat")
642 (eq_attr "type" "int"))
643 "i0|i1")
644
645 (define_insn_reservation "i1_mul" 3
646 (and (eq_attr "cpu" "generic,fr500,tomcat")
647 (eq_attr "type" "mul"))
648 "i0|i1")
649
650 (define_insn_reservation "i1_div" 19
651 (and (eq_attr "cpu" "generic,fr500,tomcat")
652 (eq_attr "type" "div"))
653 "(i0|i1),(idiv1*18|idiv2*18)")
654
655 (define_insn_reservation "i2_gload" 4
656 (and (eq_attr "cpu" "generic,fr500,tomcat")
657 (eq_attr "type" "gload"))
658 "(i0|i1)+(l0|l1)")
659
660 (define_insn_reservation "i2_fload" 4
661 (and (eq_attr "cpu" "generic,fr500,tomcat")
662 (eq_attr "type" "fload"))
663 "(i0|i1)+(l0|l1)")
664
665 (define_insn_reservation "i3_gstore" 0
666 (and (eq_attr "cpu" "generic,fr500,tomcat")
667 (eq_attr "type" "gstore"))
668 "i0+s0")
669
670 (define_insn_reservation "i3_fstore" 0
671 (and (eq_attr "cpu" "generic,fr500,tomcat")
672 (eq_attr "type" "fstore"))
673 "i0+s0")
674
675 (define_insn_reservation "i4_move_gf" 3
676 (and (eq_attr "cpu" "generic,fr500,tomcat")
677 (eq_attr "type" "movgf"))
678 "i0")
679
680 (define_insn_reservation "i4_move_fg" 3
681 (and (eq_attr "cpu" "generic,fr500,tomcat")
682 (eq_attr "type" "movfg"))
683 "i0")
684
685 (define_insn_reservation "i5" 0
686 (and (eq_attr "cpu" "generic,fr500,tomcat")
687 (eq_attr "type" "jumpl"))
688 "i0")
689
690 ;; Clear/commit is not generated now:
691 (define_insn_reservation "i6" 0 (const_int 0) "i0|i1")
692
693 ;;
694 ;; Branch-instructions
695 ;;
696 (define_insn_reservation "b1/b3" 0
697 (and (eq_attr "cpu" "generic,fr500,tomcat")
698 (eq_attr "type" "jump,branch,ccr"))
699 "b0|b1")
700
701 ;; The following insn is not generated now.
702
703 (define_insn_reservation "b2" 0 (const_int 0) "b0")
704
705 (define_insn_reservation "b4" 0
706 (and (eq_attr "cpu" "generic,fr500,tomcat")
707 (eq_attr "type" "call"))
708 "b0")
709
710 ;; The following insns are not generated now.
711 (define_insn_reservation "b5" 0 (const_int 0) "b0|b1")
712 (define_insn_reservation "b6" 0 (const_int 0) "b0|b1")
713
714 ;; Control insns
715 (define_insn_reservation "trap" 0
716 (and (eq_attr "cpu" "generic,fr500,tomcat")
717 (eq_attr "type" "trap"))
718 "c")
719
720 (define_insn_reservation "control" 0
721 (and (eq_attr "cpu" "generic,fr500,tomcat")
722 (eq_attr "type" "spr"))
723 "c")
724
725 ;; Floating point insns
726 (define_cpu_unit "add0" "nodiv")
727 (define_cpu_unit "add1" "nodiv")
728 (define_cpu_unit "mul0" "nodiv")
729 (define_cpu_unit "mul1" "nodiv")
730 (define_cpu_unit "div1" "div")
731 (define_cpu_unit "div2" "div")
732 (define_cpu_unit "root" "div")
733
734 (define_bypass 4 "f1" "m1,m2,m3,m4,m5,m6,m7")
735 (define_insn_reservation "f1" 3
736 (and (eq_attr "cpu" "generic,fr500,tomcat")
737 (eq_attr "type" "fsconv,fdconv"))
738 "(f0|f1)")
739
740 (define_bypass 4 "f2" "m1,m2,m3,m4,m5,m6,m7")
741 (define_insn_reservation "f2" 3
742 (and (eq_attr "cpu" "generic,fr500,tomcat")
743 (eq_attr "type" "fsadd,fdadd"))
744 "(f0|f1)+(add0|add1)")
745
746 (define_bypass 4 "f3" "m1,m2,m3,m4,m5,m6,m7")
747 (define_insn_reservation "f3" 3
748 (and (eq_attr "cpu" "generic,fr500,tomcat")
749 (eq_attr "type" "fsmul,fdmul"))
750 "(f0|f1)+(mul0|mul1)")
751
752 (define_bypass 11 "f4_div" "m1,m2,m3,m4,m5,m6,m7")
753 (define_insn_reservation "f4_div" 10
754 (and (eq_attr "cpu" "generic,fr500,tomcat")
755 (eq_attr "type" "fsdiv,fddiv"))
756 "(f0|f1),(div1*9|div2*9)")
757
758 (define_bypass 16 "f4_root" "m1,m2,m3,m4,m5,m6,m7")
759 (define_insn_reservation "f4_root" 15
760 (and (eq_attr "cpu" "generic,fr500,tomcat")
761 (eq_attr "type" "sqrt_single,sqrt_double"))
762 "(f0|f1)+root*15")
763
764 (define_bypass 4 "f5" "m1,m2,m3,m4,m5,m6,m7")
765 (define_insn_reservation "f5" 3
766 (and (eq_attr "cpu" "generic,fr500,tomcat")
767 (eq_attr "type" "fmas"))
768 "(f0|f1)+(add0|add1)+(mul0|mul1)")
769
770 ;; The following insns are not generated by gcc now:
771 (define_insn_reservation "f6" 0 (const_int 0) "(f0|f1)+add0+add1")
772 (define_insn_reservation "f7" 0 (const_int 0) "(f0|f1)+mul0+mul1")
773
774 ;; Media insns. Now they are all not generated now.
775 (define_cpu_unit "m1_0" "nodiv")
776 (define_cpu_unit "m1_1" "nodiv")
777 (define_cpu_unit "m2_0" "nodiv")
778 (define_cpu_unit "m2_1" "nodiv")
779 (define_cpu_unit "m3_0" "nodiv")
780 (define_cpu_unit "m3_1" "nodiv")
781 (define_cpu_unit "m4_0" "nodiv")
782 (define_cpu_unit "m4_1" "nodiv")
783 (define_cpu_unit "m5" "nodiv")
784 (define_cpu_unit "m6" "nodiv")
785 (define_cpu_unit "m7" "nodiv")
786
787 (exclusion_set "m5,m6,m7" "m2_0,m2_1,m3_0,m3_1")
788 (exclusion_set "m5" "m6,m7")
789 (exclusion_set "m6" "m4_0,m4_1,m7")
790 (exclusion_set "m7" "m1_0,m1_1,add0,add1,mul0,mul1")
791
792 (define_bypass 2 "m1" "m1,m2,m3,m4,m5,m6,m7")
793 (define_bypass 4 "m1" "f1,f2,f3,f4_div,f4_root,f5,f6,f7")
794 (define_insn_reservation "m1" 3
795 (and (eq_attr "cpu" "generic,fr500,tomcat")
796 (eq_attr "type" "mlogic,maveh,msath,maddh,mqaddh"))
797 "(m0|m1)+(m1_0|m1_1)")
798
799 (define_bypass 2 "m2" "m1,m2,m3,m4,m5,m6,m7")
800 (define_bypass 4 "m2" "f1,f2,f3,f4_div,f4_root,f5,f6,f7")
801 (define_insn_reservation "m2" 3
802 (and (eq_attr "cpu" "generic,fr500,tomcat")
803 (eq_attr "type" "mrdacc,mpackh,munpackh,mbhconv,mrot,mshift,mexpdhw,mexpdhd,mwcut,mcut,mdunpackh,mbhconve"))
804 "(m0|m1)+(m2_0|m2_1)")
805
806 (define_bypass 1 "m3" "m4")
807 (define_insn_reservation "m3" 2
808 (and (eq_attr "cpu" "generic,fr500,tomcat")
809 (eq_attr "type" "mclracc,mwtacc"))
810 "(m0|m1)+(m3_0|m3_1)")
811
812 (define_bypass 1 "m4" "m4")
813 (define_insn_reservation "m4" 2
814 (and (eq_attr "cpu" "generic,fr500,tomcat")
815 (eq_attr "type" "mmulh,mmulxh,mmach,mmrdh,mqmulh,mqmulxh,mqmach,mcpx,mqcpx"))
816 "(m0|m1)+(m4_0|m4_1)")
817
818 (define_bypass 2 "m5" "m1,m2,m3,m4,m5,m6,m7")
819 (define_bypass 4 "m5" "f1,f2,f3,f4_div,f4_root,f5,f6,f7")
820 (define_insn_reservation "m5" 3
821 (and (eq_attr "cpu" "generic,fr500,tomcat")
822 (eq_attr "type" "mdpackh"))
823 "(m0|m1)+m5")
824
825 (define_bypass 1 "m6" "m4")
826 (define_insn_reservation "m6" 2
827 (and (eq_attr "cpu" "generic,fr500,tomcat")
828 (eq_attr "type" "mclracca"))
829 "(m0|m1)+m6")
830
831 (define_bypass 2 "m7" "m1,m2,m3,m4,m5,m6,m7")
832 (define_bypass 4 "m7" "f1,f2,f3,f4_div,f4_root,f5,f6,f7")
833
834 (define_insn_reservation "m7" 3
835 (and (eq_attr "cpu" "generic,fr500,tomcat")
836 (eq_attr "type" "m7"))
837 "(m0|m1)+m7")
838
839 ;; Unknown & multi insns starts on new cycle and the next insn starts
840 ;; on new cycle. To describe this we consider as a control insn.
841 (define_insn_reservation "unknown" 1
842 (and (eq_attr "cpu" "generic,fr500,tomcat")
843 (eq_attr "type" "unknown,multi"))
844 "c")
845
846 ;; ::::::::::::::::::::
847 ;; ::
848 ;; :: FR400 scheduler description
849 ;; ::
850 ;; ::::::::::::::::::::
851
852 ;; Category 2 media instructions use both media units, but can be packed
853 ;; with non-media instructions. Use fr400_m1unit to claim the M1 unit
854 ;; without claiming a slot.
855
856 (define_cpu_unit "fr400_m1unit" "nodiv")
857
858 (define_reservation "fr400_i0" "sl0_i0")
859 (define_reservation "fr400_i1" "sl1_i1")
860 (define_reservation "fr400_m0" "sl0_fm0|sl1_fm0")
861 (define_reservation "fr400_m1" "sl1_fm1")
862 (define_reservation "fr400_meither" "fr400_m0|(fr400_m1+fr400_m1unit)")
863 (define_reservation "fr400_mboth" "fr400_m0+fr400_m1unit")
864 (define_reservation "fr400_b" "sl0_b0|sl1_b0")
865 (define_reservation "fr400_c" "sl0_c")
866
867 ;; Name Class Units Latency
868 ;; ==== ===== ===== =======
869 ;; int I1 I0/I1 1
870 ;; sethi I1 I0/I1 0 -- does not interfere with setlo
871 ;; setlo I1 I0/I1 1
872 ;; mul I1 I0 3 (*)
873 ;; div I1 I0 20 (*)
874 ;; gload I2 I0 4 (*)
875 ;; fload I2 I0 4 -- only 3 if read by a media insn
876 ;; gstore I3 I0 0 -- provides no result
877 ;; fstore I3 I0 0 -- provides no result
878 ;; movfg I4 I0 3 (*)
879 ;; movgf I4 I0 3 (*)
880 ;; jumpl I5 I0 0 -- provides no result
881 ;;
882 ;; (*) The results of these instructions can be read one cycle earlier
883 ;; than indicated. The penalty given is for instructions with write-after-
884 ;; write dependencies.
885
886 ;; The FR400 can only do loads and stores in I0, so we there's no danger
887 ;; of memory unit collision in the same packet. There's only one divide
888 ;; unit too.
889
890 (define_insn_reservation "fr400_i1_int" 1
891 (and (eq_attr "cpu" "fr400")
892 (eq_attr "type" "int"))
893 "fr400_i0|fr400_i1")
894
895 (define_insn_reservation "fr400_i1_sethi" 0
896 (and (eq_attr "cpu" "fr400")
897 (eq_attr "type" "sethi"))
898 "fr400_i0|fr400_i1")
899
900 (define_insn_reservation "fr400_i1_setlo" 1
901 (and (eq_attr "cpu" "fr400")
902 (eq_attr "type" "setlo"))
903 "fr400_i0|fr400_i1")
904
905 (define_insn_reservation "fr400_i1_mul" 3
906 (and (eq_attr "cpu" "fr400")
907 (eq_attr "type" "mul"))
908 "fr400_i0")
909
910 (define_insn_reservation "fr400_i1_div" 20
911 (and (eq_attr "cpu" "fr400")
912 (eq_attr "type" "div"))
913 "fr400_i0+idiv1*19")
914
915 (define_insn_reservation "fr400_i2_gload" 4
916 (and (eq_attr "cpu" "fr400")
917 (eq_attr "type" "gload"))
918 "fr400_i0")
919
920 (define_insn_reservation "fr400_i2_fload" 4
921 (and (eq_attr "cpu" "fr400")
922 (eq_attr "type" "fload"))
923 "fr400_i0")
924
925 (define_insn_reservation "fr400_i3_gstore" 0
926 (and (eq_attr "cpu" "fr400")
927 (eq_attr "type" "gstore"))
928 "fr400_i0")
929
930 (define_insn_reservation "fr400_i3_fstore" 0
931 (and (eq_attr "cpu" "fr400")
932 (eq_attr "type" "fstore"))
933 "fr400_i0")
934
935 (define_insn_reservation "fr400_i4_movfg" 3
936 (and (eq_attr "cpu" "fr400")
937 (eq_attr "type" "movfg"))
938 "fr400_i0")
939
940 (define_insn_reservation "fr400_i4_movgf" 3
941 (and (eq_attr "cpu" "fr400")
942 (eq_attr "type" "movgf"))
943 "fr400_i0")
944
945 (define_insn_reservation "fr400_i5_jumpl" 0
946 (and (eq_attr "cpu" "fr400")
947 (eq_attr "type" "jumpl"))
948 "fr400_i0")
949
950 ;; The bypass between FPR loads and media instructions, described above.
951
952 (define_bypass 3
953 "fr400_i2_fload"
954 "fr400_m1_1,fr400_m1_2,\
955 fr400_m2_1,fr400_m2_2,\
956 fr400_m3_1,fr400_m3_2,\
957 fr400_m4_1,fr400_m4_2,\
958 fr400_m5")
959
960 ;; The branch instructions all use the B unit and produce no result.
961
962 (define_insn_reservation "fr400_b" 0
963 (and (eq_attr "cpu" "fr400")
964 (eq_attr "type" "jump,branch,ccr,call"))
965 "fr400_b")
966
967 ;; Control instructions use the C unit, which excludes all the others.
968
969 (define_insn_reservation "fr400_c" 0
970 (and (eq_attr "cpu" "fr400")
971 (eq_attr "type" "spr,trap"))
972 "fr400_c")
973
974 ;; Unknown instructions use the C unit, since it requires single-operation
975 ;; packets.
976
977 (define_insn_reservation "fr400_unknown" 1
978 (and (eq_attr "cpu" "fr400")
979 (eq_attr "type" "unknown,multi"))
980 "fr400_c")
981
982 ;; FP->FP moves are marked as "fsconv" instructions in the define_insns
983 ;; below, but are implemented on the FR400 using "mlogic" instructions.
984 ;; It's easier to class "fsconv" as a "m1:1" instruction than provide
985 ;; separate define_insns for the FR400.
986
987 ;; M1 instructions store their results in FPRs. Any instruction can read
988 ;; the result in the following cycle, so no penalty occurs.
989
990 (define_insn_reservation "fr400_m1_1" 1
991 (and (eq_attr "cpu" "fr400")
992 (eq_attr "type" "fsconv,mlogic,maveh,msath,maddh,mabsh,mset"))
993 "fr400_meither")
994
995 (define_insn_reservation "fr400_m1_2" 1
996 (and (eq_attr "cpu" "fr400")
997 (eq_attr "type" "mqaddh,mqsath"))
998 "fr400_mboth")
999
1000 ;; M2 instructions store their results in accumulators, which are read
1001 ;; by M2 or M4 media commands. M2 instructions can read the results in
1002 ;; the following cycle, but M4 instructions must wait a cycle more.
1003
1004 (define_bypass 1
1005 "fr400_m2_1,fr400_m2_2"
1006 "fr400_m2_1,fr400_m2_2")
1007
1008 (define_insn_reservation "fr400_m2_1" 2
1009 (and (eq_attr "cpu" "fr400")
1010 (eq_attr "type" "mmulh,mmulxh,mmach,mmrdh,mcpx,maddacc"))
1011 "fr400_meither")
1012
1013 (define_insn_reservation "fr400_m2_2" 2
1014 (and (eq_attr "cpu" "fr400")
1015 (eq_attr "type" "mqmulh,mqmulxh,mqmach,mqcpx,mdaddacc"))
1016 "fr400_mboth")
1017
1018 ;; For our purposes, there seems to be little real difference between
1019 ;; M1 and M3 instructions. Keep them separate anyway in case the distinction
1020 ;; is needed later.
1021
1022 (define_insn_reservation "fr400_m3_1" 1
1023 (and (eq_attr "cpu" "fr400")
1024 (eq_attr "type" "mpackh,mrot,mshift,mexpdhw"))
1025 "fr400_meither")
1026
1027 (define_insn_reservation "fr400_m3_2" 1
1028 (and (eq_attr "cpu" "fr400")
1029 (eq_attr "type" "munpackh,mdpackh,mbhconv,mexpdhd,mwcut,mdrot,mcpl"))
1030 "fr400_mboth")
1031
1032 ;; M4 instructions write to accumulators or FPRs. MOVFG and STF
1033 ;; instructions can read an FPR result in the following cycle, but
1034 ;; M-unit instructions must wait a cycle more for either kind of result.
1035
1036 (define_bypass 1
1037 "fr400_m4_1,fr400_m4_2"
1038 "fr400_i3_fstore,fr400_i4_movfg")
1039
1040 (define_insn_reservation "fr400_m4_1" 2
1041 (and (eq_attr "cpu" "fr400")
1042 (eq_attr "type" "mrdacc,mcut,mclracc"))
1043 "fr400_meither")
1044
1045 (define_insn_reservation "fr400_m4_2" 2
1046 (and (eq_attr "cpu" "fr400")
1047 (eq_attr "type" "mclracca,mdcut"))
1048 "fr400_mboth")
1049
1050 ;; M5 instructions always incur a 1-cycle penalty.
1051
1052 (define_insn_reservation "fr400_m5" 2
1053 (and (eq_attr "cpu" "fr400")
1054 (eq_attr "type" "mwtacc"))
1055 "fr400_mboth")
1056
1057 ;; ::::::::::::::::::::
1058 ;; ::
1059 ;; :: Simple/FR300 scheduler description
1060 ;; ::
1061 ;; ::::::::::::::::::::
1062
1063 ;; Fr300 or simple processor. To describe it as 1 insn issue
1064 ;; processor, we use control unit.
1065
1066 (define_insn_reservation "fr300_lat1" 1
1067 (and (eq_attr "cpu" "fr300,simple")
1068 (eq_attr "type" "!gload,fload,movfg,movgf"))
1069 "c")
1070
1071 (define_insn_reservation "fr300_lat2" 2
1072 (and (eq_attr "cpu" "fr300,simple")
1073 (eq_attr "type" "gload,fload,movfg,movgf"))
1074 "c")
1075
1076 \f
1077 ;; ::::::::::::::::::::
1078 ;; ::
1079 ;; :: Delay Slots
1080 ;; ::
1081 ;; ::::::::::::::::::::
1082
1083 ;; The insn attribute mechanism can be used to specify the requirements for
1084 ;; delay slots, if any, on a target machine. An instruction is said to require
1085 ;; a "delay slot" if some instructions that are physically after the
1086 ;; instruction are executed as if they were located before it. Classic
1087 ;; examples are branch and call instructions, which often execute the following
1088 ;; instruction before the branch or call is performed.
1089
1090 ;; On some machines, conditional branch instructions can optionally "annul"
1091 ;; instructions in the delay slot. This means that the instruction will not be
1092 ;; executed for certain branch outcomes. Both instructions that annul if the
1093 ;; branch is true and instructions that annul if the branch is false are
1094 ;; supported.
1095
1096 ;; Delay slot scheduling differs from instruction scheduling in that
1097 ;; determining whether an instruction needs a delay slot is dependent only
1098 ;; on the type of instruction being generated, not on data flow between the
1099 ;; instructions. See the next section for a discussion of data-dependent
1100 ;; instruction scheduling.
1101
1102 ;; The requirement of an insn needing one or more delay slots is indicated via
1103 ;; the `define_delay' expression. It has the following form:
1104 ;;
1105 ;; (define_delay TEST
1106 ;; [DELAY-1 ANNUL-TRUE-1 ANNUL-FALSE-1
1107 ;; DELAY-2 ANNUL-TRUE-2 ANNUL-FALSE-2
1108 ;; ...])
1109
1110 ;; TEST is an attribute test that indicates whether this `define_delay' applies
1111 ;; to a particular insn. If so, the number of required delay slots is
1112 ;; determined by the length of the vector specified as the second argument. An
1113 ;; insn placed in delay slot N must satisfy attribute test DELAY-N.
1114 ;; ANNUL-TRUE-N is an attribute test that specifies which insns may be annulled
1115 ;; if the branch is true. Similarly, ANNUL-FALSE-N specifies which insns in
1116 ;; the delay slot may be annulled if the branch is false. If annulling is not
1117 ;; supported for that delay slot, `(nil)' should be coded.
1118
1119 ;; For example, in the common case where branch and call insns require a single
1120 ;; delay slot, which may contain any insn other than a branch or call, the
1121 ;; following would be placed in the `md' file:
1122
1123 ;; (define_delay (eq_attr "type" "branch,call")
1124 ;; [(eq_attr "type" "!branch,call") (nil) (nil)])
1125
1126 ;; Multiple `define_delay' expressions may be specified. In this case, each
1127 ;; such expression specifies different delay slot requirements and there must
1128 ;; be no insn for which tests in two `define_delay' expressions are both true.
1129
1130 ;; For example, if we have a machine that requires one delay slot for branches
1131 ;; but two for calls, no delay slot can contain a branch or call insn, and any
1132 ;; valid insn in the delay slot for the branch can be annulled if the branch is
1133 ;; true, we might represent this as follows:
1134
1135 ;; (define_delay (eq_attr "type" "branch")
1136 ;; [(eq_attr "type" "!branch,call")
1137 ;; (eq_attr "type" "!branch,call")
1138 ;; (nil)])
1139 ;;
1140 ;; (define_delay (eq_attr "type" "call")
1141 ;; [(eq_attr "type" "!branch,call") (nil) (nil)
1142 ;; (eq_attr "type" "!branch,call") (nil) (nil)])
1143
1144 ;; Note - it is the backend's responsibility to fill any unfilled delay slots
1145 ;; at assembler generation time. This is usually done by adding a special print
1146 ;; operand to the delayed instruction, and then in the PRINT_OPERAND function
1147 ;; calling dbr_sequence_length() to determine how many delay slots were filled.
1148 ;; For example:
1149 ;;
1150 ;; --------------<machine>.md-----------------
1151 ;; (define_insn "call"
1152 ;; [(call (match_operand 0 "memory_operand" "m")
1153 ;; (match_operand 1 "" ""))]
1154 ;; ""
1155 ;; "call_delayed %0,%1,%2%#"
1156 ;; [(set_attr "length" "4")
1157 ;; (set_attr "type" "call")])
1158 ;;
1159 ;; -------------<machine>.h-------------------
1160 ;; #define PRINT_OPERAND_PUNCT_VALID_P(CODE) (CODE == '#')
1161 ;;
1162 ;; ------------<machine>.c------------------
1163 ;; void
1164 ;; machine_print_operand (file, x, code)
1165 ;; FILE * file;
1166 ;; rtx x;
1167 ;; int code;
1168 ;; {
1169 ;; switch (code)
1170 ;; {
1171 ;; case '#':
1172 ;; if (dbr_sequence_length () == 0)
1173 ;; fputs ("\n\tnop", file);
1174 ;; return;
1175 \f
1176 ;; ::::::::::::::::::::
1177 ;; ::
1178 ;; :: Notes on Patterns
1179 ;; ::
1180 ;; ::::::::::::::::::::
1181
1182 ;; If you need to construct a sequence of assembler instructions in order
1183 ;; to implement a pattern be sure to escape any backslashes and double quotes
1184 ;; that you use, eg:
1185 ;;
1186 ;; (define_insn "an example"
1187 ;; [(some rtl)]
1188 ;; ""
1189 ;; "*
1190 ;; { static char buffer [100];
1191 ;; sprintf (buffer, \"insn \\t %d\", REGNO (operands[1]));
1192 ;; return buffer;
1193 ;; }"
1194 ;; )
1195 ;;
1196 ;; Also if there is more than one instruction, they can be separated by \\;
1197 ;; which is a space saving synonym for \\n\\t:
1198 ;;
1199 ;; (define_insn "another example"
1200 ;; [(some rtl)]
1201 ;; ""
1202 ;; "*
1203 ;; { static char buffer [100];
1204 ;; sprintf (buffer, \"insn1 \\t %d\\;insn2 \\t %%1\",
1205 ;; REGNO (operands[1]));
1206 ;; return buffer;
1207 ;; }"
1208 ;; )
1209 ;;
1210
1211 \f
1212 ;; ::::::::::::::::::::
1213 ;; ::
1214 ;; :: Moves
1215 ;; ::
1216 ;; ::::::::::::::::::::
1217
1218 ;; Wrap moves in define_expand to prevent memory->memory moves from being
1219 ;; generated at the RTL level, which generates better code for most machines
1220 ;; which can't do mem->mem moves.
1221
1222 ;; If operand 0 is a `subreg' with mode M of a register whose own mode is wider
1223 ;; than M, the effect of this instruction is to store the specified value in
1224 ;; the part of the register that corresponds to mode M. The effect on the rest
1225 ;; of the register is undefined.
1226
1227 ;; This class of patterns is special in several ways. First of all, each of
1228 ;; these names *must* be defined, because there is no other way to copy a datum
1229 ;; from one place to another.
1230
1231 ;; Second, these patterns are not used solely in the RTL generation pass. Even
1232 ;; the reload pass can generate move insns to copy values from stack slots into
1233 ;; temporary registers. When it does so, one of the operands is a hard
1234 ;; register and the other is an operand that can need to be reloaded into a
1235 ;; register.
1236
1237 ;; Therefore, when given such a pair of operands, the pattern must
1238 ;; generate RTL which needs no reloading and needs no temporary
1239 ;; registers--no registers other than the operands. For example, if
1240 ;; you support the pattern with a `define_expand', then in such a
1241 ;; case the `define_expand' mustn't call `force_reg' or any other such
1242 ;; function which might generate new pseudo registers.
1243
1244 ;; This requirement exists even for subword modes on a RISC machine
1245 ;; where fetching those modes from memory normally requires several
1246 ;; insns and some temporary registers. Look in `spur.md' to see how
1247 ;; the requirement can be satisfied.
1248
1249 ;; During reload a memory reference with an invalid address may be passed as an
1250 ;; operand. Such an address will be replaced with a valid address later in the
1251 ;; reload pass. In this case, nothing may be done with the address except to
1252 ;; use it as it stands. If it is copied, it will not be replaced with a valid
1253 ;; address. No attempt should be made to make such an address into a valid
1254 ;; address and no routine (such as `change_address') that will do so may be
1255 ;; called. Note that `general_operand' will fail when applied to such an
1256 ;; address.
1257 ;;
1258 ;; The global variable `reload_in_progress' (which must be explicitly declared
1259 ;; if required) can be used to determine whether such special handling is
1260 ;; required.
1261 ;;
1262 ;; The variety of operands that have reloads depends on the rest of
1263 ;; the machine description, but typically on a RISC machine these can
1264 ;; only be pseudo registers that did not get hard registers, while on
1265 ;; other machines explicit memory references will get optional
1266 ;; reloads.
1267 ;;
1268 ;; If a scratch register is required to move an object to or from memory, it
1269 ;; can be allocated using `gen_reg_rtx' prior to reload. But this is
1270 ;; impossible during and after reload. If there are cases needing scratch
1271 ;; registers after reload, you must define `SECONDARY_INPUT_RELOAD_CLASS' and
1272 ;; perhaps also `SECONDARY_OUTPUT_RELOAD_CLASS' to detect them, and provide
1273 ;; patterns `reload_inM' or `reload_outM' to handle them.
1274
1275 ;; The constraints on a `moveM' must permit moving any hard register to any
1276 ;; other hard register provided that `HARD_REGNO_MODE_OK' permits mode M in
1277 ;; both registers and `REGISTER_MOVE_COST' applied to their classes returns a
1278 ;; value of 2.
1279
1280 ;; It is obligatory to support floating point `moveM' instructions
1281 ;; into and out of any registers that can hold fixed point values,
1282 ;; because unions and structures (which have modes `SImode' or
1283 ;; `DImode') can be in those registers and they may have floating
1284 ;; point members.
1285
1286 ;; There may also be a need to support fixed point `moveM' instructions in and
1287 ;; out of floating point registers. Unfortunately, I have forgotten why this
1288 ;; was so, and I don't know whether it is still true. If `HARD_REGNO_MODE_OK'
1289 ;; rejects fixed point values in floating point registers, then the constraints
1290 ;; of the fixed point `moveM' instructions must be designed to avoid ever
1291 ;; trying to reload into a floating point register.
1292
1293 (define_expand "movqi"
1294 [(set (match_operand:QI 0 "general_operand" "")
1295 (match_operand:QI 1 "general_operand" ""))]
1296 ""
1297 "
1298 {
1299 if (!reload_in_progress
1300 && !reload_completed
1301 && !register_operand (operands[0], QImode)
1302 && !reg_or_0_operand (operands[1], QImode))
1303 operands[1] = copy_to_mode_reg (QImode, operands[1]);
1304 }")
1305
1306 (define_insn "*movqi_load"
1307 [(set (match_operand:QI 0 "register_operand" "=d,f")
1308 (match_operand:QI 1 "frv_load_operand" "m,m"))]
1309 ""
1310 "* return output_move_single (operands, insn);"
1311 [(set_attr "length" "4")
1312 (set_attr "type" "gload,fload")])
1313
1314 (define_insn "*movqi_internal"
1315 [(set (match_operand:QI 0 "move_destination_operand" "=d,d,m,m,?f,?f,?d,?m,f")
1316 (match_operand:QI 1 "move_source_operand" "L,d,d,O, d, f, f, f,GO"))]
1317 "register_operand(operands[0], QImode) || reg_or_0_operand (operands[1], QImode)"
1318 "* return output_move_single (operands, insn);"
1319 [(set_attr "length" "4")
1320 (set_attr "type" "int,int,gstore,gstore,movgf,fsconv,movfg,fstore,movgf")])
1321
1322 (define_expand "movhi"
1323 [(set (match_operand:HI 0 "general_operand" "")
1324 (match_operand:HI 1 "general_operand" ""))]
1325 ""
1326 "
1327 {
1328 if (!reload_in_progress
1329 && !reload_completed
1330 && !register_operand (operands[0], HImode)
1331 && !reg_or_0_operand (operands[1], HImode))
1332 operands[1] = copy_to_mode_reg (HImode, operands[1]);
1333 }")
1334
1335 (define_insn "*movhi_load"
1336 [(set (match_operand:HI 0 "register_operand" "=d,f")
1337 (match_operand:HI 1 "frv_load_operand" "m,m"))]
1338 ""
1339 "* return output_move_single (operands, insn);"
1340 [(set_attr "length" "4")
1341 (set_attr "type" "gload,fload")])
1342
1343 (define_insn "*movhi_internal"
1344 [(set (match_operand:HI 0 "move_destination_operand" "=d,d,d,m,m,?f,?f,?d,?m,f")
1345 (match_operand:HI 1 "move_source_operand" "L,n,d,d,O, d, f, f, f,GO"))]
1346 "register_operand(operands[0], HImode) || reg_or_0_operand (operands[1], HImode)"
1347 "* return output_move_single (operands, insn);"
1348 [(set_attr "length" "4,8,4,4,4,4,4,4,4,4")
1349 (set_attr "type" "int,multi,int,gstore,gstore,movgf,fsconv,movfg,fstore,movgf")])
1350
1351 ;; Split 2 word load of constants into sethi/setlo instructions
1352 (define_split
1353 [(set (match_operand:HI 0 "integer_register_operand" "")
1354 (match_operand:HI 1 "int_2word_operand" ""))]
1355 "reload_completed"
1356 [(set (match_dup 0)
1357 (high:HI (match_dup 1)))
1358 (set (match_dup 0)
1359 (lo_sum:HI (match_dup 0)
1360 (match_dup 1)))]
1361 "")
1362
1363 (define_insn "movhi_high"
1364 [(set (match_operand:HI 0 "integer_register_operand" "=d")
1365 (high:HI (match_operand:HI 1 "int_2word_operand" "i")))]
1366 ""
1367 "sethi #hi(%1), %0"
1368 [(set_attr "type" "sethi")
1369 (set_attr "length" "4")])
1370
1371 (define_insn "movhi_lo_sum"
1372 [(set (match_operand:HI 0 "integer_register_operand" "+d")
1373 (lo_sum:HI (match_dup 0)
1374 (match_operand:HI 1 "int_2word_operand" "i")))]
1375 ""
1376 "setlo #lo(%1), %0"
1377 [(set_attr "type" "setlo")
1378 (set_attr "length" "4")])
1379
1380 (define_expand "movsi"
1381 [(set (match_operand:SI 0 "move_destination_operand" "")
1382 (match_operand:SI 1 "move_source_operand" ""))]
1383 ""
1384 "
1385 {
1386 if (frv_emit_movsi (operands[0], operands[1]))
1387 DONE;
1388 }")
1389
1390 ;; Note - it is best to only have one movsi pattern and to handle
1391 ;; all the various contingencies by the use of alternatives. This
1392 ;; allows reload the greatest amount of flexibility (since reload will
1393 ;; only choose amoungst alternatives for a selected insn, it will not
1394 ;; replace the insn with another one).
1395
1396 ;; Unfortunately, we do have to separate out load-type moves from the rest,
1397 ;; and only allow memory source operands in the former. If we do memory and
1398 ;; constant loads in a single pattern, reload will be tempted to force
1399 ;; constants into memory when the destination is a floating-point register.
1400 ;; That may make a function use a PIC pointer when it didn't before, and we
1401 ;; cannot change PIC usage (and hence stack layout) so late in the game.
1402 ;; The resulting sequences for loading constants into FPRs are preferable
1403 ;; even when we're not generating PIC code.
1404
1405 (define_insn "*movsi_load"
1406 [(set (match_operand:SI 0 "register_operand" "=d,f")
1407 (match_operand:SI 1 "frv_load_operand" "m,m"))]
1408 ""
1409 "* return output_move_single (operands, insn);"
1410 [(set_attr "length" "4")
1411 (set_attr "type" "gload,fload")])
1412
1413 (define_insn "*movsi_got"
1414 [(set (match_operand:SI 0 "integer_register_operand" "=d")
1415 (match_operand:SI 1 "got12_operand" ""))]
1416 ""
1417 "addi gr0, %1, %0"
1418 [(set_attr "type" "int")
1419 (set_attr "length" "4")])
1420
1421 (define_insn "*movsi_high_got"
1422 [(set (match_operand:SI 0 "integer_register_operand" "=d")
1423 (high:SI (match_operand:SI 1 "const_unspec_operand" "")))]
1424 ""
1425 "sethi %1, %0"
1426 [(set_attr "type" "sethi")
1427 (set_attr "length" "4")])
1428
1429 (define_insn "*movsi_lo_sum_got"
1430 [(set (match_operand:SI 0 "integer_register_operand" "=d")
1431 (lo_sum:SI (match_operand:SI 1 "integer_register_operand" "0")
1432 (match_operand:SI 2 "const_unspec_operand" "")))]
1433 ""
1434 "setlo %2, %0"
1435 [(set_attr "type" "setlo")
1436 (set_attr "length" "4")])
1437
1438 (define_insn "*movsi_internal"
1439 [(set (match_operand:SI 0 "move_destination_operand" "=d,d,d,m,m,z,d,d,f,f,m,?f,?z")
1440 (match_operand:SI 1 "move_source_operand" "L,n,d,d,O,d,z,f,d,f,f,GO,GO"))]
1441 "register_operand (operands[0], SImode) || reg_or_0_operand (operands[1], SImode)"
1442 "* return output_move_single (operands, insn);"
1443 [(set_attr "length" "4,8,4,4,4,4,4,4,4,4,4,4,4")
1444 (set_attr "type" "int,multi,int,gstore,gstore,spr,spr,movfg,movgf,fsconv,fstore,movgf,spr")])
1445
1446 ;; Split 2 word load of constants into sethi/setlo instructions
1447 (define_insn_and_split "*movsi_2word"
1448 [(set (match_operand:SI 0 "integer_register_operand" "=d")
1449 (match_operand:SI 1 "int_2word_operand" "i"))]
1450 ""
1451 "#"
1452 "reload_completed"
1453 [(set (match_dup 0)
1454 (high:SI (match_dup 1)))
1455 (set (match_dup 0)
1456 (lo_sum:SI (match_dup 0)
1457 (match_dup 1)))]
1458 ""
1459 [(set_attr "length" "8")
1460 (set_attr "type" "multi")])
1461
1462 (define_insn "movsi_high"
1463 [(set (match_operand:SI 0 "integer_register_operand" "=d")
1464 (high:SI (match_operand:SI 1 "int_2word_operand" "i")))]
1465 ""
1466 "sethi #hi(%1), %0"
1467 [(set_attr "type" "sethi")
1468 (set_attr "length" "4")])
1469
1470 (define_insn "movsi_lo_sum"
1471 [(set (match_operand:SI 0 "integer_register_operand" "+d")
1472 (lo_sum:SI (match_dup 0)
1473 (match_operand:SI 1 "int_2word_operand" "i")))]
1474 ""
1475 "setlo #lo(%1), %0"
1476 [(set_attr "type" "setlo")
1477 (set_attr "length" "4")])
1478
1479 (define_expand "movdi"
1480 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1481 (match_operand:DI 1 "general_operand" ""))]
1482 ""
1483 "
1484 {
1485 if (!reload_in_progress
1486 && !reload_completed
1487 && !register_operand (operands[0], DImode)
1488 && !reg_or_0_operand (operands[1], DImode))
1489 operands[1] = copy_to_mode_reg (DImode, operands[1]);
1490 }")
1491
1492 (define_insn "*movdi_double"
1493 [(set (match_operand:DI 0 "move_destination_operand" "=e,?h,??d,??f,R,?R,??m,??m,e,?h,??d,??f,?e,??d,?h,??f,R,m,e,??d,e,??d,?h,??f")
1494 (match_operand:DI 1 "move_source_operand" " e,h,d,f,e,h,d,f,R,R,m,m,h,f,e,d,GO,GO,GO,GO,nF,nF,GO,GO"))]
1495 "TARGET_DOUBLE
1496 && (register_operand (operands[0], DImode)
1497 || reg_or_0_operand (operands[1], DImode))"
1498 "* return output_move_double (operands, insn);"
1499 [(set_attr "length" "8,4,8,8,4,4,8,8,4,4,8,8,4,8,4,8,4,8,8,8,16,16,8,8")
1500 (set_attr "type" "multi,fdconv,multi,multi,gstore,fstore,gstore,fstore,gload,fload,gload,fload,movfg,movfg,movgf,movgf,gstore,gstore,multi,multi,multi,multi,movgf,movgf")])
1501
1502 (define_insn "*movdi_nodouble"
1503 [(set (match_operand:DI 0 "move_destination_operand" "=e,?h,??d,??f,R,?R,??m,??m,e,?h,??d,??f,?e,??d,?h,??f,R,m,e,??d,e,??d,?h,??f")
1504 (match_operand:DI 1 "move_source_operand" " e,h,d,f,e,h,d,f,R,R,m,m,h,f,e,d,GO,GO,GO,GO,nF,nF,GO,GO"))]
1505 "!TARGET_DOUBLE
1506 && (register_operand (operands[0], DImode)
1507 || reg_or_0_operand (operands[1], DImode))"
1508 "* return output_move_double (operands, insn);"
1509 [(set_attr "length" "8,8,8,8,4,4,8,8,4,4,8,8,8,8,8,8,4,8,8,8,16,16,8,8")
1510 (set_attr "type" "multi,multi,multi,multi,gstore,fstore,gstore,fstore,gload,fload,gload,fload,movfg,movfg,movgf,movgf,gstore,gstore,multi,multi,multi,multi,movgf,movgf")])
1511
1512 (define_split
1513 [(set (match_operand:DI 0 "register_operand" "")
1514 (match_operand:DI 1 "dbl_memory_two_insn_operand" ""))]
1515 "reload_completed"
1516 [(const_int 0)]
1517 "frv_split_double_load (operands[0], operands[1]);")
1518
1519 (define_split
1520 [(set (match_operand:DI 0 "odd_reg_operand" "")
1521 (match_operand:DI 1 "memory_operand" ""))]
1522 "reload_completed"
1523 [(const_int 0)]
1524 "frv_split_double_load (operands[0], operands[1]);")
1525
1526 (define_split
1527 [(set (match_operand:DI 0 "dbl_memory_two_insn_operand" "")
1528 (match_operand:DI 1 "reg_or_0_operand" ""))]
1529 "reload_completed"
1530 [(const_int 0)]
1531 "frv_split_double_store (operands[0], operands[1]);")
1532
1533 (define_split
1534 [(set (match_operand:DI 0 "memory_operand" "")
1535 (match_operand:DI 1 "odd_reg_operand" ""))]
1536 "reload_completed"
1537 [(const_int 0)]
1538 "frv_split_double_store (operands[0], operands[1]);")
1539
1540 (define_split
1541 [(set (match_operand:DI 0 "register_operand" "")
1542 (match_operand:DI 1 "register_operand" ""))]
1543 "reload_completed
1544 && (odd_reg_operand (operands[0], DImode)
1545 || odd_reg_operand (operands[1], DImode)
1546 || (integer_register_operand (operands[0], DImode)
1547 && integer_register_operand (operands[1], DImode))
1548 || (!TARGET_DOUBLE
1549 && fpr_operand (operands[0], DImode)
1550 && fpr_operand (operands[1], DImode)))"
1551 [(set (match_dup 2) (match_dup 4))
1552 (set (match_dup 3) (match_dup 5))]
1553 "
1554 {
1555 rtx op0 = operands[0];
1556 rtx op0_low = gen_lowpart (SImode, op0);
1557 rtx op0_high = gen_highpart (SImode, op0);
1558 rtx op1 = operands[1];
1559 rtx op1_low = gen_lowpart (SImode, op1);
1560 rtx op1_high = gen_highpart (SImode, op1);
1561
1562 /* We normally copy the low-numbered register first. However, if the first
1563 register operand 0 is the same as the second register of operand 1, we
1564 must copy in the opposite order. */
1565
1566 if (REGNO (op0_high) == REGNO (op1_low))
1567 {
1568 operands[2] = op0_low;
1569 operands[3] = op0_high;
1570 operands[4] = op1_low;
1571 operands[5] = op1_high;
1572 }
1573 else
1574 {
1575 operands[2] = op0_high;
1576 operands[3] = op0_low;
1577 operands[4] = op1_high;
1578 operands[5] = op1_low;
1579 }
1580 }")
1581
1582 (define_split
1583 [(set (match_operand:DI 0 "register_operand" "")
1584 (match_operand:DI 1 "const_int_operand" ""))]
1585 "reload_completed"
1586 [(set (match_dup 2) (match_dup 4))
1587 (set (match_dup 3) (match_dup 1))]
1588 "
1589 {
1590 rtx op0 = operands[0];
1591 rtx op1 = operands[1];
1592
1593 operands[2] = gen_highpart (SImode, op0);
1594 operands[3] = gen_lowpart (SImode, op0);
1595 operands[4] = GEN_INT ((INTVAL (op1) < 0) ? -1 : 0);
1596 }")
1597
1598 (define_split
1599 [(set (match_operand:DI 0 "register_operand" "")
1600 (match_operand:DI 1 "const_double_operand" ""))]
1601 "reload_completed"
1602 [(set (match_dup 2) (match_dup 4))
1603 (set (match_dup 3) (match_dup 5))]
1604 "
1605 {
1606 rtx op0 = operands[0];
1607 rtx op1 = operands[1];
1608
1609 operands[2] = gen_highpart (SImode, op0);
1610 operands[3] = gen_lowpart (SImode, op0);
1611 operands[4] = GEN_INT (CONST_DOUBLE_HIGH (op1));
1612 operands[5] = GEN_INT (CONST_DOUBLE_LOW (op1));
1613 }")
1614
1615 ;; Floating Point Moves
1616 ;;
1617 ;; Note - Patterns for SF mode moves are compulsory, but
1618 ;; patterns for DF are optional, as GCC can synthesize them.
1619
1620 (define_expand "movsf"
1621 [(set (match_operand:SF 0 "general_operand" "")
1622 (match_operand:SF 1 "general_operand" ""))]
1623 ""
1624 "
1625 {
1626 if (!reload_in_progress
1627 && !reload_completed
1628 && !register_operand (operands[0], SFmode)
1629 && !reg_or_0_operand (operands[1], SFmode))
1630 operands[1] = copy_to_mode_reg (SFmode, operands[1]);
1631 }")
1632
1633 (define_split
1634 [(set (match_operand:SF 0 "integer_register_operand" "")
1635 (match_operand:SF 1 "int_2word_operand" ""))]
1636 "reload_completed"
1637 [(set (match_dup 0)
1638 (high:SF (match_dup 1)))
1639 (set (match_dup 0)
1640 (lo_sum:SF (match_dup 0)
1641 (match_dup 1)))]
1642 "")
1643
1644 (define_insn "*movsf_load_has_fprs"
1645 [(set (match_operand:SF 0 "register_operand" "=f,d")
1646 (match_operand:SF 1 "frv_load_operand" "m,m"))]
1647 "TARGET_HAS_FPRS"
1648 "* return output_move_single (operands, insn);"
1649 [(set_attr "length" "4")
1650 (set_attr "type" "fload,gload")])
1651
1652 (define_insn "*movsf_internal_has_fprs"
1653 [(set (match_operand:SF 0 "move_destination_operand" "=f,f,m,m,?f,?d,?d,m,?d")
1654 (match_operand:SF 1 "move_source_operand" "f,OG,f,OG,d,f,d,d,F"))]
1655 "TARGET_HAS_FPRS
1656 && (register_operand (operands[0], SFmode) || reg_or_0_operand (operands[1], SFmode))"
1657 "* return output_move_single (operands, insn);"
1658 [(set_attr "length" "4,4,4,4,4,4,4,4,8")
1659 (set_attr "type" "fsconv,movgf,fstore,gstore,movgf,movfg,int,gstore,multi")])
1660
1661 ;; If we don't support the double instructions, prefer gprs over fprs, since it
1662 ;; will all be emulated
1663 (define_insn "*movsf_internal_no_fprs"
1664 [(set (match_operand:SF 0 "move_destination_operand" "=d,d,m,d,d")
1665 (match_operand:SF 1 "move_source_operand" " d,OG,dOG,m,F"))]
1666 "!TARGET_HAS_FPRS
1667 && (register_operand (operands[0], SFmode) || reg_or_0_operand (operands[1], SFmode))"
1668 "* return output_move_single (operands, insn);"
1669 [(set_attr "length" "4,4,4,4,8")
1670 (set_attr "type" "int,int,gstore,gload,multi")])
1671
1672 (define_insn "movsf_high"
1673 [(set (match_operand:SF 0 "integer_register_operand" "=d")
1674 (high:SF (match_operand:SF 1 "int_2word_operand" "i")))]
1675 ""
1676 "sethi #hi(%1), %0"
1677 [(set_attr "type" "sethi")
1678 (set_attr "length" "4")])
1679
1680 (define_insn "movsf_lo_sum"
1681 [(set (match_operand:SF 0 "integer_register_operand" "+d")
1682 (lo_sum:SF (match_dup 0)
1683 (match_operand:SF 1 "int_2word_operand" "i")))]
1684 ""
1685 "setlo #lo(%1), %0"
1686 [(set_attr "type" "setlo")
1687 (set_attr "length" "4")])
1688
1689 (define_expand "movdf"
1690 [(set (match_operand:DF 0 "nonimmediate_operand" "")
1691 (match_operand:DF 1 "general_operand" ""))]
1692 ""
1693 "
1694 {
1695 if (!reload_in_progress
1696 && !reload_completed
1697 && !register_operand (operands[0], DFmode)
1698 && !reg_or_0_operand (operands[1], DFmode))
1699 operands[1] = copy_to_mode_reg (DFmode, operands[1]);
1700 }")
1701
1702 (define_insn "*movdf_double"
1703 [(set (match_operand:DF 0 "move_destination_operand" "=h,?e,??f,??d,R,?R,??m,??m,h,?e,??f,??d,?h,??f,?e,??d,R,m,h,??f,e,??d,e,??d")
1704 (match_operand:DF 1 "move_source_operand" " h,e,f,d,h,e,f,d,R,R,m,m,e,d,h,f,GO,GO,GO,GO,GO,GO,F,F"))]
1705 "TARGET_DOUBLE
1706 && (register_operand (operands[0], DFmode)
1707 || reg_or_0_operand (operands[1], DFmode))"
1708 "* return output_move_double (operands, insn);"
1709 [(set_attr "length" "4,8,8,8,4,4,8,8,4,4,8,8,4,8,4,8,4,8,8,8,8,8,16,16")
1710 (set_attr "type" "fdconv,multi,multi,multi,fstore,gstore,fstore,gstore,fload,gload,fload,gload,movgf,movgf,movfg,movfg,gstore,gstore,movgf,movgf,multi,multi,multi,multi")])
1711
1712 ;; If we don't support the double instructions, prefer gprs over fprs, since it
1713 ;; will all be emulated
1714 (define_insn "*movdf_nodouble"
1715 [(set (match_operand:DF 0 "move_destination_operand" "=e,?h,??d,??f,R,?R,??m,??m,e,?h,??d,??f,?e,??d,?h,??f,R,m,e,??d,e,??d,?h,??f")
1716 (match_operand:DF 1 "move_source_operand" " e,h,d,f,e,h,d,f,R,R,m,m,h,f,e,d,GO,GO,GO,GO,nF,nF,GO,GO"))]
1717 "!TARGET_DOUBLE
1718 && (register_operand (operands[0], DFmode)
1719 || reg_or_0_operand (operands[1], DFmode))"
1720 "* return output_move_double (operands, insn);"
1721 [(set_attr "length" "8,8,8,8,4,4,8,8,4,4,8,8,8,8,8,8,4,8,8,8,16,16,8,8")
1722 (set_attr "type" "multi,multi,multi,multi,gstore,fstore,gstore,fstore,gload,fload,gload,fload,movfg,movfg,movgf,movgf,gstore,gstore,multi,multi,multi,multi,movgf,movgf")])
1723
1724 (define_split
1725 [(set (match_operand:DF 0 "register_operand" "")
1726 (match_operand:DF 1 "dbl_memory_two_insn_operand" ""))]
1727 "reload_completed"
1728 [(const_int 0)]
1729 "frv_split_double_load (operands[0], operands[1]);")
1730
1731 (define_split
1732 [(set (match_operand:DF 0 "odd_reg_operand" "")
1733 (match_operand:DF 1 "memory_operand" ""))]
1734 "reload_completed"
1735 [(const_int 0)]
1736 "frv_split_double_load (operands[0], operands[1]);")
1737
1738 (define_split
1739 [(set (match_operand:DF 0 "dbl_memory_two_insn_operand" "")
1740 (match_operand:DF 1 "reg_or_0_operand" ""))]
1741 "reload_completed"
1742 [(const_int 0)]
1743 "frv_split_double_store (operands[0], operands[1]);")
1744
1745 (define_split
1746 [(set (match_operand:DF 0 "memory_operand" "")
1747 (match_operand:DF 1 "odd_reg_operand" ""))]
1748 "reload_completed"
1749 [(const_int 0)]
1750 "frv_split_double_store (operands[0], operands[1]);")
1751
1752 (define_split
1753 [(set (match_operand:DF 0 "register_operand" "")
1754 (match_operand:DF 1 "register_operand" ""))]
1755 "reload_completed
1756 && (odd_reg_operand (operands[0], DFmode)
1757 || odd_reg_operand (operands[1], DFmode)
1758 || (integer_register_operand (operands[0], DFmode)
1759 && integer_register_operand (operands[1], DFmode))
1760 || (!TARGET_DOUBLE
1761 && fpr_operand (operands[0], DFmode)
1762 && fpr_operand (operands[1], DFmode)))"
1763 [(set (match_dup 2) (match_dup 4))
1764 (set (match_dup 3) (match_dup 5))]
1765 "
1766 {
1767 rtx op0 = operands[0];
1768 rtx op0_low = gen_lowpart (SImode, op0);
1769 rtx op0_high = gen_highpart (SImode, op0);
1770 rtx op1 = operands[1];
1771 rtx op1_low = gen_lowpart (SImode, op1);
1772 rtx op1_high = gen_highpart (SImode, op1);
1773
1774 /* We normally copy the low-numbered register first. However, if the first
1775 register operand 0 is the same as the second register of operand 1, we
1776 must copy in the opposite order. */
1777
1778 if (REGNO (op0_high) == REGNO (op1_low))
1779 {
1780 operands[2] = op0_low;
1781 operands[3] = op0_high;
1782 operands[4] = op1_low;
1783 operands[5] = op1_high;
1784 }
1785 else
1786 {
1787 operands[2] = op0_high;
1788 operands[3] = op0_low;
1789 operands[4] = op1_high;
1790 operands[5] = op1_low;
1791 }
1792 }")
1793
1794 (define_split
1795 [(set (match_operand:DF 0 "register_operand" "")
1796 (match_operand:DF 1 "const_int_operand" ""))]
1797 "reload_completed"
1798 [(set (match_dup 2) (match_dup 4))
1799 (set (match_dup 3) (match_dup 1))]
1800 "
1801 {
1802 rtx op0 = operands[0];
1803 rtx op1 = operands[1];
1804
1805 operands[2] = gen_highpart (SImode, op0);
1806 operands[3] = gen_lowpart (SImode, op0);
1807 operands[4] = GEN_INT ((INTVAL (op1) < 0) ? -1 : 0);
1808 }")
1809
1810 (define_split
1811 [(set (match_operand:DF 0 "register_operand" "")
1812 (match_operand:DF 1 "const_double_operand" ""))]
1813 "reload_completed"
1814 [(set (match_dup 2) (match_dup 4))
1815 (set (match_dup 3) (match_dup 5))]
1816 "
1817 {
1818 rtx op0 = operands[0];
1819 rtx op1 = operands[1];
1820 REAL_VALUE_TYPE rv;
1821 long l[2];
1822
1823 REAL_VALUE_FROM_CONST_DOUBLE (rv, op1);
1824 REAL_VALUE_TO_TARGET_DOUBLE (rv, l);
1825
1826 operands[2] = gen_highpart (SImode, op0);
1827 operands[3] = gen_lowpart (SImode, op0);
1828 operands[4] = GEN_INT (l[0]);
1829 operands[5] = GEN_INT (l[1]);
1830 }")
1831
1832 ;; String/block move insn.
1833 ;; Argument 0 is the destination
1834 ;; Argument 1 is the source
1835 ;; Argument 2 is the length
1836 ;; Argument 3 is the alignment
1837
1838 (define_expand "movstrsi"
1839 [(parallel [(set (match_operand:BLK 0 "" "")
1840 (match_operand:BLK 1 "" ""))
1841 (use (match_operand:SI 2 "" ""))
1842 (use (match_operand:SI 3 "" ""))])]
1843 ""
1844 "
1845 {
1846 if (frv_expand_block_move (operands))
1847 DONE;
1848 else
1849 FAIL;
1850 }")
1851
1852 ;; String/block clear insn.
1853 ;; Argument 0 is the destination
1854 ;; Argument 1 is the length
1855 ;; Argument 2 is the alignment
1856
1857 (define_expand "clrstrsi"
1858 [(parallel [(set (match_operand:BLK 0 "" "")
1859 (const_int 0))
1860 (use (match_operand:SI 1 "" ""))
1861 (use (match_operand:SI 2 "" ""))])]
1862 ""
1863 "
1864 {
1865 if (frv_expand_block_clear (operands))
1866 DONE;
1867 else
1868 FAIL;
1869 }")
1870
1871 \f
1872 ;; ::::::::::::::::::::
1873 ;; ::
1874 ;; :: Reload CC registers
1875 ;; ::
1876 ;; ::::::::::::::::::::
1877
1878 ;; Use as a define_expand so that cse/gcse/combine can't accidentally
1879 ;; create movcc insns.
1880
1881 (define_expand "movcc"
1882 [(parallel [(set (match_operand:CC 0 "move_destination_operand" "")
1883 (match_operand:CC 1 "move_source_operand" ""))
1884 (clobber (match_dup 2))])]
1885 ""
1886 "
1887 {
1888 if (! reload_in_progress && ! reload_completed)
1889 FAIL;
1890
1891 operands[2] = gen_rtx_REG (CC_CCRmode, ICR_TEMP);
1892 }")
1893
1894 (define_insn "*internal_movcc"
1895 [(set (match_operand:CC 0 "move_destination_operand" "=t,d,d,m,d")
1896 (match_operand:CC 1 "move_source_operand" "d,d,m,d,t"))
1897 (clobber (match_scratch:CC_CCR 2 "=X,X,X,X,&v"))]
1898 "reload_in_progress || reload_completed"
1899 "@
1900 cmpi %1, #0, %0
1901 mov %1, %0
1902 ld%I1%U1 %M1, %0
1903 st%I0%U0 %1, %M0
1904 #"
1905 [(set_attr "length" "4,4,4,4,20")
1906 (set_attr "type" "int,int,gload,gstore,multi")])
1907
1908 ;; To move an ICC value to a GPR for a signed comparison, we create a value
1909 ;; that when compared to 0, sets the N and Z flags appropriately (we don't care
1910 ;; about the V and C flags, since these comparisons are signed).
1911
1912 (define_split
1913 [(set (match_operand:CC 0 "integer_register_operand" "")
1914 (match_operand:CC 1 "icc_operand" ""))
1915 (clobber (match_operand:CC_CCR 2 "icr_operand" ""))]
1916 "reload_in_progress || reload_completed"
1917 [(match_dup 3)]
1918 "
1919 {
1920 rtx dest = simplify_gen_subreg (SImode, operands[0], CCmode, 0);
1921 rtx icc = operands[1];
1922 rtx icr = operands[2];
1923
1924 start_sequence ();
1925
1926 emit_insn (gen_rtx_SET (VOIDmode, icr,
1927 gen_rtx_LT (CC_CCRmode, icc, const0_rtx)));
1928
1929 emit_insn (gen_movsi (dest, const1_rtx));
1930
1931 emit_insn (gen_rtx_COND_EXEC (VOIDmode,
1932 gen_rtx_NE (CC_CCRmode, icr, const0_rtx),
1933 gen_rtx_SET (VOIDmode, dest,
1934 gen_rtx_NEG (SImode, dest))));
1935
1936 emit_insn (gen_rtx_SET (VOIDmode, icr,
1937 gen_rtx_EQ (CC_CCRmode, icc, const0_rtx)));
1938
1939 emit_insn (gen_rtx_COND_EXEC (VOIDmode,
1940 gen_rtx_NE (CC_CCRmode, icr, const0_rtx),
1941 gen_rtx_SET (VOIDmode, dest, const0_rtx)));
1942
1943 operands[3] = get_insns ();
1944 end_sequence ();
1945 }")
1946
1947 (define_expand "reload_incc"
1948 [(parallel [(set (match_operand:CC 2 "integer_register_operand" "=&d")
1949 (match_operand:CC 1 "memory_operand" "m"))
1950 (clobber (match_scratch:CC_CCR 3 ""))])
1951 (parallel [(set (match_operand:CC 0 "icc_operand" "=t")
1952 (match_dup 2))
1953 (clobber (match_scratch:CC_CCR 4 ""))])]
1954 ""
1955 "")
1956
1957 (define_expand "reload_outcc"
1958 [(parallel [(set (match_operand:CC 2 "integer_register_operand" "=&d")
1959 (match_operand:CC 1 "icc_operand" "t"))
1960 (clobber (match_dup 3))])
1961 (parallel [(set (match_operand:CC 0 "memory_operand" "=m")
1962 (match_dup 2))
1963 (clobber (match_scratch:CC_CCR 4 ""))])]
1964 ""
1965 "operands[3] = gen_rtx_REG (CC_CCRmode, ICR_TEMP);")
1966
1967 ;; Reload CC_UNSmode for unsigned integer comparisons
1968 ;; Use define_expand so that cse/gcse/combine can't create movcc_uns insns
1969
1970 (define_expand "movcc_uns"
1971 [(parallel [(set (match_operand:CC_UNS 0 "move_destination_operand" "")
1972 (match_operand:CC_UNS 1 "move_source_operand" ""))
1973 (clobber (match_dup 2))])]
1974 ""
1975 "
1976 {
1977 if (! reload_in_progress && ! reload_completed)
1978 FAIL;
1979 operands[2] = gen_rtx_REG (CC_CCRmode, ICR_TEMP);
1980 }")
1981
1982 (define_insn "*internal_movcc_uns"
1983 [(set (match_operand:CC_UNS 0 "move_destination_operand" "=t,d,d,m,d")
1984 (match_operand:CC_UNS 1 "move_source_operand" "d,d,m,d,t"))
1985 (clobber (match_scratch:CC_CCR 2 "=X,X,X,X,&v"))]
1986 "reload_in_progress || reload_completed"
1987 "@
1988 cmpi %1, #1, %0
1989 mov %1, %0
1990 ld%I1%U1 %M1, %0
1991 st%I0%U0 %1, %M0
1992 #"
1993 [(set_attr "length" "4,4,4,4,20")
1994 (set_attr "type" "int,int,gload,gstore,multi")])
1995
1996 ;; To move an ICC value to a GPR for an unsigned comparison, we create a value
1997 ;; that when compared to 1, sets the Z, V, and C flags appropriately (we don't
1998 ;; care about the N flag, since these comparisons are unsigned).
1999
2000 (define_split
2001 [(set (match_operand:CC_UNS 0 "integer_register_operand" "")
2002 (match_operand:CC_UNS 1 "icc_operand" ""))
2003 (clobber (match_operand:CC_CCR 2 "icr_operand" ""))]
2004 "reload_in_progress || reload_completed"
2005 [(match_dup 3)]
2006 "
2007 {
2008 rtx dest = simplify_gen_subreg (SImode, operands[0], CC_UNSmode, 0);
2009 rtx icc = operands[1];
2010 rtx icr = operands[2];
2011
2012 start_sequence ();
2013
2014 emit_insn (gen_rtx_SET (VOIDmode, icr,
2015 gen_rtx_GTU (CC_CCRmode, icc, const0_rtx)));
2016
2017 emit_insn (gen_movsi (dest, const1_rtx));
2018
2019 emit_insn (gen_rtx_COND_EXEC (VOIDmode,
2020 gen_rtx_NE (CC_CCRmode, icr, const0_rtx),
2021 gen_addsi3 (dest, dest, dest)));
2022
2023 emit_insn (gen_rtx_SET (VOIDmode, icr,
2024 gen_rtx_LTU (CC_CCRmode, icc, const0_rtx)));
2025
2026 emit_insn (gen_rtx_COND_EXEC (VOIDmode,
2027 gen_rtx_NE (CC_CCRmode, icr, const0_rtx),
2028 gen_rtx_SET (VOIDmode, dest, const0_rtx)));
2029
2030 operands[3] = get_insns ();
2031 end_sequence ();
2032 }")
2033
2034 (define_expand "reload_incc_uns"
2035 [(parallel [(set (match_operand:CC_UNS 2 "integer_register_operand" "=&d")
2036 (match_operand:CC_UNS 1 "memory_operand" "m"))
2037 (clobber (match_scratch:CC_CCR 3 ""))])
2038 (parallel [(set (match_operand:CC_UNS 0 "icc_operand" "=t")
2039 (match_dup 2))
2040 (clobber (match_scratch:CC_CCR 4 ""))])]
2041 ""
2042 "")
2043
2044 (define_expand "reload_outcc_uns"
2045 [(parallel [(set (match_operand:CC_UNS 2 "integer_register_operand" "=&d")
2046 (match_operand:CC_UNS 1 "icc_operand" "t"))
2047 (clobber (match_dup 3))])
2048 (parallel [(set (match_operand:CC_UNS 0 "memory_operand" "=m")
2049 (match_dup 2))
2050 (clobber (match_scratch:CC_CCR 4 ""))])]
2051 ""
2052 "operands[3] = gen_rtx_REG (CC_CCRmode, ICR_TEMP);")
2053
2054 ;; Reload CC_FPmode for floating point comparisons
2055 ;; We use a define_expand here so that cse/gcse/combine can't accidentally
2056 ;; create movcc insns. If this was a named define_insn, we would not be able
2057 ;; to make it conditional on reload.
2058
2059 (define_expand "movcc_fp"
2060 [(set (match_operand:CC_FP 0 "move_destination_operand" "")
2061 (match_operand:CC_FP 1 "move_source_operand" ""))]
2062 "TARGET_HAS_FPRS"
2063 "
2064 {
2065 if (! reload_in_progress && ! reload_completed)
2066 FAIL;
2067 }")
2068
2069 (define_insn "*movcc_fp_internal"
2070 [(set (match_operand:CC_FP 0 "move_destination_operand" "=d,d,d,m")
2071 (match_operand:CC_FP 1 "move_source_operand" "u,d,m,d"))]
2072 "TARGET_HAS_FPRS && (reload_in_progress || reload_completed)"
2073 "@
2074 #
2075 mov %1, %0
2076 ld%I1%U1 %M1, %0
2077 st%I0%U0 %1, %M0"
2078 [(set_attr "length" "12,4,4,4")
2079 (set_attr "type" "multi,int,gload,gstore")])
2080
2081
2082 (define_expand "reload_incc_fp"
2083 [(match_operand:CC_FP 0 "fcc_operand" "=u")
2084 (match_operand:CC_FP 1 "memory_operand" "m")
2085 (match_operand:TI 2 "integer_register_operand" "=&d")]
2086 "TARGET_HAS_FPRS"
2087 "
2088 {
2089 rtx cc_op2 = simplify_gen_subreg (CC_FPmode, operands[2], TImode, 0);
2090 rtx int_op2 = simplify_gen_subreg (SImode, operands[2], TImode, 0);
2091 rtx temp1 = simplify_gen_subreg (SImode, operands[2], TImode, 4);
2092 rtx temp2 = simplify_gen_subreg (SImode, operands[2], TImode, 8);
2093 int shift = CC_SHIFT_RIGHT (REGNO (operands[0]));
2094 HOST_WIDE_INT mask;
2095
2096 emit_insn (gen_movcc_fp (cc_op2, operands[1]));
2097 if (shift)
2098 emit_insn (gen_ashlsi3 (int_op2, int_op2, GEN_INT (shift)));
2099
2100 mask = ~ ((HOST_WIDE_INT)CC_MASK << shift);
2101 emit_insn (gen_movsi (temp1, GEN_INT (mask)));
2102 emit_insn (gen_update_fcc (operands[0], int_op2, temp1, temp2));
2103 DONE;
2104 }")
2105
2106 (define_expand "reload_outcc_fp"
2107 [(set (match_operand:CC_FP 2 "integer_register_operand" "=&d")
2108 (match_operand:CC_FP 1 "fcc_operand" "u"))
2109 (set (match_operand:CC_FP 0 "memory_operand" "=m")
2110 (match_dup 2))]
2111 "TARGET_HAS_FPRS"
2112 "")
2113
2114 ;; Convert a FCC value to gpr
2115 (define_insn "read_fcc"
2116 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2117 (unspec:SI [(match_operand:CC_FP 1 "fcc_operand" "u")]
2118 UNSPEC_CC_TO_GPR))]
2119 "TARGET_HAS_FPRS"
2120 "movsg ccr, %0"
2121 [(set_attr "type" "spr")
2122 (set_attr "length" "4")])
2123
2124 (define_split
2125 [(set (match_operand:CC_FP 0 "integer_register_operand" "")
2126 (match_operand:CC_FP 1 "fcc_operand" ""))]
2127 "reload_completed && TARGET_HAS_FPRS"
2128 [(match_dup 2)]
2129 "
2130 {
2131 rtx int_op0 = simplify_gen_subreg (SImode, operands[0], CC_FPmode, 0);
2132 int shift = CC_SHIFT_RIGHT (REGNO (operands[1]));
2133
2134 start_sequence ();
2135
2136 emit_insn (gen_read_fcc (int_op0, operands[1]));
2137 if (shift)
2138 emit_insn (gen_lshrsi3 (int_op0, int_op0, GEN_INT (shift)));
2139
2140 emit_insn (gen_andsi3 (int_op0, int_op0, GEN_INT (CC_MASK)));
2141
2142 operands[2] = get_insns ();
2143 end_sequence ();
2144 }")
2145
2146 ;; Move a gpr value to FCC.
2147 ;; Operand0 = FCC
2148 ;; Operand1 = reloaded value shifted appropriately
2149 ;; Operand2 = mask to eliminate current register
2150 ;; Operand3 = temporary to load/store ccr
2151 (define_insn "update_fcc"
2152 [(set (match_operand:CC_FP 0 "fcc_operand" "=u")
2153 (unspec:CC_FP [(match_operand:SI 1 "integer_register_operand" "d")
2154 (match_operand:SI 2 "integer_register_operand" "d")]
2155 UNSPEC_GPR_TO_CC))
2156 (clobber (match_operand:SI 3 "integer_register_operand" "=&d"))]
2157 "TARGET_HAS_FPRS"
2158 "movsg ccr, %3\;and %2, %3, %3\;or %1, %3, %3\;movgs %3, ccr"
2159 [(set_attr "type" "multi")
2160 (set_attr "length" "16")])
2161
2162 ;; Reload CC_CCRmode for conditional execution registers
2163 (define_insn "movcc_ccr"
2164 [(set (match_operand:CC_CCR 0 "move_destination_operand" "=d,d,d,m,v,?w,C,d")
2165 (match_operand:CC_CCR 1 "move_source_operand" "C,d,m,d,n,n,C,L"))]
2166 ""
2167 "@
2168 #
2169 mov %1, %0
2170 ld%I1%U1 %M1, %0
2171 st%I0%U0 %1, %M0
2172 #
2173 #
2174 orcr %1, %1, %0
2175 setlos #%1, %0"
2176 [(set_attr "length" "8,4,4,4,8,12,4,4")
2177 (set_attr "type" "multi,int,gload,gstore,multi,multi,ccr,int")])
2178
2179 (define_expand "reload_incc_ccr"
2180 [(match_operand:CC_CCR 0 "cr_operand" "=C")
2181 (match_operand:CC_CCR 1 "memory_operand" "m")
2182 (match_operand:CC_CCR 2 "integer_register_operand" "=&d")]
2183 ""
2184 "
2185 {
2186 rtx icc = gen_rtx_REG (CCmode, ICC_TEMP);
2187 rtx int_op2 = simplify_gen_subreg (SImode, operands[2], CC_CCRmode, 0);
2188 rtx icr = (ICR_P (REGNO (operands[0]))
2189 ? operands[0] : gen_rtx_REG (CC_CCRmode, ICR_TEMP));
2190
2191 emit_insn (gen_movcc_ccr (operands[2], operands[1]));
2192 emit_insn (gen_cmpsi_cc (icc, int_op2, const0_rtx));
2193 emit_insn (gen_movcc_ccr (icr, gen_rtx_NE (CC_CCRmode, icc, const0_rtx)));
2194
2195 if (! ICR_P (REGNO (operands[0])))
2196 emit_insn (gen_movcc_ccr (operands[0], icr));
2197
2198 DONE;
2199 }")
2200
2201 (define_expand "reload_outcc_ccr"
2202 [(set (match_operand:CC_CCR 2 "integer_register_operand" "=&d")
2203 (match_operand:CC_CCR 1 "cr_operand" "C"))
2204 (set (match_operand:CC_CCR 0 "memory_operand" "=m")
2205 (match_dup 2))]
2206 ""
2207 "")
2208
2209 (define_split
2210 [(set (match_operand:CC_CCR 0 "integer_register_operand" "")
2211 (match_operand:CC_CCR 1 "cr_operand" ""))]
2212 "reload_completed"
2213 [(match_dup 2)]
2214 "
2215 {
2216 rtx int_op0 = simplify_gen_subreg (SImode, operands[0], CC_CCRmode, 0);
2217
2218 start_sequence ();
2219 emit_move_insn (operands[0], const1_rtx);
2220 emit_insn (gen_rtx_COND_EXEC (VOIDmode,
2221 gen_rtx_EQ (CC_CCRmode,
2222 operands[1],
2223 const0_rtx),
2224 gen_rtx_SET (VOIDmode, int_op0,
2225 const0_rtx)));
2226
2227 operands[2] = get_insns ();
2228 end_sequence ();
2229 }")
2230
2231 (define_split
2232 [(set (match_operand:CC_CCR 0 "cr_operand" "")
2233 (match_operand:CC_CCR 1 "const_int_operand" ""))]
2234 "reload_completed"
2235 [(match_dup 2)]
2236 "
2237 {
2238 rtx icc = gen_rtx_REG (CCmode, ICC_TEMP);
2239 rtx r0 = gen_rtx_REG (SImode, GPR_FIRST);
2240 rtx icr = (ICR_P (REGNO (operands[0]))
2241 ? operands[0] : gen_rtx_REG (CC_CCRmode, ICR_TEMP));
2242
2243 start_sequence ();
2244
2245 emit_insn (gen_cmpsi_cc (icc, r0, const0_rtx));
2246
2247 emit_insn (gen_movcc_ccr (icr,
2248 gen_rtx_fmt_ee (((INTVAL (operands[1]) == 0)
2249 ? EQ : NE), CC_CCRmode,
2250 r0, const0_rtx)));
2251
2252 if (! ICR_P (REGNO (operands[0])))
2253 emit_insn (gen_movcc_ccr (operands[0], icr));
2254
2255 operands[2] = get_insns ();
2256 end_sequence ();
2257 }")
2258
2259 \f
2260 ;; ::::::::::::::::::::
2261 ;; ::
2262 ;; :: Conversions
2263 ;; ::
2264 ;; ::::::::::::::::::::
2265
2266 ;; Signed conversions from a smaller integer to a larger integer
2267 ;;
2268 ;; These operations are optional. If they are not
2269 ;; present GCC will synthesize them for itself
2270 ;; Even though frv does not provide these instructions, we define them
2271 ;; to allow load + sign extend to be collapsed together
2272 (define_insn "extendqihi2"
2273 [(set (match_operand:HI 0 "integer_register_operand" "=d,d")
2274 (sign_extend:HI (match_operand:QI 1 "gpr_or_memory_operand" "d,m")))]
2275 ""
2276 "@
2277 #
2278 ldsb%I1%U1 %M1,%0"
2279 [(set_attr "length" "8,4")
2280 (set_attr "type" "multi,gload")])
2281
2282 (define_split
2283 [(set (match_operand:HI 0 "integer_register_operand" "")
2284 (sign_extend:HI (match_operand:QI 1 "integer_register_operand" "")))]
2285 "reload_completed"
2286 [(match_dup 2)
2287 (match_dup 3)]
2288 "
2289 {
2290 rtx op0 = gen_lowpart (SImode, operands[0]);
2291 rtx op1 = gen_lowpart (SImode, operands[1]);
2292 rtx shift = GEN_INT (24);
2293
2294 operands[2] = gen_ashlsi3 (op0, op1, shift);
2295 operands[3] = gen_ashrsi3 (op0, op0, shift);
2296 }")
2297
2298 (define_insn "extendqisi2"
2299 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
2300 (sign_extend:SI (match_operand:QI 1 "gpr_or_memory_operand" "d,m")))]
2301 ""
2302 "@
2303 #
2304 ldsb%I1%U1 %M1,%0"
2305 [(set_attr "length" "8,4")
2306 (set_attr "type" "multi,gload")])
2307
2308 (define_split
2309 [(set (match_operand:SI 0 "integer_register_operand" "")
2310 (sign_extend:SI (match_operand:QI 1 "integer_register_operand" "")))]
2311 "reload_completed"
2312 [(match_dup 2)
2313 (match_dup 3)]
2314 "
2315 {
2316 rtx op0 = gen_lowpart (SImode, operands[0]);
2317 rtx op1 = gen_lowpart (SImode, operands[1]);
2318 rtx shift = GEN_INT (24);
2319
2320 operands[2] = gen_ashlsi3 (op0, op1, shift);
2321 operands[3] = gen_ashrsi3 (op0, op0, shift);
2322 }")
2323
2324 ;;(define_insn "extendqidi2"
2325 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2326 ;; (sign_extend:DI (match_operand:QI 1 "general_operand" "g")))]
2327 ;; ""
2328 ;; "extendqihi2 %0,%1"
2329 ;; [(set_attr "length" "4")])
2330
2331 (define_insn "extendhisi2"
2332 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
2333 (sign_extend:SI (match_operand:HI 1 "gpr_or_memory_operand" "d,m")))]
2334 ""
2335 "@
2336 #
2337 ldsh%I1%U1 %M1,%0"
2338 [(set_attr "length" "8,4")
2339 (set_attr "type" "multi,gload")])
2340
2341 (define_split
2342 [(set (match_operand:SI 0 "integer_register_operand" "")
2343 (sign_extend:SI (match_operand:HI 1 "integer_register_operand" "")))]
2344 "reload_completed"
2345 [(match_dup 2)
2346 (match_dup 3)]
2347 "
2348 {
2349 rtx op0 = gen_lowpart (SImode, operands[0]);
2350 rtx op1 = gen_lowpart (SImode, operands[1]);
2351 rtx shift = GEN_INT (16);
2352
2353 operands[2] = gen_ashlsi3 (op0, op1, shift);
2354 operands[3] = gen_ashrsi3 (op0, op0, shift);
2355 }")
2356
2357 ;;(define_insn "extendhidi2"
2358 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2359 ;; (sign_extend:DI (match_operand:HI 1 "general_operand" "g")))]
2360 ;; ""
2361 ;; "extendhihi2 %0,%1"
2362 ;; [(set_attr "length" "4")])
2363 ;;
2364 ;;(define_insn "extendsidi2"
2365 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2366 ;; (sign_extend:DI (match_operand:SI 1 "general_operand" "g")))]
2367 ;; ""
2368 ;; "extendsidi2 %0,%1"
2369 ;; [(set_attr "length" "4")])
2370
2371 ;; Unsigned conversions from a smaller integer to a larger integer
2372 (define_insn "zero_extendqihi2"
2373 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d")
2374 (zero_extend:HI
2375 (match_operand:QI 1 "gpr_or_memory_operand" "d,L,m")))]
2376 ""
2377 "@
2378 andi %1,#0xff,%0
2379 setlos %1,%0
2380 ldub%I1%U1 %M1,%0"
2381 [(set_attr "length" "4")
2382 (set_attr "type" "int,int,gload")])
2383
2384 (define_insn "zero_extendqisi2"
2385 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d")
2386 (zero_extend:SI
2387 (match_operand:QI 1 "gpr_or_memory_operand" "d,L,m")))]
2388 ""
2389 "@
2390 andi %1,#0xff,%0
2391 setlos %1,%0
2392 ldub%I1%U1 %M1,%0"
2393 [(set_attr "length" "4")
2394 (set_attr "type" "int,int,gload")])
2395
2396 ;;(define_insn "zero_extendqidi2"
2397 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2398 ;; (zero_extend:DI (match_operand:QI 1 "general_operand" "g")))]
2399 ;; ""
2400 ;; "zero_extendqihi2 %0,%1"
2401 ;; [(set_attr "length" "4")])
2402
2403 ;; Do not set the type for the sethi to "sethi", since the scheduler will think
2404 ;; the sethi takes 0 cycles as part of allowing sethi/setlo to be in the same
2405 ;; VLIW instruction.
2406 (define_insn "zero_extendhisi2"
2407 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
2408 (zero_extend:SI (match_operand:HI 1 "gpr_or_memory_operand" "0,m")))]
2409 ""
2410 "@
2411 sethi #hi(#0),%0
2412 lduh%I1%U1 %M1,%0"
2413 [(set_attr "length" "4")
2414 (set_attr "type" "int,gload")])
2415
2416 ;;(define_insn "zero_extendhidi2"
2417 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2418 ;; (zero_extend:DI (match_operand:HI 1 "general_operand" "g")))]
2419 ;; ""
2420 ;; "zero_extendhihi2 %0,%1"
2421 ;; [(set_attr "length" "4")])
2422 ;;
2423 ;;(define_insn "zero_extendsidi2"
2424 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2425 ;; (zero_extend:DI (match_operand:SI 1 "general_operand" "g")))]
2426 ;; ""
2427 ;; "zero_extendsidi2 %0,%1"
2428 ;; [(set_attr "length" "4")])
2429 ;;
2430 ;;;; Convert between floating point types of different sizes.
2431 ;;
2432 ;;(define_insn "extendsfdf2"
2433 ;; [(set (match_operand:DF 0 "register_operand" "=r")
2434 ;; (float_extend:DF (match_operand:SF 1 "register_operand" "r")))]
2435 ;; ""
2436 ;; "extendsfdf2 %0,%1"
2437 ;; [(set_attr "length" "4")])
2438 ;;
2439 ;;(define_insn "truncdfsf2"
2440 ;; [(set (match_operand:SF 0 "register_operand" "=r")
2441 ;; (float_truncate:SF (match_operand:DF 1 "register_operand" "r")))]
2442 ;; ""
2443 ;; "truncdfsf2 %0,%1"
2444 ;; [(set_attr "length" "4")])
2445
2446 ;;;; Convert between signed integer types and floating point.
2447 (define_insn "floatsisf2"
2448 [(set (match_operand:SF 0 "fpr_operand" "=f")
2449 (float:SF (match_operand:SI 1 "fpr_operand" "f")))]
2450 "TARGET_HARD_FLOAT"
2451 "fitos %1,%0"
2452 [(set_attr "length" "4")
2453 (set_attr "type" "fsconv")])
2454
2455 (define_insn "floatsidf2"
2456 [(set (match_operand:DF 0 "fpr_operand" "=h")
2457 (float:DF (match_operand:SI 1 "fpr_operand" "f")))]
2458 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
2459 "fitod %1,%0"
2460 [(set_attr "length" "4")
2461 (set_attr "type" "fdconv")])
2462
2463 ;;(define_insn "floatdisf2"
2464 ;; [(set (match_operand:SF 0 "register_operand" "=r")
2465 ;; (float:SF (match_operand:DI 1 "register_operand" "r")))]
2466 ;; ""
2467 ;; "floatdisf2 %0,%1"
2468 ;; [(set_attr "length" "4")])
2469 ;;
2470 ;;(define_insn "floatdidf2"
2471 ;; [(set (match_operand:DF 0 "register_operand" "=r")
2472 ;; (float:DF (match_operand:DI 1 "register_operand" "r")))]
2473 ;; ""
2474 ;; "floatdidf2 %0,%1"
2475 ;; [(set_attr "length" "4")])
2476
2477 (define_insn "fix_truncsfsi2"
2478 [(set (match_operand:SI 0 "fpr_operand" "=f")
2479 (fix:SI (match_operand:SF 1 "fpr_operand" "f")))]
2480 "TARGET_HARD_FLOAT"
2481 "fstoi %1,%0"
2482 [(set_attr "length" "4")
2483 (set_attr "type" "fsconv")])
2484
2485 (define_insn "fix_truncdfsi2"
2486 [(set (match_operand:SI 0 "fpr_operand" "=f")
2487 (fix:SI (match_operand:DF 1 "fpr_operand" "h")))]
2488 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
2489 "fdtoi %1,%0"
2490 [(set_attr "length" "4")
2491 (set_attr "type" "fdconv")])
2492
2493 ;;(define_insn "fix_truncsfdi2"
2494 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2495 ;; (fix:DI (match_operand:SF 1 "register_operand" "r")))]
2496 ;; ""
2497 ;; "fix_truncsfdi2 %0,%1"
2498 ;; [(set_attr "length" "4")])
2499 ;;
2500 ;;(define_insn "fix_truncdfdi2"
2501 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2502 ;; (fix:DI (match_operand:DF 1 "register_operand" "r")))]
2503 ;; ""
2504 ;; "fix_truncdfdi2 %0,%1"
2505 ;; [(set_attr "length" "4")])
2506 ;;
2507 ;;;; Convert between unsigned integer types and floating point.
2508 ;;
2509 ;;(define_insn "floatunssisf2"
2510 ;; [(set (match_operand:SF 0 "register_operand" "=r")
2511 ;; (unsigned_float:SF (match_operand:SI 1 "register_operand" "r")))]
2512 ;; ""
2513 ;; "floatunssisf2 %0,%1"
2514 ;; [(set_attr "length" "4")])
2515 ;;
2516 ;;(define_insn "floatunssidf2"
2517 ;; [(set (match_operand:DF 0 "register_operand" "=r")
2518 ;; (unsigned_float:DF (match_operand:SI 1 "register_operand" "r")))]
2519 ;; ""
2520 ;; "floatunssidf2 %0,%1"
2521 ;; [(set_attr "length" "4")])
2522 ;;
2523 ;;(define_insn "floatunsdisf2"
2524 ;; [(set (match_operand:SF 0 "register_operand" "=r")
2525 ;; (unsigned_float:SF (match_operand:DI 1 "register_operand" "r")))]
2526 ;; ""
2527 ;; "floatunsdisf2 %0,%1"
2528 ;; [(set_attr "length" "4")])
2529 ;;
2530 ;;(define_insn "floatunsdidf2"
2531 ;; [(set (match_operand:DF 0 "register_operand" "=r")
2532 ;; (unsigned_float:DF (match_operand:DI 1 "register_operand" "r")))]
2533 ;; ""
2534 ;; "floatunsdidf2 %0,%1"
2535 ;; [(set_attr "length" "4")])
2536 ;;
2537 ;;(define_insn "fixuns_truncsfsi2"
2538 ;; [(set (match_operand:SI 0 "register_operand" "=r")
2539 ;; (unsigned_fix:SI (match_operand:SF 1 "register_operand" "r")))]
2540 ;; ""
2541 ;; "fixuns_truncsfsi2 %0,%1"
2542 ;; [(set_attr "length" "4")])
2543 ;;
2544 ;;(define_insn "fixuns_truncdfsi2"
2545 ;; [(set (match_operand:SI 0 "register_operand" "=r")
2546 ;; (unsigned_fix:SI (match_operand:DF 1 "register_operand" "r")))]
2547 ;; ""
2548 ;; "fixuns_truncdfsi2 %0,%1"
2549 ;; [(set_attr "length" "4")])
2550 ;;
2551 ;;(define_insn "fixuns_truncsfdi2"
2552 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2553 ;; (unsigned_fix:DI (match_operand:SF 1 "register_operand" "r")))]
2554 ;; ""
2555 ;; "fixuns_truncsfdi2 %0,%1"
2556 ;; [(set_attr "length" "4")])
2557 ;;
2558 ;;(define_insn "fixuns_truncdfdi2"
2559 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2560 ;; (unsigned_fix:DI (match_operand:DF 1 "register_operand" "r")))]
2561 ;; ""
2562 ;; "fixuns_truncdfdi2 %0,%1"
2563 ;; [(set_attr "length" "4")])
2564
2565 \f
2566 ;; ::::::::::::::::::::
2567 ;; ::
2568 ;; :: 32 bit Integer arithmetic
2569 ;; ::
2570 ;; ::::::::::::::::::::
2571
2572 ;; Addition
2573 (define_insn "addsi3"
2574 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2575 (plus:SI (match_operand:SI 1 "integer_register_operand" "%d")
2576 (match_operand:SI 2 "gpr_or_int12_operand" "dNOPQ")))]
2577 ""
2578 "add%I2 %1,%2,%0"
2579 [(set_attr "length" "4")
2580 (set_attr "type" "int")])
2581
2582 ;; Subtraction. No need to worry about constants, since the compiler
2583 ;; canonicalizes them into addsi3's. We prevent SUBREG's here to work around a
2584 ;; combine bug, that combines the 32x32->upper 32 bit multiply that uses a
2585 ;; SUBREG with a minus that shows up in modulus by constants.
2586 (define_insn "subsi3"
2587 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2588 (minus:SI (match_operand:SI 1 "gpr_no_subreg_operand" "d")
2589 (match_operand:SI 2 "gpr_no_subreg_operand" "d")))]
2590 ""
2591 "sub %1,%2,%0"
2592 [(set_attr "length" "4")
2593 (set_attr "type" "int")])
2594
2595 ;; Signed multiplication producing 64 bit results from 32 bit inputs
2596 ;; Note, frv doesn't have a 32x32->32 bit multiply, but the compiler
2597 ;; will do the 32x32->64 bit multiply and use the bottom word.
2598 (define_expand "mulsidi3"
2599 [(set (match_operand:DI 0 "integer_register_operand" "")
2600 (mult:DI (sign_extend:DI (match_operand:SI 1 "integer_register_operand" ""))
2601 (sign_extend:DI (match_operand:SI 2 "gpr_or_int12_operand" ""))))]
2602 ""
2603 "
2604 {
2605 if (GET_CODE (operands[2]) == CONST_INT)
2606 {
2607 emit_insn (gen_mulsidi3_const (operands[0], operands[1], operands[2]));
2608 DONE;
2609 }
2610 }")
2611
2612 (define_insn "*mulsidi3_reg"
2613 [(set (match_operand:DI 0 "even_gpr_operand" "=e")
2614 (mult:DI (sign_extend:DI (match_operand:SI 1 "integer_register_operand" "%d"))
2615 (sign_extend:DI (match_operand:SI 2 "integer_register_operand" "d"))))]
2616 ""
2617 "smul %1,%2,%0"
2618 [(set_attr "length" "4")
2619 (set_attr "type" "mul")])
2620
2621 (define_insn "mulsidi3_const"
2622 [(set (match_operand:DI 0 "even_gpr_operand" "=e")
2623 (mult:DI (sign_extend:DI (match_operand:SI 1 "integer_register_operand" "d"))
2624 (match_operand:SI 2 "int12_operand" "NOP")))]
2625 ""
2626 "smuli %1,%2,%0"
2627 [(set_attr "length" "4")
2628 (set_attr "type" "mul")])
2629
2630 ;; Unsigned multiplication producing 64 bit results from 32 bit inputs
2631 (define_expand "umulsidi3"
2632 [(set (match_operand:DI 0 "even_gpr_operand" "")
2633 (mult:DI (zero_extend:DI (match_operand:SI 1 "integer_register_operand" ""))
2634 (zero_extend:DI (match_operand:SI 2 "gpr_or_int12_operand" ""))))]
2635 ""
2636 "
2637 {
2638 if (GET_CODE (operands[2]) == CONST_INT)
2639 {
2640 emit_insn (gen_umulsidi3_const (operands[0], operands[1], operands[2]));
2641 DONE;
2642 }
2643 }")
2644
2645 (define_insn "*mulsidi3_reg"
2646 [(set (match_operand:DI 0 "even_gpr_operand" "=e")
2647 (mult:DI (zero_extend:DI (match_operand:SI 1 "integer_register_operand" "%d"))
2648 (zero_extend:DI (match_operand:SI 2 "integer_register_operand" "d"))))]
2649 ""
2650 "umul %1,%2,%0"
2651 [(set_attr "length" "4")
2652 (set_attr "type" "mul")])
2653
2654 (define_insn "umulsidi3_const"
2655 [(set (match_operand:DI 0 "even_gpr_operand" "=e")
2656 (mult:DI (zero_extend:DI (match_operand:SI 1 "integer_register_operand" "d"))
2657 (match_operand:SI 2 "int12_operand" "NOP")))]
2658 ""
2659 "umuli %1,%2,%0"
2660 [(set_attr "length" "4")
2661 (set_attr "type" "mul")])
2662
2663 ;; Signed Division
2664 (define_insn "divsi3"
2665 [(set (match_operand:SI 0 "register_operand" "=d,d")
2666 (div:SI (match_operand:SI 1 "register_operand" "d,d")
2667 (match_operand:SI 2 "gpr_or_int12_operand" "d,NOP")))]
2668 ""
2669 "sdiv%I2 %1,%2,%0"
2670 [(set_attr "length" "4")
2671 (set_attr "type" "div")])
2672
2673 ;; Unsigned Division
2674 (define_insn "udivsi3"
2675 [(set (match_operand:SI 0 "register_operand" "=d,d")
2676 (udiv:SI (match_operand:SI 1 "register_operand" "d,d")
2677 (match_operand:SI 2 "gpr_or_int12_operand" "d,NOP")))]
2678 ""
2679 "udiv%I2 %1,%2,%0"
2680 [(set_attr "length" "4")
2681 (set_attr "type" "div")])
2682
2683 ;; Negation
2684 (define_insn "negsi2"
2685 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2686 (neg:SI (match_operand:SI 1 "integer_register_operand" "d")))]
2687 ""
2688 "sub %.,%1,%0"
2689 [(set_attr "length" "4")
2690 (set_attr "type" "int")])
2691
2692 ;; Find first one bit
2693 ;; (define_insn "ffssi2"
2694 ;; [(set (match_operand:SI 0 "register_operand" "=r")
2695 ;; (ffs:SI (match_operand:SI 1 "register_operand" "r")))]
2696 ;; ""
2697 ;; "ffssi2 %0,%1"
2698 ;; [(set_attr "length" "4")])
2699
2700 \f
2701 ;; ::::::::::::::::::::
2702 ;; ::
2703 ;; :: 64 bit Integer arithmetic
2704 ;; ::
2705 ;; ::::::::::::::::::::
2706
2707 ;; Addition
2708 (define_expand "adddi3"
2709 [(parallel [(set (match_operand:DI 0 "integer_register_operand" "")
2710 (plus:DI (match_operand:DI 1 "integer_register_operand" "")
2711 (match_operand:DI 2 "gpr_or_int10_operand" "")))
2712 (clobber (match_scratch:CC 3 ""))])]
2713 ""
2714 "
2715 {
2716 if (GET_CODE (operands[2]) == CONST_INT
2717 && INTVAL (operands[2]) == -2048
2718 && !no_new_pseudos)
2719 operands[2] = force_reg (DImode, operands[2]);
2720 }")
2721
2722 (define_insn_and_split "*adddi3_internal"
2723 [(set (match_operand:DI 0 "integer_register_operand" "=&e,e,e,&e,e,&e,e")
2724 (plus:DI (match_operand:DI 1 "integer_register_operand" "%e,0,e,e,0,e,0")
2725 (match_operand:DI 2 "gpr_or_int10_operand" "e,e,0,N,N,OP,OP")))
2726 (clobber (match_scratch:CC 3 "=t,t,t,t,t,t,t"))]
2727 "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != -2048"
2728 "#"
2729 "reload_completed"
2730 [(match_dup 4)
2731 (match_dup 5)]
2732 "
2733 {
2734 rtx op0_high = gen_highpart (SImode, operands[0]);
2735 rtx op1_high = gen_highpart (SImode, operands[1]);
2736 rtx op0_low = gen_lowpart (SImode, operands[0]);
2737 rtx op1_low = gen_lowpart (SImode, operands[1]);
2738 rtx op2 = operands[2];
2739 rtx op3 = operands[3];
2740
2741 if (GET_CODE (op2) != CONST_INT)
2742 {
2743 rtx op2_high = gen_highpart (SImode, operands[2]);
2744 rtx op2_low = gen_lowpart (SImode, operands[2]);
2745 operands[4] = gen_adddi3_lower (op0_low, op1_low, op2_low, op3);
2746 operands[5] = gen_adddi3_upper (op0_high, op1_high, op2_high, op3);
2747 }
2748 else if (INTVAL (op2) >= 0)
2749 {
2750 operands[4] = gen_adddi3_lower (op0_low, op1_low, op2, op3);
2751 operands[5] = gen_adddi3_upper (op0_high, op1_high, const0_rtx, op3);
2752 }
2753 else
2754 {
2755 operands[4] = gen_subdi3_lower (op0_low, op1_low,
2756 GEN_INT (- INTVAL (op2)), op3);
2757 operands[5] = gen_subdi3_upper (op0_high, op1_high, const0_rtx, op3);
2758 }
2759 }"
2760 [(set_attr "length" "8")
2761 (set_attr "type" "multi")])
2762
2763 ;; Subtraction No need to worry about constants, since the compiler
2764 ;; canonicalizes them into adddi3's.
2765 (define_insn_and_split "subdi3"
2766 [(set (match_operand:DI 0 "integer_register_operand" "=&e,e,e")
2767 (minus:DI (match_operand:DI 1 "integer_register_operand" "e,0,e")
2768 (match_operand:DI 2 "integer_register_operand" "e,e,0")))
2769 (clobber (match_scratch:CC 3 "=t,t,t"))]
2770 ""
2771 "#"
2772 "reload_completed"
2773 [(match_dup 4)
2774 (match_dup 5)]
2775 "
2776 {
2777 rtx op0_high = gen_highpart (SImode, operands[0]);
2778 rtx op1_high = gen_highpart (SImode, operands[1]);
2779 rtx op2_high = gen_highpart (SImode, operands[2]);
2780 rtx op0_low = gen_lowpart (SImode, operands[0]);
2781 rtx op1_low = gen_lowpart (SImode, operands[1]);
2782 rtx op2_low = gen_lowpart (SImode, operands[2]);
2783 rtx op3 = operands[3];
2784
2785 operands[4] = gen_subdi3_lower (op0_low, op1_low, op2_low, op3);
2786 operands[5] = gen_subdi3_upper (op0_high, op1_high, op2_high, op3);
2787 }"
2788 [(set_attr "length" "8")
2789 (set_attr "type" "multi")])
2790
2791 ;; Patterns for addsi3/subdi3 after spliting
2792 (define_insn "adddi3_lower"
2793 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2794 (plus:SI (match_operand:SI 1 "integer_register_operand" "d")
2795 (match_operand:SI 2 "gpr_or_int10_operand" "dOP")))
2796 (set (match_operand:CC 3 "icc_operand" "=t")
2797 (compare:CC (plus:SI (match_dup 1)
2798 (match_dup 2))
2799 (const_int 0)))]
2800 "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) >= 0"
2801 "add%I2cc %1,%2,%0,%3"
2802 [(set_attr "length" "4")
2803 (set_attr "type" "int")])
2804
2805 (define_insn "adddi3_upper"
2806 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
2807 (plus:SI (match_operand:SI 1 "integer_register_operand" "d,d")
2808 (plus:SI (match_operand:SI 2 "reg_or_0_operand" "d,O")
2809 (match_operand:CC 3 "icc_operand" "t,t"))))]
2810 ""
2811 "@
2812 addx %1,%2,%0,%3
2813 addx %1,%.,%0,%3"
2814 [(set_attr "length" "4")
2815 (set_attr "type" "int")])
2816
2817 (define_insn "subdi3_lower"
2818 [(set (match_operand:SI 0 "integer_register_operand" "=d")
2819 (minus:SI (match_operand:SI 1 "integer_register_operand" "d")
2820 (match_operand:SI 2 "gpr_or_int10_operand" "dOP")))
2821 (set (match_operand:CC 3 "icc_operand" "=t")
2822 (compare:CC (plus:SI (match_dup 1)
2823 (match_dup 2))
2824 (const_int 0)))]
2825 "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) >= 0"
2826 "sub%I2cc %1,%2,%0,%3"
2827 [(set_attr "length" "4")
2828 (set_attr "type" "int")])
2829
2830 (define_insn "subdi3_upper"
2831 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
2832 (minus:SI (match_operand:SI 1 "integer_register_operand" "d,d")
2833 (minus:SI (match_operand:SI 2 "reg_or_0_operand" "d,O")
2834 (match_operand:CC 3 "icc_operand" "t,t"))))]
2835 ""
2836 "@
2837 subx %1,%2,%0,%3
2838 subx %1,%.,%0,%3"
2839 [(set_attr "length" "4")
2840 (set_attr "type" "int")])
2841
2842 (define_insn_and_split "negdi2"
2843 [(set (match_operand:DI 0 "integer_register_operand" "=&e,e")
2844 (neg:DI (match_operand:DI 1 "integer_register_operand" "e,0")))
2845 (clobber (match_scratch:CC 2 "=t,t"))]
2846 ""
2847 "#"
2848 "reload_completed"
2849 [(match_dup 3)
2850 (match_dup 4)]
2851 "
2852 {
2853 rtx op0_high = gen_highpart (SImode, operands[0]);
2854 rtx op1_high = gen_rtx_REG (SImode, GPR_FIRST);
2855 rtx op2_high = gen_highpart (SImode, operands[1]);
2856 rtx op0_low = gen_lowpart (SImode, operands[0]);
2857 rtx op1_low = op1_high;
2858 rtx op2_low = gen_lowpart (SImode, operands[1]);
2859 rtx op3 = operands[2];
2860
2861 operands[3] = gen_subdi3_lower (op0_low, op1_low, op2_low, op3);
2862 operands[4] = gen_subdi3_upper (op0_high, op1_high, op2_high, op3);
2863 }"
2864 [(set_attr "length" "8")
2865 (set_attr "type" "multi")])
2866
2867 ;; Multiplication (same size)
2868 ;; (define_insn "muldi3"
2869 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2870 ;; (mult:DI (match_operand:DI 1 "register_operand" "%r")
2871 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
2872 ;; ""
2873 ;; "muldi3 %0,%1,%2"
2874 ;; [(set_attr "length" "4")])
2875
2876 ;; Signed Division
2877 ;; (define_insn "divdi3"
2878 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2879 ;; (div:DI (match_operand:DI 1 "register_operand" "r")
2880 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
2881 ;; ""
2882 ;; "divdi3 %0,%1,%2"
2883 ;; [(set_attr "length" "4")])
2884
2885 ;; Undsgned Division
2886 ;; (define_insn "udivdi3"
2887 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2888 ;; (udiv:DI (match_operand:DI 1 "register_operand" "r")
2889 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
2890 ;; ""
2891 ;; "udivdi3 %0,%1,%2"
2892 ;; [(set_attr "length" "4")])
2893
2894 ;; Negation
2895 ;; (define_insn "negdi2"
2896 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2897 ;; (neg:DI (match_operand:DI 1 "register_operand" "r")))]
2898 ;; ""
2899 ;; "negdi2 %0,%1"
2900 ;; [(set_attr "length" "4")])
2901
2902 ;; Find first one bit
2903 ;; (define_insn "ffsdi2"
2904 ;; [(set (match_operand:DI 0 "register_operand" "=r")
2905 ;; (ffs:DI (match_operand:DI 1 "register_operand" "r")))]
2906 ;; ""
2907 ;; "ffsdi2 %0,%1"
2908 ;; [(set_attr "length" "4")])
2909
2910 \f
2911 ;; ::::::::::::::::::::
2912 ;; ::
2913 ;; :: 32 bit floating point arithmetic
2914 ;; ::
2915 ;; ::::::::::::::::::::
2916
2917 ;; Addition
2918 (define_insn "addsf3"
2919 [(set (match_operand:SF 0 "fpr_operand" "=f")
2920 (plus:SF (match_operand:SF 1 "fpr_operand" "%f")
2921 (match_operand:SF 2 "fpr_operand" "f")))]
2922 "TARGET_HARD_FLOAT"
2923 "fadds %1,%2,%0"
2924 [(set_attr "length" "4")
2925 (set_attr "type" "fsadd")])
2926
2927 ;; Subtraction
2928 (define_insn "subsf3"
2929 [(set (match_operand:SF 0 "fpr_operand" "=f")
2930 (minus:SF (match_operand:SF 1 "fpr_operand" "f")
2931 (match_operand:SF 2 "fpr_operand" "f")))]
2932 "TARGET_HARD_FLOAT"
2933 "fsubs %1,%2,%0"
2934 [(set_attr "length" "4")
2935 (set_attr "type" "fsadd")])
2936
2937 ;; Multiplication
2938 (define_insn "mulsf3"
2939 [(set (match_operand:SF 0 "fpr_operand" "=f")
2940 (mult:SF (match_operand:SF 1 "fpr_operand" "%f")
2941 (match_operand:SF 2 "fpr_operand" "f")))]
2942 "TARGET_HARD_FLOAT"
2943 "fmuls %1,%2,%0"
2944 [(set_attr "length" "4")
2945 (set_attr "type" "fsmul")])
2946
2947 ;; Multiplication with addition/subtraction
2948 (define_insn "*muladdsf4"
2949 [(set (match_operand:SF 0 "fpr_operand" "=f")
2950 (plus:SF (mult:SF (match_operand:SF 1 "fpr_operand" "%f")
2951 (match_operand:SF 2 "fpr_operand" "f"))
2952 (match_operand:SF 3 "fpr_operand" "0")))]
2953 "TARGET_HARD_FLOAT && TARGET_MULADD"
2954 "fmadds %1,%2,%0"
2955 [(set_attr "length" "4")
2956 (set_attr "type" "fmas")])
2957
2958 (define_insn "*mulsubsf4"
2959 [(set (match_operand:SF 0 "fpr_operand" "=f")
2960 (minus:SF (mult:SF (match_operand:SF 1 "fpr_operand" "%f")
2961 (match_operand:SF 2 "fpr_operand" "f"))
2962 (match_operand:SF 3 "fpr_operand" "0")))]
2963 "TARGET_HARD_FLOAT && TARGET_MULADD"
2964 "fmsubs %1,%2,%0"
2965 [(set_attr "length" "4")
2966 (set_attr "type" "fmas")])
2967
2968 ;; Division
2969 (define_insn "divsf3"
2970 [(set (match_operand:SF 0 "fpr_operand" "=f")
2971 (div:SF (match_operand:SF 1 "fpr_operand" "f")
2972 (match_operand:SF 2 "fpr_operand" "f")))]
2973 "TARGET_HARD_FLOAT"
2974 "fdivs %1,%2,%0"
2975 [(set_attr "length" "4")
2976 (set_attr "type" "fsdiv")])
2977
2978 ;; Negation
2979 (define_insn "negsf2"
2980 [(set (match_operand:SF 0 "fpr_operand" "=f")
2981 (neg:SF (match_operand:SF 1 "fpr_operand" "f")))]
2982 "TARGET_HARD_FLOAT"
2983 "fnegs %1,%0"
2984 [(set_attr "length" "4")
2985 (set_attr "type" "fsconv")])
2986
2987 ;; Absolute value
2988 (define_insn "abssf2"
2989 [(set (match_operand:SF 0 "fpr_operand" "=f")
2990 (abs:SF (match_operand:SF 1 "fpr_operand" "f")))]
2991 "TARGET_HARD_FLOAT"
2992 "fabss %1,%0"
2993 [(set_attr "length" "4")
2994 (set_attr "type" "fsconv")])
2995
2996 ;; Square root
2997 (define_insn "sqrtsf2"
2998 [(set (match_operand:SF 0 "fpr_operand" "=f")
2999 (sqrt:SF (match_operand:SF 1 "fpr_operand" "f")))]
3000 "TARGET_HARD_FLOAT"
3001 "fsqrts %1,%0"
3002 [(set_attr "length" "4")
3003 (set_attr "type" "sqrt_single")])
3004
3005 \f
3006 ;; ::::::::::::::::::::
3007 ;; ::
3008 ;; :: 64 bit floating point arithmetic
3009 ;; ::
3010 ;; ::::::::::::::::::::
3011
3012 ;; Addition
3013 (define_insn "adddf3"
3014 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3015 (plus:DF (match_operand:DF 1 "fpr_operand" "%h")
3016 (match_operand:DF 2 "fpr_operand" "h")))]
3017 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3018 "faddd %1,%2,%0"
3019 [(set_attr "length" "4")
3020 (set_attr "type" "fdadd")])
3021
3022 ;; Subtraction
3023 (define_insn "subdf3"
3024 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3025 (minus:DF (match_operand:DF 1 "fpr_operand" "h")
3026 (match_operand:DF 2 "fpr_operand" "h")))]
3027 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3028 "fsubd %1,%2,%0"
3029 [(set_attr "length" "4")
3030 (set_attr "type" "fdadd")])
3031
3032 ;; Multiplication
3033 (define_insn "muldf3"
3034 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3035 (mult:DF (match_operand:DF 1 "fpr_operand" "%h")
3036 (match_operand:DF 2 "fpr_operand" "h")))]
3037 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3038 "fmuld %1,%2,%0"
3039 [(set_attr "length" "4")
3040 (set_attr "type" "fdmul")])
3041
3042 ;; Multiplication with addition/subtraction
3043 (define_insn "*muladddf4"
3044 [(set (match_operand:DF 0 "fpr_operand" "=f")
3045 (plus:DF (mult:DF (match_operand:DF 1 "fpr_operand" "%f")
3046 (match_operand:DF 2 "fpr_operand" "f"))
3047 (match_operand:DF 3 "fpr_operand" "0")))]
3048 "TARGET_HARD_FLOAT && TARGET_DOUBLE && TARGET_MULADD"
3049 "fmaddd %1,%2,%0"
3050 [(set_attr "length" "4")
3051 (set_attr "type" "fmas")])
3052
3053 (define_insn "*mulsubdf4"
3054 [(set (match_operand:DF 0 "fpr_operand" "=f")
3055 (minus:DF (mult:DF (match_operand:DF 1 "fpr_operand" "%f")
3056 (match_operand:DF 2 "fpr_operand" "f"))
3057 (match_operand:DF 3 "fpr_operand" "0")))]
3058 "TARGET_HARD_FLOAT && TARGET_DOUBLE && TARGET_MULADD"
3059 "fmsubd %1,%2,%0"
3060 [(set_attr "length" "4")
3061 (set_attr "type" "fmas")])
3062
3063 ;; Division
3064 (define_insn "divdf3"
3065 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3066 (div:DF (match_operand:DF 1 "fpr_operand" "h")
3067 (match_operand:DF 2 "fpr_operand" "h")))]
3068 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3069 "fdivd %1,%2,%0"
3070 [(set_attr "length" "4")
3071 (set_attr "type" "fddiv")])
3072
3073 ;; Negation
3074 (define_insn "negdf2"
3075 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3076 (neg:DF (match_operand:DF 1 "fpr_operand" "h")))]
3077 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3078 "fnegd %1,%0"
3079 [(set_attr "length" "4")
3080 (set_attr "type" "fdconv")])
3081
3082 ;; Absolute value
3083 (define_insn "absdf2"
3084 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3085 (abs:DF (match_operand:DF 1 "fpr_operand" "h")))]
3086 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3087 "fabsd %1,%0"
3088 [(set_attr "length" "4")
3089 (set_attr "type" "fdconv")])
3090
3091 ;; Square root
3092 (define_insn "sqrtdf2"
3093 [(set (match_operand:DF 0 "even_fpr_operand" "=h")
3094 (sqrt:DF (match_operand:DF 1 "fpr_operand" "h")))]
3095 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3096 "fsqrtd %1,%0"
3097 [(set_attr "length" "4")
3098 (set_attr "type" "sqrt_double")])
3099
3100 \f
3101 ;; ::::::::::::::::::::
3102 ;; ::
3103 ;; :: 32 bit Integer Shifts and Rotates
3104 ;; ::
3105 ;; ::::::::::::::::::::
3106
3107 ;; Arithmetic Shift Left
3108 (define_insn "ashlsi3"
3109 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
3110 (ashift:SI (match_operand:SI 1 "integer_register_operand" "d,d")
3111 (match_operand:SI 2 "gpr_or_int12_operand" "d,NOP")))]
3112 ""
3113 "sll%I2 %1,%2,%0"
3114 [(set_attr "length" "4")
3115 (set_attr "type" "int")])
3116
3117 ;; Arithmetic Shift Right
3118 (define_insn "ashrsi3"
3119 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
3120 (ashiftrt:SI (match_operand:SI 1 "integer_register_operand" "d,d")
3121 (match_operand:SI 2 "gpr_or_int12_operand" "d,NOP")))]
3122 ""
3123 "sra%I2 %1, %2, %0"
3124 [(set_attr "length" "4")
3125 (set_attr "type" "int")])
3126
3127 ;; Logical Shift Right
3128 (define_insn "lshrsi3"
3129 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
3130 (lshiftrt:SI (match_operand:SI 1 "integer_register_operand" "d,d")
3131 (match_operand:SI 2 "gpr_or_int12_operand" "d,NOP")))]
3132 ""
3133 "srl%I2 %1, %2, %0"
3134 [(set_attr "length" "4")
3135 (set_attr "type" "int")])
3136
3137 ;; Rotate Left
3138 ;; (define_insn "rotlsi3"
3139 ;; [(set (match_operand:SI 0 "register_operand" "=r")
3140 ;; (rotate:SI (match_operand:SI 1 "register_operand" "r")
3141 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3142 ;; ""
3143 ;; "rotlsi3 %0,%1,%2"
3144 ;; [(set_attr "length" "4")])
3145
3146 ;; Rotate Right
3147 ;; (define_insn "rotrsi3"
3148 ;; [(set (match_operand:SI 0 "register_operand" "=r")
3149 ;; (rotatert:SI (match_operand:SI 1 "register_operand" "r")
3150 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3151 ;; ""
3152 ;; "rotrsi3 %0,%1,%2"
3153 ;; [(set_attr "length" "4")])
3154
3155 \f
3156 ;; ::::::::::::::::::::
3157 ;; ::
3158 ;; :: 64 bit Integer Shifts and Rotates
3159 ;; ::
3160 ;; ::::::::::::::::::::
3161
3162 ;; Arithmetic Shift Left
3163 ;; (define_insn "ashldi3"
3164 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3165 ;; (ashift:DI (match_operand:DI 1 "register_operand" "r")
3166 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3167 ;; ""
3168 ;; "ashldi3 %0,%1,%2"
3169 ;; [(set_attr "length" "4")])
3170
3171 ;; Arithmetic Shift Right
3172 ;; (define_insn "ashrdi3"
3173 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3174 ;; (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
3175 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3176 ;; ""
3177 ;; "ashrdi3 %0,%1,%2"
3178 ;; [(set_attr "length" "4")])
3179
3180 ;; Logical Shift Right
3181 ;; (define_insn "lshrdi3"
3182 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3183 ;; (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
3184 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3185 ;; ""
3186 ;; "lshrdi3 %0,%1,%2"
3187 ;; [(set_attr "length" "4")])
3188
3189 ;; Rotate Left
3190 ;; (define_insn "rotldi3"
3191 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3192 ;; (rotate:DI (match_operand:DI 1 "register_operand" "r")
3193 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3194 ;; ""
3195 ;; "rotldi3 %0,%1,%2"
3196 ;; [(set_attr "length" "4")])
3197
3198 ;; Rotate Right
3199 ;; (define_insn "rotrdi3"
3200 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3201 ;; (rotatert:DI (match_operand:DI 1 "register_operand" "r")
3202 ;; (match_operand:SI 2 "nonmemory_operand" "ri")))]
3203 ;; ""
3204 ;; "rotrdi3 %0,%1,%2"
3205 ;; [(set_attr "length" "4")])
3206
3207 \f
3208 ;; ::::::::::::::::::::
3209 ;; ::
3210 ;; :: 32 Bit Integer Logical operations
3211 ;; ::
3212 ;; ::::::::::::::::::::
3213
3214 ;; Logical AND, 32 bit integers
3215 (define_insn "andsi3_media"
3216 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "=d,f")
3217 (and:SI (match_operand:SI 1 "gpr_or_fpr_operand" "%d,f")
3218 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "dNOP,f")))]
3219 "TARGET_MEDIA"
3220 "@
3221 and%I2 %1, %2, %0
3222 mand %1, %2, %0"
3223 [(set_attr "length" "4")
3224 (set_attr "type" "int,mlogic")])
3225
3226 (define_insn "andsi3_nomedia"
3227 [(set (match_operand:SI 0 "integer_register_operand" "=d")
3228 (and:SI (match_operand:SI 1 "integer_register_operand" "%d")
3229 (match_operand:SI 2 "gpr_or_int12_operand" "dNOP")))]
3230 "!TARGET_MEDIA"
3231 "and%I2 %1, %2, %0"
3232 [(set_attr "length" "4")
3233 (set_attr "type" "int")])
3234
3235 (define_expand "andsi3"
3236 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "")
3237 (and:SI (match_operand:SI 1 "gpr_or_fpr_operand" "")
3238 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "")))]
3239 ""
3240 "")
3241
3242 ;; Inclusive OR, 32 bit integers
3243 (define_insn "iorsi3_media"
3244 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "=d,f")
3245 (ior:SI (match_operand:SI 1 "gpr_or_fpr_operand" "%d,f")
3246 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "dNOP,f")))]
3247 "TARGET_MEDIA"
3248 "@
3249 or%I2 %1, %2, %0
3250 mor %1, %2, %0"
3251 [(set_attr "length" "4")
3252 (set_attr "type" "int,mlogic")])
3253
3254 (define_insn "iorsi3_nomedia"
3255 [(set (match_operand:SI 0 "integer_register_operand" "=d")
3256 (ior:SI (match_operand:SI 1 "integer_register_operand" "%d")
3257 (match_operand:SI 2 "gpr_or_int12_operand" "dNOP")))]
3258 "!TARGET_MEDIA"
3259 "or%I2 %1, %2, %0"
3260 [(set_attr "length" "4")
3261 (set_attr "type" "int")])
3262
3263 (define_expand "iorsi3"
3264 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "")
3265 (ior:SI (match_operand:SI 1 "gpr_or_fpr_operand" "")
3266 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "")))]
3267 ""
3268 "")
3269
3270 ;; Exclusive OR, 32 bit integers
3271 (define_insn "xorsi3_media"
3272 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "=d,f")
3273 (xor:SI (match_operand:SI 1 "gpr_or_fpr_operand" "%d,f")
3274 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "dNOP,f")))]
3275 "TARGET_MEDIA"
3276 "@
3277 xor%I2 %1, %2, %0
3278 mxor %1, %2, %0"
3279 [(set_attr "length" "4")
3280 (set_attr "type" "int,mlogic")])
3281
3282 (define_insn "xorsi3_nomedia"
3283 [(set (match_operand:SI 0 "integer_register_operand" "=d")
3284 (xor:SI (match_operand:SI 1 "integer_register_operand" "%d")
3285 (match_operand:SI 2 "gpr_or_int12_operand" "dNOP")))]
3286 "!TARGET_MEDIA"
3287 "xor%I2 %1, %2, %0"
3288 [(set_attr "length" "4")
3289 (set_attr "type" "int")])
3290
3291 (define_expand "xorsi3"
3292 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "")
3293 (xor:SI (match_operand:SI 1 "gpr_or_fpr_operand" "")
3294 (match_operand:SI 2 "gpr_fpr_or_int12_operand" "")))]
3295 ""
3296 "")
3297
3298 ;; One's complement, 32 bit integers
3299 (define_insn "one_cmplsi2_media"
3300 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "=d,f")
3301 (not:SI (match_operand:SI 1 "gpr_or_fpr_operand" "d,f")))]
3302 "TARGET_MEDIA"
3303 "@
3304 not %1, %0
3305 mnot %1, %0"
3306 [(set_attr "length" "4")
3307 (set_attr "type" "int,mlogic")])
3308
3309 (define_insn "one_cmplsi2_nomedia"
3310 [(set (match_operand:SI 0 "integer_register_operand" "=d")
3311 (not:SI (match_operand:SI 1 "integer_register_operand" "d")))]
3312 "!TARGET_MEDIA"
3313 "not %1,%0"
3314 [(set_attr "length" "4")
3315 (set_attr "type" "int")])
3316
3317 (define_expand "one_cmplsi2"
3318 [(set (match_operand:SI 0 "gpr_or_fpr_operand" "")
3319 (not:SI (match_operand:SI 1 "gpr_or_fpr_operand" "")))]
3320 ""
3321 "")
3322
3323 \f
3324 ;; ::::::::::::::::::::
3325 ;; ::
3326 ;; :: 64 Bit Integer Logical operations
3327 ;; ::
3328 ;; ::::::::::::::::::::
3329
3330 ;; Logical AND, 64 bit integers
3331 ;; (define_insn "anddi3"
3332 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3333 ;; (and:DI (match_operand:DI 1 "register_operand" "%r")
3334 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
3335 ;; ""
3336 ;; "anddi3 %0,%1,%2"
3337 ;; [(set_attr "length" "4")])
3338
3339 ;; Inclusive OR, 64 bit integers
3340 ;; (define_insn "iordi3"
3341 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3342 ;; (ior:DI (match_operand:DI 1 "register_operand" "%r")
3343 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
3344 ;; ""
3345 ;; "iordi3 %0,%1,%2"
3346 ;; [(set_attr "length" "4")])
3347
3348 ;; Exclusive OR, 64 bit integers
3349 ;; (define_insn "xordi3"
3350 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3351 ;; (xor:DI (match_operand:DI 1 "register_operand" "%r")
3352 ;; (match_operand:DI 2 "nonmemory_operand" "ri")))]
3353 ;; ""
3354 ;; "xordi3 %0,%1,%2"
3355 ;; [(set_attr "length" "4")])
3356
3357 ;; One's complement, 64 bit integers
3358 ;; (define_insn "one_cmpldi2"
3359 ;; [(set (match_operand:DI 0 "register_operand" "=r")
3360 ;; (not:DI (match_operand:DI 1 "register_operand" "r")))]
3361 ;; ""
3362 ;; "notdi3 %0,%1"
3363 ;; [(set_attr "length" "4")])
3364
3365 \f
3366 ;; ::::::::::::::::::::
3367 ;; ::
3368 ;; :: Combination of integer operation with comparison
3369 ;; ::
3370 ;; ::::::::::::::::::::
3371
3372 (define_insn "*combo_intop_compare1"
3373 [(set (match_operand:CC 0 "icc_operand" "=t")
3374 (compare:CC (match_operator:SI 1 "intop_compare_operator"
3375 [(match_operand:SI 2 "integer_register_operand" "d")
3376 (match_operand:SI 3 "gpr_or_int10_operand" "dJ")])
3377 (const_int 0)))]
3378 ""
3379 "%O1%I3cc %2, %3, %., %0"
3380 [(set_attr "type" "int")
3381 (set_attr "length" "4")])
3382
3383 (define_insn "*combo_intop_compare2"
3384 [(set (match_operand:CC_UNS 0 "icc_operand" "=t")
3385 (compare:CC_UNS (match_operator:SI 1 "intop_compare_operator"
3386 [(match_operand:SI 2 "integer_register_operand" "d")
3387 (match_operand:SI 3 "gpr_or_int10_operand" "dJ")])
3388 (const_int 0)))]
3389 ""
3390 "%O1%I3cc %2, %3, %., %0"
3391 [(set_attr "type" "int")
3392 (set_attr "length" "4")])
3393
3394 (define_insn "*combo_intop_compare3"
3395 [(set (match_operand:CC 0 "icc_operand" "=t")
3396 (compare:CC (match_operator:SI 1 "intop_compare_operator"
3397 [(match_operand:SI 2 "integer_register_operand" "d")
3398 (match_operand:SI 3 "gpr_or_int10_operand" "dJ")])
3399 (const_int 0)))
3400 (set (match_operand:SI 4 "integer_register_operand" "=d")
3401 (match_operator:SI 5 "intop_compare_operator"
3402 [(match_dup 2)
3403 (match_dup 3)]))]
3404 "GET_CODE (operands[1]) == GET_CODE (operands[5])"
3405 "%O1%I3cc %2, %3, %4, %0"
3406 [(set_attr "type" "int")
3407 (set_attr "length" "4")])
3408
3409 (define_insn "*combo_intop_compare4"
3410 [(set (match_operand:CC_UNS 0 "icc_operand" "=t")
3411 (compare:CC_UNS (match_operator:SI 1 "intop_compare_operator"
3412 [(match_operand:SI 2 "integer_register_operand" "d")
3413 (match_operand:SI 3 "gpr_or_int10_operand" "dJ")])
3414 (const_int 0)))
3415 (set (match_operand:SI 4 "integer_register_operand" "=d")
3416 (match_operator:SI 5 "intop_compare_operator"
3417 [(match_dup 2)
3418 (match_dup 3)]))]
3419 "GET_CODE (operands[1]) == GET_CODE (operands[5])"
3420 "%O1%I3cc %2, %3, %4, %0"
3421 [(set_attr "type" "int")
3422 (set_attr "length" "4")])
3423
3424 \f
3425 ;; ::::::::::::::::::::
3426 ;; ::
3427 ;; :: Comparisons
3428 ;; ::
3429 ;; ::::::::::::::::::::
3430
3431 ;; Note, we store the operands in the comparison insns, and use them later
3432 ;; when generating the branch or scc operation.
3433
3434 ;; First the routines called by the machine independent part of the compiler
3435 (define_expand "cmpsi"
3436 [(set (cc0)
3437 (compare (match_operand:SI 0 "integer_register_operand" "")
3438 (match_operand:SI 1 "gpr_or_int10_operand" "")))]
3439 ""
3440 "
3441 {
3442 frv_compare_op0 = operands[0];
3443 frv_compare_op1 = operands[1];
3444 DONE;
3445 }")
3446
3447 ;(define_expand "cmpdi"
3448 ; [(set (cc0)
3449 ; (compare (match_operand:DI 0 "register_operand" "")
3450 ; (match_operand:DI 1 "nonmemory_operand" "")))]
3451 ; ""
3452 ; "
3453 ;{
3454 ; frv_compare_op0 = operands[0];
3455 ; frv_compare_op1 = operands[1];
3456 ; DONE;
3457 ;}")
3458
3459 (define_expand "cmpsf"
3460 [(set (cc0)
3461 (compare (match_operand:SF 0 "fpr_operand" "")
3462 (match_operand:SF 1 "fpr_operand" "")))]
3463 "TARGET_HARD_FLOAT"
3464 "
3465 {
3466 frv_compare_op0 = operands[0];
3467 frv_compare_op1 = operands[1];
3468 DONE;
3469 }")
3470
3471 (define_expand "cmpdf"
3472 [(set (cc0)
3473 (compare (match_operand:DF 0 "fpr_operand" "")
3474 (match_operand:DF 1 "fpr_operand" "")))]
3475 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3476 "
3477 {
3478 frv_compare_op0 = operands[0];
3479 frv_compare_op1 = operands[1];
3480 DONE;
3481 }")
3482
3483 ;; Now, the actual comparisons, generated by the branch and/or scc operations
3484
3485 (define_insn "cmpsi_cc"
3486 [(set (match_operand:CC 0 "icc_operand" "=t,t")
3487 (compare:CC (match_operand:SI 1 "integer_register_operand" "d,d")
3488 (match_operand:SI 2 "gpr_or_int10_operand" "d,J")))]
3489 ""
3490 "cmp%I2 %1,%2,%0"
3491 [(set_attr "length" "4")
3492 (set_attr "type" "int")])
3493
3494 (define_insn "*cmpsi_cc_uns"
3495 [(set (match_operand:CC_UNS 0 "icc_operand" "=t,t")
3496 (compare:CC_UNS (match_operand:SI 1 "integer_register_operand" "d,d")
3497 (match_operand:SI 2 "gpr_or_int10_operand" "d,J")))]
3498 ""
3499 "cmp%I2 %1,%2,%0"
3500 [(set_attr "length" "4")
3501 (set_attr "type" "int")])
3502
3503 (define_insn "*cmpsf_cc_fp"
3504 [(set (match_operand:CC_FP 0 "fcc_operand" "=u")
3505 (compare:CC_FP (match_operand:SF 1 "fpr_operand" "f")
3506 (match_operand:SF 2 "fpr_operand" "f")))]
3507 "TARGET_HARD_FLOAT"
3508 "fcmps %1,%2,%0"
3509 [(set_attr "length" "4")
3510 (set_attr "type" "fsadd")])
3511
3512 (define_insn "*cmpdf_cc_fp"
3513 [(set (match_operand:CC_FP 0 "fcc_operand" "=u")
3514 (compare:CC_FP (match_operand:DF 1 "even_fpr_operand" "h")
3515 (match_operand:DF 2 "even_fpr_operand" "h")))]
3516 "TARGET_HARD_FLOAT && TARGET_DOUBLE"
3517 "fcmpd %1,%2,%0"
3518 [(set_attr "length" "4")
3519 (set_attr "type" "fdadd")])
3520
3521 \f
3522 ;; ::::::::::::::::::::
3523 ;; ::
3524 ;; :: Branches
3525 ;; ::
3526 ;; ::::::::::::::::::::
3527
3528 ;; Define_expands called by the machine independent part of the compiler
3529 ;; to allocate a new comparison register. Each of these named patterns
3530 ;; must be present, and they cannot be amalgamated into one pattern.
3531 ;;
3532 ;; If a fixed condition code register is being used, (as opposed to, say,
3533 ;; using cc0), then the expands should look like this:
3534 ;;
3535 ;; (define_expand "<name_of_test>"
3536 ;; [(set (reg:CC <number_of_CC_register>)
3537 ;; (compare:CC (match_dup 1)
3538 ;; (match_dup 2)))
3539 ;; (set (pc)
3540 ;; (if_then_else (eq:CC (reg:CC <number_of_CC_register>)
3541 ;; (const_int 0))
3542 ;; (label_ref (match_operand 0 "" ""))
3543 ;; (pc)))]
3544 ;; ""
3545 ;; "{
3546 ;; operands[1] = frv_compare_op0;
3547 ;; operands[2] = frv_compare_op1;
3548 ;; }"
3549 ;; )
3550
3551 (define_expand "beq"
3552 [(use (match_operand 0 "" ""))]
3553 ""
3554 "
3555 {
3556 if (! frv_emit_cond_branch (EQ, operands[0]))
3557 FAIL;
3558
3559 DONE;
3560 }")
3561
3562 (define_expand "bne"
3563 [(use (match_operand 0 "" ""))]
3564 ""
3565 "
3566 {
3567 if (! frv_emit_cond_branch (NE, operands[0]))
3568 FAIL;
3569
3570 DONE;
3571 }")
3572
3573 (define_expand "blt"
3574 [(use (match_operand 0 "" ""))]
3575 ""
3576 "
3577 {
3578 if (! frv_emit_cond_branch (LT, operands[0]))
3579 FAIL;
3580
3581 DONE;
3582 }")
3583
3584 (define_expand "ble"
3585 [(use (match_operand 0 "" ""))]
3586 ""
3587 "
3588 {
3589 if (! frv_emit_cond_branch (LE, operands[0]))
3590 FAIL;
3591
3592 DONE;
3593 }")
3594
3595 (define_expand "bgt"
3596 [(use (match_operand 0 "" ""))]
3597 ""
3598 "
3599 {
3600 if (! frv_emit_cond_branch (GT, operands[0]))
3601 FAIL;
3602
3603 DONE;
3604 }")
3605
3606 (define_expand "bge"
3607 [(use (match_operand 0 "" ""))]
3608 ""
3609 "
3610 {
3611 if (! frv_emit_cond_branch (GE, operands[0]))
3612 FAIL;
3613
3614 DONE;
3615 }")
3616
3617 (define_expand "bltu"
3618 [(use (match_operand 0 "" ""))]
3619 ""
3620 "
3621 {
3622 if (! frv_emit_cond_branch (LTU, operands[0]))
3623 FAIL;
3624
3625 DONE;
3626 }")
3627
3628 (define_expand "bleu"
3629 [(use (match_operand 0 "" ""))]
3630 ""
3631 "
3632 {
3633 if (! frv_emit_cond_branch (LEU, operands[0]))
3634 FAIL;
3635
3636 DONE;
3637 }")
3638
3639 (define_expand "bgtu"
3640 [(use (match_operand 0 "" ""))]
3641 ""
3642 "
3643 {
3644 if (! frv_emit_cond_branch (GTU, operands[0]))
3645 FAIL;
3646
3647 DONE;
3648 }")
3649
3650 (define_expand "bgeu"
3651 [(use (match_operand 0 "" ""))]
3652 ""
3653 "
3654 {
3655 if (! frv_emit_cond_branch (GEU, operands[0]))
3656 FAIL;
3657
3658 DONE;
3659 }")
3660
3661 ;; Actual branches. We must allow for the (label_ref) and the (pc) to be
3662 ;; swapped. If they are swapped, it reverses the sense of the branch.
3663 ;;
3664 ;; Note - unlike the define expands above, these patterns can be amalgamated
3665 ;; into one pattern for branch-if-true and one for branch-if-false. This does
3666 ;; require an operand operator to select the correct branch mnemonic.
3667 ;;
3668 ;; If a fixed condition code register is being used, (as opposed to, say,
3669 ;; using cc0), then the expands could look like this:
3670 ;;
3671 ;; (define_insn "*branch_true"
3672 ;; [(set (pc)
3673 ;; (if_then_else (match_operator:CC 0 "comparison_operator"
3674 ;; [(reg:CC <number_of_CC_register>)
3675 ;; (const_int 0)])
3676 ;; (label_ref (match_operand 1 "" ""))
3677 ;; (pc)))]
3678 ;; ""
3679 ;; "b%B0 %1"
3680 ;; [(set_attr "length" "4")]
3681 ;; )
3682 ;;
3683 ;; In the above example the %B is a directive to frv_print_operand()
3684 ;; to decode and print the correct branch mnemonic.
3685
3686 (define_insn "*branch_signed_true"
3687 [(set (pc)
3688 (if_then_else (match_operator:CC 0 "signed_relational_operator"
3689 [(match_operand 1 "icc_operand" "t")
3690 (const_int 0)])
3691 (label_ref (match_operand 2 "" ""))
3692 (pc)))]
3693 ""
3694 "*
3695 {
3696 if (get_attr_length (insn) == 4)
3697 return \"b%c0 %1,%#,%l2\";
3698 else
3699 return \"b%C0 %1,%#,1f\;call %l2\\n1:\";
3700 }"
3701 [(set (attr "length")
3702 (if_then_else
3703 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3704 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3705 (const_int 4)
3706 (const_int 8)))
3707 (set (attr "far_jump")
3708 (if_then_else
3709 (eq_attr "length" "4")
3710 (const_string "no")
3711 (const_string "yes")))
3712 (set (attr "type")
3713 (if_then_else
3714 (eq_attr "length" "4")
3715 (const_string "branch")
3716 (const_string "multi")))])
3717
3718 (define_insn "*branch_signed_false"
3719 [(set (pc)
3720 (if_then_else (match_operator:CC 0 "signed_relational_operator"
3721 [(match_operand 1 "icc_operand" "t")
3722 (const_int 0)])
3723 (pc)
3724 (label_ref (match_operand 2 "" ""))))]
3725 ""
3726 "*
3727 {
3728 if (get_attr_length (insn) == 4)
3729 return \"b%C0 %1,%#,%l2\";
3730 else
3731 return \"b%c0 %1,%#,1f\;call %l2\\n1:\";
3732 }"
3733 [(set (attr "length")
3734 (if_then_else
3735 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3736 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3737 (const_int 4)
3738 (const_int 8)))
3739 (set (attr "far_jump")
3740 (if_then_else
3741 (eq_attr "length" "4")
3742 (const_string "no")
3743 (const_string "yes")))
3744 (set (attr "type")
3745 (if_then_else
3746 (eq_attr "length" "4")
3747 (const_string "branch")
3748 (const_string "multi")))])
3749
3750 (define_insn "*branch_unsigned_true"
3751 [(set (pc)
3752 (if_then_else (match_operator:CC_UNS 0 "unsigned_relational_operator"
3753 [(match_operand 1 "icc_operand" "t")
3754 (const_int 0)])
3755 (label_ref (match_operand 2 "" ""))
3756 (pc)))]
3757 ""
3758 "*
3759 {
3760 if (get_attr_length (insn) == 4)
3761 return \"b%c0 %1,%#,%l2\";
3762 else
3763 return \"b%C0 %1,%#,1f\;call %l2\\n1:\";
3764 }"
3765 [(set (attr "length")
3766 (if_then_else
3767 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3768 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3769 (const_int 4)
3770 (const_int 8)))
3771 (set (attr "far_jump")
3772 (if_then_else
3773 (eq_attr "length" "4")
3774 (const_string "no")
3775 (const_string "yes")))
3776 (set (attr "type")
3777 (if_then_else
3778 (eq_attr "length" "4")
3779 (const_string "branch")
3780 (const_string "multi")))])
3781
3782 (define_insn "*branch_unsigned_false"
3783 [(set (pc)
3784 (if_then_else (match_operator:CC_UNS 0 "unsigned_relational_operator"
3785 [(match_operand 1 "icc_operand" "t")
3786 (const_int 0)])
3787 (pc)
3788 (label_ref (match_operand 2 "" ""))))]
3789 ""
3790 "*
3791 {
3792 if (get_attr_length (insn) == 4)
3793 return \"b%C0 %1,%#,%l2\";
3794 else
3795 return \"b%c0 %1,%#,1f\;call %l2\\n1:\";
3796 }"
3797 [(set (attr "length")
3798 (if_then_else
3799 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3800 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3801 (const_int 4)
3802 (const_int 8)))
3803 (set (attr "far_jump")
3804 (if_then_else
3805 (eq_attr "length" "4")
3806 (const_string "no")
3807 (const_string "yes")))
3808 (set (attr "type")
3809 (if_then_else
3810 (eq_attr "length" "4")
3811 (const_string "branch")
3812 (const_string "multi")))])
3813
3814 (define_insn "*branch_fp_true"
3815 [(set (pc)
3816 (if_then_else (match_operator:CC_FP 0 "float_relational_operator"
3817 [(match_operand 1 "fcc_operand" "u")
3818 (const_int 0)])
3819 (label_ref (match_operand 2 "" ""))
3820 (pc)))]
3821 ""
3822 "*
3823 {
3824 if (get_attr_length (insn) == 4)
3825 return \"fb%f0 %1,%#,%l2\";
3826 else
3827 return \"fb%F0 %1,%#,1f\;call %l2\\n1:\";
3828 }"
3829 [(set (attr "length")
3830 (if_then_else
3831 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3832 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3833 (const_int 4)
3834 (const_int 8)))
3835 (set (attr "far_jump")
3836 (if_then_else
3837 (eq_attr "length" "4")
3838 (const_string "no")
3839 (const_string "yes")))
3840 (set (attr "type")
3841 (if_then_else
3842 (eq_attr "length" "4")
3843 (const_string "branch")
3844 (const_string "multi")))])
3845
3846 (define_insn "*branch_fp_false"
3847 [(set (pc)
3848 (if_then_else (match_operator:CC_FP 0 "float_relational_operator"
3849 [(match_operand 1 "fcc_operand" "u")
3850 (const_int 0)])
3851 (pc)
3852 (label_ref (match_operand 2 "" ""))))]
3853 ""
3854 "*
3855 {
3856 if (get_attr_length (insn) == 4)
3857 return \"fb%F0 %1,%#,%l2\";
3858 else
3859 return \"fb%f0 %1,%#,1f\;call %l2\\n1:\";
3860 }"
3861 [(set (attr "length")
3862 (if_then_else
3863 (and (ge (minus (match_dup 2) (pc)) (const_int -32768))
3864 (le (minus (match_dup 2) (pc)) (const_int 32764)))
3865 (const_int 4)
3866 (const_int 8)))
3867 (set (attr "far_jump")
3868 (if_then_else
3869 (eq_attr "length" "4")
3870 (const_string "no")
3871 (const_string "yes")))
3872 (set (attr "type")
3873 (if_then_else
3874 (eq_attr "length" "4")
3875 (const_string "branch")
3876 (const_string "multi")))])
3877
3878 \f
3879 ;; ::::::::::::::::::::
3880 ;; ::
3881 ;; :: Set flag operations
3882 ;; ::
3883 ;; ::::::::::::::::::::
3884
3885 ;; Define_expands called by the machine independent part of the compiler
3886 ;; to allocate a new comparison register
3887
3888 (define_expand "seq"
3889 [(match_operand:SI 0 "integer_register_operand" "")]
3890 "TARGET_SCC"
3891 "
3892 {
3893 if (! frv_emit_scc (EQ, operands[0]))
3894 FAIL;
3895
3896 DONE;
3897 }")
3898
3899 (define_expand "sne"
3900 [(match_operand:SI 0 "integer_register_operand" "")]
3901 "TARGET_SCC"
3902 "
3903 {
3904 if (! frv_emit_scc (NE, operands[0]))
3905 FAIL;
3906
3907 DONE;
3908 }")
3909
3910 (define_expand "slt"
3911 [(match_operand:SI 0 "integer_register_operand" "")]
3912 "TARGET_SCC"
3913 "
3914 {
3915 if (! frv_emit_scc (LT, operands[0]))
3916 FAIL;
3917
3918 DONE;
3919 }")
3920
3921 (define_expand "sle"
3922 [(match_operand:SI 0 "integer_register_operand" "")]
3923 "TARGET_SCC"
3924 "
3925 {
3926 if (! frv_emit_scc (LE, operands[0]))
3927 FAIL;
3928
3929 DONE;
3930 }")
3931
3932 (define_expand "sgt"
3933 [(match_operand:SI 0 "integer_register_operand" "")]
3934 "TARGET_SCC"
3935 "
3936 {
3937 if (! frv_emit_scc (GT, operands[0]))
3938 FAIL;
3939
3940 DONE;
3941 }")
3942
3943 (define_expand "sge"
3944 [(match_operand:SI 0 "integer_register_operand" "")]
3945 "TARGET_SCC"
3946 "
3947 {
3948 if (! frv_emit_scc (GE, operands[0]))
3949 FAIL;
3950
3951 DONE;
3952 }")
3953
3954 (define_expand "sltu"
3955 [(match_operand:SI 0 "integer_register_operand" "")]
3956 "TARGET_SCC"
3957 "
3958 {
3959 if (! frv_emit_scc (LTU, operands[0]))
3960 FAIL;
3961
3962 DONE;
3963 }")
3964
3965 (define_expand "sleu"
3966 [(match_operand:SI 0 "integer_register_operand" "")]
3967 "TARGET_SCC"
3968 "
3969 {
3970 if (! frv_emit_scc (LEU, operands[0]))
3971 FAIL;
3972
3973 DONE;
3974 }")
3975
3976 (define_expand "sgtu"
3977 [(match_operand:SI 0 "integer_register_operand" "")]
3978 "TARGET_SCC"
3979 "
3980 {
3981 if (! frv_emit_scc (GTU, operands[0]))
3982 FAIL;
3983
3984 DONE;
3985 }")
3986
3987 (define_expand "sgeu"
3988 [(match_operand:SI 0 "integer_register_operand" "")]
3989 "TARGET_SCC"
3990 "
3991 {
3992 if (! frv_emit_scc (GEU, operands[0]))
3993 FAIL;
3994
3995 DONE;
3996 }")
3997
3998 (define_insn "*scc_signed"
3999 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4000 (match_operator:SI 1 "signed_relational_operator"
4001 [(match_operand:CC 2 "icc_operand" "t")
4002 (const_int 0)]))
4003 (clobber (match_operand:CC_CCR 3 "icr_operand" "=v"))]
4004 ""
4005 "#"
4006 [(set_attr "length" "12")
4007 (set_attr "type" "multi")])
4008
4009 (define_insn "*scc_unsigned"
4010 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4011 (match_operator:SI 1 "unsigned_relational_operator"
4012 [(match_operand:CC_UNS 2 "icc_operand" "t")
4013 (const_int 0)]))
4014 (clobber (match_operand:CC_CCR 3 "icr_operand" "=v"))]
4015 ""
4016 "#"
4017 [(set_attr "length" "12")
4018 (set_attr "type" "multi")])
4019
4020 (define_insn "*scc_float"
4021 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4022 (match_operator:SI 1 "float_relational_operator"
4023 [(match_operand:CC_FP 2 "fcc_operand" "u")
4024 (const_int 0)]))
4025 (clobber (match_operand:CC_CCR 3 "fcr_operand" "=w"))]
4026 ""
4027 "#"
4028 [(set_attr "length" "12")
4029 (set_attr "type" "multi")])
4030
4031 ;; XXX -- add reload_completed to the splits, because register allocation
4032 ;; currently isn't ready to see cond_exec packets.
4033 (define_split
4034 [(set (match_operand:SI 0 "integer_register_operand" "")
4035 (match_operator:SI 1 "relational_operator"
4036 [(match_operand 2 "cc_operand" "")
4037 (const_int 0)]))
4038 (clobber (match_operand 3 "cr_operand" ""))]
4039 "reload_completed"
4040 [(match_dup 4)]
4041 "operands[4] = frv_split_scc (operands[0], operands[1], operands[2],
4042 operands[3], (HOST_WIDE_INT) 1);")
4043
4044 (define_insn "*scc_neg1_signed"
4045 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4046 (neg:SI (match_operator:SI 1 "signed_relational_operator"
4047 [(match_operand:CC 2 "icc_operand" "t")
4048 (const_int 0)])))
4049 (clobber (match_operand:CC_CCR 3 "icr_operand" "=v"))]
4050 ""
4051 "#"
4052 [(set_attr "length" "12")
4053 (set_attr "type" "multi")])
4054
4055 (define_insn "*scc_neg1_unsigned"
4056 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4057 (neg:SI (match_operator:SI 1 "unsigned_relational_operator"
4058 [(match_operand:CC_UNS 2 "icc_operand" "t")
4059 (const_int 0)])))
4060 (clobber (match_operand:CC_CCR 3 "icr_operand" "=v"))]
4061 ""
4062 "#"
4063 [(set_attr "length" "12")
4064 (set_attr "type" "multi")])
4065
4066 (define_insn "*scc_neg1_float"
4067 [(set (match_operand:SI 0 "integer_register_operand" "=d")
4068 (neg:SI (match_operator:SI 1 "float_relational_operator"
4069 [(match_operand:CC_FP 2 "fcc_operand" "u")
4070 (const_int 0)])))
4071 (clobber (match_operand:CC_CCR 3 "fcr_operand" "=w"))]
4072 ""
4073 "#"
4074 [(set_attr "length" "12")
4075 (set_attr "type" "multi")])
4076
4077 (define_split
4078 [(set (match_operand:SI 0 "integer_register_operand" "")
4079 (neg:SI (match_operator:SI 1 "relational_operator"
4080 [(match_operand 2 "cc_operand" "")
4081 (const_int 0)])))
4082 (clobber (match_operand 3 "cr_operand" ""))]
4083 "reload_completed"
4084 [(match_dup 4)]
4085 "operands[4] = frv_split_scc (operands[0], operands[1], operands[2],
4086 operands[3], (HOST_WIDE_INT) -1);")
4087
4088 \f
4089 ;; ::::::::::::::::::::
4090 ;; ::
4091 ;; :: Conditionally executed instructions
4092 ;; ::
4093 ;; ::::::::::::::::::::
4094
4095 ;; Convert ICC/FCC comparison into CCR bits so we can do conditional execution
4096 (define_insn "*ck_signed"
4097 [(set (match_operand:CC_CCR 0 "icr_operand" "=v")
4098 (match_operator:CC_CCR 1 "signed_relational_operator"
4099 [(match_operand:CC 2 "icc_operand" "t")
4100 (const_int 0)]))]
4101 ""
4102 "ck%c1 %2, %0"
4103 [(set_attr "length" "4")
4104 (set_attr "type" "ccr")])
4105
4106 (define_insn "*ck_unsigned"
4107 [(set (match_operand:CC_CCR 0 "icr_operand" "=v")
4108 (match_operator:CC_CCR 1 "unsigned_relational_operator"
4109 [(match_operand:CC_UNS 2 "icc_operand" "t")
4110 (const_int 0)]))]
4111 ""
4112 "ck%c1 %2, %0"
4113 [(set_attr "length" "4")
4114 (set_attr "type" "ccr")])
4115
4116 (define_insn "*fck_float"
4117 [(set (match_operand:CC_CCR 0 "fcr_operand" "=w")
4118 (match_operator:CC_CCR 1 "float_relational_operator"
4119 [(match_operand:CC_FP 2 "fcc_operand" "u")
4120 (const_int 0)]))]
4121 "TARGET_HAS_FPRS"
4122 "fck%c1 %2, %0"
4123 [(set_attr "length" "4")
4124 (set_attr "type" "ccr")])
4125
4126 ;; Conditionally convert ICC/FCC comparison into CCR bits to provide && and ||
4127 ;; tests in conditional execution
4128 (define_insn "cond_exec_ck"
4129 [(set (match_operand:CC_CCR 0 "cr_operand" "=v,w")
4130 (if_then_else:CC_CCR (match_operator 1 "ccr_eqne_operator"
4131 [(match_operand 2 "cr_operand" "C,C")
4132 (const_int 0)])
4133 (match_operator 3 "relational_operator"
4134 [(match_operand 4 "cc_operand" "t,u")
4135 (const_int 0)])
4136 (const_int 0)))]
4137 ""
4138 "@
4139 cck%c3 %4, %0, %2, %e1
4140 cfck%f3 %4, %0, %2, %e1"
4141 [(set_attr "length" "4")
4142 (set_attr "type" "ccr")])
4143
4144 ;; Conditionally set a register to either 0 or another register
4145 (define_insn "*cond_exec_movqi"
4146 [(cond_exec
4147 (match_operator 0 "ccr_eqne_operator"
4148 [(match_operand 1 "cr_operand" "C,C,C,C,C,C")
4149 (const_int 0)])
4150 (set (match_operand:QI 2 "condexec_dest_operand" "=d,d,U,?f,?f,?d")
4151 (match_operand:QI 3 "condexec_source_operand" "dO,U,dO,f,d,f")))]
4152 "register_operand(operands[2], QImode) || reg_or_0_operand (operands[3], QImode)"
4153 "* return output_condmove_single (operands, insn);"
4154 [(set_attr "length" "4")
4155 (set_attr "type" "int,gload,gstore,fsconv,movgf,movfg")])
4156
4157 (define_insn "*cond_exec_movhi"
4158 [(cond_exec
4159 (match_operator 0 "ccr_eqne_operator"
4160 [(match_operand 1 "cr_operand" "C,C,C,C,C,C")
4161 (const_int 0)])
4162 (set (match_operand:HI 2 "condexec_dest_operand" "=d,d,U,?f,?f,?d")
4163 (match_operand:HI 3 "condexec_source_operand" "dO,U,dO,f,d,f")))]
4164 "register_operand(operands[2], HImode) || reg_or_0_operand (operands[3], HImode)"
4165 "* return output_condmove_single (operands, insn);"
4166 [(set_attr "length" "4")
4167 (set_attr "type" "int,gload,gstore,fsconv,movgf,movfg")])
4168
4169 (define_insn "*cond_exec_movsi"
4170 [(cond_exec
4171 (match_operator 0 "ccr_eqne_operator"
4172 [(match_operand 1 "cr_operand" "C,C,C,C,C,C,C,C")
4173 (const_int 0)])
4174 (set (match_operand:SI 2 "condexec_dest_operand" "=d,d,U,?f,?f,?d,?f,?m")
4175 (match_operand:SI 3 "condexec_source_operand" "dO,U,dO,f,d,f,m,f")))]
4176 "register_operand(operands[2], SImode) || reg_or_0_operand (operands[3], SImode)"
4177 "* return output_condmove_single (operands, insn);"
4178 [(set_attr "length" "4")
4179 (set_attr "type" "int,gload,gstore,fsconv,movgf,movfg,fload,fstore")])
4180
4181
4182 (define_insn "*cond_exec_movsf_has_fprs"
4183 [(cond_exec
4184 (match_operator 0 "ccr_eqne_operator"
4185 [(match_operand 1 "cr_operand" "C,C,C,C,C,C,C,C,C,C")
4186 (const_int 0)])
4187 (set (match_operand:SF 2 "condexec_dest_operand" "=f,?d,?d,?f,f,f,?d,U,?U,U")
4188 (match_operand:SF 3 "condexec_source_operand" "f,d,f,d,G,U,U,f,d,G")))]
4189 "TARGET_HAS_FPRS"
4190 "* return output_condmove_single (operands, insn);"
4191 [(set_attr "length" "4")
4192 (set_attr "type" "fsconv,int,movgf,movfg,movgf,fload,gload,fstore,gstore,gstore")])
4193
4194 (define_insn "*cond_exec_movsf_no_fprs"
4195 [(cond_exec
4196 (match_operator 0 "ccr_eqne_operator"
4197 [(match_operand 1 "cr_operand" "C,C,C")
4198 (const_int 0)])
4199 (set (match_operand:SF 2 "condexec_dest_operand" "=d,d,U")
4200 (match_operand:SF 3 "condexec_source_operand" "d,U,dG")))]
4201 "! TARGET_HAS_FPRS"
4202 "* return output_condmove_single (operands, insn);"
4203 [(set_attr "length" "4")
4204 (set_attr "type" "int,gload,gstore")])
4205
4206 (define_insn "*cond_exec_si_binary1"
4207 [(cond_exec
4208 (match_operator 0 "ccr_eqne_operator"
4209 [(match_operand 1 "cr_operand" "C")
4210 (const_int 0)])
4211 (set (match_operand:SI 2 "integer_register_operand" "=d")
4212 (match_operator:SI 3 "condexec_si_binary_operator"
4213 [(match_operand:SI 4 "integer_register_operand" "d")
4214 (match_operand:SI 5 "integer_register_operand" "d")])))]
4215 ""
4216 "*
4217 {
4218 switch (GET_CODE (operands[3]))
4219 {
4220 case PLUS: return \"cadd %4, %z5, %2, %1, %e0\";
4221 case MINUS: return \"csub %4, %z5, %2, %1, %e0\";
4222 case AND: return \"cand %4, %z5, %2, %1, %e0\";
4223 case IOR: return \"cor %4, %z5, %2, %1, %e0\";
4224 case XOR: return \"cxor %4, %z5, %2, %1, %e0\";
4225 case ASHIFT: return \"csll %4, %z5, %2, %1, %e0\";
4226 case ASHIFTRT: return \"csra %4, %z5, %2, %1, %e0\";
4227 case LSHIFTRT: return \"csrl %4, %z5, %2, %1, %e0\";
4228 default: abort ();
4229 }
4230 }"
4231 [(set_attr "length" "4")
4232 (set_attr "type" "int")])
4233
4234 (define_insn "*cond_exec_si_binary2"
4235 [(cond_exec
4236 (match_operator 0 "ccr_eqne_operator"
4237 [(match_operand 1 "cr_operand" "C")
4238 (const_int 0)])
4239 (set (match_operand:SI 2 "fpr_operand" "=f")
4240 (match_operator:SI 3 "condexec_si_media_operator"
4241 [(match_operand:SI 4 "fpr_operand" "f")
4242 (match_operand:SI 5 "fpr_operand" "f")])))]
4243 "TARGET_MEDIA"
4244 "*
4245 {
4246 switch (GET_CODE (operands[3]))
4247 {
4248 case AND: return \"cmand %4, %5, %2, %1, %e0\";
4249 case IOR: return \"cmor %4, %5, %2, %1, %e0\";
4250 case XOR: return \"cmxor %4, %5, %2, %1, %e0\";
4251 default: abort ();
4252 }
4253 }"
4254 [(set_attr "length" "4")
4255 (set_attr "type" "mlogic")])
4256
4257 ;; Note, flow does not (currently) know how to handle an operation that uses
4258 ;; only part of the hard registers allocated for a multiregister value, such as
4259 ;; DImode in this case if the user is only interested in the lower 32-bits. So
4260 ;; we emit a USE of the entire register after the csmul instruction so it won't
4261 ;; get confused. See frv_ifcvt_modify_insn for more details.
4262
4263 (define_insn "*cond_exec_si_smul"
4264 [(cond_exec
4265 (match_operator 0 "ccr_eqne_operator"
4266 [(match_operand 1 "cr_operand" "C")
4267 (const_int 0)])
4268 (set (match_operand:DI 2 "even_gpr_operand" "=e")
4269 (mult:DI (sign_extend:DI (match_operand:SI 3 "integer_register_operand" "%d"))
4270 (sign_extend:DI (match_operand:SI 4 "integer_register_operand" "d")))))]
4271 ""
4272 "csmul %3, %4, %2, %1, %e0"
4273 [(set_attr "length" "4")
4274 (set_attr "type" "mul")])
4275
4276 (define_insn "*cond_exec_si_divide"
4277 [(cond_exec
4278 (match_operator 0 "ccr_eqne_operator"
4279 [(match_operand 1 "cr_operand" "C")
4280 (const_int 0)])
4281 (set (match_operand:SI 2 "integer_register_operand" "=d")
4282 (match_operator:SI 3 "condexec_si_divide_operator"
4283 [(match_operand:SI 4 "integer_register_operand" "d")
4284 (match_operand:SI 5 "integer_register_operand" "d")])))]
4285 ""
4286 "*
4287 {
4288 switch (GET_CODE (operands[3]))
4289 {
4290 case DIV: return \"csdiv %4, %z5, %2, %1, %e0\";
4291 case UDIV: return \"cudiv %4, %z5, %2, %1, %e0\";
4292 default: abort ();
4293 }
4294 }"
4295 [(set_attr "length" "4")
4296 (set_attr "type" "div")])
4297
4298 (define_insn "*cond_exec_si_unary1"
4299 [(cond_exec
4300 (match_operator 0 "ccr_eqne_operator"
4301 [(match_operand 1 "cr_operand" "C")
4302 (const_int 0)])
4303 (set (match_operand:SI 2 "integer_register_operand" "=d")
4304 (match_operator:SI 3 "condexec_si_unary_operator"
4305 [(match_operand:SI 4 "integer_register_operand" "d")])))]
4306 ""
4307 "*
4308 {
4309 switch (GET_CODE (operands[3]))
4310 {
4311 case NOT: return \"cnot %4, %2, %1, %e0\";
4312 case NEG: return \"csub %., %4, %2, %1, %e0\";
4313 default: abort ();
4314 }
4315 }"
4316 [(set_attr "length" "4")
4317 (set_attr "type" "int")])
4318
4319 (define_insn "*cond_exec_si_unary2"
4320 [(cond_exec
4321 (match_operator 0 "ccr_eqne_operator"
4322 [(match_operand 1 "cr_operand" "C")
4323 (const_int 0)])
4324 (set (match_operand:SI 2 "fpr_operand" "=f")
4325 (not:SI (match_operand:SI 3 "fpr_operand" "f"))))]
4326 "TARGET_MEDIA"
4327 "cmnot %3, %2, %1, %e0"
4328 [(set_attr "length" "4")
4329 (set_attr "type" "mlogic")])
4330
4331 (define_insn "*cond_exec_cmpsi_cc"
4332 [(cond_exec
4333 (match_operator 0 "ccr_eqne_operator"
4334 [(match_operand 1 "cr_operand" "C")
4335 (const_int 0)])
4336 (set (match_operand:CC 2 "icc_operand" "=t")
4337 (compare:CC (match_operand:SI 3 "integer_register_operand" "d")
4338 (match_operand:SI 4 "reg_or_0_operand" "dO"))))]
4339 "reload_completed
4340 && REGNO (operands[1]) == REGNO (operands[2]) - ICC_FIRST + ICR_FIRST"
4341 "ccmp %3, %z4, %1, %e0"
4342 [(set_attr "length" "4")
4343 (set_attr "type" "int")])
4344
4345 (define_insn "*cond_exec_cmpsi_cc_uns"
4346 [(cond_exec
4347 (match_operator 0 "ccr_eqne_operator"
4348 [(match_operand 1 "cr_operand" "C")
4349 (const_int 0)])
4350 (set (match_operand:CC_UNS 2 "icc_operand" "=t")
4351 (compare:CC_UNS (match_operand:SI 3 "integer_register_operand" "d")
4352 (match_operand:SI 4 "reg_or_0_operand" "dO"))))]
4353 "reload_completed
4354 && REGNO (operands[1]) == REGNO (operands[2]) - ICC_FIRST + ICR_FIRST"
4355 "ccmp %3, %z4, %1, %e0"
4356 [(set_attr "length" "4")
4357 (set_attr "type" "int")])
4358
4359 (define_insn "*cond_exec_sf_conv"
4360 [(cond_exec
4361 (match_operator 0 "ccr_eqne_operator"
4362 [(match_operand 1 "cr_operand" "C")
4363 (const_int 0)])
4364 (set (match_operand:SF 2 "fpr_operand" "=f")
4365 (match_operator:SF 3 "condexec_sf_conv_operator"
4366 [(match_operand:SF 4 "fpr_operand" "f")])))]
4367 "TARGET_HARD_FLOAT"
4368 "*
4369 {
4370 switch (GET_CODE (operands[3]))
4371 {
4372 case ABS: return \"cfabss %4, %2, %1, %e0\";
4373 case NEG: return \"cfnegs %4, %2, %1, %e0\";
4374 default: abort ();
4375 }
4376 }"
4377 [(set_attr "length" "4")
4378 (set_attr "type" "fsconv")])
4379
4380 (define_insn "*cond_exec_sf_add"
4381 [(cond_exec
4382 (match_operator 0 "ccr_eqne_operator"
4383 [(match_operand 1 "cr_operand" "C")
4384 (const_int 0)])
4385 (set (match_operand:SF 2 "fpr_operand" "=f")
4386 (match_operator:SF 3 "condexec_sf_add_operator"
4387 [(match_operand:SF 4 "fpr_operand" "f")
4388 (match_operand:SF 5 "fpr_operand" "f")])))]
4389 "TARGET_HARD_FLOAT"
4390 "*
4391 {
4392 switch (GET_CODE (operands[3]))
4393 {
4394 case PLUS: return \"cfadds %4, %5, %2, %1, %e0\";
4395 case MINUS: return \"cfsubs %4, %5, %2, %1, %e0\";
4396 default: abort ();
4397 }
4398 }"
4399 [(set_attr "length" "4")
4400 (set_attr "type" "fsadd")])
4401
4402 (define_insn "*cond_exec_sf_mul"
4403 [(cond_exec
4404 (match_operator 0 "ccr_eqne_operator"
4405 [(match_operand 1 "cr_operand" "C")
4406 (const_int 0)])
4407 (set (match_operand:SF 2 "fpr_operand" "=f")
4408 (mult:SF (match_operand:SF 3 "fpr_operand" "f")
4409 (match_operand:SF 4 "fpr_operand" "f"))))]
4410 "TARGET_HARD_FLOAT"
4411 "cfmuls %3, %4, %2, %1, %e0"
4412 [(set_attr "length" "4")
4413 (set_attr "type" "fsmul")])
4414
4415 (define_insn "*cond_exec_sf_div"
4416 [(cond_exec
4417 (match_operator 0 "ccr_eqne_operator"
4418 [(match_operand 1 "cr_operand" "C")
4419 (const_int 0)])
4420 (set (match_operand:SF 2 "fpr_operand" "=f")
4421 (div:SF (match_operand:SF 3 "fpr_operand" "f")
4422 (match_operand:SF 4 "fpr_operand" "f"))))]
4423 "TARGET_HARD_FLOAT"
4424 "cfdivs %3, %4, %2, %1, %e0"
4425 [(set_attr "length" "4")
4426 (set_attr "type" "fsdiv")])
4427
4428 (define_insn "*cond_exec_sf_sqrt"
4429 [(cond_exec
4430 (match_operator 0 "ccr_eqne_operator"
4431 [(match_operand 1 "cr_operand" "C")
4432 (const_int 0)])
4433 (set (match_operand:SF 2 "fpr_operand" "=f")
4434 (sqrt:SF (match_operand:SF 3 "fpr_operand" "f"))))]
4435 "TARGET_HARD_FLOAT"
4436 "cfsqrts %3, %2, %1, %e0"
4437 [(set_attr "length" "4")
4438 (set_attr "type" "fsdiv")])
4439
4440 (define_insn "*cond_exec_cmpsi_cc_fp"
4441 [(cond_exec
4442 (match_operator 0 "ccr_eqne_operator"
4443 [(match_operand 1 "cr_operand" "C")
4444 (const_int 0)])
4445 (set (match_operand:CC_FP 2 "fcc_operand" "=u")
4446 (compare:CC_FP (match_operand:SF 3 "fpr_operand" "f")
4447 (match_operand:SF 4 "fpr_operand" "f"))))]
4448 "reload_completed && TARGET_HARD_FLOAT
4449 && REGNO (operands[1]) == REGNO (operands[2]) - FCC_FIRST + FCR_FIRST"
4450 "cfcmps %3, %4, %2, %1, %e0"
4451 [(set_attr "length" "4")
4452 (set_attr "type" "fsconv")])
4453
4454 \f
4455 ;; ::::::::::::::::::::
4456 ;; ::
4457 ;; :: Logical operations on CR registers
4458 ;; ::
4459 ;; ::::::::::::::::::::
4460
4461 ;; We use UNSPEC to encode andcr/iorcr/etc. rather than the normal RTL
4462 ;; operations, since the RTL operations only have an idea of TRUE and FALSE,
4463 ;; while the CRs have TRUE, FALSE, and UNDEFINED.
4464
4465 (define_expand "andcr"
4466 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4467 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4468 (match_operand:CC_CCR 2 "cr_operand" "")
4469 (const_int 0)] UNSPEC_CR_LOGIC))]
4470 ""
4471 "")
4472
4473 (define_expand "orcr"
4474 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4475 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4476 (match_operand:CC_CCR 2 "cr_operand" "")
4477 (const_int 1)] UNSPEC_CR_LOGIC))]
4478 ""
4479 "")
4480
4481 (define_expand "xorcr"
4482 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4483 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4484 (match_operand:CC_CCR 2 "cr_operand" "")
4485 (const_int 2)] UNSPEC_CR_LOGIC))]
4486 ""
4487 "")
4488
4489 (define_expand "nandcr"
4490 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4491 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4492 (match_operand:CC_CCR 2 "cr_operand" "")
4493 (const_int 3)] UNSPEC_CR_LOGIC))]
4494 ""
4495 "")
4496
4497 (define_expand "norcr"
4498 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4499 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4500 (match_operand:CC_CCR 2 "cr_operand" "")
4501 (const_int 4)] UNSPEC_CR_LOGIC))]
4502 ""
4503 "")
4504
4505 (define_expand "andncr"
4506 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4507 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4508 (match_operand:CC_CCR 2 "cr_operand" "")
4509 (const_int 5)] UNSPEC_CR_LOGIC))]
4510 ""
4511 "")
4512
4513 (define_expand "orncr"
4514 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4515 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4516 (match_operand:CC_CCR 2 "cr_operand" "")
4517 (const_int 6)] UNSPEC_CR_LOGIC))]
4518 ""
4519 "")
4520
4521 (define_expand "nandncr"
4522 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4523 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4524 (match_operand:CC_CCR 2 "cr_operand" "")
4525 (const_int 7)] UNSPEC_CR_LOGIC))]
4526 ""
4527 "")
4528
4529 (define_expand "norncr"
4530 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4531 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4532 (match_operand:CC_CCR 2 "cr_operand" "")
4533 (const_int 8)] UNSPEC_CR_LOGIC))]
4534 ""
4535 "")
4536
4537 (define_expand "notcr"
4538 [(set (match_operand:CC_CCR 0 "cr_operand" "")
4539 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "")
4540 (match_dup 1)
4541 (const_int 9)] UNSPEC_CR_LOGIC))]
4542 ""
4543 "")
4544
4545 (define_insn "*logical_cr"
4546 [(set (match_operand:CC_CCR 0 "cr_operand" "=C")
4547 (unspec:CC_CCR [(match_operand:CC_CCR 1 "cr_operand" "C")
4548 (match_operand:CC_CCR 2 "cr_operand" "C")
4549 (match_operand:SI 3 "const_int_operand" "n")]
4550 UNSPEC_CR_LOGIC))]
4551 ""
4552 "*
4553 {
4554 switch (INTVAL (operands[3]))
4555 {
4556 default: break;
4557 case 0: return \"andcr %1, %2, %0\";
4558 case 1: return \"orcr %1, %2, %0\";
4559 case 2: return \"xorcr %1, %2, %0\";
4560 case 3: return \"nandcr %1, %2, %0\";
4561 case 4: return \"norcr %1, %2, %0\";
4562 case 5: return \"andncr %1, %2, %0\";
4563 case 6: return \"orncr %1, %2, %0\";
4564 case 7: return \"nandncr %1, %2, %0\";
4565 case 8: return \"norncr %1, %2, %0\";
4566 case 9: return \"notcr %1, %0\";
4567 }
4568
4569 fatal_insn (\"logical_cr\", insn);
4570 }"
4571 [(set_attr "length" "4")
4572 (set_attr "type" "ccr")])
4573
4574 \f
4575 ;; ::::::::::::::::::::
4576 ;; ::
4577 ;; :: Conditional move instructions
4578 ;; ::
4579 ;; ::::::::::::::::::::
4580
4581
4582 ;; - conditional moves based on floating-point comparisons require
4583 ;; TARGET_HARD_FLOAT, because an FPU is required to do the comparison.
4584
4585 ;; - conditional moves between FPRs based on integer comparisons
4586 ;; require TARGET_HAS_FPRS.
4587
4588 (define_expand "movqicc"
4589 [(set (match_operand:QI 0 "integer_register_operand" "")
4590 (if_then_else:QI (match_operand 1 "" "")
4591 (match_operand:QI 2 "gpr_or_int_operand" "")
4592 (match_operand:QI 3 "gpr_or_int_operand" "")))]
4593 "TARGET_COND_MOVE"
4594 "
4595 {
4596 if (!frv_emit_cond_move (operands[0], operands[1], operands[2], operands[3]))
4597 FAIL;
4598
4599 DONE;
4600 }")
4601
4602 (define_insn "*movqicc_internal1_signed"
4603 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d")
4604 (if_then_else:QI (match_operator:CC 1 "signed_relational_operator"
4605 [(match_operand:CC 2 "icc_operand" "t,t,t")
4606 (const_int 0)])
4607 (match_operand:QI 3 "reg_or_0_operand" "0,dO,dO")
4608 (match_operand:QI 4 "reg_or_0_operand" "dO,0,dO")))
4609 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4610 ""
4611 "#"
4612 [(set_attr "length" "8,8,12")
4613 (set_attr "type" "multi")])
4614
4615 (define_insn "*movqicc_internal1_unsigned"
4616 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d")
4617 (if_then_else:QI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4618 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t")
4619 (const_int 0)])
4620 (match_operand:QI 3 "reg_or_0_operand" "0,dO,dO")
4621 (match_operand:QI 4 "reg_or_0_operand" "dO,0,dO")))
4622 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4623 ""
4624 "#"
4625 [(set_attr "length" "8,8,12")
4626 (set_attr "type" "multi")])
4627
4628 (define_insn "*movqicc_internal1_float"
4629 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d")
4630 (if_then_else:QI (match_operator:CC_FP 1 "float_relational_operator"
4631 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u")
4632 (const_int 0)])
4633 (match_operand:QI 3 "reg_or_0_operand" "0,dO,dO")
4634 (match_operand:QI 4 "reg_or_0_operand" "dO,0,dO")))
4635 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w"))]
4636 "TARGET_HARD_FLOAT"
4637 "#"
4638 [(set_attr "length" "8,8,12")
4639 (set_attr "type" "multi")])
4640
4641 (define_insn "*movqicc_internal2_signed"
4642 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d,d,d")
4643 (if_then_else:QI (match_operator:CC 1 "signed_relational_operator"
4644 [(match_operand:CC 2 "icc_operand" "t,t,t,t,t")
4645 (const_int 0)])
4646 (match_operand:QI 3 "const_int_operand" "O,O,L,n,n")
4647 (match_operand:QI 4 "const_int_operand" "L,n,O,O,n")))
4648 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4649 "(INTVAL (operands[3]) == 0
4650 || INTVAL (operands[4]) == 0
4651 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4652 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4653 "#"
4654 [(set_attr "length" "8,12,8,12,12")
4655 (set_attr "type" "multi")])
4656
4657 (define_insn "*movqicc_internal2_unsigned"
4658 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d,d,d")
4659 (if_then_else:QI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4660 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t,t,t")
4661 (const_int 0)])
4662 (match_operand:QI 3 "const_int_operand" "O,O,L,n,n")
4663 (match_operand:QI 4 "const_int_operand" "L,n,O,O,n")))
4664 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4665 "(INTVAL (operands[3]) == 0
4666 || INTVAL (operands[4]) == 0
4667 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4668 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4669 "#"
4670 [(set_attr "length" "8,12,8,12,12")
4671 (set_attr "type" "multi")])
4672
4673 (define_insn "*movqicc_internal2_float"
4674 [(set (match_operand:QI 0 "integer_register_operand" "=d,d,d,d,d")
4675 (if_then_else:QI (match_operator:CC_FP 1 "float_relational_operator"
4676 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u,u,u")
4677 (const_int 0)])
4678 (match_operand:QI 3 "const_int_operand" "O,O,L,n,n")
4679 (match_operand:QI 4 "const_int_operand" "L,n,O,O,n")))
4680 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w,w,w"))]
4681 "TARGET_HARD_FLOAT
4682 && (INTVAL (operands[3]) == 0
4683 || INTVAL (operands[4]) == 0
4684 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4685 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4686 "#"
4687 [(set_attr "length" "8,12,8,12,12")
4688 (set_attr "type" "multi")])
4689
4690 (define_split
4691 [(set (match_operand:QI 0 "integer_register_operand" "")
4692 (if_then_else:QI (match_operator 1 "relational_operator"
4693 [(match_operand 2 "cc_operand" "")
4694 (const_int 0)])
4695 (match_operand:QI 3 "gpr_or_int_operand" "")
4696 (match_operand:QI 4 "gpr_or_int_operand" "")))
4697 (clobber (match_operand:CC_CCR 5 "cr_operand" ""))]
4698 "reload_completed"
4699 [(match_dup 6)]
4700 "operands[6] = frv_split_cond_move (operands);")
4701
4702 (define_expand "movhicc"
4703 [(set (match_operand:HI 0 "integer_register_operand" "")
4704 (if_then_else:HI (match_operand 1 "" "")
4705 (match_operand:HI 2 "gpr_or_int_operand" "")
4706 (match_operand:HI 3 "gpr_or_int_operand" "")))]
4707 "TARGET_COND_MOVE"
4708 "
4709 {
4710 if (!frv_emit_cond_move (operands[0], operands[1], operands[2], operands[3]))
4711 FAIL;
4712
4713 DONE;
4714 }")
4715
4716 (define_insn "*movhicc_internal1_signed"
4717 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d")
4718 (if_then_else:HI (match_operator:CC 1 "signed_relational_operator"
4719 [(match_operand:CC 2 "icc_operand" "t,t,t")
4720 (const_int 0)])
4721 (match_operand:HI 3 "reg_or_0_operand" "0,dO,dO")
4722 (match_operand:HI 4 "reg_or_0_operand" "dO,0,dO")))
4723 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4724 ""
4725 "#"
4726 [(set_attr "length" "8,8,12")
4727 (set_attr "type" "multi")])
4728
4729 (define_insn "*movhicc_internal1_unsigned"
4730 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d")
4731 (if_then_else:HI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4732 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t")
4733 (const_int 0)])
4734 (match_operand:HI 3 "reg_or_0_operand" "0,dO,dO")
4735 (match_operand:HI 4 "reg_or_0_operand" "dO,0,dO")))
4736 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4737 ""
4738 "#"
4739 [(set_attr "length" "8,8,12")
4740 (set_attr "type" "multi")])
4741
4742 (define_insn "*movhicc_internal1_float"
4743 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d")
4744 (if_then_else:HI (match_operator:CC_FP 1 "float_relational_operator"
4745 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u")
4746 (const_int 0)])
4747 (match_operand:HI 3 "reg_or_0_operand" "0,dO,dO")
4748 (match_operand:HI 4 "reg_or_0_operand" "dO,0,dO")))
4749 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w"))]
4750 "TARGET_HARD_FLOAT"
4751 "#"
4752 [(set_attr "length" "8,8,12")
4753 (set_attr "type" "multi")])
4754
4755 (define_insn "*movhicc_internal2_signed"
4756 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d,d,d")
4757 (if_then_else:HI (match_operator:CC 1 "signed_relational_operator"
4758 [(match_operand:CC 2 "icc_operand" "t,t,t,t,t")
4759 (const_int 0)])
4760 (match_operand:HI 3 "const_int_operand" "O,O,L,n,n")
4761 (match_operand:HI 4 "const_int_operand" "L,n,O,O,n")))
4762 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4763 "(INTVAL (operands[3]) == 0
4764 || INTVAL (operands[4]) == 0
4765 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4766 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4767 "#"
4768 [(set_attr "length" "8,12,8,12,12")
4769 (set_attr "type" "multi")])
4770
4771 (define_insn "*movhicc_internal2_unsigned"
4772 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d,d,d")
4773 (if_then_else:HI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4774 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t,t,t")
4775 (const_int 0)])
4776 (match_operand:HI 3 "const_int_operand" "O,O,L,n,n")
4777 (match_operand:HI 4 "const_int_operand" "L,n,O,O,n")))
4778 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4779 "(INTVAL (operands[3]) == 0
4780 || INTVAL (operands[4]) == 0
4781 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4782 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4783 "#"
4784 [(set_attr "length" "8,12,8,12,12")
4785 (set_attr "type" "multi")])
4786
4787 (define_insn "*movhicc_internal2_float"
4788 [(set (match_operand:HI 0 "integer_register_operand" "=d,d,d,d,d")
4789 (if_then_else:HI (match_operator:CC_FP 1 "float_relational_operator"
4790 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u,u,u")
4791 (const_int 0)])
4792 (match_operand:HI 3 "const_int_operand" "O,O,L,n,n")
4793 (match_operand:HI 4 "const_int_operand" "L,n,O,O,n")))
4794 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w,w,w"))]
4795 "TARGET_HARD_FLOAT
4796 && (INTVAL (operands[3]) == 0
4797 || INTVAL (operands[4]) == 0
4798 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4799 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4800 "#"
4801 [(set_attr "length" "8,12,8,12,12")
4802 (set_attr "type" "multi")])
4803
4804 (define_split
4805 [(set (match_operand:HI 0 "integer_register_operand" "")
4806 (if_then_else:HI (match_operator 1 "relational_operator"
4807 [(match_operand 2 "cc_operand" "")
4808 (const_int 0)])
4809 (match_operand:HI 3 "gpr_or_int_operand" "")
4810 (match_operand:HI 4 "gpr_or_int_operand" "")))
4811 (clobber (match_operand:CC_CCR 5 "cr_operand" ""))]
4812 "reload_completed"
4813 [(match_dup 6)]
4814 "operands[6] = frv_split_cond_move (operands);")
4815
4816 (define_expand "movsicc"
4817 [(set (match_operand:SI 0 "integer_register_operand" "")
4818 (if_then_else:SI (match_operand 1 "" "")
4819 (match_operand:SI 2 "gpr_or_int_operand" "")
4820 (match_operand:SI 3 "gpr_or_int_operand" "")))]
4821 "TARGET_COND_MOVE"
4822 "
4823 {
4824 if (!frv_emit_cond_move (operands[0], operands[1], operands[2], operands[3]))
4825 FAIL;
4826
4827 DONE;
4828 }")
4829
4830 (define_insn "*movsicc_internal1_signed"
4831 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d")
4832 (if_then_else:SI (match_operator:CC 1 "signed_relational_operator"
4833 [(match_operand:CC 2 "icc_operand" "t,t,t")
4834 (const_int 0)])
4835 (match_operand:SI 3 "reg_or_0_operand" "0,dO,dO")
4836 (match_operand:SI 4 "reg_or_0_operand" "dO,0,dO")))
4837 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4838 ""
4839 "#"
4840 [(set_attr "length" "8,8,12")
4841 (set_attr "type" "multi")])
4842
4843 (define_insn "*movsicc_internal1_unsigned"
4844 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d")
4845 (if_then_else:SI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4846 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t")
4847 (const_int 0)])
4848 (match_operand:SI 3 "reg_or_0_operand" "0,dO,dO")
4849 (match_operand:SI 4 "reg_or_0_operand" "dO,0,dO")))
4850 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4851 ""
4852 "#"
4853 [(set_attr "length" "8,8,12")
4854 (set_attr "type" "multi")])
4855
4856 (define_insn "*movsicc_internal1_float"
4857 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d")
4858 (if_then_else:SI (match_operator:CC_FP 1 "float_relational_operator"
4859 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u")
4860 (const_int 0)])
4861 (match_operand:SI 3 "reg_or_0_operand" "0,dO,dO")
4862 (match_operand:SI 4 "reg_or_0_operand" "dO,0,dO")))
4863 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w"))]
4864 "TARGET_HARD_FLOAT"
4865 "#"
4866 [(set_attr "length" "8,8,12")
4867 (set_attr "type" "multi")])
4868
4869 (define_insn "*movsicc_internal2_signed"
4870 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d,d,d")
4871 (if_then_else:SI (match_operator:CC 1 "signed_relational_operator"
4872 [(match_operand:CC 2 "icc_operand" "t,t,t,t,t")
4873 (const_int 0)])
4874 (match_operand:SI 3 "const_int_operand" "O,O,L,n,n")
4875 (match_operand:SI 4 "const_int_operand" "L,n,O,O,n")))
4876 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4877 "(INTVAL (operands[3]) == 0
4878 || INTVAL (operands[4]) == 0
4879 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4880 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4881 "#"
4882 [(set_attr "length" "8,12,8,12,12")
4883 (set_attr "type" "multi")])
4884
4885 (define_insn "*movsicc_internal2_unsigned"
4886 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d,d,d")
4887 (if_then_else:SI (match_operator:CC_UNS 1 "unsigned_relational_operator"
4888 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t,t,t")
4889 (const_int 0)])
4890 (match_operand:SI 3 "const_int_operand" "O,O,L,n,n")
4891 (match_operand:SI 4 "const_int_operand" "L,n,O,O,n")))
4892 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v"))]
4893 "(INTVAL (operands[3]) == 0
4894 || INTVAL (operands[4]) == 0
4895 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4896 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4897 "#"
4898 [(set_attr "length" "8,12,8,12,12")
4899 (set_attr "type" "multi")])
4900
4901 (define_insn "*movsicc_internal2_float"
4902 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,d,d,d")
4903 (if_then_else:SI (match_operator:CC_FP 1 "float_relational_operator"
4904 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u,u,u")
4905 (const_int 0)])
4906 (match_operand:SI 3 "const_int_operand" "O,O,L,n,n")
4907 (match_operand:SI 4 "const_int_operand" "L,n,O,O,n")))
4908 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w,w,w"))]
4909 "TARGET_HARD_FLOAT
4910 && (INTVAL (operands[3]) == 0
4911 || INTVAL (operands[4]) == 0
4912 || (IN_RANGE_P (INTVAL (operands[3]), -2048, 2047)
4913 && IN_RANGE_P (INTVAL (operands[4]) - INTVAL (operands[3]), -2048, 2047)))"
4914 "#"
4915 [(set_attr "length" "8,12,8,12,12")
4916 (set_attr "type" "multi")])
4917
4918 (define_split
4919 [(set (match_operand:SI 0 "integer_register_operand" "")
4920 (if_then_else:SI (match_operator 1 "relational_operator"
4921 [(match_operand 2 "cc_operand" "")
4922 (const_int 0)])
4923 (match_operand:SI 3 "gpr_or_int_operand" "")
4924 (match_operand:SI 4 "gpr_or_int_operand" "")))
4925 (clobber (match_operand:CC_CCR 5 "cr_operand" ""))]
4926 "reload_completed"
4927 [(match_dup 6)]
4928 "operands[6] = frv_split_cond_move (operands);")
4929
4930 (define_expand "movsfcc"
4931 [(set (match_operand:SF 0 "register_operand" "")
4932 (if_then_else:SF (match_operand 1 "" "")
4933 (match_operand:SF 2 "register_operand" "")
4934 (match_operand:SF 3 "register_operand" "")))]
4935 "TARGET_COND_MOVE"
4936 "
4937 {
4938 if (!frv_emit_cond_move (operands[0], operands[1], operands[2], operands[3]))
4939 FAIL;
4940
4941 DONE;
4942 }")
4943
4944 (define_insn "*movsfcc_has_fprs_signed"
4945 [(set (match_operand:SF 0 "register_operand" "=f,f,f,?f,?f,?d")
4946 (if_then_else:SF (match_operator:CC 1 "signed_relational_operator"
4947 [(match_operand:CC 2 "icc_operand" "t,t,t,t,t,t")
4948 (const_int 0)])
4949 (match_operand:SF 3 "register_operand" "0,f,f,f,d,fd")
4950 (match_operand:SF 4 "register_operand" "f,0,f,d,fd,fd")))
4951 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v,v"))]
4952 "TARGET_HAS_FPRS"
4953 "#"
4954 [(set_attr "length" "8,8,12,12,12,12")
4955 (set_attr "type" "multi")])
4956
4957 (define_insn "*movsfcc_has_fprs_unsigned"
4958 [(set (match_operand:SF 0 "register_operand" "=f,f,f,?f,?f,?d")
4959 (if_then_else:SF (match_operator:CC_UNS 1 "unsigned_relational_operator"
4960 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t,t,t,t")
4961 (const_int 0)])
4962 (match_operand:SF 3 "register_operand" "0,f,f,f,d,fd")
4963 (match_operand:SF 4 "register_operand" "f,0,f,d,fd,fd")))
4964 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v,v,v,v"))]
4965 "TARGET_HAS_FPRS"
4966 "#"
4967 [(set_attr "length" "8,8,12,12,12,12")
4968 (set_attr "type" "multi")])
4969
4970 (define_insn "*movsfcc_hardfloat_float"
4971 [(set (match_operand:SF 0 "register_operand" "=f,f,f,?f,?f,?d")
4972 (if_then_else:SF (match_operator:CC_FP 1 "float_relational_operator"
4973 [(match_operand:CC_FP 2 "fcc_operand" "u,u,u,u,u,u")
4974 (const_int 0)])
4975 (match_operand:SF 3 "register_operand" "0,f,f,f,d,fd")
4976 (match_operand:SF 4 "register_operand" "f,0,f,d,fd,fd")))
4977 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w,w,w,w"))]
4978 "TARGET_HARD_FLOAT"
4979 "#"
4980 [(set_attr "length" "8,8,12,12,12,12")
4981 (set_attr "type" "multi")])
4982
4983 (define_insn "*movsfcc_no_fprs_signed"
4984 [(set (match_operand:SF 0 "integer_register_operand" "=d,d,d")
4985 (if_then_else:SF (match_operator:CC 1 "signed_relational_operator"
4986 [(match_operand:CC 2 "icc_operand" "t,t,t")
4987 (const_int 0)])
4988 (match_operand:SF 3 "integer_register_operand" "0,d,d")
4989 (match_operand:SF 4 "integer_register_operand" "d,0,d")))
4990 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
4991 "! TARGET_HAS_FPRS"
4992 "#"
4993 [(set_attr "length" "8,8,12")
4994 (set_attr "type" "multi")])
4995
4996 (define_insn "*movsfcc_no_fprs_unsigned"
4997 [(set (match_operand:SF 0 "integer_register_operand" "=d,d,d")
4998 (if_then_else:SF (match_operator:CC_UNS 1 "unsigned_relational_operator"
4999 [(match_operand:CC_UNS 2 "icc_operand" "t,t,t")
5000 (const_int 0)])
5001 (match_operand:SF 3 "integer_register_operand" "0,d,d")
5002 (match_operand:SF 4 "integer_register_operand" "d,0,d")))
5003 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
5004 "! TARGET_HAS_FPRS"
5005 "#"
5006 [(set_attr "length" "8,8,12")
5007 (set_attr "type" "multi")])
5008
5009 (define_split
5010 [(set (match_operand:SF 0 "register_operand" "")
5011 (if_then_else:SF (match_operator 1 "relational_operator"
5012 [(match_operand 2 "cc_operand" "")
5013 (const_int 0)])
5014 (match_operand:SF 3 "register_operand" "")
5015 (match_operand:SF 4 "register_operand" "")))
5016 (clobber (match_operand:CC_CCR 5 "cr_operand" ""))]
5017 "reload_completed"
5018 [(match_dup 6)]
5019 "operands[6] = frv_split_cond_move (operands);")
5020
5021 \f
5022 ;; ::::::::::::::::::::
5023 ;; ::
5024 ;; :: Minimum, maximum, and integer absolute value
5025 ;; ::
5026 ;; ::::::::::::::::::::
5027
5028 ;; These 'instructions' are provided to give the compiler a slightly better
5029 ;; nudge at register allocation, then it would if it constructed the
5030 ;; instructions from basic building blocks (since it indicates it prefers one
5031 ;; of the operands to be the same as the destination. It also helps the
5032 ;; earlier passes of the compiler, by not breaking things into small basic
5033 ;; blocks.
5034
5035 (define_expand "abssi2"
5036 [(parallel [(set (match_operand:SI 0 "integer_register_operand" "")
5037 (abs:SI (match_operand:SI 1 "integer_register_operand" "")))
5038 (clobber (match_dup 2))
5039 (clobber (match_dup 3))])]
5040 "TARGET_COND_MOVE"
5041 "
5042 {
5043 operands[2] = gen_reg_rtx (CCmode);
5044 operands[3] = gen_reg_rtx (CC_CCRmode);
5045 }")
5046
5047 (define_insn_and_split "*abssi2_internal"
5048 [(set (match_operand:SI 0 "integer_register_operand" "=d,d")
5049 (abs:SI (match_operand:SI 1 "integer_register_operand" "0,d")))
5050 (clobber (match_operand:CC 2 "icc_operand" "=t,t"))
5051 (clobber (match_operand:CC_CCR 3 "icr_operand" "=v,v"))]
5052 "TARGET_COND_MOVE"
5053 "#"
5054 "reload_completed"
5055 [(match_dup 4)]
5056 "operands[4] = frv_split_abs (operands);"
5057 [(set_attr "length" "12,16")
5058 (set_attr "type" "multi")])
5059
5060 (define_expand "sminsi3"
5061 [(parallel [(set (match_operand:SI 0 "integer_register_operand" "")
5062 (smin:SI (match_operand:SI 1 "integer_register_operand" "")
5063 (match_operand:SI 2 "gpr_or_int10_operand" "")))
5064 (clobber (match_dup 3))
5065 (clobber (match_dup 4))])]
5066 "TARGET_COND_MOVE"
5067 "
5068 {
5069 operands[3] = gen_reg_rtx (CCmode);
5070 operands[4] = gen_reg_rtx (CC_CCRmode);
5071 }")
5072
5073 (define_expand "smaxsi3"
5074 [(parallel [(set (match_operand:SI 0 "integer_register_operand" "")
5075 (smax:SI (match_operand:SI 1 "integer_register_operand" "")
5076 (match_operand:SI 2 "gpr_or_int10_operand" "")))
5077 (clobber (match_dup 3))
5078 (clobber (match_dup 4))])]
5079 "TARGET_COND_MOVE"
5080 "
5081 {
5082 operands[3] = gen_reg_rtx (CCmode);
5083 operands[4] = gen_reg_rtx (CC_CCRmode);
5084 }")
5085
5086 (define_insn_and_split "*minmax_si_signed"
5087 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,&d")
5088 (match_operator:SI 1 "minmax_operator"
5089 [(match_operand:SI 2 "integer_register_operand" "%0,dO,d")
5090 (match_operand:SI 3 "gpr_or_int10_operand" "dO,0,dJ")]))
5091 (clobber (match_operand:CC 4 "icc_operand" "=t,t,t"))
5092 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
5093 "TARGET_COND_MOVE"
5094 "#"
5095 "reload_completed"
5096 [(match_dup 6)]
5097 "operands[6] = frv_split_minmax (operands);"
5098 [(set_attr "length" "12,12,16")
5099 (set_attr "type" "multi")])
5100
5101 (define_expand "uminsi3"
5102 [(parallel [(set (match_operand:SI 0 "integer_register_operand" "")
5103 (umin:SI (match_operand:SI 1 "integer_register_operand" "")
5104 (match_operand:SI 2 "gpr_or_int10_operand" "")))
5105 (clobber (match_dup 3))
5106 (clobber (match_dup 4))])]
5107 "TARGET_COND_MOVE"
5108 "
5109 {
5110 operands[3] = gen_reg_rtx (CC_UNSmode);
5111 operands[4] = gen_reg_rtx (CC_CCRmode);
5112 }")
5113
5114 (define_expand "umaxsi3"
5115 [(parallel [(set (match_operand:SI 0 "integer_register_operand" "")
5116 (umax:SI (match_operand:SI 1 "integer_register_operand" "")
5117 (match_operand:SI 2 "gpr_or_int10_operand" "")))
5118 (clobber (match_dup 3))
5119 (clobber (match_dup 4))])]
5120 "TARGET_COND_MOVE"
5121 "
5122 {
5123 operands[3] = gen_reg_rtx (CC_UNSmode);
5124 operands[4] = gen_reg_rtx (CC_CCRmode);
5125 }")
5126
5127 (define_insn_and_split "*minmax_si_unsigned"
5128 [(set (match_operand:SI 0 "integer_register_operand" "=d,d,&d")
5129 (match_operator:SI 1 "minmax_operator"
5130 [(match_operand:SI 2 "integer_register_operand" "%0,dO,d")
5131 (match_operand:SI 3 "gpr_or_int10_operand" "dO,0,dJ")]))
5132 (clobber (match_operand:CC_UNS 4 "icc_operand" "=t,t,t"))
5133 (clobber (match_operand:CC_CCR 5 "icr_operand" "=v,v,v"))]
5134 "TARGET_COND_MOVE"
5135 "#"
5136 "reload_completed"
5137 [(match_dup 6)]
5138 "operands[6] = frv_split_minmax (operands);"
5139 [(set_attr "length" "12,12,16")
5140 (set_attr "type" "multi")])
5141
5142 (define_expand "sminsf3"
5143 [(parallel [(set (match_operand:SF 0 "fpr_operand" "")
5144 (smin:SF (match_operand:SF 1 "fpr_operand" "")
5145 (match_operand:SF 2 "fpr_operand" "")))
5146 (clobber (match_dup 3))
5147 (clobber (match_dup 4))])]
5148 "TARGET_COND_MOVE && TARGET_HARD_FLOAT"
5149 "
5150 {
5151 operands[3] = gen_reg_rtx (CC_FPmode);
5152 operands[4] = gen_reg_rtx (CC_CCRmode);
5153 }")
5154
5155 (define_expand "smaxsf3"
5156 [(parallel [(set (match_operand:SF 0 "fpr_operand" "")
5157 (smax:SF (match_operand:SF 1 "fpr_operand" "")
5158 (match_operand:SF 2 "fpr_operand" "")))
5159 (clobber (match_dup 3))
5160 (clobber (match_dup 4))])]
5161 "TARGET_COND_MOVE && TARGET_HARD_FLOAT"
5162 "
5163 {
5164 operands[3] = gen_reg_rtx (CC_FPmode);
5165 operands[4] = gen_reg_rtx (CC_CCRmode);
5166 }")
5167
5168 (define_insn_and_split "*minmax_sf"
5169 [(set (match_operand:SF 0 "fpr_operand" "=f,f,f")
5170 (match_operator:SF 1 "minmax_operator"
5171 [(match_operand:SF 2 "fpr_operand" "%0,f,f")
5172 (match_operand:SF 3 "fpr_operand" "f,0,f")]))
5173 (clobber (match_operand:CC_FP 4 "fcc_operand" "=u,u,u"))
5174 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w"))]
5175 "TARGET_COND_MOVE && TARGET_HARD_FLOAT"
5176 "#"
5177 "reload_completed"
5178 [(match_dup 6)]
5179 "operands[6] = frv_split_minmax (operands);"
5180 [(set_attr "length" "12,12,16")
5181 (set_attr "type" "multi")])
5182
5183 (define_expand "smindf3"
5184 [(parallel [(set (match_operand:DF 0 "fpr_operand" "")
5185 (smin:DF (match_operand:DF 1 "fpr_operand" "")
5186 (match_operand:DF 2 "fpr_operand" "")))
5187 (clobber (match_dup 3))
5188 (clobber (match_dup 4))])]
5189 "TARGET_COND_MOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE"
5190 "
5191 {
5192 operands[3] = gen_reg_rtx (CC_FPmode);
5193 operands[4] = gen_reg_rtx (CC_CCRmode);
5194 }")
5195
5196 (define_expand "smaxdf3"
5197 [(parallel [(set (match_operand:DF 0 "fpr_operand" "")
5198 (smax:DF (match_operand:DF 1 "fpr_operand" "")
5199 (match_operand:DF 2 "fpr_operand" "")))
5200 (clobber (match_dup 3))
5201 (clobber (match_dup 4))])]
5202 "TARGET_COND_MOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE"
5203 "
5204 {
5205 operands[3] = gen_reg_rtx (CC_FPmode);
5206 operands[4] = gen_reg_rtx (CC_CCRmode);
5207 }")
5208
5209 (define_insn_and_split "*minmax_df"
5210 [(set (match_operand:DF 0 "fpr_operand" "=f,f,f")
5211 (match_operator:DF 1 "minmax_operator"
5212 [(match_operand:DF 2 "fpr_operand" "%0,f,f")
5213 (match_operand:DF 3 "fpr_operand" "f,0,f")]))
5214 (clobber (match_operand:CC_FP 4 "fcc_operand" "=u,u,u"))
5215 (clobber (match_operand:CC_CCR 5 "fcr_operand" "=w,w,w"))]
5216 "TARGET_COND_MOVE && TARGET_HARD_FLOAT && TARGET_DOUBLE"
5217 "#"
5218 "reload_completed"
5219 [(match_dup 6)]
5220 "operands[6] = frv_split_minmax (operands);"
5221 [(set_attr "length" "12,12,16")
5222 (set_attr "type" "multi")])
5223
5224 \f
5225 ;; ::::::::::::::::::::
5226 ;; ::
5227 ;; :: Call and branch instructions
5228 ;; ::
5229 ;; ::::::::::::::::::::
5230
5231 ;; Subroutine call instruction returning no value. Operand 0 is the function
5232 ;; to call; operand 1 is the number of bytes of arguments pushed (in mode
5233 ;; `SImode', except it is normally a `const_int'); operand 2 is the number of
5234 ;; registers used as operands.
5235
5236 ;; On most machines, operand 2 is not actually stored into the RTL pattern. It
5237 ;; is supplied for the sake of some RISC machines which need to put this
5238 ;; information into the assembler code; they can put it in the RTL instead of
5239 ;; operand 1.
5240
5241 (define_expand "call"
5242 [(use (match_operand:QI 0 "" ""))
5243 (use (match_operand 1 "" ""))
5244 (use (match_operand 2 "" ""))
5245 (use (match_operand 3 "" ""))]
5246 ""
5247 "
5248 {
5249 rtx lr = gen_rtx_REG (Pmode, LR_REGNO);
5250 rtx addr;
5251
5252 if (GET_CODE (operands[0]) != MEM)
5253 abort ();
5254
5255 addr = XEXP (operands[0], 0);
5256 if (! call_operand (addr, Pmode))
5257 addr = force_reg (Pmode, addr);
5258
5259 if (! operands[2])
5260 operands[2] = const0_rtx;
5261
5262 if (TARGET_FDPIC)
5263 frv_expand_fdpic_call (operands, 0);
5264 else
5265 emit_call_insn (gen_call_internal (addr, operands[1], operands[2], lr));
5266
5267 DONE;
5268 }")
5269
5270 (define_insn "call_internal"
5271 [(call (mem:QI (match_operand:SI 0 "call_operand" "S,dNOP"))
5272 (match_operand 1 "" ""))
5273 (use (match_operand 2 "" ""))
5274 (clobber (match_operand:SI 3 "lr_operand" "=l,l"))]
5275 "! TARGET_FDPIC"
5276 "@
5277 call %0
5278 call%i0l %M0"
5279 [(set_attr "length" "4")
5280 (set_attr "type" "call,jumpl")])
5281
5282 ;; The odd use of GR0 within the UNSPEC below prevents cseing or
5283 ;; hoisting function descriptor loads out of loops. This is almost
5284 ;; never desirable, since if we preserve the function descriptor in a
5285 ;; pair of registers, it takes two insns to move it to gr14/gr15, and
5286 ;; if it's in the stack, we just waste space with the store, since
5287 ;; we'll have to load back from memory anyway. And, in the worst
5288 ;; case, we may end up reusing a function descriptor still pointing at
5289 ;; a PLT entry, instead of to the resolved function, which means going
5290 ;; through the resolver for every call that uses the outdated value.
5291 ;; Bad!
5292
5293 ;; The explicit MEM inside the SPEC prevents the compiler from moving
5294 ;; the load before a branch after a NULL test, or before a store that
5295 ;; initializes a function descriptor.
5296
5297 (define_insn "movdi_ldd"
5298 [(set (match_operand:DI 0 "fdpic_fptr_operand" "=e")
5299 (unspec:DI [(mem:DI (match_operand:SI 1 "ldd_address_operand" "p"))
5300 (reg:SI 0)] UNSPEC_LDD))]
5301 ""
5302 "ldd%I1 %M1, %0"
5303 [(set_attr "length" "4")
5304 (set_attr "type" "gload")])
5305
5306 (define_insn "call_fdpicdi"
5307 [(call (mem:QI (match_operand:DI 0 "fdpic_fptr_operand" "W"))
5308 (match_operand 1 "" ""))
5309 (clobber (match_operand:SI 2 "lr_operand" "=l"))]
5310 "TARGET_FDPIC"
5311 "calll %M0"
5312 [(set_attr "length" "4")
5313 (set_attr "type" "jumpl")])
5314
5315 (define_insn "call_fdpicsi"
5316 [(call (mem:QI (match_operand:SI 0 "call_operand" "S,dNOP"))
5317 (match_operand 1 "" ""))
5318 (use (match_operand 2 "" ""))
5319 (use (match_operand:SI 3 "fdpic_operand" "Z,Z"))
5320 (clobber (match_operand:SI 4 "lr_operand" "=l,l"))]
5321 "TARGET_FDPIC"
5322 "@
5323 call %0
5324 call%i0l %M0"
5325 [(set_attr "length" "4")
5326 (set_attr "type" "call,jumpl")])
5327
5328 ;; Subroutine call instruction returning a value. Operand 0 is the hard
5329 ;; register in which the value is returned. There are three more operands, the
5330 ;; same as the three operands of the `call' instruction (but with numbers
5331 ;; increased by one).
5332
5333 ;; Subroutines that return `BLKmode' objects use the `call' insn.
5334
5335 (define_expand "call_value"
5336 [(use (match_operand 0 "" ""))
5337 (use (match_operand:QI 1 "" ""))
5338 (use (match_operand 2 "" ""))
5339 (use (match_operand 3 "" ""))
5340 (use (match_operand 4 "" ""))]
5341 ""
5342 "
5343 {
5344 rtx lr = gen_rtx_REG (Pmode, LR_REGNO);
5345 rtx addr;
5346
5347 if (GET_CODE (operands[1]) != MEM)
5348 abort ();
5349
5350 addr = XEXP (operands[1], 0);
5351 if (! call_operand (addr, Pmode))
5352 addr = force_reg (Pmode, addr);
5353
5354 if (! operands[3])
5355 operands[3] = const0_rtx;
5356
5357 if (TARGET_FDPIC)
5358 frv_expand_fdpic_call (operands, 1);
5359 else
5360 emit_call_insn (gen_call_value_internal (operands[0], addr, operands[2],
5361 operands[3], lr));
5362
5363 DONE;
5364 }")
5365
5366 (define_insn "call_value_internal"
5367 [(set (match_operand 0 "register_operand" "=d,d")
5368 (call (mem:QI (match_operand:SI 1 "call_operand" "S,dNOP"))
5369 (match_operand 2 "" "")))
5370 (use (match_operand 3 "" ""))
5371 (clobber (match_operand:SI 4 "lr_operand" "=l,l"))]
5372 "! TARGET_FDPIC"
5373 "@
5374 call %1
5375 call%i1l %M1"
5376 [(set_attr "length" "4")
5377 (set_attr "type" "call,jumpl")])
5378
5379 (define_insn "call_value_fdpicdi"
5380 [(set (match_operand 0 "register_operand" "=d")
5381 (call (mem:QI (match_operand:DI 1 "fdpic_fptr_operand" "W"))
5382 (match_operand 2 "" "")))
5383 (clobber (match_operand:SI 3 "lr_operand" "=l"))]
5384 "TARGET_FDPIC"
5385 "calll %M1"
5386 [(set_attr "length" "4")
5387 (set_attr "type" "jumpl")])
5388
5389 (define_insn "call_value_fdpicsi"
5390 [(set (match_operand 0 "register_operand" "=d,d")
5391 (call (mem:QI (match_operand:SI 1 "call_operand" "S,dNOP"))
5392 (match_operand 2 "" "")))
5393 (use (match_operand 3 "" ""))
5394 (use (match_operand:SI 4 "fdpic_operand" "Z,Z"))
5395 (clobber (match_operand:SI 5 "lr_operand" "=l,l"))]
5396 "TARGET_FDPIC"
5397 "@
5398 call %1
5399 call%i1l %M1"
5400 [(set_attr "length" "4")
5401 (set_attr "type" "call,jumpl")])
5402
5403 ;; return instruction generated instead of jmp to epilog
5404 (define_expand "return"
5405 [(parallel [(return)
5406 (use (match_dup 0))
5407 (use (const_int 1))])]
5408 "direct_return_p ()"
5409 "
5410 {
5411 operands[0] = gen_rtx_REG (Pmode, LR_REGNO);
5412 }")
5413
5414 ;; return instruction generated by the epilogue
5415 (define_expand "epilogue_return"
5416 [(parallel [(return)
5417 (use (match_operand:SI 0 "register_operand" ""))
5418 (use (const_int 0))])]
5419 ""
5420 "")
5421
5422 (define_insn "*return_internal"
5423 [(return)
5424 (use (match_operand:SI 0 "register_operand" "l,d"))
5425 (use (match_operand:SI 1 "immediate_operand" "n,n"))]
5426 ""
5427 "@
5428 ret
5429 jmpl @(%0,%.)"
5430 [(set_attr "length" "4")
5431 (set_attr "type" "jump,jumpl")])
5432
5433 ;; A version of addsi3 for deallocating stack space at the end of the
5434 ;; epilogue. The addition is done in parallel with an (unspec_volatile),
5435 ;; which represents the clobbering of the deallocated space.
5436 (define_insn "stack_adjust"
5437 [(set (match_operand:SI 0 "register_operand" "=d")
5438 (plus:SI (match_operand:SI 1 "register_operand" "d")
5439 (match_operand:SI 2 "general_operand" "dNOP")))
5440 (unspec_volatile [(const_int 0)] UNSPEC_STACK_ADJUST)]
5441 ""
5442 "add%I2 %1,%2,%0"
5443 [(set_attr "length" "4")
5444 (set_attr "type" "int")])
5445
5446 ;; Normal unconditional jump
5447
5448 ;; Use the "call" instruction for long branches, but prefer to use "bra" for
5449 ;; short ones since it does not force us to save the link register.
5450
5451 ;; This define_insn uses the branch-shortening code to decide which
5452 ;; instruction it emits. Since the main branch-shortening interface is
5453 ;; through get_attr_length(), the two alternatives must be given different
5454 ;; lengths. Here we pretend that the far jump is 8 rather than 4 bytes
5455 ;; long, though both alternatives are really the same size.
5456 (define_insn "jump"
5457 [(set (pc) (label_ref (match_operand 0 "" "")))]
5458 ""
5459 "*
5460 {
5461 if (get_attr_length (insn) == 4)
5462 return \"bra %l0\";
5463 else
5464 return \"call %l0\";
5465 }"
5466 [(set (attr "length")
5467 (if_then_else
5468 (and (ge (minus (match_dup 0) (pc)) (const_int -32768))
5469 (le (minus (match_dup 0) (pc)) (const_int 32764)))
5470 (const_int 4)
5471 (const_int 8)))
5472 (set (attr "far_jump")
5473 (if_then_else
5474 (eq_attr "length" "4")
5475 (const_string "no")
5476 (const_string "yes")))
5477 (set (attr "type")
5478 (if_then_else
5479 (eq_attr "length" "4")
5480 (const_string "jump")
5481 (const_string "call")))])
5482
5483 ;; Indirect jump through a register
5484 (define_insn "indirect_jump"
5485 [(set (pc) (match_operand:SI 0 "register_operand" "d,l"))]
5486 ""
5487 "@
5488 jmpl @(%0,%.)
5489 bralr"
5490 [(set_attr "length" "4")
5491 (set_attr "type" "jumpl,branch")])
5492
5493 ;; Instruction to jump to a variable address. This is a low-level capability
5494 ;; which can be used to implement a dispatch table when there is no `casesi'
5495 ;; pattern. Either the 'casesi' pattern or the 'tablejump' pattern, or both,
5496 ;; MUST be present in this file.
5497
5498 ;; This pattern requires two operands: the address or offset, and a label which
5499 ;; should immediately precede the jump table. If the macro
5500 ;; `CASE_VECTOR_PC_RELATIVE' is defined then the first operand is an offset
5501 ;; which counts from the address of the table; otherwise, it is an absolute
5502 ;; address to jump to. In either case, the first operand has mode `Pmode'.
5503
5504 ;; The `tablejump' insn is always the last insn before the jump table it uses.
5505 ;; Its assembler code normally has no need to use the second operand, but you
5506 ;; should incorporate it in the RTL pattern so that the jump optimizer will not
5507 ;; delete the table as unreachable code.
5508
5509 (define_expand "tablejump"
5510 [(parallel [(set (pc) (match_operand:SI 0 "address_operand" "p"))
5511 (use (label_ref (match_operand 1 "" "")))])]
5512 "!flag_pic"
5513 "")
5514
5515 (define_insn "tablejump_insn"
5516 [(set (pc) (match_operand:SI 0 "address_operand" "p"))
5517 (use (label_ref (match_operand 1 "" "")))]
5518 ""
5519 "jmp%I0l %M0"
5520 [(set_attr "length" "4")
5521 (set_attr "type" "jumpl")])
5522
5523 ;; Implement switch statements when generating PIC code. Switches are
5524 ;; implemented by `tablejump' when not using -fpic.
5525
5526 ;; Emit code here to do the range checking and make the index zero based.
5527 ;; operand 0 is the index
5528 ;; operand 1 is the lower bound
5529 ;; operand 2 is the range of indices (highest - lowest + 1)
5530 ;; operand 3 is the label that precedes the table itself
5531 ;; operand 4 is the fall through label
5532
5533 (define_expand "casesi"
5534 [(use (match_operand:SI 0 "integer_register_operand" ""))
5535 (use (match_operand:SI 1 "const_int_operand" ""))
5536 (use (match_operand:SI 2 "const_int_operand" ""))
5537 (use (match_operand 3 "" ""))
5538 (use (match_operand 4 "" ""))]
5539 "flag_pic"
5540 "
5541 {
5542 rtx indx;
5543 rtx scale;
5544 rtx low = operands[1];
5545 rtx range = operands[2];
5546 rtx table = operands[3];
5547 rtx treg;
5548 rtx fail = operands[4];
5549 rtx mem;
5550 rtx reg2;
5551 rtx reg3;
5552
5553 if (GET_CODE (operands[1]) != CONST_INT)
5554 abort ();
5555
5556 if (GET_CODE (operands[2]) != CONST_INT)
5557 abort ();
5558
5559 /* If we can't generate an immediate instruction, promote to register. */
5560 if (! IN_RANGE_P (INTVAL (range), -2048, 2047))
5561 range = force_reg (SImode, range);
5562
5563 /* If low bound is 0, we don't have to subtract it. */
5564 if (INTVAL (operands[1]) == 0)
5565 indx = operands[0];
5566 else
5567 {
5568 indx = gen_reg_rtx (SImode);
5569 if (IN_RANGE_P (INTVAL (low), -2047, 2048))
5570 emit_insn (gen_addsi3 (indx, operands[0], GEN_INT (- INTVAL (low))));
5571 else
5572 emit_insn (gen_subsi3 (indx, operands[0], force_reg (SImode, low)));
5573 }
5574
5575 /* Do an unsigned comparison (in the proper mode) between the index
5576 expression and the value which represents the length of the range.
5577 Since we just finished subtracting the lower bound of the range
5578 from the index expression, this comparison allows us to simultaneously
5579 check that the original index expression value is both greater than
5580 or equal to the minimum value of the range and less than or equal to
5581 the maximum value of the range. */
5582
5583 emit_cmp_and_jump_insns (indx, range, GTU, NULL_RTX, SImode, 1, fail);
5584
5585 /* Move the table address to a register. */
5586 treg = gen_reg_rtx (Pmode);
5587 emit_insn (gen_movsi (treg, gen_rtx_LABEL_REF (VOIDmode, table)));
5588
5589 /* Scale index-low by wordsize. */
5590 scale = gen_reg_rtx (SImode);
5591 emit_insn (gen_ashlsi3 (scale, indx, const2_rtx));
5592
5593 /* Load the address, add the start of the table back in,
5594 and jump to it. */
5595 mem = gen_rtx_MEM (SImode, gen_rtx_PLUS (Pmode, scale, treg));
5596 reg2 = gen_reg_rtx (SImode);
5597 reg3 = gen_reg_rtx (SImode);
5598 emit_insn (gen_movsi (reg2, mem));
5599 emit_insn (gen_addsi3 (reg3, reg2, treg));
5600 emit_jump_insn (gen_tablejump_insn (reg3, table));
5601 DONE;
5602 }")
5603
5604 \f
5605 ;; ::::::::::::::::::::
5606 ;; ::
5607 ;; :: Prologue and Epilogue instructions
5608 ;; ::
5609 ;; ::::::::::::::::::::
5610
5611 ;; Called after register allocation to add any instructions needed for the
5612 ;; prologue. Using a prologue insn is favored compared to putting all of the
5613 ;; instructions in the FUNCTION_PROLOGUE macro, since it allows the scheduler
5614 ;; to intermix instructions with the saves of the caller saved registers. In
5615 ;; some cases, it might be necessary to emit a barrier instruction as the last
5616 ;; insn to prevent such scheduling.
5617 (define_expand "prologue"
5618 [(const_int 1)]
5619 ""
5620 "
5621 {
5622 frv_expand_prologue ();
5623 DONE;
5624 }")
5625
5626 ;; Called after register allocation to add any instructions needed for the
5627 ;; epilogue. Using an epilogue insn is favored compared to putting all of the
5628 ;; instructions in the FUNCTION_EPILOGUE macro, since it allows the scheduler
5629 ;; to intermix instructions with the restires of the caller saved registers.
5630 ;; In some cases, it might be necessary to emit a barrier instruction as the
5631 ;; first insn to prevent such scheduling.
5632 (define_expand "epilogue"
5633 [(const_int 2)]
5634 ""
5635 "
5636 {
5637 frv_expand_epilogue (FALSE);
5638 DONE;
5639 }")
5640
5641 ;; This pattern, if defined, emits RTL for exit from a function without the final
5642 ;; branch back to the calling function. This pattern will be emitted before any
5643 ;; sibling call (aka tail call) sites.
5644 ;;
5645 ;; The sibcall_epilogue pattern must not clobber any arguments used for
5646 ;; parameter passing or any stack slots for arguments passed to the current
5647 ;; function.
5648 (define_expand "sibcall_epilogue"
5649 [(const_int 3)]
5650 ""
5651 "
5652 {
5653 frv_expand_epilogue (TRUE);
5654 DONE;
5655 }")
5656
5657 ;; Set up the pic register to hold the address of the pic table
5658 (define_insn "pic_prologue"
5659 [(set (match_operand:SI 0 "integer_register_operand" "=d")
5660 (unspec_volatile:SI [(const_int 0)] UNSPEC_PIC_PROLOGUE))
5661 (clobber (match_operand:SI 1 "lr_operand" "=l"))
5662 (clobber (match_operand:SI 2 "integer_register_operand" "=d"))]
5663 ""
5664 "*
5665 {
5666 static int frv_pic_labelno = 0;
5667
5668 operands[3] = GEN_INT (frv_pic_labelno++);
5669 return \"call %P3\\n%P3:\;movsg %1, %0\;sethi #gprelhi(%P3), %2\;setlo #gprello(%P3), %2\;sub %0,%2,%0\";
5670 }"
5671 [(set_attr "length" "16")
5672 (set_attr "type" "multi")])
5673 \f
5674 ;; ::::::::::::::::::::
5675 ;; ::
5676 ;; :: Miscellaneous instructions
5677 ;; ::
5678 ;; ::::::::::::::::::::
5679
5680 ;; No operation, needed in case the user uses -g but not -O.
5681 (define_insn "nop"
5682 [(const_int 0)]
5683 ""
5684 "nop"
5685 [(set_attr "length" "4")
5686 (set_attr "type" "int")])
5687
5688 ;; Pseudo instruction that prevents the scheduler from moving code above this
5689 ;; point. Note, type unknown is used to make sure the VLIW instructions are
5690 ;; not continued past this point.
5691 (define_insn "blockage"
5692 [(unspec_volatile [(const_int 0)] UNSPEC_BLOCKAGE)]
5693 ""
5694 "# blockage"
5695 [(set_attr "length" "0")
5696 (set_attr "type" "unknown")])
5697 \f
5698 ;; ::::::::::::::::::::
5699 ;; ::
5700 ;; :: Media instructions
5701 ;; ::
5702 ;; ::::::::::::::::::::
5703
5704 ;; Unimplemented instructions:
5705 ;; - MCMPSH, MCMPUH
5706
5707 (define_constants
5708 [(UNSPEC_MLOGIC 100)
5709 (UNSPEC_MNOT 101)
5710 (UNSPEC_MAVEH 102)
5711 (UNSPEC_MSATH 103)
5712 (UNSPEC_MADDH 104)
5713 (UNSPEC_MQADDH 105)
5714 (UNSPEC_MPACKH 106)
5715 (UNSPEC_MUNPACKH 107)
5716 (UNSPEC_MDPACKH 108)
5717 (UNSPEC_MBTOH 109)
5718 (UNSPEC_MHTOB 110)
5719 (UNSPEC_MROT 111)
5720 (UNSPEC_MSHIFT 112)
5721 (UNSPEC_MEXPDHW 113)
5722 (UNSPEC_MEXPDHD 114)
5723 (UNSPEC_MWCUT 115)
5724 (UNSPEC_MMULH 116)
5725 (UNSPEC_MMULXH 117)
5726 (UNSPEC_MMACH 118)
5727 (UNSPEC_MMRDH 119)
5728 (UNSPEC_MQMULH 120)
5729 (UNSPEC_MQMULXH 121)
5730 (UNSPEC_MQMACH 122)
5731 (UNSPEC_MCPX 123)
5732 (UNSPEC_MQCPX 124)
5733 (UNSPEC_MCUT 125)
5734 (UNSPEC_MRDACC 126)
5735 (UNSPEC_MRDACCG 127)
5736 (UNSPEC_MWTACC 128)
5737 (UNSPEC_MWTACCG 129)
5738 (UNSPEC_MTRAP 130)
5739 (UNSPEC_MCLRACC 131)
5740 (UNSPEC_MCLRACCA 132)
5741 (UNSPEC_MCOP1 133)
5742 (UNSPEC_MCOP2 134)
5743 (UNSPEC_MDUNPACKH 135)
5744 (UNSPEC_MDUNPACKH_INTERNAL 136)
5745 (UNSPEC_MBTOHE 137)
5746 (UNSPEC_MBTOHE_INTERNAL 138)
5747 (UNSPEC_MBTOHE 137)
5748 (UNSPEC_MBTOHE_INTERNAL 138)
5749 (UNSPEC_MQMACH2 139)
5750 (UNSPEC_MADDACC 140)
5751 (UNSPEC_MDADDACC 141)
5752 (UNSPEC_MABSHS 142)
5753 (UNSPEC_MDROTLI 143)
5754 (UNSPEC_MCPLHI 144)
5755 (UNSPEC_MCPLI 145)
5756 (UNSPEC_MDCUTSSI 146)
5757 (UNSPEC_MQSATHS 147)
5758 (UNSPEC_MHSETLOS 148)
5759 (UNSPEC_MHSETLOH 149)
5760 (UNSPEC_MHSETHIS 150)
5761 (UNSPEC_MHSETHIH 151)
5762 (UNSPEC_MHDSETS 152)
5763 (UNSPEC_MHDSETH 153)
5764 ])
5765
5766 ;; Logic operations: type "mlogic"
5767
5768 (define_expand "mand"
5769 [(set (match_operand:SI 0 "fpr_operand" "")
5770 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
5771 (match_operand:SI 2 "fpr_operand" "")
5772 (match_dup 3)]
5773 UNSPEC_MLOGIC))]
5774 "TARGET_MEDIA"
5775 "operands[3] = GEN_INT (FRV_BUILTIN_MAND);")
5776
5777 (define_expand "mor"
5778 [(set (match_operand:SI 0 "fpr_operand" "")
5779 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
5780 (match_operand:SI 2 "fpr_operand" "")
5781 (match_dup 3)]
5782 UNSPEC_MLOGIC))]
5783 "TARGET_MEDIA"
5784 "operands[3] = GEN_INT (FRV_BUILTIN_MOR);")
5785
5786 (define_expand "mxor"
5787 [(set (match_operand:SI 0 "fpr_operand" "")
5788 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
5789 (match_operand:SI 2 "fpr_operand" "")
5790 (match_dup 3)]
5791 UNSPEC_MLOGIC))]
5792 "TARGET_MEDIA"
5793 "operands[3] = GEN_INT (FRV_BUILTIN_MXOR);")
5794
5795 (define_insn "*mlogic"
5796 [(set (match_operand:SI 0 "fpr_operand" "=f")
5797 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5798 (match_operand:SI 2 "fpr_operand" "f")
5799 (match_operand:SI 3 "const_int_operand" "n")]
5800 UNSPEC_MLOGIC))]
5801 "TARGET_MEDIA"
5802 "*
5803 {
5804 switch (INTVAL (operands[3]))
5805 {
5806 default: break;
5807 case FRV_BUILTIN_MAND: return \"mand %1, %2, %0\";
5808 case FRV_BUILTIN_MOR: return \"mor %1, %2, %0\";
5809 case FRV_BUILTIN_MXOR: return \"mxor %1, %2, %0\";
5810 }
5811
5812 fatal_insn (\"Bad media insn, mlogic\", insn);
5813 }"
5814 [(set_attr "length" "4")
5815 (set_attr "type" "mlogic")])
5816
5817 (define_insn "*cond_exec_mlogic"
5818 [(cond_exec
5819 (match_operator 0 "ccr_eqne_operator"
5820 [(match_operand 1 "cr_operand" "C")
5821 (const_int 0)])
5822 (set (match_operand:SI 2 "fpr_operand" "=f")
5823 (unspec:SI [(match_operand:SI 3 "fpr_operand" "f")
5824 (match_operand:SI 4 "fpr_operand" "f")
5825 (match_operand:SI 5 "const_int_operand" "n")]
5826 UNSPEC_MLOGIC)))]
5827 "TARGET_MEDIA"
5828 "*
5829 {
5830 switch (INTVAL (operands[5]))
5831 {
5832 default: break;
5833 case FRV_BUILTIN_MAND: return \"cmand %3, %4, %2, %1, %e0\";
5834 case FRV_BUILTIN_MOR: return \"cmor %3, %4, %2, %1, %e0\";
5835 case FRV_BUILTIN_MXOR: return \"cmxor %3, %4, %2, %1, %e0\";
5836 }
5837
5838 fatal_insn (\"Bad media insn, cond_exec_mlogic\", insn);
5839 }"
5840 [(set_attr "length" "4")
5841 (set_attr "type" "mlogic")])
5842
5843 ;; Logical not: type "mlogic"
5844
5845 (define_insn "mnot"
5846 [(set (match_operand:SI 0 "fpr_operand" "=f")
5847 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")] UNSPEC_MNOT))]
5848 "TARGET_MEDIA"
5849 "mnot %1, %0"
5850 [(set_attr "length" "4")
5851 (set_attr "type" "mlogic")])
5852
5853 (define_insn "*cond_exec_mnot"
5854 [(cond_exec
5855 (match_operator 0 "ccr_eqne_operator"
5856 [(match_operand 1 "cr_operand" "C")
5857 (const_int 0)])
5858 (set (match_operand:SI 2 "fpr_operand" "=f")
5859 (unspec:SI [(match_operand:SI 3 "fpr_operand" "f")] UNSPEC_MNOT)))]
5860 "TARGET_MEDIA"
5861 "cmnot %3, %2, %1, %e0"
5862 [(set_attr "length" "4")
5863 (set_attr "type" "mlogic")])
5864
5865 ;; Dual average (halfword): type "maveh"
5866
5867 (define_insn "maveh"
5868 [(set (match_operand:SI 0 "fpr_operand" "=f")
5869 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5870 (match_operand:SI 2 "fpr_operand" "f")]
5871 UNSPEC_MAVEH))]
5872 "TARGET_MEDIA"
5873 "maveh %1, %2, %0"
5874 [(set_attr "length" "4")
5875 (set_attr "type" "maveh")])
5876
5877 ;; Dual saturation (halfword): type "msath"
5878
5879 (define_expand "msaths"
5880 [(set (match_operand:SI 0 "fpr_operand" "=f")
5881 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5882 (match_operand:SI 2 "fpr_operand" "f")
5883 (match_dup 3)]
5884 UNSPEC_MSATH))]
5885 "TARGET_MEDIA"
5886 "operands[3] = GEN_INT (FRV_BUILTIN_MSATHS);")
5887
5888 (define_expand "msathu"
5889 [(set (match_operand:SI 0 "fpr_operand" "=f")
5890 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5891 (match_operand:SI 2 "fpr_operand" "f")
5892 (match_dup 3)]
5893 UNSPEC_MSATH))]
5894 "TARGET_MEDIA"
5895 "operands[3] = GEN_INT (FRV_BUILTIN_MSATHU);")
5896
5897 (define_insn "*msath"
5898 [(set (match_operand:SI 0 "fpr_operand" "=f")
5899 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5900 (match_operand:SI 2 "fpr_operand" "f")
5901 (match_operand:SI 3 "const_int_operand" "n")]
5902 UNSPEC_MSATH))]
5903 "TARGET_MEDIA"
5904 "*
5905 {
5906 switch (INTVAL (operands[3]))
5907 {
5908 default: break;
5909 case FRV_BUILTIN_MSATHS: return \"msaths %1, %2, %0\";
5910 case FRV_BUILTIN_MSATHU: return \"msathu %1, %2, %0\";
5911 }
5912
5913 fatal_insn (\"Bad media insn, msath\", insn);
5914 }"
5915 [(set_attr "length" "4")
5916 (set_attr "type" "msath")])
5917
5918 ;; Dual addition/subtraction with saturation (halfword): type "maddh"
5919
5920 (define_expand "maddhss"
5921 [(set (match_operand:SI 0 "fpr_operand" "=f")
5922 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5923 (match_operand:SI 2 "fpr_operand" "f")
5924 (match_dup 3)]
5925 UNSPEC_MADDH))]
5926 "TARGET_MEDIA"
5927 "operands[3] = GEN_INT (FRV_BUILTIN_MADDHSS);")
5928
5929 (define_expand "maddhus"
5930 [(set (match_operand:SI 0 "fpr_operand" "=f")
5931 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5932 (match_operand:SI 2 "fpr_operand" "f")
5933 (match_dup 3)]
5934 UNSPEC_MADDH))]
5935 "TARGET_MEDIA"
5936 "operands[3] = GEN_INT (FRV_BUILTIN_MADDHUS);")
5937
5938 (define_expand "msubhss"
5939 [(set (match_operand:SI 0 "fpr_operand" "=f")
5940 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5941 (match_operand:SI 2 "fpr_operand" "f")
5942 (match_dup 3)]
5943 UNSPEC_MADDH))]
5944 "TARGET_MEDIA"
5945 "operands[3] = GEN_INT (FRV_BUILTIN_MSUBHSS);")
5946
5947 (define_expand "msubhus"
5948 [(set (match_operand:SI 0 "fpr_operand" "=f")
5949 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5950 (match_operand:SI 2 "fpr_operand" "f")
5951 (match_dup 3)]
5952 UNSPEC_MADDH))]
5953 "TARGET_MEDIA"
5954 "operands[3] = GEN_INT (FRV_BUILTIN_MSUBHUS);")
5955
5956 (define_insn "*maddh"
5957 [(set (match_operand:SI 0 "fpr_operand" "=f")
5958 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
5959 (match_operand:SI 2 "fpr_operand" "f")
5960 (match_operand:SI 3 "const_int_operand" "n")]
5961 UNSPEC_MADDH))]
5962 "TARGET_MEDIA"
5963 "*
5964 {
5965 switch (INTVAL (operands[3]))
5966 {
5967 default: break;
5968 case FRV_BUILTIN_MADDHSS: return \"maddhss %1, %2, %0\";
5969 case FRV_BUILTIN_MADDHUS: return \"maddhus %1, %2, %0\";
5970 case FRV_BUILTIN_MSUBHSS: return \"msubhss %1, %2, %0\";
5971 case FRV_BUILTIN_MSUBHUS: return \"msubhus %1, %2, %0\";
5972 }
5973
5974 fatal_insn (\"Bad media insn, maddh\", insn);
5975 }"
5976 [(set_attr "length" "4")
5977 (set_attr "type" "maddh")])
5978
5979 (define_insn "*cond_exec_maddh"
5980 [(cond_exec
5981 (match_operator 0 "ccr_eqne_operator"
5982 [(match_operand 1 "cr_operand" "C")
5983 (const_int 0)])
5984 (set (match_operand:SI 2 "fpr_operand" "=f")
5985 (unspec:SI [(match_operand:SI 3 "fpr_operand" "f")
5986 (match_operand:SI 4 "fpr_operand" "f")
5987 (match_operand:SI 5 "const_int_operand" "n")]
5988 UNSPEC_MADDH)))]
5989 "TARGET_MEDIA"
5990 "*
5991 {
5992 switch (INTVAL (operands[5]))
5993 {
5994 default: break;
5995 case FRV_BUILTIN_MADDHSS: return \"cmaddhss %3, %4, %2, %1, %e0\";
5996 case FRV_BUILTIN_MADDHUS: return \"cmaddhus %3, %4, %2, %1, %e0\";
5997 case FRV_BUILTIN_MSUBHSS: return \"cmsubhss %3, %4, %2, %1, %e0\";
5998 case FRV_BUILTIN_MSUBHUS: return \"cmsubhus %3, %4, %2, %1, %e0\";
5999 }
6000
6001 fatal_insn (\"Bad media insn, cond_exec_maddh\", insn);
6002 }"
6003 [(set_attr "length" "4")
6004 (set_attr "type" "maddh")])
6005
6006 ;; Quad addition/subtraction with saturation (halfword): type "mqaddh"
6007
6008 (define_expand "mqaddhss"
6009 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6010 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6011 (match_operand:DI 2 "even_fpr_operand" "h")
6012 (match_dup 3)]
6013 UNSPEC_MQADDH))]
6014 "TARGET_MEDIA"
6015 "operands[3] = GEN_INT (FRV_BUILTIN_MQADDHSS);")
6016
6017 (define_expand "mqaddhus"
6018 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6019 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6020 (match_operand:DI 2 "even_fpr_operand" "h")
6021 (match_dup 3)]
6022 UNSPEC_MQADDH))]
6023 "TARGET_MEDIA"
6024 "operands[3] = GEN_INT (FRV_BUILTIN_MQADDHUS);")
6025
6026 (define_expand "mqsubhss"
6027 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6028 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6029 (match_operand:DI 2 "even_fpr_operand" "h")
6030 (match_dup 3)]
6031 UNSPEC_MQADDH))]
6032 "TARGET_MEDIA"
6033 "operands[3] = GEN_INT (FRV_BUILTIN_MQSUBHSS);")
6034
6035 (define_expand "mqsubhus"
6036 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6037 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6038 (match_operand:DI 2 "even_fpr_operand" "h")
6039 (match_dup 3)]
6040 UNSPEC_MQADDH))]
6041 "TARGET_MEDIA"
6042 "operands[3] = GEN_INT (FRV_BUILTIN_MQSUBHUS);")
6043
6044 (define_insn "*mqaddh"
6045 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6046 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6047 (match_operand:DI 2 "even_fpr_operand" "h")
6048 (match_operand:SI 3 "const_int_operand" "n")]
6049 UNSPEC_MQADDH))]
6050 "TARGET_MEDIA"
6051 "*
6052 {
6053 switch (INTVAL (operands[3]))
6054 {
6055 default: break;
6056 case FRV_BUILTIN_MQADDHSS: return \"mqaddhss %1, %2, %0\";
6057 case FRV_BUILTIN_MQADDHUS: return \"mqaddhus %1, %2, %0\";
6058 case FRV_BUILTIN_MQSUBHSS: return \"mqsubhss %1, %2, %0\";
6059 case FRV_BUILTIN_MQSUBHUS: return \"mqsubhus %1, %2, %0\";
6060 }
6061
6062 fatal_insn (\"Bad media insn, mqaddh\", insn);
6063 }"
6064 [(set_attr "length" "4")
6065 (set_attr "type" "mqaddh")])
6066
6067 (define_insn "*cond_exec_mqaddh"
6068 [(cond_exec
6069 (match_operator 0 "ccr_eqne_operator"
6070 [(match_operand 1 "cr_operand" "C")
6071 (const_int 0)])
6072 (set (match_operand:DI 2 "even_fpr_operand" "=h")
6073 (unspec:DI [(match_operand:DI 3 "even_fpr_operand" "h")
6074 (match_operand:DI 4 "even_fpr_operand" "h")
6075 (match_operand:SI 5 "const_int_operand" "n")]
6076 UNSPEC_MQADDH)))]
6077 "TARGET_MEDIA"
6078 "*
6079 {
6080 switch (INTVAL (operands[5]))
6081 {
6082 default: break;
6083 case FRV_BUILTIN_MQADDHSS: return \"cmqaddhss %3, %4, %2, %1, %e0\";
6084 case FRV_BUILTIN_MQADDHUS: return \"cmqaddhus %3, %4, %2, %1, %e0\";
6085 case FRV_BUILTIN_MQSUBHSS: return \"cmqsubhss %3, %4, %2, %1, %e0\";
6086 case FRV_BUILTIN_MQSUBHUS: return \"cmqsubhus %3, %4, %2, %1, %e0\";
6087 }
6088
6089 fatal_insn (\"Bad media insn, cond_exec_mqaddh\", insn);
6090 }"
6091 [(set_attr "length" "4")
6092 (set_attr "type" "mqaddh")])
6093
6094 ;; Pack halfword: type "mpackh"
6095
6096 (define_insn "mpackh"
6097 [(set (match_operand:SI 0 "fpr_operand" "=f")
6098 (unspec:SI [(match_operand:HI 1 "fpr_operand" "f")
6099 (match_operand:HI 2 "fpr_operand" "f")]
6100 UNSPEC_MPACKH))]
6101 "TARGET_MEDIA"
6102 "mpackh %1, %2, %0"
6103 [(set_attr "length" "4")
6104 (set_attr "type" "mpackh")])
6105
6106 ;; Unpack halfword: type "mpackh"
6107
6108 (define_insn "munpackh"
6109 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6110 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")]
6111 UNSPEC_MUNPACKH))]
6112 "TARGET_MEDIA"
6113 "munpackh %1, %0"
6114 [(set_attr "length" "4")
6115 (set_attr "type" "munpackh")])
6116
6117 ;; Dual pack halfword: type "mdpackh"
6118
6119 (define_insn "mdpackh"
6120 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6121 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
6122 (match_operand:DI 2 "even_fpr_operand" "h")]
6123 UNSPEC_MDPACKH))]
6124 "TARGET_MEDIA"
6125 "mdpackh %1, %2, %0"
6126 [(set_attr "length" "4")
6127 (set_attr "type" "mdpackh")])
6128
6129 ;; Byte-halfword conversion: type "mbhconv"
6130
6131 (define_insn "mbtoh"
6132 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6133 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")]
6134 UNSPEC_MBTOH))]
6135 "TARGET_MEDIA"
6136 "mbtoh %1, %0"
6137 [(set_attr "length" "4")
6138 (set_attr "type" "mbhconv")])
6139
6140 (define_insn "*cond_exec_mbtoh"
6141 [(cond_exec
6142 (match_operator 0 "ccr_eqne_operator"
6143 [(match_operand 1 "cr_operand" "C")
6144 (const_int 0)])
6145 (set (match_operand:DI 2 "even_fpr_operand" "=h")
6146 (unspec:DI [(match_operand:SI 3 "fpr_operand" "f")]
6147 UNSPEC_MBTOH)))]
6148 "TARGET_MEDIA"
6149 "cmbtoh %3, %2, %1, %e0"
6150 [(set_attr "length" "4")
6151 (set_attr "type" "mbhconv")])
6152
6153 (define_insn "mhtob"
6154 [(set (match_operand:SI 0 "fpr_operand" "=f")
6155 (unspec:SI [(match_operand:DI 1 "even_fpr_operand" "h")]
6156 UNSPEC_MHTOB))]
6157 "TARGET_MEDIA"
6158 "mhtob %1, %0"
6159 [(set_attr "length" "4")
6160 (set_attr "type" "mbhconv")])
6161
6162 (define_insn "*cond_exec_mhtob"
6163 [(cond_exec
6164 (match_operator 0 "ccr_eqne_operator"
6165 [(match_operand 1 "cr_operand" "C")
6166 (const_int 0)])
6167 (set (match_operand:SI 2 "fpr_operand" "=f")
6168 (unspec:SI [(match_operand:DI 3 "even_fpr_operand" "h")]
6169 UNSPEC_MHTOB)))]
6170 "TARGET_MEDIA"
6171 "cmhtob %3, %2, %1, %e0"
6172 [(set_attr "length" "4")
6173 (set_attr "type" "mbhconv")])
6174
6175 ;; Rotate: type "mrot"
6176
6177 (define_expand "mrotli"
6178 [(set (match_operand:SI 0 "fpr_operand" "")
6179 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
6180 (match_operand:SI 2 "uint5_operand" "")
6181 (match_dup 3)]
6182 UNSPEC_MROT))]
6183 "TARGET_MEDIA"
6184 "operands[3] = GEN_INT (FRV_BUILTIN_MROTLI);")
6185
6186 (define_expand "mrotri"
6187 [(set (match_operand:SI 0 "fpr_operand" "")
6188 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
6189 (match_operand:SI 2 "uint5_operand" "")
6190 (match_dup 3)]
6191 UNSPEC_MROT))]
6192 "TARGET_MEDIA"
6193 "operands[3] = GEN_INT (FRV_BUILTIN_MROTRI);")
6194
6195 (define_insn "*mrot"
6196 [(set (match_operand:SI 0 "fpr_operand" "=f")
6197 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6198 (match_operand:SI 2 "uint5_operand" "I")
6199 (match_operand:SI 3 "const_int_operand" "n")]
6200 UNSPEC_MROT))]
6201 "TARGET_MEDIA"
6202 "*
6203 {
6204 switch (INTVAL (operands[3]))
6205 {
6206 default: break;
6207 case FRV_BUILTIN_MROTLI: return \"mrotli %1, %2, %0\";
6208 case FRV_BUILTIN_MROTRI: return \"mrotri %1, %2, %0\";
6209 }
6210
6211 fatal_insn (\"Bad media insn, mrot\", insn);
6212 }"
6213 [(set_attr "length" "4")
6214 (set_attr "type" "mrot")])
6215
6216 ;; Dual shift halfword: type "msh"
6217
6218 (define_expand "msllhi"
6219 [(set (match_operand:SI 0 "fpr_operand" "")
6220 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
6221 (match_operand:SI 2 "uint4_operand" "")
6222 (match_dup 3)]
6223 UNSPEC_MSHIFT))]
6224 "TARGET_MEDIA"
6225 "operands[3] = GEN_INT (FRV_BUILTIN_MSLLHI);")
6226
6227 (define_expand "msrlhi"
6228 [(set (match_operand:SI 0 "fpr_operand" "")
6229 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
6230 (match_operand:SI 2 "uint4_operand" "")
6231 (match_dup 3)]
6232 UNSPEC_MSHIFT))]
6233 "TARGET_MEDIA"
6234 "operands[3] = GEN_INT (FRV_BUILTIN_MSRLHI);")
6235
6236 (define_expand "msrahi"
6237 [(set (match_operand:SI 0 "fpr_operand" "")
6238 (unspec:SI [(match_operand:SI 1 "fpr_operand" "")
6239 (match_operand:SI 2 "uint4_operand" "")
6240 (match_dup 3)]
6241 UNSPEC_MSHIFT))]
6242 "TARGET_MEDIA"
6243 "operands[3] = GEN_INT (FRV_BUILTIN_MSRAHI);")
6244
6245 (define_insn "*mshift"
6246 [(set (match_operand:SI 0 "fpr_operand" "=f")
6247 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6248 (match_operand:SI 2 "uint4_operand" "I")
6249 (match_operand:SI 3 "const_int_operand" "n")]
6250 UNSPEC_MSHIFT))]
6251 "TARGET_MEDIA"
6252 "*
6253 {
6254 switch (INTVAL (operands[3]))
6255 {
6256 default: break;
6257 case FRV_BUILTIN_MSLLHI: return \"msllhi %1, %2, %0\";
6258 case FRV_BUILTIN_MSRLHI: return \"msrlhi %1, %2, %0\";
6259 case FRV_BUILTIN_MSRAHI: return \"msrahi %1, %2, %0\";
6260 }
6261
6262 fatal_insn (\"Bad media insn, mshift\", insn);
6263 }"
6264 [(set_attr "length" "4")
6265 (set_attr "type" "mshift")])
6266
6267 ;; Expand halfword to word: type "mexpdhw"
6268
6269 (define_insn "mexpdhw"
6270 [(set (match_operand:SI 0 "even_fpr_operand" "=h")
6271 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6272 (match_operand:SI 2 "uint1_operand" "I")]
6273 UNSPEC_MEXPDHW))]
6274 "TARGET_MEDIA"
6275 "mexpdhw %1, %2, %0"
6276 [(set_attr "length" "4")
6277 (set_attr "type" "mexpdhw")])
6278
6279 (define_insn "*cond_exec_mexpdhw"
6280 [(cond_exec
6281 (match_operator 0 "ccr_eqne_operator"
6282 [(match_operand 1 "cr_operand" "C")
6283 (const_int 0)])
6284 (set (match_operand:SI 2 "even_fpr_operand" "=h")
6285 (unspec:SI [(match_operand:SI 3 "fpr_operand" "f")
6286 (match_operand:SI 4 "uint1_operand" "I")]
6287 UNSPEC_MEXPDHW)))]
6288 "TARGET_MEDIA"
6289 "cmexpdhw %3, %4, %2, %1, %e0"
6290 [(set_attr "length" "4")
6291 (set_attr "type" "mexpdhw")])
6292
6293 ;; Expand halfword to double: type "mexpdhd"
6294
6295 (define_insn "mexpdhd"
6296 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
6297 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6298 (match_operand:SI 2 "uint1_operand" "I")]
6299 UNSPEC_MEXPDHD))]
6300 "TARGET_MEDIA"
6301 "mexpdhd %1, %2, %0"
6302 [(set_attr "length" "4")
6303 (set_attr "type" "mexpdhd")])
6304
6305 (define_insn "*cond_exec_mexpdhd"
6306 [(cond_exec
6307 (match_operator 0 "ccr_eqne_operator"
6308 [(match_operand 1 "cr_operand" "C")
6309 (const_int 0)])
6310 (set (match_operand:DI 2 "even_fpr_operand" "=h")
6311 (unspec:DI [(match_operand:SI 3 "fpr_operand" "f")
6312 (match_operand:SI 4 "uint1_operand" "I")]
6313 UNSPEC_MEXPDHD)))]
6314 "TARGET_MEDIA"
6315 "cmexpdhd %3, %4, %2, %1, %e0"
6316 [(set_attr "length" "4")
6317 (set_attr "type" "mexpdhd")])
6318
6319 ;; FR cut: type "mwcut"
6320
6321 (define_insn "mwcut"
6322 [(set (match_operand:SI 0 "fpr_operand" "=f")
6323 (unspec:SI [(match_operand:DI 1 "fpr_operand" "f")
6324 (match_operand:SI 2 "fpr_or_int6_operand" "fI")]
6325 UNSPEC_MWCUT))]
6326 "TARGET_MEDIA"
6327 "mwcut%i2 %1, %2, %0"
6328 [(set_attr "length" "4")
6329 (set_attr "type" "mwcut")])
6330
6331 ;; Dual multiplication (halfword): type "mmulh"
6332
6333 (define_expand "mmulhs"
6334 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6335 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6336 (match_operand:SI 2 "fpr_operand" "f")
6337 (match_dup 4)]
6338 UNSPEC_MMULH))
6339 (set (match_operand:HI 3 "accg_operand" "=B")
6340 (unspec:HI [(const_int 0)] UNSPEC_MMULH))])]
6341 "TARGET_MEDIA"
6342 "operands[4] = GEN_INT (FRV_BUILTIN_MMULHS);")
6343
6344 (define_expand "mmulhu"
6345 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6346 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6347 (match_operand:SI 2 "fpr_operand" "f")
6348 (match_dup 4)]
6349 UNSPEC_MMULH))
6350 (set (match_operand:HI 3 "accg_operand" "=B")
6351 (unspec:HI [(const_int 0)] UNSPEC_MMULH))])]
6352 "TARGET_MEDIA"
6353 "operands[4] = GEN_INT (FRV_BUILTIN_MMULHU);")
6354
6355 (define_insn "*mmulh"
6356 [(set (match_operand:DI 0 "even_acc_operand" "=b")
6357 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6358 (match_operand:SI 2 "fpr_operand" "f")
6359 (match_operand:SI 3 "const_int_operand" "n")]
6360 UNSPEC_MMULH))
6361 (set (match_operand:HI 4 "accg_operand" "=B")
6362 (unspec:HI [(const_int 0)] UNSPEC_MMULH))]
6363 "TARGET_MEDIA"
6364 "*
6365 {
6366 switch (INTVAL (operands[3]))
6367 {
6368 default: break;
6369 case FRV_BUILTIN_MMULHS: return \"mmulhs %1, %2, %0\";
6370 case FRV_BUILTIN_MMULHU: return \"mmulhu %1, %2, %0\";
6371 }
6372
6373 fatal_insn (\"Bad media insn, mmulh\", insn);
6374 }"
6375 [(set_attr "length" "4")
6376 (set_attr "type" "mmulh")])
6377
6378 (define_insn "*cond_exec_mmulh"
6379 [(cond_exec
6380 (match_operator 0 "ccr_eqne_operator"
6381 [(match_operand 1 "cr_operand" "C")
6382 (const_int 0)])
6383 (parallel [(set (match_operand:DI 2 "even_acc_operand" "=b")
6384 (unspec:DI [(match_operand:SI 3 "fpr_operand" "f")
6385 (match_operand:SI 4 "fpr_operand" "f")
6386 (match_operand:SI 5 "const_int_operand" "n")]
6387 UNSPEC_MMULH))
6388 (set (match_operand:HI 6 "accg_operand" "=B")
6389 (unspec:HI [(const_int 0)] UNSPEC_MMULH))]))]
6390 "TARGET_MEDIA"
6391 "*
6392 {
6393 switch (INTVAL (operands[5]))
6394 {
6395 default: break;
6396 case FRV_BUILTIN_MMULHS: return \"cmmulhs %3, %4, %2, %1, %e0\";
6397 case FRV_BUILTIN_MMULHU: return \"cmmulhu %3, %4, %2, %1, %e0\";
6398 }
6399
6400 fatal_insn (\"Bad media insn, cond_exec_mmulh\", insn);
6401 }"
6402 [(set_attr "length" "4")
6403 (set_attr "type" "mmulh")])
6404
6405 ;; Dual cross multiplication (halfword): type "mmulxh"
6406
6407 (define_expand "mmulxhs"
6408 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6409 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6410 (match_operand:SI 2 "fpr_operand" "f")
6411 (match_dup 4)]
6412 UNSPEC_MMULXH))
6413 (set (match_operand:HI 3 "accg_operand" "=B")
6414 (unspec:HI [(const_int 0)] UNSPEC_MMULXH))])]
6415 "TARGET_MEDIA"
6416 "operands[4] = GEN_INT (FRV_BUILTIN_MMULXHS);")
6417
6418 (define_expand "mmulxhu"
6419 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6420 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6421 (match_operand:SI 2 "fpr_operand" "f")
6422 (match_dup 4)]
6423 UNSPEC_MMULXH))
6424 (set (match_operand:HI 3 "accg_operand" "=B")
6425 (unspec:HI [(const_int 0)] UNSPEC_MMULXH))])]
6426 "TARGET_MEDIA"
6427 "operands[4] = GEN_INT (FRV_BUILTIN_MMULXHU);")
6428
6429 (define_insn "*mmulxh"
6430 [(set (match_operand:DI 0 "even_acc_operand" "=b")
6431 (unspec:DI [(match_operand:SI 1 "fpr_operand" "f")
6432 (match_operand:SI 2 "fpr_operand" "f")
6433 (match_operand:SI 3 "const_int_operand" "n")]
6434 UNSPEC_MMULXH))
6435 (set (match_operand:HI 4 "accg_operand" "=B")
6436 (unspec:HI [(const_int 0)] UNSPEC_MMULXH))]
6437 "TARGET_MEDIA"
6438 "*
6439 {
6440 switch (INTVAL (operands[3]))
6441 {
6442 default: break;
6443 case FRV_BUILTIN_MMULXHS: return \"mmulxhs %1, %2, %0\";
6444 case FRV_BUILTIN_MMULXHU: return \"mmulxhu %1, %2, %0\";
6445 }
6446
6447 fatal_insn (\"Bad media insn, mmulxh\", insn);
6448 }"
6449 [(set_attr "length" "4")
6450 (set_attr "type" "mmulxh")])
6451
6452 ;; Dual product-sum (halfword): type "mmach"
6453
6454 (define_expand "mmachs"
6455 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "+b")
6456 (unspec:DI [(match_dup 0)
6457 (match_operand:SI 1 "fpr_operand" "f")
6458 (match_operand:SI 2 "fpr_operand" "f")
6459 (match_operand:HI 3 "accg_operand" "+B")
6460 (match_dup 4)]
6461 UNSPEC_MMACH))
6462 (set (match_dup 3)
6463 (unspec:HI [(const_int 0)] UNSPEC_MMACH))])]
6464 "TARGET_MEDIA"
6465 "operands[4] = GEN_INT (FRV_BUILTIN_MMACHS);")
6466
6467 (define_expand "mmachu"
6468 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "+b")
6469 (unspec:DI [(match_dup 0)
6470 (match_operand:SI 1 "fpr_operand" "f")
6471 (match_operand:SI 2 "fpr_operand" "f")
6472 (match_operand:HI 3 "accg_operand" "+B")
6473 (match_dup 4)]
6474 UNSPEC_MMACH))
6475 (set (match_dup 3)
6476 (unspec:HI [(const_int 0)] UNSPEC_MMACH))])]
6477 "TARGET_MEDIA"
6478 "operands[4] = GEN_INT (FRV_BUILTIN_MMACHU);")
6479
6480 (define_insn "*mmach"
6481 [(set (match_operand:DI 0 "even_acc_operand" "+b")
6482 (unspec:DI [(match_dup 0)
6483 (match_operand:SI 1 "fpr_operand" "f")
6484 (match_operand:SI 2 "fpr_operand" "f")
6485 (match_operand:HI 3 "accg_operand" "+B")
6486 (match_operand:SI 4 "const_int_operand" "n")]
6487 UNSPEC_MMACH))
6488 (set (match_dup 3) (unspec:HI [(const_int 0)] UNSPEC_MMACH))]
6489 "TARGET_MEDIA"
6490 "*
6491 {
6492 switch (INTVAL (operands[4]))
6493 {
6494 default: break;
6495 case FRV_BUILTIN_MMACHS: return \"mmachs %1, %2, %0\";
6496 case FRV_BUILTIN_MMACHU: return \"mmachu %1, %2, %0\";
6497 }
6498
6499 fatal_insn (\"Bad media insn, mmach\", insn);
6500 }"
6501 [(set_attr "length" "4")
6502 (set_attr "type" "mmach")])
6503
6504 (define_insn "*cond_exec_mmach"
6505 [(cond_exec
6506 (match_operator 0 "ccr_eqne_operator"
6507 [(match_operand 1 "cr_operand" "C")
6508 (const_int 0)])
6509 (parallel [(set (match_operand:DI 2 "even_acc_operand" "+b")
6510 (unspec:DI [(match_dup 2)
6511 (match_operand:SI 3 "fpr_operand" "f")
6512 (match_operand:SI 4 "fpr_operand" "f")
6513 (match_operand:HI 5 "accg_operand" "+B")
6514 (match_operand:SI 6 "const_int_operand" "n")]
6515 UNSPEC_MMACH))
6516 (set (match_dup 5)
6517 (unspec:HI [(const_int 0)] UNSPEC_MMACH))]))]
6518 "TARGET_MEDIA"
6519 "*
6520 {
6521 switch (INTVAL (operands[6]))
6522 {
6523 default: break;
6524 case FRV_BUILTIN_MMACHS: return \"cmmachs %3, %4, %2, %1, %e0\";
6525 case FRV_BUILTIN_MMACHU: return \"cmmachu %3, %4, %2, %1, %e0\";
6526 }
6527
6528 fatal_insn (\"Bad media insn, cond_exec_mmach\", insn);
6529 }"
6530 [(set_attr "length" "4")
6531 (set_attr "type" "mmach")])
6532
6533 ;; Dual product-difference: type "mmrdh"
6534
6535 (define_expand "mmrdhs"
6536 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "+b")
6537 (unspec:DI [(match_dup 0)
6538 (match_operand:SI 1 "fpr_operand" "f")
6539 (match_operand:SI 2 "fpr_operand" "f")
6540 (match_operand:HI 3 "accg_operand" "+B")
6541 (match_dup 4)]
6542 UNSPEC_MMRDH))
6543 (set (match_dup 3)
6544 (unspec:HI [(const_int 0)] UNSPEC_MMRDH))])]
6545 "TARGET_MEDIA"
6546 "operands[4] = GEN_INT (FRV_BUILTIN_MMRDHS);")
6547
6548 (define_expand "mmrdhu"
6549 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "+b")
6550 (unspec:DI [(match_dup 0)
6551 (match_operand:SI 1 "fpr_operand" "f")
6552 (match_operand:SI 2 "fpr_operand" "f")
6553 (match_operand:HI 3 "accg_operand" "+B")
6554 (match_dup 4)]
6555 UNSPEC_MMRDH))
6556 (set (match_dup 3)
6557 (unspec:HI [(const_int 0)] UNSPEC_MMRDH))])]
6558 "TARGET_MEDIA"
6559 "operands[4] = GEN_INT (FRV_BUILTIN_MMRDHU);")
6560
6561 (define_insn "*mmrdh"
6562 [(set (match_operand:DI 0 "even_acc_operand" "+b")
6563 (unspec:DI [(match_dup 0)
6564 (match_operand:SI 1 "fpr_operand" "f")
6565 (match_operand:SI 2 "fpr_operand" "f")
6566 (match_operand:HI 3 "accg_operand" "+B")
6567 (match_operand:SI 4 "const_int_operand" "n")]
6568 UNSPEC_MMRDH))
6569 (set (match_dup 3)
6570 (unspec:HI [(const_int 0)] UNSPEC_MMRDH))]
6571 "TARGET_MEDIA"
6572 "*
6573 {
6574 switch (INTVAL (operands[4]))
6575 {
6576 default: break;
6577 case FRV_BUILTIN_MMRDHS: return \"mmrdhs %1, %2, %0\";
6578 case FRV_BUILTIN_MMRDHU: return \"mmrdhu %1, %2, %0\";
6579 }
6580
6581 fatal_insn (\"Bad media insn, mrdh\", insn);
6582 }"
6583 [(set_attr "length" "4")
6584 (set_attr "type" "mmrdh")])
6585
6586 ;; Quad multiply (halfword): type "mqmulh"
6587
6588 (define_expand "mqmulhs"
6589 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6590 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6591 (match_operand:DI 2 "even_fpr_operand" "h")
6592 (match_dup 4)]
6593 UNSPEC_MQMULH))
6594 (set (match_operand:V4QI 3 "accg_operand" "=B")
6595 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULH))])]
6596 "TARGET_MEDIA"
6597 "operands[4] = GEN_INT (FRV_BUILTIN_MQMULHS);")
6598
6599 (define_expand "mqmulhu"
6600 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6601 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6602 (match_operand:DI 2 "even_fpr_operand" "h")
6603 (match_dup 4)]
6604 UNSPEC_MQMULH))
6605 (set (match_operand:V4QI 3 "accg_operand" "=B")
6606 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULH))])]
6607 "TARGET_MEDIA"
6608 "operands[4] = GEN_INT (FRV_BUILTIN_MQMULHU);")
6609
6610 (define_insn "*mqmulh"
6611 [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6612 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6613 (match_operand:DI 2 "even_fpr_operand" "h")
6614 (match_operand:SI 3 "const_int_operand" "n")]
6615 UNSPEC_MQMULH))
6616 (set (match_operand:V4QI 4 "accg_operand" "=B")
6617 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULH))]
6618 "TARGET_MEDIA"
6619 "*
6620 {
6621 switch (INTVAL (operands[3]))
6622 {
6623 default: break;
6624 case FRV_BUILTIN_MQMULHS: return \"mqmulhs %1, %2, %0\";
6625 case FRV_BUILTIN_MQMULHU: return \"mqmulhu %1, %2, %0\";
6626 }
6627
6628 fatal_insn (\"Bad media insn, mqmulh\", insn);
6629 }"
6630 [(set_attr "length" "4")
6631 (set_attr "type" "mqmulh")])
6632
6633 (define_insn "*cond_exec_mqmulh"
6634 [(cond_exec
6635 (match_operator 0 "ccr_eqne_operator"
6636 [(match_operand 1 "cr_operand" "C")
6637 (const_int 0)])
6638 (parallel [(set (match_operand:V4SI 2 "quad_acc_operand" "=A")
6639 (unspec:V4SI [(match_operand:DI 3 "even_fpr_operand" "h")
6640 (match_operand:DI 4 "even_fpr_operand" "h")
6641 (match_operand:SI 5 "const_int_operand" "n")]
6642 UNSPEC_MQMULH))
6643 (set (match_operand:V4QI 6 "accg_operand" "=B")
6644 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULH))]))]
6645 "TARGET_MEDIA"
6646 "*
6647 {
6648 switch (INTVAL (operands[5]))
6649 {
6650 default: break;
6651 case FRV_BUILTIN_MQMULHS: return \"cmqmulhs %3, %4, %2, %1, %e0\";
6652 case FRV_BUILTIN_MQMULHU: return \"cmqmulhu %3, %4, %2, %1, %e0\";
6653 }
6654
6655 fatal_insn (\"Bad media insn, cond_exec_mqmulh\", insn);
6656 }"
6657 [(set_attr "length" "4")
6658 (set_attr "type" "mqmulh")])
6659
6660 ;; Quad cross multiply (halfword): type "mqmulxh"
6661
6662 (define_expand "mqmulxhs"
6663 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6664 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6665 (match_operand:DI 2 "even_fpr_operand" "h")
6666 (match_dup 4)]
6667 UNSPEC_MQMULXH))
6668 (set (match_operand:V4QI 3 "accg_operand" "=B")
6669 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULXH))])]
6670 "TARGET_MEDIA"
6671 "operands[4] = GEN_INT (FRV_BUILTIN_MQMULXHS);")
6672
6673 (define_expand "mqmulxhu"
6674 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6675 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6676 (match_operand:DI 2 "even_fpr_operand" "h")
6677 (match_dup 4)]
6678 UNSPEC_MQMULXH))
6679 (set (match_operand:V4QI 3 "accg_operand" "=B")
6680 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULXH))])]
6681 "TARGET_MEDIA"
6682 "operands[4] = GEN_INT (FRV_BUILTIN_MQMULXHU);")
6683
6684 (define_insn "*mqmulxh"
6685 [(set (match_operand:V4SI 0 "quad_acc_operand" "=A")
6686 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")
6687 (match_operand:DI 2 "even_fpr_operand" "h")
6688 (match_operand:SI 3 "const_int_operand" "n")]
6689 UNSPEC_MQMULXH))
6690 (set (match_operand:V4QI 4 "accg_operand" "=B")
6691 (unspec:V4QI [(const_int 0)] UNSPEC_MQMULXH))]
6692 "TARGET_MEDIA"
6693 "*
6694 {
6695 switch (INTVAL (operands[3]))
6696 {
6697 default: break;
6698 case FRV_BUILTIN_MQMULXHS: return \"mqmulxhs %1, %2, %0\";
6699 case FRV_BUILTIN_MQMULXHU: return \"mqmulxhu %1, %2, %0\";
6700 }
6701
6702 fatal_insn (\"Bad media insn, mqmulxh\", insn);
6703 }"
6704 [(set_attr "length" "4")
6705 (set_attr "type" "mqmulxh")])
6706
6707 ;; Quad product-sum (halfword): type "mqmach"
6708
6709 (define_expand "mqmachs"
6710 [(parallel [(set (match_operand:V4SI 0 "even_acc_operand" "+A")
6711 (unspec:V4SI [(match_dup 0)
6712 (match_operand:DI 1 "even_fpr_operand" "h")
6713 (match_operand:DI 2 "even_fpr_operand" "h")
6714 (match_operand:V4QI 3 "accg_operand" "+B")
6715 (match_dup 4)]
6716 UNSPEC_MQMACH))
6717 (set (match_dup 3)
6718 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH))])]
6719 "TARGET_MEDIA"
6720 "operands[4] = GEN_INT (FRV_BUILTIN_MQMACHS);")
6721
6722 (define_expand "mqmachu"
6723 [(parallel [(set (match_operand:V4SI 0 "even_acc_operand" "+A")
6724 (unspec:V4SI [(match_dup 0)
6725 (match_operand:DI 1 "even_fpr_operand" "h")
6726 (match_operand:DI 2 "even_fpr_operand" "h")
6727 (match_operand:V4QI 3 "accg_operand" "+B")
6728 (match_dup 4)]
6729 UNSPEC_MQMACH))
6730 (set (match_dup 3)
6731 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH))])]
6732 "TARGET_MEDIA"
6733 "operands[4] = GEN_INT (FRV_BUILTIN_MQMACHU);")
6734
6735 (define_insn "*mqmach"
6736 [(set (match_operand:V4SI 0 "even_acc_operand" "+A")
6737 (unspec:V4SI [(match_dup 0)
6738 (match_operand:DI 1 "even_fpr_operand" "h")
6739 (match_operand:DI 2 "even_fpr_operand" "h")
6740 (match_operand:V4QI 3 "accg_operand" "+B")
6741 (match_operand:SI 4 "const_int_operand" "n")]
6742 UNSPEC_MQMACH))
6743 (set (match_dup 3)
6744 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH))]
6745 "TARGET_MEDIA"
6746 "*
6747 {
6748 switch (INTVAL (operands[4]))
6749 {
6750 default: break;
6751 case FRV_BUILTIN_MQMACHS: return \"mqmachs %1, %2, %0\";
6752 case FRV_BUILTIN_MQMACHU: return \"mqmachu %1, %2, %0\";
6753 }
6754
6755 fatal_insn (\"Bad media insn, mqmach\", insn);
6756 }"
6757 [(set_attr "length" "4")
6758 (set_attr "type" "mqmach")])
6759
6760 (define_insn "*cond_exec_mqmach"
6761 [(cond_exec
6762 (match_operator 0 "ccr_eqne_operator"
6763 [(match_operand 1 "cr_operand" "C")
6764 (const_int 0)])
6765 (parallel [(set (match_operand:V4SI 2 "even_acc_operand" "+A")
6766 (unspec:V4SI [(match_dup 2)
6767 (match_operand:DI 3 "even_fpr_operand" "h")
6768 (match_operand:DI 4 "even_fpr_operand" "h")
6769 (match_operand:V4QI 5 "accg_operand" "+B")
6770 (match_operand:SI 6 "const_int_operand" "n")]
6771 UNSPEC_MQMACH))
6772 (set (match_dup 5)
6773 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH))]))]
6774 "TARGET_MEDIA"
6775 "*
6776 {
6777 switch (INTVAL (operands[6]))
6778 {
6779 default: break;
6780 case FRV_BUILTIN_MQMACHS: return \"cmqmachs %3, %4, %2, %1, %e0\";
6781 case FRV_BUILTIN_MQMACHU: return \"cmqmachu %3, %4, %2, %1, %e0\";
6782 }
6783
6784 fatal_insn (\"Bad media insn, cond_exec_mqmach\", insn);
6785 }"
6786 [(set_attr "length" "4")
6787 (set_attr "type" "mqmach")])
6788
6789 ;; Dual complex number product-sum (halfword)
6790
6791 (define_expand "mcpxrs"
6792 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
6793 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6794 (match_operand:SI 2 "fpr_operand" "f")
6795 (match_dup 4)]
6796 UNSPEC_MCPX))
6797 (set (match_operand:QI 3 "accg_operand" "=B")
6798 (unspec:QI [(const_int 0)] UNSPEC_MCPX))])]
6799 "TARGET_MEDIA"
6800 "operands[4] = GEN_INT (FRV_BUILTIN_MCPXRS);")
6801
6802 (define_expand "mcpxru"
6803 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
6804 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6805 (match_operand:SI 2 "fpr_operand" "f")
6806 (match_dup 4)]
6807 UNSPEC_MCPX))
6808 (set (match_operand:QI 3 "accg_operand" "=B")
6809 (unspec:QI [(const_int 0)] UNSPEC_MCPX))])]
6810 "TARGET_MEDIA"
6811 "operands[4] = GEN_INT (FRV_BUILTIN_MCPXRU);")
6812
6813 (define_expand "mcpxis"
6814 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
6815 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6816 (match_operand:SI 2 "fpr_operand" "f")
6817 (match_dup 4)]
6818 UNSPEC_MCPX))
6819 (set (match_operand:QI 3 "accg_operand" "=B")
6820 (unspec:QI [(const_int 0)] UNSPEC_MCPX))])]
6821 "TARGET_MEDIA"
6822 "operands[4] = GEN_INT (FRV_BUILTIN_MCPXIS);")
6823
6824 (define_expand "mcpxiu"
6825 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
6826 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6827 (match_operand:SI 2 "fpr_operand" "f")
6828 (match_dup 4)]
6829 UNSPEC_MCPX))
6830 (set (match_operand:QI 3 "accg_operand" "=B")
6831 (unspec:QI [(const_int 0)] UNSPEC_MCPX))])]
6832 "TARGET_MEDIA"
6833 "operands[4] = GEN_INT (FRV_BUILTIN_MCPXIU);")
6834
6835 (define_insn "*mcpx"
6836 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
6837 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
6838 (match_operand:SI 2 "fpr_operand" "f")
6839 (match_operand:SI 3 "const_int_operand" "n")]
6840 UNSPEC_MCPX))
6841 (set (match_operand:QI 4 "accg_operand" "=B")
6842 (unspec:QI [(const_int 0)] UNSPEC_MCPX))])]
6843 "TARGET_MEDIA"
6844 "*
6845 {
6846 switch (INTVAL (operands[3]))
6847 {
6848 default: break;
6849 case FRV_BUILTIN_MCPXRS: return \"mcpxrs %1, %2, %0\";
6850 case FRV_BUILTIN_MCPXRU: return \"mcpxru %1, %2, %0\";
6851 case FRV_BUILTIN_MCPXIS: return \"mcpxis %1, %2, %0\";
6852 case FRV_BUILTIN_MCPXIU: return \"mcpxiu %1, %2, %0\";
6853 }
6854
6855 fatal_insn (\"Bad media insn, mcpx\", insn);
6856 }"
6857 [(set_attr "length" "4")
6858 (set_attr "type" "mcpx")])
6859
6860 (define_insn "*cond_exec_mcpx"
6861 [(cond_exec
6862 (match_operator 0 "ccr_eqne_operator"
6863 [(match_operand 1 "cr_operand" "C")
6864 (const_int 0)])
6865 (parallel [(set (match_operand:SI 2 "acc_operand" "=a")
6866 (unspec:SI [(match_operand:SI 3 "fpr_operand" "f")
6867 (match_operand:SI 4 "fpr_operand" "f")
6868 (match_operand:SI 5 "const_int_operand" "n")]
6869 UNSPEC_MCPX))
6870 (set (match_operand:QI 6 "accg_operand" "=B")
6871 (unspec:QI [(const_int 0)] UNSPEC_MCPX))]))]
6872 "TARGET_MEDIA"
6873 "*
6874 {
6875 switch (INTVAL (operands[5]))
6876 {
6877 default: break;
6878 case FRV_BUILTIN_MCPXRS: return \"cmcpxrs %3, %4, %2, %1, %e0\";
6879 case FRV_BUILTIN_MCPXRU: return \"cmcpxru %3, %4, %2, %1, %e0\";
6880 case FRV_BUILTIN_MCPXIS: return \"cmcpxis %3, %4, %2, %1, %e0\";
6881 case FRV_BUILTIN_MCPXIU: return \"cmcpxiu %3, %4, %2, %1, %e0\";
6882 }
6883
6884 fatal_insn (\"Bad media insn, cond_exec_mcpx\", insn);
6885 }"
6886 [(set_attr "length" "4")
6887 (set_attr "type" "mcpx")])
6888
6889 ;; Quad complex number product-sum (halfword): type "mqcpx"
6890
6891 (define_expand "mqcpxrs"
6892 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6893 (unspec:DI [(match_operand:DI 1 "fpr_operand" "f")
6894 (match_operand:DI 2 "fpr_operand" "f")
6895 (match_dup 4)]
6896 UNSPEC_MQCPX))
6897 (set (match_operand:HI 3 "accg_operand" "=B")
6898 (unspec:HI [(const_int 0)] UNSPEC_MQCPX))])]
6899 "TARGET_MEDIA"
6900 "operands[4] = GEN_INT (FRV_BUILTIN_MQCPXRS);")
6901
6902 (define_expand "mqcpxru"
6903 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6904 (unspec:DI [(match_operand:DI 1 "fpr_operand" "f")
6905 (match_operand:DI 2 "fpr_operand" "f")
6906 (match_dup 4)]
6907 UNSPEC_MQCPX))
6908 (set (match_operand:HI 3 "accg_operand" "=B")
6909 (unspec:HI [(const_int 0)] UNSPEC_MQCPX))])]
6910 "TARGET_MEDIA"
6911 "operands[4] = GEN_INT (FRV_BUILTIN_MQCPXRU);")
6912
6913 (define_expand "mqcpxis"
6914 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6915 (unspec:DI [(match_operand:DI 1 "fpr_operand" "f")
6916 (match_operand:DI 2 "fpr_operand" "f")
6917 (match_dup 4)]
6918 UNSPEC_MQCPX))
6919 (set (match_operand:HI 3 "accg_operand" "=B")
6920 (unspec:HI [(const_int 0)] UNSPEC_MQCPX))])]
6921 "TARGET_MEDIA"
6922 "operands[4] = GEN_INT (FRV_BUILTIN_MQCPXIS);")
6923
6924 (define_expand "mqcpxiu"
6925 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "=b")
6926 (unspec:DI [(match_operand:DI 1 "fpr_operand" "f")
6927 (match_operand:DI 2 "fpr_operand" "f")
6928 (match_dup 4)]
6929 UNSPEC_MQCPX))
6930 (set (match_operand:HI 3 "accg_operand" "=B")
6931 (unspec:HI [(const_int 0)] UNSPEC_MQCPX))])]
6932 "TARGET_MEDIA"
6933 "operands[4] = GEN_INT (FRV_BUILTIN_MQCPXIU);")
6934
6935 (define_insn "*mqcpx"
6936 [(set (match_operand:DI 0 "even_acc_operand" "=b")
6937 (unspec:DI [(match_operand:DI 1 "fpr_operand" "f")
6938 (match_operand:DI 2 "fpr_operand" "f")
6939 (match_operand:SI 3 "const_int_operand" "n")]
6940 UNSPEC_MQCPX))
6941 (set (match_operand:HI 4 "accg_operand" "=B")
6942 (unspec:HI [(const_int 0)] UNSPEC_MQCPX))]
6943 "TARGET_MEDIA"
6944 "*
6945 {
6946 switch (INTVAL (operands[3]))
6947 {
6948 default: break;
6949 case FRV_BUILTIN_MQCPXRS: return \"mqcpxrs %1, %2, %0\";
6950 case FRV_BUILTIN_MQCPXRU: return \"mqcpxru %1, %2, %0\";
6951 case FRV_BUILTIN_MQCPXIS: return \"mqcpxis %1, %2, %0\";
6952 case FRV_BUILTIN_MQCPXIU: return \"mqcpxiu %1, %2, %0\";
6953 }
6954
6955 fatal_insn (\"Bad media insn, mqcpx\", insn);
6956 }"
6957 [(set_attr "length" "4")
6958 (set_attr "type" "mqcpx")])
6959
6960 ;; Cut: type "mcut"
6961
6962 (define_expand "mcut"
6963 [(set (match_operand:SI 0 "fpr_operand" "=f")
6964 (unspec:SI [(match_operand:SI 1 "acc_operand" "a")
6965 (match_operand:SI 2 "fpr_or_int6_operand" "fI")
6966 (match_operand:QI 3 "accg_operand" "B")
6967 (match_dup 4)]
6968 UNSPEC_MCUT))]
6969 "TARGET_MEDIA"
6970 "operands[4] = GEN_INT (FRV_BUILTIN_MCUT);")
6971
6972 (define_expand "mcutss"
6973 [(set (match_operand:SI 0 "fpr_operand" "=f")
6974 (unspec:SI [(match_operand:SI 1 "acc_operand" "a")
6975 (match_operand:SI 2 "fpr_or_int6_operand" "fI")
6976 (match_operand:QI 3 "accg_operand" "B")
6977 (match_dup 4)]
6978 UNSPEC_MCUT))]
6979 "TARGET_MEDIA"
6980 "operands[4] = GEN_INT (FRV_BUILTIN_MCUTSS);")
6981
6982 (define_insn "*mcut"
6983 [(set (match_operand:SI 0 "fpr_operand" "=f")
6984 (unspec:SI [(match_operand:SI 1 "acc_operand" "a")
6985 (match_operand:SI 2 "fpr_or_int6_operand" "fI")
6986 (match_operand:QI 3 "accg_operand" "B")
6987 (match_operand:SI 4 "const_int_operand" "n")]
6988 UNSPEC_MCUT))]
6989 "TARGET_MEDIA"
6990 "*
6991 {
6992 switch (INTVAL (operands[4]))
6993 {
6994 default: break;
6995 case FRV_BUILTIN_MCUT: return \"mcut%i2 %1, %2, %0\";
6996 case FRV_BUILTIN_MCUTSS: return \"mcutss%i2 %1, %2, %0\";
6997 }
6998
6999 fatal_insn (\"Bad media insn, mcut\", insn);
7000 }"
7001 [(set_attr "length" "4")
7002 (set_attr "type" "mcut")])
7003
7004 ;; Accumulator read: type "mrdacc"
7005
7006 (define_insn "mrdacc"
7007 [(set (match_operand:SI 0 "fpr_operand" "=f")
7008 (unspec:SI [(match_operand:SI 1 "acc_operand" "a")] UNSPEC_MRDACC))]
7009 "TARGET_MEDIA"
7010 "mrdacc %1, %0"
7011 [(set_attr "length" "4")
7012 (set_attr "type" "mrdacc")])
7013
7014 (define_insn "mrdaccg"
7015 [(set (match_operand:SI 0 "fpr_operand" "=f")
7016 (unspec:SI [(match_operand:QI 1 "accg_operand" "B")] UNSPEC_MRDACCG))]
7017 "TARGET_MEDIA"
7018 "mrdaccg %1, %0"
7019 [(set_attr "length" "4")
7020 (set_attr "type" "mrdacc")])
7021
7022 ;; Accumulator write: type "mwtacc"
7023
7024 (define_insn "mwtacc"
7025 [(set (match_operand:SI 0 "acc_operand" "=a")
7026 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")] UNSPEC_MWTACC))]
7027 "TARGET_MEDIA"
7028 "mwtacc %1, %0"
7029 [(set_attr "length" "4")
7030 (set_attr "type" "mwtacc")])
7031
7032 (define_insn "mwtaccg"
7033 [(set (match_operand:QI 0 "accg_operand" "=B")
7034 (unspec:QI [(match_operand:SI 1 "fpr_operand" "f")] UNSPEC_MWTACCG))]
7035 "TARGET_MEDIA"
7036 "mwtaccg %1, %0"
7037 [(set_attr "length" "4")
7038 (set_attr "type" "mwtacc")])
7039
7040 ;; Trap: This one executes on the control unit, not the media units.
7041
7042 (define_insn "mtrap"
7043 [(unspec_volatile [(const_int 0)] UNSPEC_MTRAP)]
7044 "TARGET_MEDIA"
7045 "mtrap"
7046 [(set_attr "length" "4")
7047 (set_attr "type" "trap")])
7048
7049 ;; Clear single accumulator: type "mclracc"
7050
7051 (define_insn "mclracc_internal"
7052 [(set (match_operand:SI 0 "acc_operand" "=a")
7053 (unspec:SI [(const_int 0)] UNSPEC_MCLRACC))
7054 (set (match_operand:QI 1 "accg_operand" "=B")
7055 (unspec:QI [(const_int 0)] UNSPEC_MCLRACC))]
7056 "TARGET_MEDIA"
7057 "mclracc %0,#0"
7058 [(set_attr "length" "4")
7059 (set_attr "type" "mclracc")])
7060
7061 (define_expand "mclracc"
7062 [(parallel [(set (match_operand:SI 0 "acc_operand" "=a")
7063 (unspec:SI [(const_int 0)] UNSPEC_MCLRACC))
7064 (set (match_dup 1)
7065 (unspec:QI [(const_int 0)] UNSPEC_MCLRACC))])]
7066 "TARGET_MEDIA"
7067 "
7068 {
7069 if (GET_CODE (operands[0]) != REG || !ACC_P (REGNO (operands[0])))
7070 FAIL;
7071
7072 operands[1] = frv_matching_accg_for_acc (operands[0]);
7073 }")
7074
7075 ;; Clear all accumulators: type "mclracca"
7076
7077 (define_insn "mclracca8_internal"
7078 [(set (match_operand:V4SI 0 "quad_acc_operand" "=b")
7079 (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7080 (set (match_operand:V4SI 1 "quad_acc_operand" "=b")
7081 (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7082 (set (match_operand:V4QI 2 "accg_operand" "=B")
7083 (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))
7084 (set (match_operand:V4QI 3 "accg_operand" "=B")
7085 (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))]
7086 "TARGET_MEDIA && TARGET_ACC_8"
7087 "mclracc acc0,#1"
7088 [(set_attr "length" "4")
7089 (set_attr "type" "mclracca")])
7090
7091 (define_insn "mclracca4_internal"
7092 [(set (match_operand:V4SI 0 "quad_acc_operand" "=b")
7093 (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7094 (set (match_operand:V4QI 1 "accg_operand" "=B")
7095 (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))]
7096 "TARGET_MEDIA && TARGET_ACC_4"
7097 "mclracc acc0,#1"
7098 [(set_attr "length" "4")
7099 (set_attr "type" "mclracca")])
7100
7101 (define_expand "mclracca8"
7102 [(parallel [(set (match_dup 0) (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7103 (set (match_dup 1) (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7104 (set (match_dup 2) (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))
7105 (set (match_dup 3) (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))])]
7106 "TARGET_MEDIA && TARGET_ACC_8"
7107 "
7108 {
7109 operands[0] = gen_rtx_REG (V4SImode, ACC_FIRST);
7110 operands[1] = gen_rtx_REG (V4SImode, ACC_FIRST + 4);
7111 operands[2] = gen_rtx_REG (V4QImode, ACCG_FIRST);
7112 operands[3] = gen_rtx_REG (V4QImode, ACCG_FIRST + 4);
7113 }")
7114
7115 (define_expand "mclracca4"
7116 [(parallel [(set (match_dup 0) (unspec:V4SI [(const_int 0)] UNSPEC_MCLRACCA))
7117 (set (match_dup 1) (unspec:V4QI [(const_int 0)] UNSPEC_MCLRACCA))])]
7118 "TARGET_MEDIA && TARGET_ACC_4"
7119 "
7120 {
7121 operands[0] = gen_rtx_REG (V4SImode, ACC_FIRST);
7122 operands[1] = gen_rtx_REG (V4QImode, ACCG_FIRST);
7123 }")
7124
7125 (define_insn "mcop1"
7126 [(set (match_operand:SI 0 "fpr_operand" "=f")
7127 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
7128 (match_operand:SI 2 "fpr_operand" "f")] UNSPEC_MCOP1))]
7129 "TARGET_MEDIA_REV1"
7130 "mcop1 %1, %2, %0"
7131 [(set_attr "length" "4")
7132 ;; What is the class of the insn ???
7133 (set_attr "type" "multi")])
7134
7135 (define_insn "mcop2"
7136 [(set (match_operand:SI 0 "fpr_operand" "=f")
7137 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")
7138 (match_operand:SI 2 "fpr_operand" "f")] UNSPEC_MCOP2))]
7139 "TARGET_MEDIA_REV1"
7140 "mcop2 %1, %2, %0"
7141 [(set_attr "length" "4")
7142 ;; What is the class of the insn ???
7143 (set_attr "type" "multi")])
7144
7145 (define_insn "*mdunpackh_internal"
7146 [(set (match_operand:V4SI 0 "quad_fpr_operand" "=x")
7147 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")]
7148 UNSPEC_MDUNPACKH_INTERNAL))]
7149 "TARGET_MEDIA_REV1"
7150 "mdunpackh %1, %0"
7151 [(set_attr "length" "4")
7152 (set_attr "type" "mdunpackh")])
7153
7154 (define_insn_and_split "mdunpackh"
7155 [(set (match_operand:V4SI 0 "memory_operand" "=o")
7156 (unspec:V4SI [(match_operand:DI 1 "even_fpr_operand" "h")]
7157 UNSPEC_MDUNPACKH))
7158 (clobber (match_scratch:V4SI 2 "=x"))]
7159 "TARGET_MEDIA_REV1"
7160 "#"
7161 "reload_completed"
7162 [(set (match_dup 2)
7163 (unspec:V4SI [(match_dup 1)] UNSPEC_MDUNPACKH_INTERNAL))
7164 (set (match_dup 3)
7165 (match_dup 4))
7166 (set (match_dup 5)
7167 (match_dup 6))]
7168 "
7169 {
7170 operands[3] = change_address (operands[0], DImode, NULL_RTX);
7171 operands[4] = gen_rtx_REG (DImode, REGNO (operands[2]));
7172 operands[5] = frv_index_memory (operands[0], DImode, 1);
7173 operands[6] = gen_rtx_REG (DImode, REGNO (operands[2])+2);
7174 }"
7175 [(set_attr "length" "20")
7176 (set_attr "type" "multi")])
7177
7178 (define_insn "*mbtohe_internal"
7179 [(set (match_operand:V4SI 0 "quad_fpr_operand" "=x")
7180 (unspec:V4SI [(match_operand:SI 1 "fpr_operand" "f")]
7181 UNSPEC_MBTOHE_INTERNAL))]
7182 "TARGET_MEDIA_REV1"
7183 "mbtohe %1, %0"
7184 [(set_attr "length" "4")
7185 (set_attr "type" "mbhconve")])
7186
7187 (define_insn_and_split "mbtohe"
7188 [(set (match_operand:V4SI 0 "memory_operand" "=o")
7189 (unspec:V4SI [(match_operand:SI 1 "fpr_operand" "f")]
7190 UNSPEC_MBTOHE))
7191 (clobber (match_scratch:V4SI 2 "=x"))]
7192 "TARGET_MEDIA_REV1"
7193 "#"
7194 "reload_completed"
7195 [(set (match_dup 2)
7196 (unspec:V4SI [(match_dup 1)] UNSPEC_MBTOHE_INTERNAL))
7197 (set (match_dup 3)
7198 (match_dup 4))
7199 (set (match_dup 5)
7200 (match_dup 6))]
7201 "
7202 {
7203 operands[3] = change_address (operands[0], DImode, NULL_RTX);
7204 operands[4] = gen_rtx_REG (DImode, REGNO (operands[2]));
7205 operands[5] = frv_index_memory (operands[0], DImode, 1);
7206 operands[6] = gen_rtx_REG (DImode, REGNO (operands[2])+2);
7207 }"
7208 [(set_attr "length" "20")
7209 (set_attr "type" "multi")])
7210
7211 ;; Quad product-sum (halfword) instructions only found on the FR400.
7212 ;; type "mqmach"
7213
7214 (define_expand "mqxmachs"
7215 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7216 (unspec:V4SI [(match_dup 0)
7217 (match_operand:DI 1 "even_fpr_operand" "")
7218 (match_operand:DI 2 "even_fpr_operand" "")
7219 (match_operand:V4QI 3 "accg_operand" "")
7220 (match_dup 4)]
7221 UNSPEC_MQMACH2))
7222 (set (match_dup 3)
7223 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH2))])]
7224 "TARGET_MEDIA_REV2"
7225 "operands[4] = GEN_INT (FRV_BUILTIN_MQXMACHS);")
7226
7227 (define_expand "mqxmacxhs"
7228 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7229 (unspec:V4SI [(match_dup 0)
7230 (match_operand:DI 1 "even_fpr_operand" "")
7231 (match_operand:DI 2 "even_fpr_operand" "")
7232 (match_operand:V4QI 3 "accg_operand" "")
7233 (match_dup 4)]
7234 UNSPEC_MQMACH2))
7235 (set (match_dup 3)
7236 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH2))])]
7237 "TARGET_MEDIA_REV2"
7238 "operands[4] = GEN_INT (FRV_BUILTIN_MQXMACXHS);")
7239
7240 (define_expand "mqmacxhs"
7241 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7242 (unspec:V4SI [(match_dup 0)
7243 (match_operand:DI 1 "even_fpr_operand" "")
7244 (match_operand:DI 2 "even_fpr_operand" "")
7245 (match_operand:V4QI 3 "accg_operand" "")
7246 (match_dup 4)]
7247 UNSPEC_MQMACH2))
7248 (set (match_dup 3)
7249 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH2))])]
7250 "TARGET_MEDIA_REV2"
7251 "operands[4] = GEN_INT (FRV_BUILTIN_MQMACXHS);")
7252
7253 (define_insn "*mqmach2"
7254 [(set (match_operand:V4SI 0 "quad_acc_operand" "+A")
7255 (unspec:V4SI [(match_dup 0)
7256 (match_operand:DI 1 "even_fpr_operand" "h")
7257 (match_operand:DI 2 "even_fpr_operand" "h")
7258 (match_operand:V4QI 3 "accg_operand" "+B")
7259 (match_operand:SI 4 "const_int_operand" "n")]
7260 UNSPEC_MQMACH2))
7261 (set (match_dup 3)
7262 (unspec:V4QI [(const_int 0)] UNSPEC_MQMACH2))]
7263 "TARGET_MEDIA_REV2"
7264 "*
7265 {
7266 switch (INTVAL (operands[4]))
7267 {
7268 default: break;
7269 case FRV_BUILTIN_MQXMACHS: return \"mqxmachs %1, %2, %0\";
7270 case FRV_BUILTIN_MQXMACXHS: return \"mqxmacxhs %1, %2, %0\";
7271 case FRV_BUILTIN_MQMACXHS: return \"mqmacxhs %1, %2, %0\";
7272 }
7273
7274 fatal_insn (\"Bad media insn, mqmach2\", insn);
7275 }"
7276 [(set_attr "length" "4")
7277 (set_attr "type" "mqmach")])
7278
7279 ;; Accumulator addition/subtraction: type "maddacc"
7280
7281 (define_expand "maddaccs"
7282 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "")
7283 (unspec:DI [(match_dup 0)
7284 (match_operand:DI 1 "even_acc_operand" "")]
7285 UNSPEC_MADDACC))
7286 (set (match_operand:HI 2 "accg_operand" "")
7287 (unspec:HI [(match_dup 2)
7288 (match_operand:HI 3 "accg_operand" "")
7289 (match_dup 4)]
7290 UNSPEC_MADDACC))])]
7291 "TARGET_MEDIA_REV2"
7292 "operands[4] = GEN_INT (FRV_BUILTIN_MADDACCS);")
7293
7294 (define_expand "msubaccs"
7295 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "")
7296 (unspec:DI [(match_dup 0)
7297 (match_operand:DI 1 "even_acc_operand" "")]
7298 UNSPEC_MADDACC))
7299 (set (match_operand:HI 2 "accg_operand" "")
7300 (unspec:HI [(match_dup 2)
7301 (match_operand:HI 3 "accg_operand" "")
7302 (match_dup 4)]
7303 UNSPEC_MADDACC))])]
7304 "TARGET_MEDIA_REV2"
7305 "operands[4] = GEN_INT (FRV_BUILTIN_MSUBACCS);")
7306
7307 (define_expand "masaccs"
7308 [(parallel [(set (match_operand:DI 0 "even_acc_operand" "")
7309 (unspec:DI [(match_dup 0)
7310 (match_operand:DI 1 "even_acc_operand" "")]
7311 UNSPEC_MADDACC))
7312 (set (match_operand:HI 2 "accg_operand" "")
7313 (unspec:HI [(match_dup 2)
7314 (match_operand:HI 3 "accg_operand" "")
7315 (match_dup 4)]
7316 UNSPEC_MADDACC))])]
7317 "TARGET_MEDIA_REV2"
7318 "operands[4] = GEN_INT (FRV_BUILTIN_MASACCS);")
7319
7320 (define_insn "*maddacc"
7321 [(set (match_operand:DI 0 "even_acc_operand" "+b")
7322 (unspec:DI [(match_dup 0)
7323 (match_operand:DI 1 "even_acc_operand" "b")]
7324 UNSPEC_MADDACC))
7325 (set (match_operand:HI 2 "accg_operand" "+B")
7326 (unspec:HI [(match_dup 2)
7327 (match_operand:HI 3 "accg_operand" "B")
7328 (match_operand:SI 4 "const_int_operand" "n")]
7329 UNSPEC_MADDACC))]
7330 "TARGET_MEDIA_REV2"
7331 "*
7332 {
7333 switch (INTVAL (operands[4]))
7334 {
7335 default: break;
7336 case FRV_BUILTIN_MADDACCS: return \"maddaccs %1, %0\";
7337 case FRV_BUILTIN_MSUBACCS: return \"msubaccs %1, %0\";
7338 case FRV_BUILTIN_MASACCS: return \"masaccs %1, %0\";
7339 }
7340
7341 fatal_insn (\"Bad media insn, maddacc\", insn);
7342 }"
7343 [(set_attr "length" "4")
7344 (set_attr "type" "maddacc")])
7345
7346 ;; Dual accumulator addition/subtraction: type "mdaddacc"
7347
7348 (define_expand "mdaddaccs"
7349 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7350 (unspec:V4SI [(match_dup 0)
7351 (match_operand:V4SI 1 "quad_acc_operand" "")]
7352 UNSPEC_MDADDACC))
7353 (set (match_operand:V4QI 2 "accg_operand" "")
7354 (unspec:V4QI [(match_dup 2)
7355 (match_operand:V4QI 3 "accg_operand" "")
7356 (match_dup 4)]
7357 UNSPEC_MDADDACC))])]
7358 "TARGET_MEDIA_REV2"
7359 "operands[4] = GEN_INT (FRV_BUILTIN_MDADDACCS);")
7360
7361 (define_expand "mdsubaccs"
7362 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7363 (unspec:V4SI [(match_dup 0)
7364 (match_operand:V4SI 1 "quad_acc_operand" "")]
7365 UNSPEC_MDADDACC))
7366 (set (match_operand:V4QI 2 "accg_operand" "")
7367 (unspec:V4QI [(match_dup 2)
7368 (match_operand:V4QI 3 "accg_operand" "")
7369 (match_dup 4)]
7370 UNSPEC_MDADDACC))])]
7371 "TARGET_MEDIA_REV2"
7372 "operands[4] = GEN_INT (FRV_BUILTIN_MDSUBACCS);")
7373
7374 (define_expand "mdasaccs"
7375 [(parallel [(set (match_operand:V4SI 0 "quad_acc_operand" "")
7376 (unspec:V4SI [(match_dup 0)
7377 (match_operand:V4SI 1 "quad_acc_operand" "")]
7378 UNSPEC_MDADDACC))
7379 (set (match_operand:V4QI 2 "accg_operand" "")
7380 (unspec:V4QI [(match_dup 2)
7381 (match_operand:V4QI 3 "accg_operand" "")
7382 (match_dup 4)]
7383 UNSPEC_MDADDACC))])]
7384 "TARGET_MEDIA_REV2"
7385 "operands[4] = GEN_INT (FRV_BUILTIN_MDASACCS);")
7386
7387 (define_insn "*mdaddacc"
7388 [(set (match_operand:V4SI 0 "quad_acc_operand" "+A")
7389 (unspec:V4SI [(match_dup 0)
7390 (match_operand:V4SI 1 "quad_acc_operand" "A")]
7391 UNSPEC_MDADDACC))
7392 (set (match_operand:V4QI 2 "accg_operand" "+B")
7393 (unspec:V4QI [(match_dup 2)
7394 (match_operand:V4QI 3 "accg_operand" "B")
7395 (match_operand:SI 4 "const_int_operand" "n")]
7396 UNSPEC_MDADDACC))]
7397 "TARGET_MEDIA_REV2"
7398 "*
7399 {
7400 switch (INTVAL (operands[4]))
7401 {
7402 default: break;
7403 case FRV_BUILTIN_MDADDACCS: return \"mdaddaccs %1, %0\";
7404 case FRV_BUILTIN_MDSUBACCS: return \"mdsubaccs %1, %0\";
7405 case FRV_BUILTIN_MDASACCS: return \"mdasaccs %1, %0\";
7406 }
7407
7408 fatal_insn (\"Bad media insn, mdaddacc\", insn);
7409 }"
7410 [(set_attr "length" "4")
7411 (set_attr "type" "mdaddacc")])
7412
7413 ;; Dual absolute (halfword): type "mabsh"
7414
7415 (define_insn "mabshs"
7416 [(set (match_operand:SI 0 "fpr_operand" "=f")
7417 (unspec:SI [(match_operand:SI 1 "fpr_operand" "f")] UNSPEC_MABSHS))]
7418 "TARGET_MEDIA_REV2"
7419 "mabshs %1, %0"
7420 [(set_attr "length" "4")
7421 (set_attr "type" "mabsh")])
7422
7423 ;; Dual rotate: type "mdrot"
7424
7425 (define_insn "mdrotli"
7426 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
7427 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
7428 (match_operand:SI 2 "uint5_operand" "I")]
7429 UNSPEC_MDROTLI))]
7430 "TARGET_MEDIA_REV2"
7431 "mdrotli %1, %2, %0"
7432 [(set_attr "length" "4")
7433 (set_attr "type" "mdrot")])
7434
7435 ;; Dual coupling (concatenation): type "mcpl"
7436
7437 (define_insn "mcplhi"
7438 [(set (match_operand:SI 0 "fpr_operand" "=f")
7439 (unspec:SI [(match_operand:DI 1 "fpr_operand" "h")
7440 (match_operand:SI 2 "uint4_operand" "I")]
7441 UNSPEC_MCPLHI))]
7442 "TARGET_MEDIA_REV2"
7443 "mcplhi %1, %2, %0"
7444 [(set_attr "length" "4")
7445 (set_attr "type" "mcpl")])
7446
7447 (define_insn "mcpli"
7448 [(set (match_operand:SI 0 "fpr_operand" "=f")
7449 (unspec:SI [(match_operand:DI 1 "fpr_operand" "h")
7450 (match_operand:SI 2 "uint5_operand" "I")]
7451 UNSPEC_MCPLI))]
7452 "TARGET_MEDIA_REV2"
7453 "mcpli %1, %2, %0"
7454 [(set_attr "length" "4")
7455 (set_attr "type" "mcpl")])
7456
7457 ;; Dual cut: type "mdcut"
7458
7459 (define_insn "mdcutssi"
7460 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
7461 (unspec:DI [(match_operand:DI 1 "even_acc_operand" "b")
7462 (match_operand:SI 2 "int6_operand" "I")
7463 (match_operand:HI 3 "accg_operand" "B")]
7464 UNSPEC_MDCUTSSI))]
7465 "TARGET_MEDIA_REV2"
7466 "mdcutssi %1, %2, %0"
7467 [(set_attr "length" "4")
7468 (set_attr "type" "mdcut")])
7469
7470 ;; Quad saturate (halfword): type "mqsath"
7471
7472 (define_insn "mqsaths"
7473 [(set (match_operand:DI 0 "even_fpr_operand" "=h")
7474 (unspec:DI [(match_operand:DI 1 "even_fpr_operand" "h")
7475 (match_operand:DI 2 "even_fpr_operand" "h")]
7476 UNSPEC_MQSATHS))]
7477 "TARGET_MEDIA_REV2"
7478 "mqsaths %1, %2, %0"
7479 [(set_attr "length" "4")
7480 (set_attr "type" "mqsath")])
7481
7482 ;; Set hi/lo instructions: type "mset"
7483
7484 (define_insn "mhsetlos"
7485 [(set (match_operand:SI 0 "fpr_operand" "=f")
7486 (unspec:SI [(match_operand:SI 1 "fpr_operand" "0")
7487 (match_operand:SI 2 "int12_operand" "NOP")]
7488 UNSPEC_MHSETLOS))]
7489 "TARGET_MEDIA_REV2"
7490 "mhsetlos %2, %0"
7491 [(set_attr "length" "4")
7492 (set_attr "type" "mset")])
7493
7494 (define_insn "mhsetloh"
7495 [(set (match_operand:SI 0 "fpr_operand" "=f")
7496 (unspec:SI [(match_operand:SI 1 "fpr_operand" "0")
7497 (match_operand:SI 2 "int5_operand" "I")]
7498 UNSPEC_MHSETLOH))]
7499 "TARGET_MEDIA_REV2"
7500 "mhsetloh %2, %0"
7501 [(set_attr "length" "4")
7502 (set_attr "type" "mset")])
7503
7504 (define_insn "mhsethis"
7505 [(set (match_operand:SI 0 "fpr_operand" "=f")
7506 (unspec:SI [(match_operand:SI 1 "fpr_operand" "0")
7507 (match_operand:SI 2 "int12_operand" "NOP")]
7508 UNSPEC_MHSETHIS))]
7509 "TARGET_MEDIA_REV2"
7510 "mhsethis %2, %0"
7511 [(set_attr "length" "4")
7512 (set_attr "type" "mset")])
7513
7514 (define_insn "mhsethih"
7515 [(set (match_operand:SI 0 "fpr_operand" "=f")
7516 (unspec:SI [(match_operand:SI 1 "fpr_operand" "0")
7517 (match_operand:SI 2 "int5_operand" "I")]
7518 UNSPEC_MHSETHIH))]
7519 "TARGET_MEDIA_REV2"
7520 "mhsethih %2, %0"
7521 [(set_attr "length" "4")
7522 (set_attr "type" "mset")])
7523
7524 (define_insn "mhdsets"
7525 [(set (match_operand:SI 0 "fpr_operand" "=f")
7526 (unspec:SI [(match_operand:SI 1 "int12_operand" "NOP")]
7527 UNSPEC_MHDSETS))]
7528 "TARGET_MEDIA_REV2"
7529 "mhdsets %1, %0"
7530 [(set_attr "length" "4")
7531 (set_attr "type" "mset")])
7532
7533 (define_insn "mhdseth"
7534 [(set (match_operand:SI 0 "fpr_operand" "=f")
7535 (unspec:SI [(match_operand:SI 1 "fpr_operand" "0")
7536 (match_operand:SI 2 "int5_operand" "I")]
7537 UNSPEC_MHDSETH))]
7538 "TARGET_MEDIA_REV2"
7539 "mhdseth %2, %0"
7540 [(set_attr "length" "4")
7541 (set_attr "type" "mset")])
7542
7543 ;;-----------------------------------------------------------------------------
7544
7545 (define_expand "symGOT2reg"
7546 [(match_operand:SI 0 "" "")
7547 (match_operand:SI 1 "" "")
7548 (match_operand:SI 2 "" "")
7549 (match_operand:SI 3 "" "")]
7550 ""
7551 "
7552 {
7553 rtx insn;
7554
7555 insn = emit_insn (gen_symGOT2reg_i (operands[0], operands[1], operands[2], operands[3]));
7556
7557 RTX_UNCHANGING_P (SET_SRC (PATTERN (insn))) = 1;
7558
7559 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_EQUAL, operands[1],
7560 REG_NOTES (insn));
7561
7562 DONE;
7563 }")
7564
7565 (define_expand "symGOT2reg_i"
7566 [(set (match_operand:SI 0 "" "")
7567 (mem:SI (plus:SI (match_operand:SI 2 "" "")
7568 (const:SI (unspec:SI [(match_operand:SI 1 "" "")
7569 (match_operand:SI 3 "" "")]
7570 UNSPEC_GOT)))))]
7571 ""
7572 "")
7573
7574 (define_expand "symGOT2reg_hilo"
7575 [(set (match_dup 6)
7576 (high:SI (const:SI (unspec:SI [(match_operand:SI 1 "" "")
7577 (match_dup 4)] UNSPEC_GOT))))
7578 (set (match_dup 5)
7579 (lo_sum:SI (match_dup 6)
7580 (const:SI (unspec:SI [(match_dup 1)
7581 (match_operand:SI 3 "" "")]
7582 UNSPEC_GOT))))
7583 (set (match_operand:SI 0 "" "")
7584 (mem:SI (plus:SI (match_dup 5)
7585 (match_operand:SI 2 "" ""))))
7586 ]
7587 ""
7588 "
7589 {
7590 if (no_new_pseudos)
7591 operands[6] = operands[5] = operands[0];
7592 else
7593 {
7594 operands[6] = gen_reg_rtx (SImode);
7595 operands[5] = gen_reg_rtx (SImode);
7596 }
7597
7598 operands[4] = GEN_INT (INTVAL (operands[3]) + 1);
7599 operands[3] = GEN_INT (INTVAL (operands[3]) + 2);
7600 }")
7601
7602 (define_expand "symGOTOFF2reg_hilo"
7603 [(set (match_dup 6)
7604 (high:SI (const:SI (unspec:SI [(match_operand:SI 1 "" "")
7605 (match_dup 4)] UNSPEC_GOT))))
7606 (set (match_dup 5)
7607 (lo_sum:SI (match_dup 6)
7608 (const:SI (unspec:SI [(match_dup 1)
7609 (match_operand:SI 3 "" "")]
7610 UNSPEC_GOT))))
7611 (set (match_operand:SI 0 "" "")
7612 (plus:SI (match_dup 5)
7613 (match_operand:SI 2 "" "")))
7614 ]
7615 ""
7616 "
7617 {
7618 if (no_new_pseudos)
7619 operands[6] = operands[5] = operands[0];
7620 else
7621 {
7622 operands[6] = gen_reg_rtx (SImode);
7623 operands[5] = gen_reg_rtx (SImode);
7624 }
7625
7626 operands[4] = GEN_INT (INTVAL (operands[3]) + 1);
7627 operands[3] = GEN_INT (INTVAL (operands[3]) + 2);
7628 }")
7629
7630 (define_expand "symGOTOFF2reg"
7631 [(match_operand:SI 0 "" "")
7632 (match_operand:SI 1 "" "")
7633 (match_operand:SI 2 "" "")
7634 (match_operand:SI 3 "" "")]
7635 ""
7636 "
7637 {
7638 rtx insn = emit_insn (gen_symGOTOFF2reg_i (operands[0], operands[1], operands[2], operands[3]));
7639
7640 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_EQUAL, operands[1],
7641 REG_NOTES (insn));
7642
7643 DONE;
7644 }")
7645
7646 (define_expand "symGOTOFF2reg_i"
7647 [(set (match_operand:SI 0 "" "")
7648 (plus:SI (match_operand:SI 2 "" "")
7649 (const:SI
7650 (unspec:SI [(match_operand:SI 1 "" "")
7651 (match_operand:SI 3 "" "")]
7652 UNSPEC_GOT))))]
7653 ""
7654 "")
7655
7656 (define_expand "symGPREL2reg"
7657 [(match_operand:SI 0 "" "")
7658 (match_operand:SI 1 "" "")
7659 (match_operand:SI 2 "" "")
7660 (match_operand:SI 3 "" "")
7661 (match_dup 4)]
7662 ""
7663 "
7664 {
7665 rtx insn;
7666
7667 if (no_new_pseudos)
7668 operands[4] = operands[0];
7669 else
7670 operands[4] = gen_reg_rtx (SImode);
7671
7672 emit_insn (frv_gen_GPsym2reg (operands[4], operands[2]));
7673
7674 insn = emit_insn (gen_symGOTOFF2reg_i (operands[0], operands[1],
7675 operands[4], operands[3]));
7676
7677 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_EQUAL, operands[1],
7678 REG_NOTES (insn));
7679
7680 DONE;
7681 }")
7682
7683 (define_expand "symGPREL2reg_hilo"
7684 [(match_operand:SI 0 "" "")
7685 (match_operand:SI 1 "" "")
7686 (match_operand:SI 2 "" "")
7687 (match_operand:SI 3 "" "")
7688 (match_dup 4)]
7689 ""
7690 "
7691 {
7692 rtx insn;
7693
7694 if (no_new_pseudos)
7695 {
7696 emit_insn (gen_symGOT2reg (operands[0], operands[1], operands[2],
7697 GEN_INT (R_FRV_GOT12)));
7698 DONE;
7699 }
7700
7701 operands[4] = gen_reg_rtx (SImode);
7702
7703 emit_insn (frv_gen_GPsym2reg (operands[4], operands[2]));
7704
7705 insn = emit_insn (gen_symGOTOFF2reg_hilo (operands[0], operands[1],
7706 operands[4], operands[3]));
7707
7708 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_EQUAL, operands[1],
7709 REG_NOTES (insn));
7710
7711 DONE;
7712 }")
This page took 0.381758 seconds and 5 git commands to generate.