5a93cfe0455347ee617ac719554961cc419e61de
[gcc.git] / gcc / config / i960 / i960.md
1 ;;- Machine description for Intel 80960 chip for GNU C compiler
2 ;; Copyright (C) 1992 Free Software Foundation, Inc.
3 ;; Contributed by Steven McGeady, Intel Corp.
4 ;; Additional work by Glenn Colon-Bonet, Jonathan Shapiro, Andy Wilson
5 ;; Converted to GCC 2.0 by Jim Wilson and Michael Tiemann, Cygnus Support.
6
7 ;; This file is part of GNU CC.
8
9 ;; GNU CC is free software; you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation; either version 2, or (at your option)
12 ;; any later version.
13
14 ;; GNU CC is distributed in the hope that it will be useful,
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 ;; GNU General Public License for more details.
18
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GNU CC; see the file COPYING. If not, write to
21 ;; the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
22
23 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
24 \f
25 ;; There are very few (4) 'f' registers, they can't be loaded/stored from/to
26 ;; memory, and some instructions explicitly require them, so we get better
27 ;; code by discouraging psuedo-registers from being allocated to them.
28 ;; However, we do want to allow all patterns which can store to them to
29 ;; include them in their constraints, so we always use '*f' in a destination
30 ;; constraint except when 'f' is the only alternative.
31 \f
32 ;; Insn attributes which describe the i960.
33
34 ;; Modscan is not used, since the compiler never emits any of these insns.
35 (define_attr "type"
36 "move,arith,alu2,mult,div,modscan,load,store,branch,call,address,compare,fpload,fpstore,fpmove,fpcvt,fpcc,fpadd,fpmul,fpdiv,multi,misc"
37 (const_string "arith"))
38
39 ;; Length (in # of insns).
40 (define_attr "length" ""
41 (cond [(eq_attr "type" "load,fpload")
42 (if_then_else (match_operand 1 "symbolic_memory_operand" "")
43 (const_int 2)
44 (const_int 1))
45 (eq_attr "type" "store,fpstore")
46 (if_then_else (match_operand 0 "symbolic_memory_operand" "")
47 (const_int 2)
48 (const_int 1))
49 (eq_attr "type" "address")
50 (const_int 2)]
51 (const_int 1)))
52
53 (define_asm_attributes
54 [(set_attr "length" "1")
55 (set_attr "type" "multi")])
56
57 ;; (define_function_unit {name} {num-units} {n-users} {test}
58 ;; {ready-delay} {issue-delay} [{conflict-list}])
59
60 ;; The integer ALU
61 (define_function_unit "alu" 2 0 (eq_attr "type" "arith,compare,move,address") 1 0)
62 (define_function_unit "alu" 2 0 (eq_attr "type" "alu2") 2 0)
63 (define_function_unit "alu" 2 0 (eq_attr "type" "mult") 5 0)
64 (define_function_unit "alu" 2 0 (eq_attr "type" "div") 35 0)
65 (define_function_unit "alu" 2 0 (eq_attr "type" "modscan") 3 0)
66
67 ;; Memory with load-delay of 1 (i.e., 2 cycle load).
68 (define_function_unit "memory" 1 0 (eq_attr "type" "load,fpload") 2 0)
69
70 ;; Floating point operations.
71 (define_function_unit "fp" 1 2 (eq_attr "type" "fpmove") 5 0)
72 (define_function_unit "fp" 1 2 (eq_attr "type" "fpcvt") 35 0)
73 (define_function_unit "fp" 1 2 (eq_attr "type" "fpcc") 10 0)
74 (define_function_unit "fp" 1 2 (eq_attr "type" "fpadd") 10 0)
75 (define_function_unit "fp" 1 2 (eq_attr "type" "fpmul") 20 0)
76 (define_function_unit "fp" 1 2 (eq_attr "type" "fpdiv") 35 0)
77 \f
78 ;; Compare instructions.
79 ;; This controls RTL generation and register allocation.
80
81 ;; We generate RTL for comparisons and branches by having the cmpxx
82 ;; patterns store away the operands. Then, the scc and bcc patterns
83 ;; emit RTL for both the compare and the branch.
84 ;;
85 ;; We start with the DEFINE_EXPANDs, then then DEFINE_INSNs to match
86 ;; the patterns. Finally, we have the DEFINE_SPLITs for some of the scc
87 ;; insns that actually require more than one machine instruction.
88
89 ;; Put cmpsi first because it is expected to be the most common.
90
91 (define_expand "cmpsi"
92 [(set (reg:CC 36)
93 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "")
94 (match_operand:SI 1 "general_operand" "")))]
95 ""
96 "
97 {
98 i960_compare_op0 = operands[0];
99 i960_compare_op1 = operands[1];
100 DONE;
101 }")
102
103 (define_expand "cmpdf"
104 [(set (reg:CC 36)
105 (compare:CC (match_operand:DF 0 "register_operand" "r")
106 (match_operand:DF 1 "nonmemory_operand" "rGH")))]
107 "TARGET_NUMERICS"
108 "
109 {
110 i960_compare_op0 = operands[0];
111 i960_compare_op1 = operands[1];
112 DONE;
113 }")
114
115 (define_expand "cmpsf"
116 [(set (reg:CC 36)
117 (compare:CC (match_operand:SF 0 "register_operand" "r")
118 (match_operand:SF 1 "nonmemory_operand" "rGH")))]
119 "TARGET_NUMERICS"
120 "
121 {
122 i960_compare_op0 = operands[0];
123 i960_compare_op1 = operands[1];
124 DONE;
125 }")
126
127 ;; Now the DEFINE_INSNs for the compare and scc cases. First the compares.
128
129 (define_insn ""
130 [(set (reg:CC 36)
131 (compare:CC (match_operand:SI 0 "register_operand" "d")
132 (match_operand:SI 1 "arith_operand" "dI")))]
133 ""
134 "cmpi %0,%1"
135 [(set_attr "type" "compare")])
136
137 (define_insn ""
138 [(set (reg:CC_UNS 36)
139 (compare:CC_UNS (match_operand:SI 0 "register_operand" "d")
140 (match_operand:SI 1 "arith_operand" "dI")))]
141 ""
142 "cmpo %0,%1"
143 [(set_attr "type" "compare")])
144
145 (define_insn ""
146 [(set (reg:CC 36)
147 (compare:CC (match_operand:DF 0 "register_operand" "r")
148 (match_operand:DF 1 "nonmemory_operand" "rGH")))]
149 "TARGET_NUMERICS"
150 "cmprl %0,%1"
151 [(set_attr "type" "fpcc")])
152
153 (define_insn ""
154 [(set (reg:CC 36)
155 (compare:CC (match_operand:SF 0 "register_operand" "r")
156 (match_operand:SF 1 "nonmemory_operand" "rGH")))]
157 "TARGET_NUMERICS"
158 "cmpr %0,%1"
159 [(set_attr "type" "fpcc")])
160
161 ;; Instruction definitions for branch-on-bit-set and clear insns.
162
163 (define_insn ""
164 [(set (pc)
165 (if_then_else
166 (ne (sign_extract:SI (match_operand:SI 1 "register_operand" "d")
167 (const_int 1)
168 (match_operand:SI 2 "arith_operand" "dI"))
169 (const_int 0))
170 (label_ref (match_operand 3 "" ""))
171 (pc)))]
172 ""
173 "bbs %2,%1,%l3"
174 [(set_attr "type" "branch")])
175
176 (define_insn ""
177 [(set (pc)
178 (if_then_else
179 (eq (sign_extract:SI (match_operand:SI 1 "register_operand" "d")
180 (const_int 1)
181 (match_operand:SI 2 "arith_operand" "dI"))
182 (const_int 0))
183 (label_ref (match_operand 3 "" ""))
184 (pc)))]
185 ""
186 "bbc %2,%1,%l3"
187 [(set_attr "type" "branch")])
188
189 (define_insn ""
190 [(set (pc)
191 (if_then_else
192 (ne (zero_extract:SI (match_operand:SI 1 "register_operand" "d")
193 (const_int 1)
194 (match_operand:SI 2 "arith_operand" "dI"))
195 (const_int 0))
196 (label_ref (match_operand 3 "" ""))
197 (pc)))]
198 ""
199 "bbs %2,%1,%l3"
200 [(set_attr "type" "branch")])
201
202 (define_insn ""
203 [(set (pc)
204 (if_then_else
205 (eq (zero_extract:SI (match_operand:SI 1 "register_operand" "d")
206 (const_int 1)
207 (match_operand:SI 2 "arith_operand" "dI"))
208 (const_int 0))
209 (label_ref (match_operand 3 "" ""))
210 (pc)))]
211 ""
212 "bbc %2,%1,%l3"
213 [(set_attr "type" "branch")])
214
215 ;; ??? These will never match. The LOG_LINKs necessary to make these match
216 ;; are not created by flow. These remain as a reminder to make this work
217 ;; some day.
218
219 (define_insn ""
220 [(set (reg:CC 36)
221 (compare (match_operand:SI 0 "arith_operand" "d")
222 (match_operand:SI 1 "arith_operand" "d")))
223 (set (match_dup 1) (plus:SI (match_dup 1) (const_int 1)))]
224 "0"
225 "cmpinci %0,%1"
226 [(set_attr "type" "compare")])
227
228 (define_insn ""
229 [(set (reg:CC_UNS 36)
230 (compare (match_operand:SI 0 "arith_operand" "d")
231 (match_operand:SI 1 "arith_operand" "d")))
232 (set (match_dup 1) (plus:SI (match_dup 1) (const_int 1)))]
233 "0"
234 "cmpinco %0,%1"
235 [(set_attr "type" "compare")])
236
237 (define_insn ""
238 [(set (reg:CC 36)
239 (compare (match_operand:SI 0 "arith_operand" "d")
240 (match_operand:SI 1 "arith_operand" "d")))
241 (set (match_dup 1) (minus:SI (match_dup 1) (const_int 1)))]
242 "0"
243 "cmpdeci %0,%1"
244 [(set_attr "type" "compare")])
245
246 (define_insn ""
247 [(set (reg:CC_UNS 36)
248 (compare (match_operand:SI 0 "arith_operand" "d")
249 (match_operand:SI 1 "arith_operand" "d")))
250 (set (match_dup 1) (minus:SI (match_dup 1) (const_int 1)))]
251 "0"
252 "cmpdeco %0,%1"
253 [(set_attr "type" "compare")])
254 \f
255 ;; Templates to store result of condition.
256 ;; '1' is stored if condition is true.
257 ;; '0' is stored if condition is false.
258 ;; These should use predicate "general_operand", since
259 ;; gcc seems to be creating mem references which use these
260 ;; templates.
261
262 (define_expand "seq"
263 [(set (match_operand:SI 0 "general_operand" "=d")
264 (eq:SI (match_dup 1) (const_int 0)))]
265 ""
266 "
267 {
268 operands[1] = gen_compare_reg (EQ, i960_compare_op0, i960_compare_op1);
269 }")
270
271 (define_expand "sne"
272 [(set (match_operand:SI 0 "general_operand" "=d")
273 (ne:SI (match_dup 1) (const_int 0)))]
274 ""
275 "
276 {
277 operands[1] = gen_compare_reg (NE, i960_compare_op0, i960_compare_op1);
278 }")
279
280 (define_expand "sgt"
281 [(set (match_operand:SI 0 "general_operand" "=d")
282 (gt:SI (match_dup 1) (const_int 0)))]
283 ""
284 "
285 {
286 operands[1] = gen_compare_reg (GT, i960_compare_op0, i960_compare_op1);
287 }")
288
289 (define_expand "sgtu"
290 [(set (match_operand:SI 0 "general_operand" "=d")
291 (gtu:SI (match_dup 1) (const_int 0)))]
292 ""
293 "
294 {
295 operands[1] = gen_compare_reg (GTU, i960_compare_op0, i960_compare_op1);
296 }")
297
298 (define_expand "slt"
299 [(set (match_operand:SI 0 "general_operand" "=d")
300 (lt:SI (match_dup 1) (const_int 0)))]
301 ""
302 "
303 {
304 operands[1] = gen_compare_reg (LT, i960_compare_op0, i960_compare_op1);
305 }")
306
307 (define_expand "sltu"
308 [(set (match_operand:SI 0 "general_operand" "=d")
309 (ltu:SI (match_dup 1) (const_int 0)))]
310 ""
311 "
312 {
313 operands[1] = gen_compare_reg (LTU, i960_compare_op0, i960_compare_op1);
314 }")
315
316 (define_expand "sge"
317 [(set (match_operand:SI 0 "general_operand" "=d")
318 (ge:SI (match_dup 1) (const_int 0)))]
319 ""
320 "
321 {
322 operands[1] = gen_compare_reg (GE, i960_compare_op0, i960_compare_op1);
323 }")
324
325 (define_expand "sgeu"
326 [(set (match_operand:SI 0 "general_operand" "=d")
327 (geu:SI (match_dup 1) (const_int 0)))]
328 ""
329 "
330 {
331 operands[1] = gen_compare_reg (GEU, i960_compare_op0, i960_compare_op1);
332 }")
333
334 (define_expand "sle"
335 [(set (match_operand:SI 0 "general_operand" "=d")
336 (le:SI (match_dup 1) (const_int 0)))]
337 ""
338 "
339 {
340 operands[1] = gen_compare_reg (LE, i960_compare_op0, i960_compare_op1);
341 }")
342
343 (define_expand "sleu"
344 [(set (match_operand:SI 0 "general_operand" "=d")
345 (leu:SI (match_dup 1) (const_int 0)))]
346 ""
347 "
348 {
349 operands[1] = gen_compare_reg (LEU, i960_compare_op0, i960_compare_op1);
350 }")
351
352 (define_insn ""
353 [(set (match_operand:SI 0 "general_operand" "=d")
354 (match_operator:SI 1 "comparison_operator" [(reg:CC 36) (const_int 0)]))]
355 ""
356 "test%C1 %0"
357 [(set_attr "type" "compare")])
358
359 (define_insn ""
360 [(set (match_operand:SI 0 "general_operand" "=d")
361 (match_operator:SI 1 "comparison_operator" [(reg:CC_UNS 36) (const_int 0)]))]
362 ""
363 "test%C1 %0"
364 [(set_attr "type" "compare")])
365 \f
366 ;; These control RTL generation for conditional jump insns
367 ;; and match them for register allocation.
368
369 (define_expand "beq"
370 [(set (pc)
371 (if_then_else (eq (match_dup 1)
372 (const_int 0))
373 (label_ref (match_operand 0 "" ""))
374 (pc)))]
375 ""
376 "
377 { operands[1] = gen_compare_reg (EQ, i960_compare_op0, i960_compare_op1); }")
378
379 (define_expand "bne"
380 [(set (pc)
381 (if_then_else (ne (match_dup 1)
382 (const_int 0))
383 (label_ref (match_operand 0 "" ""))
384 (pc)))]
385 ""
386 "
387 { operands[1] = gen_compare_reg (NE, i960_compare_op0, i960_compare_op1); }")
388
389 (define_expand "bgt"
390 [(set (pc)
391 (if_then_else (gt (match_dup 1)
392 (const_int 0))
393 (label_ref (match_operand 0 "" ""))
394 (pc)))]
395 ""
396 "
397 { operands[1] = gen_compare_reg (GT, i960_compare_op0, i960_compare_op1); }")
398
399 (define_expand "bgtu"
400 [(set (pc)
401 (if_then_else (gtu (match_dup 1)
402 (const_int 0))
403 (label_ref (match_operand 0 "" ""))
404 (pc)))]
405 ""
406 "
407 { operands[1] = gen_compare_reg (GTU, i960_compare_op0, i960_compare_op1); }")
408
409 (define_expand "blt"
410 [(set (pc)
411 (if_then_else (lt (match_dup 1)
412 (const_int 0))
413 (label_ref (match_operand 0 "" ""))
414 (pc)))]
415 ""
416 "
417 { operands[1] = gen_compare_reg (LT, i960_compare_op0, i960_compare_op1); }")
418
419 (define_expand "bltu"
420 [(set (pc)
421 (if_then_else (ltu (match_dup 1)
422 (const_int 0))
423 (label_ref (match_operand 0 "" ""))
424 (pc)))]
425 ""
426 "
427 { operands[1] = gen_compare_reg (LTU, i960_compare_op0, i960_compare_op1); }")
428
429 (define_expand "bge"
430 [(set (pc)
431 (if_then_else (ge (match_dup 1)
432 (const_int 0))
433 (label_ref (match_operand 0 "" ""))
434 (pc)))]
435 ""
436 "
437 { operands[1] = gen_compare_reg (GE, i960_compare_op0, i960_compare_op1); }")
438
439 (define_expand "bgeu"
440 [(set (pc)
441 (if_then_else (geu (match_dup 1)
442 (const_int 0))
443 (label_ref (match_operand 0 "" ""))
444 (pc)))]
445 ""
446 "
447 { operands[1] = gen_compare_reg (GEU, i960_compare_op0, i960_compare_op1); }")
448
449 (define_expand "ble"
450 [(set (pc)
451 (if_then_else (le (match_dup 1)
452 (const_int 0))
453 (label_ref (match_operand 0 "" ""))
454 (pc)))]
455 ""
456 "
457 { operands[1] = gen_compare_reg (LE, i960_compare_op0, i960_compare_op1); }")
458
459 (define_expand "bleu"
460 [(set (pc)
461 (if_then_else (leu (match_dup 1)
462 (const_int 0))
463 (label_ref (match_operand 0 "" ""))
464 (pc)))]
465 ""
466 "
467 { operands[1] = gen_compare_reg (LEU, i960_compare_op0, i960_compare_op1); }")
468 \f
469 ;; Now the normal branch insns (forward and reverse).
470
471 (define_insn ""
472 [(set (pc)
473 (if_then_else (match_operator 0 "comparison_operator"
474 [(reg:CC 36) (const_int 0)])
475 (label_ref (match_operand 1 "" ""))
476 (pc)))]
477 ""
478 "b%C0 %l1"
479 [(set_attr "type" "branch")])
480
481 (define_insn ""
482 [(set (pc)
483 (if_then_else (match_operator 0 "comparison_operator"
484 [(reg:CC 36) (const_int 0)])
485 (pc)
486 (label_ref (match_operand 1 "" ""))))]
487 ""
488 "b%I0 %l1"
489 [(set_attr "type" "branch")])
490
491 (define_insn ""
492 [(set (pc)
493 (if_then_else (match_operator 0 "comparison_operator"
494 [(reg:CC_UNS 36) (const_int 0)])
495 (label_ref (match_operand 1 "" ""))
496 (pc)))]
497 ""
498 "b%C0 %l1"
499 [(set_attr "type" "branch")])
500
501 (define_insn ""
502 [(set (pc)
503 (if_then_else (match_operator 0 "comparison_operator"
504 [(reg:CC_UNS 36) (const_int 0)])
505 (pc)
506 (label_ref (match_operand 1 "" ""))))]
507 ""
508 "b%I0 %l1"
509 [(set_attr "type" "branch")])
510
511 (define_insn ""
512 [(set (pc)
513 (if_then_else
514 (match_operator 0 "comparison_operator"
515 [(match_operand:SI 1 "arith_operand" "d")
516 (match_operand:SI 2 "arith_operand" "dI")])
517 (label_ref (match_operand 3 "" ""))
518 (pc)))]
519 ""
520 "cmp%S0%B0%R0 %2,%1,%l3"
521 [(set_attr "type" "branch")])
522
523 (define_insn ""
524 [(set (pc)
525 (if_then_else
526 (match_operator 0 "comparison_operator"
527 [(match_operand:SI 1 "arith_operand" "d")
528 (match_operand:SI 2 "arith_operand" "dI")])
529 (pc)
530 (label_ref (match_operand 3 "" ""))))]
531 ""
532 "cmp%S0%B0%X0 %2,%1,%l3"
533 [(set_attr "type" "branch")])
534 \f
535 ;; Normal move instructions.
536 ;; This code is based on the sparc machine description.
537
538 (define_expand "movsi"
539 [(set (match_operand:SI 0 "general_operand" "")
540 (match_operand:SI 1 "general_operand" ""))]
541 ""
542 "
543 {
544 if (emit_move_sequence (operands, SImode))
545 DONE;
546 }")
547
548 ;; The store case can not be separate, because reload may convert a register
549 ;; to register move insn to a store (or load) insn without rerecognizing
550 ;; the insn.
551
552 ;; The i960 does not have any store constant to memory instruction. However,
553 ;; the calling convention is defined so that the arg pointer when it is not
554 ;; overwise being used is zero. Thus, we can handle store zero to memory
555 ;; by storing an unused arg pointer. The arg pointer will be unused if
556 ;; current_function_args_size is zero. This value of this variable is not
557 ;; valid until after all rtl generation is complete, including function
558 ;; inlining (because a function that doesn't need an arg pointer may be
559 ;; inlined into a function that does need an arg pointer), so we must also
560 ;; check that rtx_equal_function_value_matters is zero.
561
562 (define_insn ""
563 [(set (match_operand:SI 0 "general_operand" "=d,d,d,m")
564 (match_operand:SI 1 "general_operand" "dI,i,m,dJ"))]
565 "(current_function_args_size == 0
566 && rtx_equal_function_value_matters == 0)
567 && (register_operand (operands[0], SImode)
568 || register_operand (operands[1], SImode)
569 || operands[1] == const0_rtx)"
570 "*
571 {
572 switch (which_alternative)
573 {
574 case 0:
575 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
576 {
577 if (GET_CODE (operands[1]) == REG)
578 return \"lda (%1),%0\";
579 else
580 return \"lda %1,%0\";
581 }
582 return \"mov %1,%0\";
583 case 1:
584 return i960_output_ldconst (operands[0], operands[1]);
585 case 2:
586 return \"ld %1,%0\";
587 case 3:
588 if (operands[1] == const0_rtx)
589 return \"st g14,%0\";
590 return \"st %1,%0\";
591 }
592 }"
593 [(set_attr "type" "move,address,load,store")
594 (set_attr "length" "*,3,*,*")])
595
596 (define_insn ""
597 [(set (match_operand:SI 0 "general_operand" "=d,d,d,m")
598 (match_operand:SI 1 "general_operand" "dI,i,m,d"))]
599 "(current_function_args_size != 0
600 || rtx_equal_function_value_matters != 0)
601 && (register_operand (operands[0], SImode)
602 || register_operand (operands[1], SImode))"
603 "*
604 {
605 switch (which_alternative)
606 {
607 case 0:
608 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
609 {
610 if (GET_CODE (operands[1]) == REG)
611 return \"lda (%1),%0\";
612 else
613 return \"lda %1,%0\";
614 }
615 return \"mov %1,%0\";
616 case 1:
617 return i960_output_ldconst (operands[0], operands[1]);
618 case 2:
619 return \"ld %1,%0\";
620 case 3:
621 return \"st %1,%0\";
622 }
623 }"
624 [(set_attr "type" "move,address,load,store")
625 (set_attr "length" "*,3,*,*")])
626
627 (define_expand "movhi"
628 [(set (match_operand:HI 0 "general_operand" "")
629 (match_operand:HI 1 "general_operand" ""))]
630 ""
631 "
632 {
633 if (emit_move_sequence (operands, HImode))
634 DONE;
635 }")
636
637 ;; Special pattern for zero stores to memory for functions which don't use
638 ;; the arg pointer.
639
640 ;; The store case can not be separate. See above.
641 (define_insn ""
642 [(set (match_operand:HI 0 "general_operand" "=d,d,d,m")
643 (match_operand:HI 1 "general_operand" "dI,i,m,dJ"))]
644 "(current_function_args_size == 0
645 && rtx_equal_function_value_matters == 0)
646 && (register_operand (operands[0], HImode)
647 || register_operand (operands[1], HImode)
648 || operands[1] == const0_rtx)"
649 "*
650 {
651 switch (which_alternative)
652 {
653 case 0:
654 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
655 {
656 if (GET_CODE (operands[1]) == REG)
657 return \"lda (%1),%0\";
658 else
659 return \"lda %1,%0\";
660 }
661 return \"mov %1,%0\";
662 case 1:
663 return i960_output_ldconst (operands[0], operands[1]);
664 case 2:
665 return \"ldos %1,%0\";
666 case 3:
667 if (operands[1] == const0_rtx)
668 return \"stos g14,%0\";
669 return \"stos %1,%0\";
670 }
671 }"
672 [(set_attr "type" "move,misc,load,store")
673 (set_attr "length" "*,3,*,*")])
674
675 ;; The store case can not be separate. See above.
676 (define_insn ""
677 [(set (match_operand:HI 0 "general_operand" "=d,d,d,m")
678 (match_operand:HI 1 "general_operand" "dI,i,m,d"))]
679 "(current_function_args_size != 0
680 || rtx_equal_function_value_matters != 0)
681 && (register_operand (operands[0], HImode)
682 || register_operand (operands[1], HImode))"
683 "*
684 {
685 switch (which_alternative)
686 {
687 case 0:
688 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
689 {
690 if (GET_CODE (operands[1]) == REG)
691 return \"lda (%1),%0\";
692 else
693 return \"lda %1,%0\";
694 }
695 return \"mov %1,%0\";
696 case 1:
697 return i960_output_ldconst (operands[0], operands[1]);
698 case 2:
699 return \"ldos %1,%0\";
700 case 3:
701 return \"stos %1,%0\";
702 }
703 }"
704 [(set_attr "type" "move,misc,load,store")
705 (set_attr "length" "*,3,*,*")])
706
707 (define_expand "movqi"
708 [(set (match_operand:QI 0 "general_operand" "")
709 (match_operand:QI 1 "general_operand" ""))]
710 ""
711 "
712 {
713 if (emit_move_sequence (operands, QImode))
714 DONE;
715 }")
716
717 ;; The store case can not be separate. See comment above.
718 (define_insn ""
719 [(set (match_operand:QI 0 "general_operand" "=d,d,d,m")
720 (match_operand:QI 1 "general_operand" "dI,i,m,dJ"))]
721 "(current_function_args_size == 0
722 && rtx_equal_function_value_matters == 0)
723 && (register_operand (operands[0], QImode)
724 || register_operand (operands[1], QImode)
725 || operands[1] == const0_rtx)"
726 "*
727 {
728 switch (which_alternative)
729 {
730 case 0:
731 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
732 {
733 if (GET_CODE (operands[1]) == REG)
734 return \"lda (%1),%0\";
735 else
736 return \"lda %1,%0\";
737 }
738 return \"mov %1,%0\";
739 case 1:
740 return i960_output_ldconst (operands[0], operands[1]);
741 case 2:
742 return \"ldob %1,%0\";
743 case 3:
744 if (operands[1] == const0_rtx)
745 return \"stob g14,%0\";
746 return \"stob %1,%0\";
747 }
748 }"
749 [(set_attr "type" "move,misc,load,store")
750 (set_attr "length" "*,3,*,*")])
751
752 ;; The store case can not be separate. See comment above.
753 (define_insn ""
754 [(set (match_operand:QI 0 "general_operand" "=d,d,d,m")
755 (match_operand:QI 1 "general_operand" "dI,i,m,d"))]
756 "(current_function_args_size != 0
757 || rtx_equal_function_value_matters != 0)
758 && (register_operand (operands[0], QImode)
759 || register_operand (operands[1], QImode))"
760 "*
761 {
762 switch (which_alternative)
763 {
764 case 0:
765 if (i960_last_insn_type == I_TYPE_REG && TARGET_C_SERIES)
766 {
767 if (GET_CODE (operands[1]) == REG)
768 return \"lda (%1),%0\";
769 else
770 return \"lda %1,%0\";
771 }
772 return \"mov %1,%0\";
773 case 1:
774 return i960_output_ldconst (operands[0], operands[1]);
775 case 2:
776 return \"ldob %1,%0\";
777 case 3:
778 return \"stob %1,%0\";
779 }
780 }"
781 [(set_attr "type" "move,misc,load,store")
782 (set_attr "length" "*,3,*,*")])
783
784 (define_expand "movdi"
785 [(set (match_operand:DI 0 "general_operand" "")
786 (match_operand:DI 1 "general_operand" ""))]
787 ""
788 "
789 {
790 if (emit_move_sequence (operands, DImode))
791 DONE;
792 }")
793
794 ;; The store case can not be separate. See comment above.
795 (define_insn ""
796 [(set (match_operand:DI 0 "general_operand" "=d,d,d,m,o")
797 (match_operand:DI 1 "general_operand" "dI,i,m,d,J"))]
798 "(current_function_args_size == 0
799 && rtx_equal_function_value_matters == 0)
800 && (register_operand (operands[0], DImode)
801 || register_operand (operands[1], DImode)
802 || operands[1] == const0_rtx)"
803 "*
804 {
805 switch (which_alternative)
806 {
807 case 0:
808 return \"movl %1,%0\";
809 case 1:
810 return i960_output_ldconst (operands[0], operands[1]);
811 case 2:
812 return \"ldl %1,%0\";
813 case 3:
814 return \"stl %1,%0\";
815 case 4:
816 operands[1] = adj_offsettable_operand (operands[0], 4);
817 return \"st g14,%0\;st g14,%1\";
818 }
819 }"
820 [(set_attr "type" "move,load,load,store,store")])
821
822 ;; The store case can not be separate. See comment above.
823 (define_insn ""
824 [(set (match_operand:DI 0 "general_operand" "=d,d,d,m")
825 (match_operand:DI 1 "general_operand" "dI,i,m,d"))]
826 "(current_function_args_size != 0
827 || rtx_equal_function_value_matters != 0)
828 && (register_operand (operands[0], DImode)
829 || register_operand (operands[1], DImode))"
830 "*
831 {
832 switch (which_alternative)
833 {
834 case 0:
835 return \"movl %1,%0\";
836 case 1:
837 return i960_output_ldconst (operands[0], operands[1]);
838 case 2:
839 return \"ldl %1,%0\";
840 case 3:
841 return \"stl %1,%0\";
842 }
843 }"
844 [(set_attr "type" "move,load,load,store")])
845
846 (define_expand "movti"
847 [(set (match_operand:TI 0 "general_operand" "")
848 (match_operand:TI 1 "general_operand" ""))]
849 ""
850 "
851 {
852 if (emit_move_sequence (operands, TImode))
853 DONE;
854 }")
855
856 ;; The store case can not be separate. See comment above.
857 (define_insn ""
858 [(set (match_operand:TI 0 "general_operand" "=d,d,d,m,o")
859 (match_operand:TI 1 "general_operand" "dI,i,m,d,J"))]
860 "(current_function_args_size == 0
861 && rtx_equal_function_value_matters == 0)
862 && (register_operand (operands[0], TImode)
863 || register_operand (operands[1], TImode)
864 || operands[1] == const0_rtx)"
865 "*
866 {
867 switch (which_alternative)
868 {
869 case 0:
870 return \"movq %1,%0\";
871 case 1:
872 return i960_output_ldconst (operands[0], operands[1]);
873 case 2:
874 return \"ldq %1,%0\";
875 case 3:
876 return \"stq %1,%0\";
877 case 4:
878 operands[1] = adj_offsettable_operand (operands[0], 4);
879 operands[2] = adj_offsettable_operand (operands[0], 8);
880 operands[3] = adj_offsettable_operand (operands[0], 12);
881 return \"st g14,%0\;st g14,%1\;st g14,%2\;st g14,%3\";
882 }
883 }"
884 [(set_attr "type" "move,load,load,store,store")])
885
886 ;; The store case can not be separate. See comment above.
887 (define_insn ""
888 [(set (match_operand:TI 0 "general_operand" "=d,d,d,m")
889 (match_operand:TI 1 "general_operand" "dI,i,m,d"))]
890 "(current_function_args_size != 0
891 || rtx_equal_function_value_matters != 0)
892 && (register_operand (operands[0], TImode)
893 || register_operand (operands[1], TImode))"
894 "*
895 {
896 switch (which_alternative)
897 {
898 case 0:
899 return \"movq %1,%0\";
900 case 1:
901 return i960_output_ldconst (operands[0], operands[1]);
902 case 2:
903 return \"ldq %1,%0\";
904 case 3:
905 return \"stq %1,%0\";
906 }
907 }"
908 [(set_attr "type" "move,load,load,store")])
909
910 (define_expand "store_multiple"
911 [(set (match_operand:SI 0 "" "") ;;- dest
912 (match_operand:SI 1 "" "")) ;;- src
913 (use (match_operand:SI 2 "" ""))] ;;- nregs
914 ""
915 "
916 {
917 int regno;
918 int count;
919 rtx from;
920 int i;
921
922 if (GET_CODE (operands[0]) != MEM
923 || GET_CODE (operands[1]) != REG
924 || GET_CODE (operands[2]) != CONST_INT)
925 FAIL;
926
927 count = INTVAL (operands[2]);
928 if (count > 12)
929 FAIL;
930
931 regno = REGNO (operands[1]);
932 from = memory_address (SImode, XEXP (operands[0], 0));
933 while (count >= 4 && ((regno & 3) == 0))
934 {
935 emit_insn (gen_rtx (SET, VOIDmode,
936 gen_rtx (MEM, TImode, from),
937 gen_rtx (REG, TImode, regno)));
938 count -= 4;
939 regno += 4;
940 from = memory_address (TImode, plus_constant (from, 16));
941 }
942 while (count >= 2 && ((regno & 1) == 0))
943 {
944 emit_insn (gen_rtx (SET, VOIDmode,
945 gen_rtx (MEM, DImode, from),
946 gen_rtx (REG, DImode, regno)));
947 count -= 2;
948 regno += 2;
949 from = memory_address (DImode, plus_constant (from, 8));
950 }
951 while (count > 0)
952 {
953 emit_insn (gen_rtx (SET, VOIDmode,
954 gen_rtx (MEM, SImode, from),
955 gen_rtx (REG, SImode, regno)));
956 count -= 1;
957 regno += 1;
958 from = memory_address (SImode, plus_constant (from, 4));
959 }
960 DONE;
961 }")
962 \f
963 ;; Floating point move insns
964
965 (define_expand "movdf"
966 [(set (match_operand:DF 0 "general_operand" "")
967 (match_operand:DF 1 "fpmove_src_operand" ""))]
968 ""
969 "
970 {
971 if (emit_move_sequence (operands, DFmode))
972 DONE;
973 }")
974
975 (define_insn ""
976 [(set (match_operand:DF 0 "general_operand" "=r,*f,d,d,m,o")
977 (match_operand:DF 1 "fpmove_src_operand" "r,GH,F,m,d,G"))]
978 "(current_function_args_size == 0
979 && rtx_equal_function_value_matters == 0)
980 && (register_operand (operands[0], DFmode)
981 || register_operand (operands[1], DFmode)
982 || operands[1] == CONST0_RTX (DFmode))"
983 "*
984 {
985 switch (which_alternative)
986 {
987 case 0:
988 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
989 return \"movrl %1,%0\";
990 else
991 return \"movl %1,%0\";
992 case 1:
993 return \"movrl %1,%0\";
994 case 2:
995 return i960_output_ldconst (operands[0], operands[1]);
996 case 3:
997 return \"ldl %1,%0\";
998 case 4:
999 return \"stl %1,%0\";
1000 case 5:
1001 operands[1] = adj_offsettable_operand (operands[0], 4);
1002 return \"st g14,%0\;st g14,%1\";
1003 }
1004 }"
1005 [(set_attr "type" "move,move,load,fpload,fpstore,fpstore")])
1006
1007 (define_insn ""
1008 [(set (match_operand:DF 0 "general_operand" "=r,*f,d,d,m")
1009 (match_operand:DF 1 "fpmove_src_operand" "r,GH,F,m,d"))]
1010 "(current_function_args_size != 0
1011 || rtx_equal_function_value_matters != 0)
1012 && (register_operand (operands[0], DFmode)
1013 || register_operand (operands[1], DFmode))"
1014 "*
1015 {
1016 switch (which_alternative)
1017 {
1018 case 0:
1019 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1020 return \"movrl %1,%0\";
1021 else
1022 return \"movl %1,%0\";
1023 case 1:
1024 return \"movrl %1,%0\";
1025 case 2:
1026 return i960_output_ldconst (operands[0], operands[1]);
1027 case 3:
1028 return \"ldl %1,%0\";
1029 case 4:
1030 return \"stl %1,%0\";
1031 }
1032 }"
1033 [(set_attr "type" "move,move,load,fpload,fpstore")])
1034
1035 (define_expand "movsf"
1036 [(set (match_operand:SF 0 "general_operand" "")
1037 (match_operand:SF 1 "fpmove_src_operand" ""))]
1038 ""
1039 "
1040 {
1041 if (emit_move_sequence (operands, SFmode))
1042 DONE;
1043 }")
1044
1045 (define_insn ""
1046 [(set (match_operand:SF 0 "general_operand" "=r,*f,d,d,m")
1047 (match_operand:SF 1 "fpmove_src_operand" "r,GH,F,m,dG"))]
1048 "(current_function_args_size == 0
1049 && rtx_equal_function_value_matters == 0)
1050 && (register_operand (operands[0], SFmode)
1051 || register_operand (operands[1], SFmode)
1052 || operands[1] == CONST0_RTX (SFmode))"
1053 "*
1054 {
1055 switch (which_alternative)
1056 {
1057 case 0:
1058 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1059 return \"movr %1,%0\";
1060 else
1061 return \"mov %1,%0\";
1062 case 1:
1063 return \"movr %1,%0\";
1064 case 2:
1065 return i960_output_ldconst (operands[0], operands[1]);
1066 case 3:
1067 return \"ld %1,%0\";
1068 case 4:
1069 if (operands[1] == CONST0_RTX (SFmode))
1070 return \"st g14,%0\";
1071 return \"st %1,%0\";
1072 }
1073 }"
1074 [(set_attr "type" "move,move,load,fpload,fpstore")])
1075
1076 (define_insn ""
1077 [(set (match_operand:SF 0 "general_operand" "=r,*f,d,d,m")
1078 (match_operand:SF 1 "fpmove_src_operand" "r,GH,F,m,d"))]
1079 "(current_function_args_size != 0
1080 || rtx_equal_function_value_matters != 0)
1081 && (register_operand (operands[0], SFmode)
1082 || register_operand (operands[1], SFmode))"
1083 "*
1084 {
1085 switch (which_alternative)
1086 {
1087 case 0:
1088 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1089 return \"movr %1,%0\";
1090 else
1091 return \"mov %1,%0\";
1092 case 1:
1093 return \"movr %1,%0\";
1094 case 2:
1095 return i960_output_ldconst (operands[0], operands[1]);
1096 case 3:
1097 return \"ld %1,%0\";
1098 case 4:
1099 return \"st %1,%0\";
1100 }
1101 }"
1102 [(set_attr "type" "move,move,load,fpload,fpstore")])
1103 \f
1104 ;; Mixed-mode moves with sign and zero-extension.
1105
1106 ;; Note that the one starting from HImode comes before those for QImode
1107 ;; so that a constant operand will match HImode, not QImode.
1108
1109 (define_expand "extendhisi2"
1110 [(set (match_operand:SI 0 "register_operand" "")
1111 (sign_extend:SI
1112 (match_operand:HI 1 "nonimmediate_operand" "")))]
1113 ""
1114 "
1115 {
1116 if (GET_CODE (operand1) == REG
1117 || (GET_CODE (operand1) == SUBREG
1118 && GET_CODE (XEXP (operand1, 0)) == REG))
1119 {
1120 rtx temp = gen_reg_rtx (SImode);
1121 rtx shift_16 = gen_rtx (CONST_INT, VOIDmode, 16);
1122 int op1_subreg_word = 0;
1123
1124 if (GET_CODE (operand1) == SUBREG)
1125 {
1126 op1_subreg_word = SUBREG_WORD (operand1);
1127 operand1 = SUBREG_REG (operand1);
1128 }
1129 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word);
1130
1131 emit_insn (gen_ashlsi3 (temp, operand1, shift_16));
1132 emit_insn (gen_ashrsi3 (operand0, temp, shift_16));
1133 DONE;
1134 }
1135 }")
1136
1137 (define_insn ""
1138 [(set (match_operand:SI 0 "register_operand" "=d")
1139 (sign_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
1140 ""
1141 "ldis %1,%0"
1142 [(set_attr "type" "load")])
1143
1144 (define_expand "extendqisi2"
1145 [(set (match_operand:SI 0 "register_operand" "")
1146 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
1147 ""
1148 "
1149 {
1150 if (GET_CODE (operand1) == REG
1151 || (GET_CODE (operand1) == SUBREG
1152 && GET_CODE (XEXP (operand1, 0)) == REG))
1153 {
1154 rtx temp = gen_reg_rtx (SImode);
1155 rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24);
1156 int op1_subreg_word = 0;
1157
1158 if (GET_CODE (operand1) == SUBREG)
1159 {
1160 op1_subreg_word = SUBREG_WORD (operand1);
1161 operand1 = SUBREG_REG (operand1);
1162 }
1163 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word),
1164
1165 emit_insn (gen_ashlsi3 (temp, operand1, shift_24));
1166 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
1167 DONE;
1168 }
1169 }")
1170
1171 (define_insn ""
1172 [(set (match_operand:SI 0 "register_operand" "=d")
1173 (sign_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
1174 ""
1175 "ldib %1,%0"
1176 [(set_attr "type" "load")])
1177
1178 (define_expand "extendqihi2"
1179 [(set (match_operand:HI 0 "register_operand" "")
1180 (sign_extend:HI
1181 (match_operand:QI 1 "nonimmediate_operand" "")))]
1182 ""
1183 "
1184 {
1185 if (GET_CODE (operand1) == REG
1186 || (GET_CODE (operand1) == SUBREG
1187 && GET_CODE (XEXP (operand1, 0)) == REG))
1188 {
1189 rtx temp = gen_reg_rtx (SImode);
1190 rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24);
1191 int op0_subreg_word = 0;
1192 int op1_subreg_word = 0;
1193
1194 if (GET_CODE (operand1) == SUBREG)
1195 {
1196 op1_subreg_word = SUBREG_WORD (operand1);
1197 operand1 = SUBREG_REG (operand1);
1198 }
1199 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word);
1200
1201 if (GET_CODE (operand0) == SUBREG)
1202 {
1203 op0_subreg_word = SUBREG_WORD (operand0);
1204 operand0 = SUBREG_REG (operand0);
1205 }
1206 if (GET_MODE (operand0) != SImode)
1207 operand0 = gen_rtx (SUBREG, SImode, operand0, op0_subreg_word);
1208
1209 emit_insn (gen_ashlsi3 (temp, operand1, shift_24));
1210 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
1211 DONE;
1212 }
1213 }")
1214
1215 (define_insn ""
1216 [(set (match_operand:HI 0 "register_operand" "=d")
1217 (sign_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
1218 ""
1219 "ldib %1,%0"
1220 [(set_attr "type" "load")])
1221
1222 (define_expand "zero_extendhisi2"
1223 [(set (match_operand:SI 0 "register_operand" "")
1224 (zero_extend:SI
1225 (match_operand:HI 1 "nonimmediate_operand" "")))]
1226 ""
1227 "
1228 {
1229 if (GET_CODE (operand1) == REG
1230 || (GET_CODE (operand1) == SUBREG
1231 && GET_CODE (XEXP (operand1, 0)) == REG))
1232 {
1233 rtx temp = gen_reg_rtx (SImode);
1234 rtx shift_16 = gen_rtx (CONST_INT, VOIDmode, 16);
1235 int op1_subreg_word = 0;
1236
1237 if (GET_CODE (operand1) == SUBREG)
1238 {
1239 op1_subreg_word = SUBREG_WORD (operand1);
1240 operand1 = SUBREG_REG (operand1);
1241 }
1242 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word);
1243
1244 emit_insn (gen_ashlsi3 (temp, operand1, shift_16));
1245 emit_insn (gen_lshrsi3 (operand0, temp, shift_16));
1246 DONE;
1247 }
1248 }")
1249
1250 (define_insn ""
1251 [(set (match_operand:SI 0 "register_operand" "=d")
1252 (zero_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
1253 ""
1254 "ldos %1,%0"
1255 [(set_attr "type" "load")])
1256
1257 ;; Using shifts here generates much better code than doing an `and 255'.
1258 ;; This is mainly because the `and' requires loading the constant separately,
1259 ;; the constant is likely to get optimized, and then the compiler can't
1260 ;; optimize the `and' because it doesn't know that one operand is a constant.
1261
1262 (define_expand "zero_extendqisi2"
1263 [(set (match_operand:SI 0 "register_operand" "")
1264 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
1265 ""
1266 "
1267 {
1268 if (GET_CODE (operand1) == REG
1269 || (GET_CODE (operand1) == SUBREG
1270 && GET_CODE (XEXP (operand1, 0)) == REG))
1271 {
1272 rtx temp = gen_reg_rtx (SImode);
1273 rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24);
1274 int op1_subreg_word = 0;
1275
1276 if (GET_CODE (operand1) == SUBREG)
1277 {
1278 op1_subreg_word = SUBREG_WORD (operand1);
1279 operand1 = SUBREG_REG (operand1);
1280 }
1281 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word);
1282
1283 emit_insn (gen_ashlsi3 (temp, operand1, shift_24));
1284 emit_insn (gen_lshrsi3 (operand0, temp, shift_24));
1285 DONE;
1286 }
1287 }")
1288
1289 (define_insn ""
1290 [(set (match_operand:SI 0 "register_operand" "=d")
1291 (zero_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
1292 ""
1293 "ldob %1,%0"
1294 [(set_attr "type" "load")])
1295
1296 (define_expand "zero_extendqihi2"
1297 [(set (match_operand:HI 0 "register_operand" "")
1298 (zero_extend:HI
1299 (match_operand:QI 1 "nonimmediate_operand" "")))]
1300 ""
1301 "
1302 {
1303 if (GET_CODE (operand1) == REG
1304 || (GET_CODE (operand1) == SUBREG
1305 && GET_CODE (XEXP (operand1, 0)) == REG))
1306 {
1307 rtx temp = gen_reg_rtx (SImode);
1308 rtx shift_24 = gen_rtx (CONST_INT, VOIDmode, 24);
1309 int op0_subreg_word = 0;
1310 int op1_subreg_word = 0;
1311
1312 if (GET_CODE (operand1) == SUBREG)
1313 {
1314 op1_subreg_word = SUBREG_WORD (operand1);
1315 operand1 = SUBREG_REG (operand1);
1316 }
1317 operand1 = gen_rtx (SUBREG, SImode, operand1, op1_subreg_word);
1318
1319 if (GET_CODE (operand0) == SUBREG)
1320 {
1321 op0_subreg_word = SUBREG_WORD (operand0);
1322 operand0 = SUBREG_REG (operand0);
1323 }
1324 if (GET_MODE (operand0) != SImode)
1325 operand0 = gen_rtx (SUBREG, SImode, operand0, op0_subreg_word);
1326
1327 emit_insn (gen_ashlsi3 (temp, operand1, shift_24));
1328 emit_insn (gen_lshrsi3 (operand0, temp, shift_24));
1329 DONE;
1330 }
1331 }")
1332
1333 (define_insn ""
1334 [(set (match_operand:HI 0 "register_operand" "=d")
1335 (zero_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
1336 ""
1337 "ldob %1,%0"
1338 [(set_attr "type" "load")])
1339 \f
1340 ;; Conversions between float and double.
1341
1342 (define_insn "extendsfdf2"
1343 [(set (match_operand:DF 0 "register_operand" "=*f,d")
1344 (float_extend:DF (match_operand:SF 1 "fp_arith_operand" "dGH,fGH")))]
1345 "TARGET_NUMERICS"
1346 "@
1347 movr %1,%0
1348 movrl %1,%0"
1349 [(set_attr "type" "fpmove")])
1350
1351 (define_insn "truncdfsf2"
1352 [(set (match_operand:SF 0 "register_operand" "=d")
1353 (float_truncate:SF
1354 (match_operand:DF 1 "fp_arith_operand" "fGH")))]
1355 "TARGET_NUMERICS"
1356 "movr %1,%0"
1357 [(set_attr "type" "fpmove")])
1358
1359 ;; Conversion between fixed point and floating point.
1360
1361 (define_insn "floatsidf2"
1362 [(set (match_operand:DF 0 "register_operand" "=f")
1363 (float:DF (match_operand:SI 1 "register_operand" "d")))]
1364 "TARGET_NUMERICS"
1365 "cvtir %1,%0"
1366 [(set_attr "type" "fpcvt")])
1367
1368 (define_insn "floatsisf2"
1369 [(set (match_operand:SF 0 "register_operand" "=d*f")
1370 (float:SF (match_operand:SI 1 "register_operand" "d")))]
1371 "TARGET_NUMERICS"
1372 "cvtir %1,%0"
1373 [(set_attr "type" "fpcvt")])
1374
1375 ;; Convert a float to an actual integer.
1376 ;; Truncation is performed as part of the conversion.
1377 ;; The i960 requires conversion from DFmode to DImode to make
1378 ;; unsigned conversions work properly.
1379
1380 (define_insn "fixuns_truncdfdi2"
1381 [(set (match_operand:DI 0 "register_operand" "=d")
1382 (unsigned_fix:DI (fix:DF (match_operand:DF 1 "fp_arith_operand" "fGH"))))]
1383 "TARGET_NUMERICS"
1384 "cvtzril %1,%0"
1385 [(set_attr "type" "fpcvt")])
1386
1387 (define_insn "fixuns_truncsfdi2"
1388 [(set (match_operand:DI 0 "register_operand" "=d")
1389 (unsigned_fix:DI (fix:SF (match_operand:SF 1 "fp_arith_operand" "fGH"))))]
1390 "TARGET_NUMERICS"
1391 "cvtzril %1,%0"
1392 [(set_attr "type" "fpcvt")])
1393
1394 (define_insn "fix_truncdfsi2"
1395 [(set (match_operand:SI 0 "register_operand" "=d")
1396 (fix:SI (fix:DF (match_operand:DF 1 "fp_arith_operand" "fGH"))))]
1397 "TARGET_NUMERICS"
1398 "cvtzri %1,%0"
1399 [(set_attr "type" "fpcvt")])
1400
1401 (define_expand "fixuns_truncdfsi2"
1402 [(set (match_operand:SI 0 "register_operand" "")
1403 (unsigned_fix:SI (fix:DF (match_operand:DF 1 "fp_arith_operand" ""))))]
1404 "TARGET_NUMERICS"
1405 "
1406 {
1407 rtx temp = gen_reg_rtx (DImode);
1408 emit_insn (gen_rtx (SET, VOIDmode, temp,
1409 gen_rtx (UNSIGNED_FIX, DImode,
1410 gen_rtx (FIX, DFmode, operands[1]))));
1411 emit_insn (gen_rtx (SET, VOIDmode, operands[0],
1412 gen_rtx (SUBREG, SImode, temp, 0)));
1413 DONE;
1414 }")
1415
1416 (define_insn "fix_truncsfsi2"
1417 [(set (match_operand:SI 0 "register_operand" "=d")
1418 (fix:SI (fix:SF (match_operand:SF 1 "fp_arith_operand" "dfGH"))))]
1419 "TARGET_NUMERICS"
1420 "cvtzri %1,%0"
1421 [(set_attr "type" "fpcvt")])
1422
1423 (define_expand "fixuns_truncsfsi2"
1424 [(set (match_operand:SI 0 "register_operand" "")
1425 (unsigned_fix:SI (fix:SF (match_operand:SF 1 "fp_arith_operand" ""))))]
1426 "TARGET_NUMERICS"
1427 "
1428 {
1429 rtx temp = gen_reg_rtx (DImode);
1430 emit_insn (gen_rtx (SET, VOIDmode, temp,
1431 gen_rtx (UNSIGNED_FIX, DImode,
1432 gen_rtx (FIX, SFmode, operands[1]))));
1433 emit_insn (gen_rtx (SET, VOIDmode, operands[0],
1434 gen_rtx (SUBREG, SImode, temp, 0)));
1435 DONE;
1436 }")
1437 \f
1438 ;; Arithmetic instructions.
1439
1440 (define_insn "subsi3"
1441 [(set (match_operand:SI 0 "register_operand" "=d")
1442 (minus:SI (match_operand:SI 1 "arith_operand" "dI")
1443 (match_operand:SI 2 "arith_operand" "dI")))]
1444 ""
1445 "subo %2,%1,%0")
1446
1447 ;; Try to generate an lda instruction when it would be faster than an
1448 ;; add instruction.
1449 ;; Some assemblers apparently won't accept two addresses added together.
1450
1451 (define_insn ""
1452 [(set (match_operand:SI 0 "register_operand" "=d,d,d")
1453 (plus:SI (match_operand:SI 1 "arith32_operand" "%dn,i,dn")
1454 (match_operand:SI 2 "arith32_operand" "dn,dn,i")))]
1455 "(TARGET_C_SERIES) && (CONSTANT_P (operands[1]) || CONSTANT_P (operands[2]))"
1456 "*
1457 {
1458 if (GET_CODE (operands[1]) == CONST_INT)
1459 {
1460 rtx tmp = operands[1];
1461 operands[1] = operands[2];
1462 operands[2] = tmp;
1463 }
1464 if (GET_CODE (operands[2]) == CONST_INT
1465 && GET_CODE (operands[1]) == REG
1466 && i960_last_insn_type != I_TYPE_REG)
1467 {
1468 if (INTVAL (operands[2]) < 0 && INTVAL (operands[2]) > -32)
1469 return \"subo %n2,%1,%0\";
1470 else if (INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) < 32)
1471 return \"addo %1,%2,%0\";
1472 }
1473 if (CONSTANT_P (operands[1]))
1474 return \"lda %1+%2,%0\";
1475 return \"lda %2(%1),%0\";
1476 }")
1477
1478 (define_insn "addsi3"
1479 [(set (match_operand:SI 0 "register_operand" "=d")
1480 (plus:SI (match_operand:SI 1 "signed_arith_operand" "%dI")
1481 (match_operand:SI 2 "signed_arith_operand" "dIK")))]
1482 ""
1483 "*
1484 {
1485 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
1486 return \"subo %n2,%1,%0\";
1487 if (i960_bypass (insn, operands[1], operands[2], 0))
1488 return \"addo %2,%1,%0\";
1489 return \"addo %1,%2,%0\";
1490 }")
1491
1492 (define_insn "mulsi3"
1493 [(set (match_operand:SI 0 "register_operand" "=d")
1494 (mult:SI (match_operand:SI 1 "arith_operand" "%dI")
1495 (match_operand:SI 2 "arith_operand" "dI")))]
1496 ""
1497 "*
1498 {
1499 if (i960_bypass (insn, operands[1], operands[2], 0))
1500 return \"mulo %2,%1,%0\";
1501 return \"mulo %1,%2,%0\";
1502 }"
1503 [(set_attr "type" "mult")])
1504
1505 (define_insn "umulsidi3"
1506 [(set (match_operand:DI 0 "register_operand" "=d")
1507 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
1508 (zero_extend:DI (match_operand:SI 2 "register_operand" "d"))))]
1509 ""
1510 "*
1511 {
1512 if (i960_bypass (insn, operands[1], operands[2], 0))
1513 return \"emul %2,%1,%0\";
1514 return \"emul %1,%2,%0\";
1515 }"
1516 [(set_attr "type" "mult")])
1517
1518 (define_insn ""
1519 [(set (match_operand:DI 0 "register_operand" "=d")
1520 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%d"))
1521 (match_operand:SI 2 "literal" "I")))]
1522 ""
1523 "*
1524 {
1525 if (i960_bypass (insn, operands[1], operands[2], 0))
1526 return \"emul %2,%1,%0\";
1527 return \"emul %1,%2,%0\";
1528 }"
1529 [(set_attr "type" "mult")])
1530
1531 ;; This goes after the move/add/sub/mul instructions
1532 ;; because those instructions are better when they apply.
1533
1534 (define_insn ""
1535 [(set (match_operand:SI 0 "register_operand" "=d")
1536 (match_operand:SI 1 "address_operand" "p"))]
1537 ""
1538 "lda %a1,%0"
1539 [(set_attr "type" "load")])
1540
1541 ;; This will never be selected because of an "optimization" that GCC does.
1542 ;; It always converts divides by a power of 2 into a sequence of instructions
1543 ;; that does a right shift, and then corrects the result if it was negative.
1544
1545 ;; (define_insn ""
1546 ;; [(set (match_operand:SI 0 "register_operand" "=d")
1547 ;; (div:SI (match_operand:SI 1 "arith_operand" "dI")
1548 ;; (match_operand:SI 2 "power2_operand" "nI")))]
1549 ;; ""
1550 ;; "*{
1551 ;; operands[2] = gen_rtx(CONST_INT, VOIDmode,bitpos (INTVAL (operands[2])));
1552 ;; return \"shrdi %2,%1,%0\";
1553 ;; }"
1554
1555 (define_insn "divsi3"
1556 [(set (match_operand:SI 0 "register_operand" "=d")
1557 (div:SI (match_operand:SI 1 "arith_operand" "dI")
1558 (match_operand:SI 2 "arith_operand" "dI")))]
1559 ""
1560 "divi %2,%1,%0"
1561 [(set_attr "type" "div")])
1562
1563 (define_insn "udivsi3"
1564 [(set (match_operand:SI 0 "register_operand" "=d")
1565 (udiv:SI (match_operand:SI 1 "arith_operand" "dI")
1566 (match_operand:SI 2 "arith_operand" "dI")))]
1567 ""
1568 "divo %2,%1,%0"
1569 [(set_attr "type" "div")])
1570
1571 ;; We must use `remi' not `modi' here, to ensure that `%' has the effects
1572 ;; specified by the ANSI C standard.
1573
1574 (define_insn "modsi3"
1575 [(set (match_operand:SI 0 "register_operand" "=d")
1576 (mod:SI (match_operand:SI 1 "arith_operand" "dI")
1577 (match_operand:SI 2 "arith_operand" "dI")))]
1578 ""
1579 "remi %2,%1,%0"
1580 [(set_attr "type" "div")])
1581
1582 (define_insn "umodsi3"
1583 [(set (match_operand:SI 0 "register_operand" "=d")
1584 (umod:SI (match_operand:SI 1 "arith_operand" "dI")
1585 (match_operand:SI 2 "arith_operand" "dI")))]
1586 ""
1587 "remo %2,%1,%0"
1588 [(set_attr "type" "div")])
1589
1590 ;; And instructions (with complement also).
1591
1592 (define_insn "andsi3"
1593 [(set (match_operand:SI 0 "register_operand" "=d")
1594 (and:SI (match_operand:SI 1 "arith_operand" "%dI")
1595 (match_operand:SI 2 "arith_operand" "dI")))]
1596 ""
1597 "*
1598 {
1599 if (i960_bypass (insn, operands[1], operands[2], 0))
1600 return \"and %2,%1,%0\";
1601 return \"and %1,%2,%0\";
1602 }")
1603
1604 (define_insn ""
1605 [(set (match_operand:SI 0 "register_operand" "=d")
1606 (and:SI (not:SI (match_operand:SI 1 "arith_operand" "dI"))
1607 (match_operand:SI 2 "arith_operand" "dI")))]
1608 ""
1609 "*
1610 {
1611 if (i960_bypass (insn, operands[1], operands[2], 0))
1612 return \"notand %2,%1,%0\";
1613 return \"andnot %1,%2,%0\";
1614 }")
1615
1616 (define_insn ""
1617 [(set (match_operand:SI 0 "register_operand" "=d")
1618 (ior:SI (not:SI (match_operand:SI 1 "arith_operand" "%dI"))
1619 (not:SI (match_operand:SI 2 "arith_operand" "dI"))))]
1620 ""
1621 "*
1622 {
1623 if (i960_bypass (insn, operands[1], operands[2], 0))
1624 return \"nand %2,%1,%0\";
1625 return \"nand %1,%2,%0\";
1626 }")
1627
1628 (define_insn ""
1629 [(set (match_operand:SI 0 "register_operand" "=d")
1630 (ior:SI (match_operand:SI 1 "arith_operand" "dI")
1631 (match_operand:SI 2 "power2_operand" "n")))]
1632 ""
1633 "*
1634 {
1635 operands[2] = gen_rtx (CONST_INT, VOIDmode,
1636 bitpos (INTVAL (operands[2])));
1637 return \"setbit %2,%1,%0\";
1638 }")
1639
1640 (define_insn ""
1641 [(set (match_operand:SI 0 "register_operand" "=d")
1642 (ior:SI (ashift:SI (const_int 1)
1643 (match_operand:SI 1 "register_operand" "d"))
1644 (match_operand:SI 2 "arith_operand" "dI")))]
1645 ""
1646 "setbit %1,%2,%0")
1647
1648 (define_insn ""
1649 [(set (match_operand:SI 0 "register_operand" "=d")
1650 (and:SI (match_operand:SI 1 "arith_operand" "dI")
1651 (match_operand:SI 2 "cmplpower2_operand" "n")))]
1652 ""
1653 "*
1654 {
1655 operands[2] = gen_rtx (CONST_INT, VOIDmode,
1656 bitpos (~INTVAL (operands[2])));
1657 return \"clrbit %2,%1,%0\";
1658 }")
1659
1660 ;; (not (ashift 1 reg)) canonicalizes to (rotate -2 reg)
1661 (define_insn ""
1662 [(set (match_operand:SI 0 "register_operand" "=d")
1663 (and:SI (rotate:SI (const_int -2)
1664 (match_operand:SI 1 "register_operand" "d"))
1665 (match_operand:SI 2 "register_operand" "d")))]
1666 ""
1667 "clrbit %1,%2,%0")
1668
1669 ;; The above pattern canonicalizes to this when both the input and output
1670 ;; are the same pseudo-register.
1671 (define_insn ""
1672 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "=d")
1673 (const_int 1)
1674 (match_operand:SI 1 "register_operand" "d"))
1675 (const_int 0))]
1676 ""
1677 "clrbit %1,%0,%0")
1678
1679 (define_insn ""
1680 [(set (match_operand:SI 0 "register_operand" "=d")
1681 (xor:SI (match_operand:SI 1 "arith_operand" "dI")
1682 (match_operand:SI 2 "power2_operand" "n")))]
1683 ""
1684 "*
1685 {
1686 operands[2] = gen_rtx (CONST_INT, VOIDmode,
1687 bitpos (INTVAL (operands[2])));
1688 return \"notbit %2,%1,%0\";
1689 }")
1690
1691 (define_insn ""
1692 [(set (match_operand:SI 0 "register_operand" "=d")
1693 (xor:SI (ashift:SI (const_int 1)
1694 (match_operand:SI 1 "register_operand" "d"))
1695 (match_operand:SI 2 "arith_operand" "dI")))]
1696 ""
1697 "notbit %1,%2,%0")
1698
1699 (define_insn "iorsi3"
1700 [(set (match_operand:SI 0 "register_operand" "=d")
1701 (ior:SI (match_operand:SI 1 "arith_operand" "%dI")
1702 (match_operand:SI 2 "arith_operand" "dI")))]
1703 ""
1704 "*
1705 {
1706 if (i960_bypass (insn, operands[1], operands[2], 0))
1707 return \"or %2,%1,%0\";
1708 return \"or %1,%2,%0\";
1709 }")
1710
1711 (define_insn ""
1712 [(set (match_operand:SI 0 "register_operand" "=d")
1713 (ior:SI (not:SI (match_operand:SI 1 "arith_operand" "dI"))
1714 (match_operand:SI 2 "arith_operand" "dI")))]
1715 ""
1716 "*
1717 {
1718 if (i960_bypass (insn, operands[1], operands[2], 0))
1719 return \"notor %2,%1,%0\";
1720 return \"ornot %1,%2,%0\";
1721 }")
1722
1723 (define_insn ""
1724 [(set (match_operand:SI 0 "register_operand" "=d")
1725 (and:SI (not:SI (match_operand:SI 1 "arith_operand" "%dI"))
1726 (not:SI (match_operand:SI 2 "arith_operand" "dI"))))]
1727 ""
1728 "*
1729 {
1730 if (i960_bypass (insn, operands[1], operands[2], 0))
1731 return \"nor %2,%1,%0\";
1732 return \"nor %1,%2,%0\";
1733 }")
1734
1735 (define_insn "xorsi3"
1736 [(set (match_operand:SI 0 "register_operand" "=d")
1737 (xor:SI (match_operand:SI 1 "arith_operand" "%dI")
1738 (match_operand:SI 2 "arith_operand" "dI")))]
1739 ""
1740 "*
1741 {
1742 if (i960_bypass (insn, operands[1], operands[2], 0))
1743 return \"xor %2,%1,%0\";
1744 return \"xor %1,%2,%0\";
1745 }")
1746
1747 (define_insn ""
1748 [(set (match_operand:SI 0 "register_operand" "=d")
1749 (not:SI (xor:SI (match_operand:SI 1 "arith_operand" "%dI")
1750 (match_operand:SI 2 "arith_operand" "dI"))))]
1751 ""
1752 "*
1753 {
1754 if (i960_bypass (insn, operands[1], operands[2], 0))
1755 return \"xnor %2,%1,%0\";
1756 return \"xnor %2,%1,%0\";
1757 }")
1758
1759 (define_insn "negsi2"
1760 [(set (match_operand:SI 0 "register_operand" "=d")
1761 (neg:SI (match_operand:SI 1 "arith_operand" "dI")))]
1762 ""
1763 "subo %1,0,%0"
1764 [(set_attr "length" "1")])
1765
1766 (define_insn "one_cmplsi2"
1767 [(set (match_operand:SI 0 "register_operand" "=d")
1768 (not:SI (match_operand:SI 1 "arith_operand" "dI")))]
1769 ""
1770 "not %1,%0"
1771 [(set_attr "length" "1")])
1772 \f
1773 ;; Floating point arithmetic instructions.
1774
1775 (define_insn "adddf3"
1776 [(set (match_operand:DF 0 "register_operand" "=d*f")
1777 (plus:DF (match_operand:DF 1 "fp_arith_operand" "%rGH")
1778 (match_operand:DF 2 "fp_arith_operand" "rGH")))]
1779 "TARGET_NUMERICS"
1780 "addrl %1,%2,%0"
1781 [(set_attr "type" "fpadd")])
1782
1783 (define_insn "addsf3"
1784 [(set (match_operand:SF 0 "register_operand" "=d*f")
1785 (plus:SF (match_operand:SF 1 "fp_arith_operand" "%rGH")
1786 (match_operand:SF 2 "fp_arith_operand" "rGH")))]
1787 "TARGET_NUMERICS"
1788 "addr %1,%2,%0"
1789 [(set_attr "type" "fpadd")])
1790
1791
1792 (define_insn "subdf3"
1793 [(set (match_operand:DF 0 "register_operand" "=d*f")
1794 (minus:DF (match_operand:DF 1 "fp_arith_operand" "rGH")
1795 (match_operand:DF 2 "fp_arith_operand" "rGH")))]
1796 "TARGET_NUMERICS"
1797 "subrl %2,%1,%0"
1798 [(set_attr "type" "fpadd")])
1799
1800 (define_insn "subsf3"
1801 [(set (match_operand:SF 0 "register_operand" "=d*f")
1802 (minus:SF (match_operand:SF 1 "fp_arith_operand" "rGH")
1803 (match_operand:SF 2 "fp_arith_operand" "rGH")))]
1804 "TARGET_NUMERICS"
1805 "subr %2,%1,%0"
1806 [(set_attr "type" "fpadd")])
1807
1808
1809 (define_insn "muldf3"
1810 [(set (match_operand:DF 0 "register_operand" "=d*f")
1811 (mult:DF (match_operand:DF 1 "fp_arith_operand" "%rGH")
1812 (match_operand:DF 2 "fp_arith_operand" "rGH")))]
1813 "TARGET_NUMERICS"
1814 "mulrl %1,%2,%0"
1815 [(set_attr "type" "fpmul")])
1816
1817 (define_insn "mulsf3"
1818 [(set (match_operand:SF 0 "register_operand" "=d*f")
1819 (mult:SF (match_operand:SF 1 "fp_arith_operand" "%rGH")
1820 (match_operand:SF 2 "fp_arith_operand" "rGH")))]
1821 "TARGET_NUMERICS"
1822 "mulr %1,%2,%0"
1823 [(set_attr "type" "fpmul")])
1824
1825
1826 (define_insn "divdf3"
1827 [(set (match_operand:DF 0 "register_operand" "=d*f")
1828 (div:DF (match_operand:DF 1 "fp_arith_operand" "rGH")
1829 (match_operand:DF 2 "fp_arith_operand" "rGH")))]
1830 "TARGET_NUMERICS"
1831 "divrl %2,%1,%0"
1832 [(set_attr "type" "fpdiv")])
1833
1834 (define_insn "divsf3"
1835 [(set (match_operand:SF 0 "register_operand" "=d*f")
1836 (div:SF (match_operand:SF 1 "fp_arith_operand" "rGH")
1837 (match_operand:SF 2 "fp_arith_operand" "rGH")))]
1838 "TARGET_NUMERICS"
1839 "divr %2,%1,%0"
1840 [(set_attr "type" "fpdiv")])
1841
1842 (define_insn "negdf2"
1843 [(set (match_operand:DF 0 "register_operand" "=d,d*f")
1844 (neg:DF (match_operand:DF 1 "register_operand" "d,r")))]
1845 ""
1846 "*
1847 {
1848 if (which_alternative == 0)
1849 {
1850 if (REGNO (operands[0]) == REGNO (operands[1]))
1851 return \"notbit 31,%D1,%D0\";
1852 return \"mov %1,%0\;notbit 31,%D1,%D0\";
1853 }
1854 return \"subrl %1,0f0.0,%0\";
1855 }"
1856 [(set_attr "type" "fpadd")])
1857
1858 (define_insn "negsf2"
1859 [(set (match_operand:SF 0 "register_operand" "=d,d*f")
1860 (neg:SF (match_operand:SF 1 "register_operand" "d,r")))]
1861 ""
1862 "@
1863 notbit 31,%1,%0
1864 subr %1,0f0.0,%0"
1865 [(set_attr "type" "fpadd")])
1866
1867 ;;; The abs patterns also work even if the target machine doesn't have
1868 ;;; floating point, because in that case dstreg and srcreg will always be
1869 ;;; less than 32.
1870
1871 (define_insn "absdf2"
1872 [(set (match_operand:DF 0 "register_operand" "=d*f")
1873 (abs:DF (match_operand:DF 1 "register_operand" "df")))]
1874 ""
1875 "*
1876 {
1877 int dstreg = REGNO (operands[0]);
1878 int srcreg = REGNO (operands[1]);
1879
1880 if (dstreg < 32)
1881 {
1882 if (srcreg < 32)
1883 {
1884 if (dstreg != srcreg)
1885 output_asm_insn (\"mov %1,%0\", operands);
1886 return \"clrbit 31,%D1,%D0\";
1887 }
1888 /* Src is an fp reg. */
1889 return \"movrl %1,%0\;clrbit 31,%D1,%D0\";
1890 }
1891 if (srcreg >= 32)
1892 return \"cpysre %1,0f0.0,%0\";
1893 return \"movrl %1,%0\;cpysre %0,0f0.0,%0\";
1894 }"
1895 [(set_attr "type" "multi")])
1896
1897 (define_insn "abssf2"
1898 [(set (match_operand:SF 0 "register_operand" "=d*f")
1899 (abs:SF (match_operand:SF 1 "register_operand" "df")))]
1900 ""
1901 "*
1902 {
1903 int dstreg = REGNO (operands[0]);
1904 int srcreg = REGNO (operands[1]);
1905
1906 if (dstreg < 32 && srcreg < 32)
1907 return \"clrbit 31,%1,%0\";
1908
1909 if (dstreg >= 32 && srcreg >= 32)
1910 return \"cpysre %1,0f0.0,%0\";
1911
1912 if (dstreg < 32)
1913 return \"movr %1,%0\;clrbit 31,%0,%0\";
1914
1915 return \"movr %1,%0\;cpysre %0,0f0.0,%0\";
1916 }"
1917 [(set_attr "type" "multi")])
1918 \f
1919 ;; Tetra (16 byte) float support.
1920
1921 (define_insn "cmptf"
1922 [(set (reg:CC 36)
1923 (compare:CC (match_operand:TF 0 "register_operand" "f")
1924 (match_operand:TF 1 "nonmemory_operand" "fG")))]
1925 "TARGET_NUMERICS"
1926 "cmpr %0,%1"
1927 [(set_attr "type" "fpcc")])
1928
1929 (define_expand "movtf"
1930 [(set (match_operand:TF 0 "general_operand" "")
1931 (match_operand:TF 1 "fpmove_src_operand" ""))]
1932 ""
1933 "
1934 {
1935 if (emit_move_sequence (operands, TFmode))
1936 DONE;
1937 }")
1938
1939 (define_insn ""
1940 [(set (match_operand:TF 0 "general_operand" "=r,*f,d,d,m,o")
1941 (match_operand:TF 1 "fpmove_src_operand" "r,GH,F,m,d,G"))]
1942 "(current_function_args_size == 0
1943 && rtx_equal_function_value_matters == 0)
1944 && (register_operand (operands[0], TFmode)
1945 || register_operand (operands[1], TFmode)
1946 || operands[1] == CONST0_RTX (TFmode))"
1947 "*
1948 {
1949 switch (which_alternative)
1950 {
1951 case 0:
1952 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1953 return \"movre %1,%0\";
1954 else
1955 return \"movq %1,%0\";
1956 case 1:
1957 return \"movre %1,%0\";
1958 case 2:
1959 return i960_output_ldconst (operands[0], operands[1]);
1960 case 3:
1961 return \"ldq %1,%0\";
1962 case 4:
1963 return \"stq %1,%0\";
1964 case 5:
1965 operands[1] = adj_offsettable_operand (operands[0], 4);
1966 operands[2] = adj_offsettable_operand (operands[0], 8);
1967 operands[3] = adj_offsettable_operand (operands[0], 12);
1968 return \"st g14,%0\;st g14,%1\;st g14,%2\;st g14,%3\";
1969 }
1970 }"
1971 [(set_attr "type" "move,move,load,fpload,fpstore,fpstore")])
1972
1973 (define_insn ""
1974 [(set (match_operand:TF 0 "general_operand" "=r,*f,d,d,m")
1975 (match_operand:TF 1 "fpmove_src_operand" "r,GH,F,m,d"))]
1976 "(current_function_args_size != 0
1977 || rtx_equal_function_value_matters != 0)
1978 && (register_operand (operands[0], TFmode)
1979 || register_operand (operands[1], TFmode))"
1980 "*
1981 {
1982 switch (which_alternative)
1983 {
1984 case 0:
1985 if (FP_REG_P (operands[0]) || FP_REG_P (operands[1]))
1986 return \"movre %1,%0\";
1987 else
1988 return \"movq %1,%0\";
1989 case 1:
1990 return \"movre %1,%0\";
1991 case 2:
1992 return i960_output_ldconst (operands[0], operands[1]);
1993 case 3:
1994 return \"ldq %1,%0\";
1995 case 4:
1996 return \"stq %1,%0\";
1997 }
1998 }"
1999 [(set_attr "type" "move,move,load,fpload,fpstore")])
2000
2001 (define_insn "extendsftf2"
2002 [(set (match_operand:TF 0 "register_operand" "=*f,d")
2003 (float_extend:TF
2004 (match_operand:SF 1 "register_operand" "d,f")))]
2005 "TARGET_NUMERICS"
2006 "@
2007 movr %1,%0
2008 movre %1,%0"
2009 [(set_attr "type" "fpmove")])
2010
2011 (define_insn "extenddftf2"
2012 [(set (match_operand:TF 0 "register_operand" "=*f,d")
2013 (float_extend:TF
2014 (match_operand:DF 1 "register_operand" "d,f")))]
2015 "TARGET_NUMERICS"
2016 "@
2017 movrl %1,%0
2018 movre %1,%0"
2019 [(set_attr "type" "fpmove")])
2020
2021 (define_insn "trunctfdf2"
2022 [(set (match_operand:DF 0 "register_operand" "=d")
2023 (float_truncate:DF
2024 (match_operand:TF 1 "register_operand" "f")))]
2025 "TARGET_NUMERICS"
2026 "movrl %1,%0"
2027 [(set_attr "type" "fpmove")])
2028
2029 (define_insn "trunctfsf2"
2030 [(set (match_operand:SF 0 "register_operand" "=d")
2031 (float_truncate:SF
2032 (match_operand:TF 1 "register_operand" "f")))]
2033 "TARGET_NUMERICS"
2034 "movr %1,%0"
2035 [(set_attr "type" "fpmove")])
2036
2037 (define_insn "floatsitf2"
2038 [(set (match_operand:TF 0 "register_operand" "=f")
2039 (float:TF (match_operand:SI 1 "register_operand" "d")))]
2040 "TARGET_NUMERICS"
2041 "cvtir %1,%0"
2042 [(set_attr "type" "fpcvt")])
2043
2044 (define_insn "fix_trunctfsi2"
2045 [(set (match_operand:SI 0 "register_operand" "=d")
2046 (fix:SI (fix:TF (match_operand:TF 1 "register_operand" "f"))))]
2047 "TARGET_NUMERICS"
2048 "cvtzri %1,%0"
2049 [(set_attr "type" "fpcvt")])
2050
2051 (define_insn "fixuns_trunctfsi2"
2052 [(set (match_operand:SI 0 "register_operand" "=d")
2053 (unsigned_fix:SI (fix:TF (match_operand:TF 1 "register_operand" "f"))))]
2054 "TARGET_NUMERICS"
2055 "cvtzri %1,%0"
2056 [(set_attr "type" "fpcvt")])
2057
2058 (define_insn "addtf3"
2059 [(set (match_operand:TF 0 "register_operand" "=f")
2060 (plus:TF (match_operand:TF 1 "nonmemory_operand" "%fG")
2061 (match_operand:TF 2 "nonmemory_operand" "fG")))]
2062 "TARGET_NUMERICS"
2063 "addr %1,%2,%0"
2064 [(set_attr "type" "fpadd")])
2065
2066 (define_insn "subtf3"
2067 [(set (match_operand:TF 0 "register_operand" "=f")
2068 (minus:TF (match_operand:TF 1 "nonmemory_operand" "fG")
2069 (match_operand:TF 2 "nonmemory_operand" "fG")))]
2070 "TARGET_NUMERICS"
2071 "subr %2,%1,%0"
2072 [(set_attr "type" "fpadd")])
2073
2074 (define_insn "multf3"
2075 [(set (match_operand:TF 0 "register_operand" "=f")
2076 (mult:TF (match_operand:TF 1 "nonmemory_operand" "%fG")
2077 (match_operand:TF 2 "nonmemory_operand" "fG")))]
2078 "TARGET_NUMERICS"
2079 "mulr %1,%2,%0"
2080 [(set_attr "type" "fpmul")])
2081
2082 (define_insn "divtf3"
2083 [(set (match_operand:TF 0 "register_operand" "=f")
2084 (div:TF (match_operand:TF 1 "nonmemory_operand" "fG")
2085 (match_operand:TF 2 "nonmemory_operand" "fG")))]
2086 "TARGET_NUMERICS"
2087 "divr %2,%1,%0"
2088 [(set_attr "type" "fpdiv")])
2089
2090 (define_insn "negtf2"
2091 [(set (match_operand:TF 0 "register_operand" "=f")
2092 (neg:TF (match_operand:TF 1 "register_operand" "f")))]
2093 "TARGET_NUMERICS"
2094 "subr %1,0f0.0,%0"
2095 [(set_attr "type" "fpadd")])
2096
2097 (define_insn "abstf2"
2098 [(set (match_operand:TF 0 "register_operand" "=f")
2099 (abs:TF (match_operand:TF 1 "register_operand" "f")))]
2100 "(TARGET_NUMERICS)"
2101 "cpysre %1,0f0.0,%0"
2102 [(set_attr "type" "fpmove")])
2103 \f
2104 ;; Arithmetic shift instructions.
2105
2106 ;; The shli instruction generates an overflow fault if the sign changes.
2107 ;; In the case of overflow, it does not give the natural result, it instead
2108 ;; gives the last shift value before the overflow. We can not use this
2109 ;; instruction because gcc thinks that arithmetic left shift and logical
2110 ;; left shift are identical, and sometimes canonicalizes the logical left
2111 ;; shift to an arithmetic left shift. Therefore we must always use the
2112 ;; logical left shift instruction.
2113
2114 (define_insn "ashlsi3"
2115 [(set (match_operand:SI 0 "register_operand" "=d")
2116 (ashift:SI (match_operand:SI 1 "arith_operand" "dI")
2117 (match_operand:SI 2 "arith_operand" "dI")))]
2118 ""
2119 "shlo %2,%1,%0"
2120 [(set_attr "type" "alu2")])
2121
2122 (define_insn "ashrsi3"
2123 [(set (match_operand:SI 0 "register_operand" "=d")
2124 (ashiftrt:SI (match_operand:SI 1 "arith_operand" "dI")
2125 (match_operand:SI 2 "arith_operand" "dI")))]
2126 ""
2127 "shri %2,%1,%0"
2128 [(set_attr "type" "alu2")])
2129
2130 (define_insn "lshrsi3"
2131 [(set (match_operand:SI 0 "register_operand" "=d")
2132 (lshiftrt:SI (match_operand:SI 1 "arith_operand" "dI")
2133 (match_operand:SI 2 "arith_operand" "dI")))]
2134 ""
2135 "shro %2,%1,%0"
2136 [(set_attr "type" "alu2")])
2137 \f
2138 ;; Unconditional and other jump instructions.
2139
2140 (define_insn "jump"
2141 [(set (pc)
2142 (label_ref (match_operand 0 "" "")))]
2143 ""
2144 "b %l0"
2145 [(set_attr "type" "branch")])
2146
2147 (define_insn "indirect_jump"
2148 [(set (pc) (match_operand:SI 0 "address_operand" "p"))]
2149 ""
2150 "bx %a0"
2151 [(set_attr "type" "branch")])
2152
2153 (define_insn "tablejump"
2154 [(set (pc) (match_operand:SI 0 "register_operand" "d"))
2155 (use (label_ref (match_operand 1 "" "")))]
2156 ""
2157 "bx (%0)"
2158 [(set_attr "type" "branch")])
2159
2160 ;;- jump to subroutine
2161
2162 (define_expand "call"
2163 [(call (match_operand:SI 0 "general_operand" "g")
2164 (match_operand:SI 1 "immediate_operand" "i"))]
2165 ""
2166 "
2167 {
2168 emit_insn (gen_call_internal (operands[0], operands[1],
2169 virtual_outgoing_args_rtx));
2170 DONE;
2171 }")
2172
2173 ;; We need a call saved register allocated for the match_scratch, so we use
2174 ;; 'l' because all local registers are call saved.
2175
2176 ;; ??? I would prefer to use a match_scratch here, but match_scratch allocated
2177 ;; registers can't be used for spills. In a function with lots of calls,
2178 ;; local-alloc may allocate all local registers to a match_scratch, leaving
2179 ;; no local registers available for spills.
2180
2181 (define_insn "call_internal"
2182 [(call (match_operand:SI 0 "general_operand" "g")
2183 (match_operand:SI 1 "immediate_operand" "i"))
2184 (use (match_operand:SI 2 "address_operand" "p"))
2185 (clobber (reg:SI 19))]
2186 ""
2187 "* return i960_output_call_insn (operands[0], operands[1], operands[2],
2188 insn);"
2189 [(set_attr "type" "call")])
2190
2191 (define_expand "call_value"
2192 [(set (match_operand 0 "register_operand" "=d")
2193 (call (match_operand:SI 1 "general_operand" "g")
2194 (match_operand:SI 2 "immediate_operand" "i")))]
2195 ""
2196 "
2197 {
2198 emit_insn (gen_call_value_internal (operands[0], operands[1], operands[2],
2199 virtual_outgoing_args_rtx));
2200 DONE;
2201 }")
2202
2203 ;; We need a call saved register allocated for the match_scratch, so we use
2204 ;; 'l' because all local registers are call saved.
2205
2206 (define_insn "call_value_internal"
2207 [(set (match_operand 0 "register_operand" "=d")
2208 (call (match_operand:SI 1 "general_operand" "g")
2209 (match_operand:SI 2 "immediate_operand" "i")))
2210 (use (match_operand:SI 3 "address_operand" "p"))
2211 (clobber (reg:SI 19))]
2212 ""
2213 "* return i960_output_call_insn (operands[1], operands[2], operands[3],
2214 insn);"
2215 [(set_attr "type" "call")])
2216
2217 (define_insn "return"
2218 [(return)]
2219 ""
2220 "* return i960_output_ret_insn (insn);"
2221 [(set_attr "type" "branch")])
2222
2223 (define_insn "nop"
2224 [(const_int 0)]
2225 ""
2226 "")
2227 \f
2228 ;; Various peephole optimizations for multiple-word moves, loads, and stores.
2229 ;; Multiple register moves.
2230
2231 ;; Matched 5/28/91
2232 (define_peephole
2233 [(set (match_operand:SI 0 "register_operand" "=r")
2234 (match_operand:SI 1 "register_operand" "r"))
2235 (set (match_operand:SI 2 "register_operand" "=r")
2236 (match_operand:SI 3 "register_operand" "r"))
2237 (set (match_operand:SI 4 "register_operand" "=r")
2238 (match_operand:SI 5 "register_operand" "r"))
2239 (set (match_operand:SI 6 "register_operand" "=r")
2240 (match_operand:SI 7 "register_operand" "r"))]
2241 "((REGNO (operands[0]) & 3) == 0)
2242 && ((REGNO (operands[1]) & 3) == 0)
2243 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2244 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2245 && (REGNO (operands[0]) + 2 == REGNO (operands[4]))
2246 && (REGNO (operands[1]) + 2 == REGNO (operands[5]))
2247 && (REGNO (operands[0]) + 3 == REGNO (operands[6]))
2248 && (REGNO (operands[1]) + 3 == REGNO (operands[7]))"
2249 "movq %1,%0")
2250
2251 ;; Matched 4/17/92
2252 (define_peephole
2253 [(set (match_operand:DI 0 "register_operand" "=r")
2254 (match_operand:DI 1 "register_operand" "r"))
2255 (set (match_operand:DI 2 "register_operand" "=r")
2256 (match_operand:DI 3 "register_operand" "r"))]
2257 "((REGNO (operands[0]) & 3) == 0)
2258 && ((REGNO (operands[1]) & 3) == 0)
2259 && (REGNO (operands[0]) + 2 == REGNO (operands[2]))
2260 && (REGNO (operands[1]) + 2 == REGNO (operands[3]))"
2261 "movq %1,%0")
2262
2263 ;; Matched 4/17/92
2264 (define_peephole
2265 [(set (match_operand:DI 0 "register_operand" "=r")
2266 (match_operand:DI 1 "register_operand" "r"))
2267 (set (match_operand:SI 2 "register_operand" "=r")
2268 (match_operand:SI 3 "register_operand" "r"))
2269 (set (match_operand:SI 4 "register_operand" "=r")
2270 (match_operand:SI 5 "register_operand" "r"))]
2271 "((REGNO (operands[0]) & 3) == 0)
2272 && ((REGNO (operands[1]) & 3) == 0)
2273 && (REGNO (operands[0]) + 2 == REGNO (operands[2]))
2274 && (REGNO (operands[1]) + 2 == REGNO (operands[3]))
2275 && (REGNO (operands[0]) + 3 == REGNO (operands[4]))
2276 && (REGNO (operands[1]) + 3 == REGNO (operands[5]))"
2277 "movq %1,%0")
2278
2279 ;; Matched 4/17/92
2280 (define_peephole
2281 [(set (match_operand:SI 0 "register_operand" "=r")
2282 (match_operand:SI 1 "register_operand" "r"))
2283 (set (match_operand:SI 2 "register_operand" "=r")
2284 (match_operand:SI 3 "register_operand" "r"))
2285 (set (match_operand:DI 4 "register_operand" "=r")
2286 (match_operand:DI 5 "register_operand" "r"))]
2287 "((REGNO (operands[0]) & 3) == 0)
2288 && ((REGNO (operands[1]) & 3) == 0)
2289 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2290 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2291 && (REGNO (operands[0]) + 2 == REGNO (operands[4]))
2292 && (REGNO (operands[1]) + 2 == REGNO (operands[5]))"
2293 "movq %1,%0")
2294
2295 ;; Matched 4/17/92
2296 (define_peephole
2297 [(set (match_operand:DI 0 "register_operand" "=r")
2298 (match_operand:DI 1 "register_operand" "r"))
2299 (set (match_operand:SI 2 "register_operand" "=r")
2300 (match_operand:SI 3 "register_operand" "r"))]
2301 "((REGNO (operands[0]) & 3) == 0)
2302 && ((REGNO (operands[1]) & 3) == 0)
2303 && (REGNO (operands[0]) + 2 == REGNO (operands[2]))
2304 && (REGNO (operands[1]) + 2 == REGNO (operands[3]))"
2305 "movt %1,%0")
2306
2307 ;; Matched 5/28/91
2308 (define_peephole
2309 [(set (match_operand:SI 0 "register_operand" "=r")
2310 (match_operand:SI 1 "register_operand" "r"))
2311 (set (match_operand:SI 2 "register_operand" "=r")
2312 (match_operand:SI 3 "register_operand" "r"))
2313 (set (match_operand:SI 4 "register_operand" "=r")
2314 (match_operand:SI 5 "register_operand" "r"))]
2315 "((REGNO (operands[0]) & 3) == 0)
2316 && ((REGNO (operands[1]) & 3) == 0)
2317 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2318 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2319 && (REGNO (operands[0]) + 2 == REGNO (operands[4]))
2320 && (REGNO (operands[1]) + 2 == REGNO (operands[5]))"
2321 "movt %1,%0")
2322
2323 ;; Matched 5/28/91
2324 (define_peephole
2325 [(set (match_operand:SI 0 "register_operand" "=r")
2326 (match_operand:SI 1 "register_operand" "r"))
2327 (set (match_operand:SI 2 "register_operand" "=r")
2328 (match_operand:SI 3 "register_operand" "r"))]
2329 "((REGNO (operands[0]) & 1) == 0)
2330 && ((REGNO (operands[1]) & 1) == 0)
2331 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2332 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))"
2333 "movl %1,%0")
2334 \f
2335 ; Multiple register loads.
2336
2337 ;; Matched 6/15/91
2338 (define_peephole
2339 [(set (match_operand:SI 0 "register_operand" "=r")
2340 (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "r")
2341 (match_operand:SI 2 "immediate_operand" "n"))))
2342 (set (match_operand:SI 3 "register_operand" "=r")
2343 (mem:SI (plus:SI (match_dup 1)
2344 (match_operand:SI 4 "immediate_operand" "n"))))
2345 (set (match_operand:SI 5 "register_operand" "=r")
2346 (mem:SI (plus:SI (match_dup 1)
2347 (match_operand:SI 6 "immediate_operand" "n"))))
2348 (set (match_operand:SI 7 "register_operand" "=r")
2349 (mem:SI (plus:SI (match_dup 1)
2350 (match_operand:SI 8 "immediate_operand" "n"))))]
2351 "(i960_si_ti (operands[1], operands[2]) && ((REGNO (operands[0]) & 3) == 0)
2352 && (REGNO (operands[1]) != REGNO (operands[0]))
2353 && (REGNO (operands[0]) + 1 == REGNO (operands[3]))
2354 && (REGNO (operands[1]) != REGNO (operands[3]))
2355 && (REGNO (operands[0]) + 2 == REGNO (operands[5]))
2356 && (REGNO (operands[1]) != REGNO (operands[5]))
2357 && (REGNO (operands[0]) + 3 == REGNO (operands[7]))
2358 && (INTVAL (operands[2]) + 4 == INTVAL (operands[4]))
2359 && (INTVAL (operands[2]) + 8 == INTVAL (operands[6]))
2360 && (INTVAL (operands[2]) + 12 == INTVAL (operands[8])))"
2361 "ldq %2(%1),%0")
2362
2363 ;; Matched 5/28/91
2364 (define_peephole
2365 [(set (match_operand:DF 0 "register_operand" "=d")
2366 (mem:DF (plus:SI (match_operand:SI 1 "register_operand" "d")
2367 (match_operand:SI 2 "immediate_operand" "n"))))
2368 (set (match_operand:DF 3 "register_operand" "=d")
2369 (mem:DF (plus:SI (match_dup 1)
2370 (match_operand:SI 4 "immediate_operand" "n"))))]
2371 "(i960_si_ti (operands[1], operands[2]) && ((REGNO (operands[0]) & 3) == 0)
2372 && (REGNO (operands[1]) != REGNO (operands[0]))
2373 && (REGNO (operands[0]) + 2 == REGNO (operands[3]))
2374 && (REGNO (operands[1]) != REGNO (operands[3]))
2375 && (INTVAL (operands[2]) + 8 == INTVAL (operands[4])))"
2376 "ldq %2(%1),%0")
2377
2378 ;; Matched 1/24/92
2379 (define_peephole
2380 [(set (match_operand:DI 0 "register_operand" "=d")
2381 (mem:DI (plus:SI (match_operand:SI 1 "register_operand" "d")
2382 (match_operand:SI 2 "immediate_operand" "n"))))
2383 (set (match_operand:DI 3 "register_operand" "=d")
2384 (mem:DI (plus:SI (match_dup 1)
2385 (match_operand:SI 4 "immediate_operand" "n"))))]
2386 "(i960_si_ti (operands[1], operands[2]) && ((REGNO (operands[0]) & 3) == 0)
2387 && (REGNO (operands[1]) != REGNO (operands[0]))
2388 && (REGNO (operands[0]) + 2 == REGNO (operands[3]))
2389 && (REGNO (operands[1]) != REGNO (operands[3]))
2390 && (INTVAL (operands[2]) + 8 == INTVAL (operands[4])))"
2391 "ldq %2(%1),%0")
2392
2393 ;; Matched 4/17/92
2394 (define_peephole
2395 [(set (match_operand:SI 0 "register_operand" "=d")
2396 (mem:SI (match_operand:SI 1 "register_operand" "d")))
2397 (set (match_operand:SI 2 "register_operand" "=d")
2398 (mem:SI (plus:SI (match_dup 1)
2399 (match_operand:SI 3 "immediate_operand" "n"))))
2400 (set (match_operand:SI 4 "register_operand" "=d")
2401 (mem:SI (plus:SI (match_dup 1)
2402 (match_operand:SI 5 "immediate_operand" "n"))))
2403 (set (match_operand:SI 6 "register_operand" "=d")
2404 (mem:SI (plus:SI (match_dup 1)
2405 (match_operand:SI 7 "immediate_operand" "n"))))]
2406 "(i960_si_ti (operands[1], 0) && ((REGNO (operands[0]) & 3) == 0)
2407 && (REGNO (operands[1]) != REGNO (operands[0]))
2408 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2409 && (REGNO (operands[1]) != REGNO (operands[2]))
2410 && (REGNO (operands[0]) + 2 == REGNO (operands[4]))
2411 && (REGNO (operands[1]) != REGNO (operands[4]))
2412 && (REGNO (operands[0]) + 3 == REGNO (operands[6]))
2413 && (INTVAL (operands[3]) == 4)
2414 && (INTVAL (operands[5]) == 8)
2415 && (INTVAL (operands[7]) == 12))"
2416 "ldq (%1),%0")
2417
2418 ;; Matched 5/28/91
2419 (define_peephole
2420 [(set (match_operand:SI 0 "register_operand" "=d")
2421 (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "d")
2422 (match_operand:SI 2 "immediate_operand" "n"))))
2423 (set (match_operand:SI 3 "register_operand" "=d")
2424 (mem:SI (plus:SI (match_dup 1)
2425 (match_operand:SI 4 "immediate_operand" "n"))))
2426 (set (match_operand:SI 5 "register_operand" "=d")
2427 (mem:SI (plus:SI (match_dup 1)
2428 (match_operand:SI 6 "immediate_operand" "n"))))]
2429 "(i960_si_ti (operands[1], operands[2]) && ((REGNO (operands[0]) & 3) == 0)
2430 && (REGNO (operands[1]) != REGNO (operands[0]))
2431 && (REGNO (operands[0]) + 1 == REGNO (operands[3]))
2432 && (REGNO (operands[1]) != REGNO (operands[3]))
2433 && (REGNO (operands[0]) + 2 == REGNO (operands[5]))
2434 && (INTVAL (operands[2]) + 4 == INTVAL (operands[4]))
2435 && (INTVAL (operands[2]) + 8 == INTVAL (operands[6])))"
2436 "ldt %2(%1),%0")
2437
2438 ;; Matched 6/15/91
2439 (define_peephole
2440 [(set (match_operand:SI 0 "register_operand" "=d")
2441 (mem:SI (match_operand:SI 1 "register_operand" "d")))
2442 (set (match_operand:SI 2 "register_operand" "=d")
2443 (mem:SI (plus:SI (match_dup 1)
2444 (match_operand:SI 3 "immediate_operand" "n"))))
2445 (set (match_operand:SI 4 "register_operand" "=d")
2446 (mem:SI (plus:SI (match_dup 1)
2447 (match_operand:SI 5 "immediate_operand" "n"))))]
2448 "(i960_si_ti (operands[1], 0) && ((REGNO (operands[0]) & 3) == 0)
2449 && (REGNO (operands[1]) != REGNO (operands[0]))
2450 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2451 && (REGNO (operands[1]) != REGNO (operands[2]))
2452 && (REGNO (operands[0]) + 2 == REGNO (operands[4]))
2453 && (INTVAL (operands[3]) == 4)
2454 && (INTVAL (operands[5]) == 8))"
2455 "ldt (%1),%0")
2456
2457 ;; Matched 5/28/91
2458 (define_peephole
2459 [(set (match_operand:SI 0 "register_operand" "=d")
2460 (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "d")
2461 (match_operand:SI 2 "immediate_operand" "n"))))
2462 (set (match_operand:SI 3 "register_operand" "=d")
2463 (mem:SI (plus:SI (match_dup 1)
2464 (match_operand:SI 4 "immediate_operand" "n"))))]
2465 "(i960_si_di (operands[1], operands[2]) && ((REGNO (operands[0]) & 1) == 0)
2466 && (REGNO (operands[1]) != REGNO (operands[0]))
2467 && (REGNO (operands[0]) + 1 == REGNO (operands[3]))
2468 && (INTVAL (operands[2]) + 4 == INTVAL (operands[4])))"
2469 "ldl %2(%1),%0")
2470
2471 ;; Matched 5/28/91
2472 (define_peephole
2473 [(set (match_operand:SI 0 "register_operand" "=d")
2474 (mem:SI (match_operand:SI 1 "register_operand" "d")))
2475 (set (match_operand:SI 2 "register_operand" "=d")
2476 (mem:SI (plus:SI (match_dup 1)
2477 (match_operand:SI 3 "immediate_operand" "n"))))]
2478 "(i960_si_di (operands[1], 0) && ((REGNO (operands[0]) & 1) == 0)
2479 && (REGNO (operands[1]) != REGNO (operands[0]))
2480 && (REGNO (operands[0]) + 1 == REGNO (operands[2]))
2481 && (INTVAL (operands[3]) == 4))"
2482 "ldl (%1),%0")
2483 \f
2484 ; Multiple register stores.
2485
2486 ;; Matched 5/28/91
2487 (define_peephole
2488 [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "d")
2489 (match_operand:SI 1 "immediate_operand" "n")))
2490 (match_operand:SI 2 "register_operand" "d"))
2491 (set (mem:SI (plus:SI (match_dup 0)
2492 (match_operand:SI 3 "immediate_operand" "n")))
2493 (match_operand:SI 4 "register_operand" "d"))
2494 (set (mem:SI (plus:SI (match_dup 0)
2495 (match_operand:SI 5 "immediate_operand" "n")))
2496 (match_operand:SI 6 "register_operand" "d"))
2497 (set (mem:SI (plus:SI (match_dup 0)
2498 (match_operand:SI 7 "immediate_operand" "n")))
2499 (match_operand:SI 8 "register_operand" "d"))]
2500 "(i960_si_ti (operands[0], operands[1]) && ((REGNO (operands[2]) & 3) == 0)
2501 && (REGNO (operands[2]) + 1 == REGNO (operands[4]))
2502 && (REGNO (operands[2]) + 2 == REGNO (operands[6]))
2503 && (REGNO (operands[2]) + 3 == REGNO (operands[8]))
2504 && (INTVAL (operands[1]) + 4 == INTVAL (operands[3]))
2505 && (INTVAL (operands[1]) + 8 == INTVAL (operands[5]))
2506 && (INTVAL (operands[1]) + 12 == INTVAL (operands[7])))"
2507 "stq %2,%1(%0)")
2508
2509 ;; Matched 6/16/91
2510 (define_peephole
2511 [(set (mem:DF (plus:SI (match_operand:SI 0 "register_operand" "d")
2512 (match_operand:SI 1 "immediate_operand" "n")))
2513 (match_operand:DF 2 "register_operand" "d"))
2514 (set (mem:DF (plus:SI (match_dup 0)
2515 (match_operand:SI 3 "immediate_operand" "n")))
2516 (match_operand:DF 4 "register_operand" "d"))]
2517 "(i960_si_ti (operands[0], operands[1]) && ((REGNO (operands[2]) & 3) == 0)
2518 && (REGNO (operands[2]) + 2 == REGNO (operands[4]))
2519 && (INTVAL (operands[1]) + 8 == INTVAL (operands[3])))"
2520 "stq %2,%1(%0)")
2521
2522 ;; Matched 4/17/92
2523 (define_peephole
2524 [(set (mem:DI (plus:SI (match_operand:SI 0 "register_operand" "d")
2525 (match_operand:SI 1 "immediate_operand" "n")))
2526 (match_operand:DI 2 "register_operand" "d"))
2527 (set (mem:DI (plus:SI (match_dup 0)
2528 (match_operand:SI 3 "immediate_operand" "n")))
2529 (match_operand:DI 4 "register_operand" "d"))]
2530 "(i960_si_ti (operands[0], operands[1]) && ((REGNO (operands[2]) & 3) == 0)
2531 && (REGNO (operands[2]) + 2 == REGNO (operands[4]))
2532 && (INTVAL (operands[1]) + 8 == INTVAL (operands[3])))"
2533 "stq %2,%1(%0)")
2534
2535 ;; Matched 1/23/92
2536 (define_peephole
2537 [(set (mem:SI (match_operand:SI 0 "register_operand" "d"))
2538 (match_operand:SI 1 "register_operand" "d"))
2539 (set (mem:SI (plus:SI (match_dup 0)
2540 (match_operand:SI 2 "immediate_operand" "n")))
2541 (match_operand:SI 3 "register_operand" "d"))
2542 (set (mem:SI (plus:SI (match_dup 0)
2543 (match_operand:SI 4 "immediate_operand" "n")))
2544 (match_operand:SI 5 "register_operand" "d"))
2545 (set (mem:SI (plus:SI (match_dup 0)
2546 (match_operand:SI 6 "immediate_operand" "n")))
2547 (match_operand:SI 7 "register_operand" "d"))]
2548 "(i960_si_ti (operands[0], 0) && ((REGNO (operands[1]) & 3) == 0)
2549 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2550 && (REGNO (operands[1]) + 2 == REGNO (operands[5]))
2551 && (REGNO (operands[1]) + 3 == REGNO (operands[7]))
2552 && (INTVAL (operands[2]) == 4)
2553 && (INTVAL (operands[4]) == 8)
2554 && (INTVAL (operands[6]) == 12))"
2555 "stq %1,(%0)")
2556
2557 ;; Matched 5/29/91
2558 (define_peephole
2559 [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "d")
2560 (match_operand:SI 1 "immediate_operand" "n")))
2561 (match_operand:SI 2 "register_operand" "d"))
2562 (set (mem:SI (plus:SI (match_dup 0)
2563 (match_operand:SI 3 "immediate_operand" "n")))
2564 (match_operand:SI 4 "register_operand" "d"))
2565 (set (mem:SI (plus:SI (match_dup 0)
2566 (match_operand:SI 5 "immediate_operand" "n")))
2567 (match_operand:SI 6 "register_operand" "d"))]
2568 "(i960_si_ti (operands[0], operands[1]) && ((REGNO (operands[2]) & 3) == 0)
2569 && (REGNO (operands[2]) + 1 == REGNO (operands[4]))
2570 && (REGNO (operands[2]) + 2 == REGNO (operands[6]))
2571 && (INTVAL (operands[1]) + 4 == INTVAL (operands[3]))
2572 && (INTVAL (operands[1]) + 8 == INTVAL (operands[5])))"
2573 "stt %2,%1(%0)")
2574
2575 ;; Matched 5/29/91
2576 (define_peephole
2577 [(set (mem:SI (match_operand:SI 0 "register_operand" "d"))
2578 (match_operand:SI 1 "register_operand" "d"))
2579 (set (mem:SI (plus:SI (match_dup 0)
2580 (match_operand:SI 2 "immediate_operand" "n")))
2581 (match_operand:SI 3 "register_operand" "d"))
2582 (set (mem:SI (plus:SI (match_dup 0)
2583 (match_operand:SI 4 "immediate_operand" "n")))
2584 (match_operand:SI 5 "register_operand" "d"))]
2585 "(i960_si_ti (operands[0], 0) && ((REGNO (operands[1]) & 3) == 0)
2586 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2587 && (REGNO (operands[1]) + 2 == REGNO (operands[5]))
2588 && (INTVAL (operands[2]) == 4)
2589 && (INTVAL (operands[4]) == 8))"
2590 "stt %1,(%0)")
2591
2592 ;; Matched 5/28/91
2593 (define_peephole
2594 [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "d")
2595 (match_operand:SI 1 "immediate_operand" "n")))
2596 (match_operand:SI 2 "register_operand" "d"))
2597 (set (mem:SI (plus:SI (match_dup 0)
2598 (match_operand:SI 3 "immediate_operand" "n")))
2599 (match_operand:SI 4 "register_operand" "d"))]
2600 "(i960_si_di (operands[0], operands[1]) && ((REGNO (operands[2]) & 1) == 0)
2601 && (REGNO (operands[2]) + 1 == REGNO (operands[4]))
2602 && (INTVAL (operands[1]) + 4 == INTVAL (operands[3])))"
2603 "stl %2,%1(%0)")
2604
2605 ;; Matched 5/28/91
2606 (define_peephole
2607 [(set (mem:SI (match_operand:SI 0 "register_operand" "d"))
2608 (match_operand:SI 1 "register_operand" "d"))
2609 (set (mem:SI (plus:SI (match_dup 0)
2610 (match_operand:SI 2 "immediate_operand" "n")))
2611 (match_operand:SI 3 "register_operand" "d"))]
2612 "(i960_si_di (operands[0], 0) && ((REGNO (operands[1]) & 1) == 0)
2613 && (REGNO (operands[1]) + 1 == REGNO (operands[3]))
2614 && (INTVAL (operands[2]) == 4))"
2615 "stl %1,(%0)")