1 ;;- Machine description for Blackfin for GNU compiler
2 ;; Copyright 2005 Free Software Foundation, Inc.
3 ;; Contributed by Analog Devices.
5 ;; This file is part of GCC.
7 ;; GCC is free software; you can redistribute it and/or modify it
8 ;; under the terms of the GNU General Public License as published
9 ;; by the Free Software Foundation; either version 2, or (at your
10 ;; option) any later version.
12 ;; GCC is distributed in the hope that it will be useful, but WITHOUT
13 ;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 ;; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
15 ;; License for more details.
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, 51 Franklin Street, Fifth Floor,
20 ;; Boston, MA 02110-1301, USA.
22 ; operand punctuation marks:
24 ; X -- integer value printed as log2
25 ; Y -- integer value printed as log2(~value) - for bitclear
26 ; h -- print half word register, low part
27 ; d -- print half word register, high part
28 ; D -- print operand as dregs pairs
29 ; w -- print operand as accumulator register word (a0w, a1w)
30 ; H -- high part of double mode operand
31 ; T -- byte register representation Oct. 02 2001
33 ; constant operand classes
35 ; J 2**N 5bit imm scaled
36 ; Ks7 -64 .. 63 signed 7bit imm
37 ; Ku5 0..31 unsigned 5bit imm
38 ; Ks4 -8 .. 7 signed 4bit imm
39 ; Ks3 -4 .. 3 signed 3bit imm
40 ; Ku3 0 .. 7 unsigned 3bit imm
41 ; Pn 0, 1, 2 constants 0, 1 or 2, corresponding to n
50 ; c (i0..i3,m0..m3) CIRCREGS
54 ;; Define constants for hard registers.
112 ;; Constants used in UNSPECs and UNSPEC_VOLATILEs.
115 [(UNSPEC_CBRANCH_TAKEN 0)
116 (UNSPEC_CBRANCH_NOPS 1)
119 (UNSPEC_LIBRARY_OFFSET 4)
120 (UNSPEC_PUSH_MULTIPLE 5)])
123 [(UNSPEC_VOLATILE_EH_RETURN 0)
124 (UNSPEC_VOLATILE_CSYNC 1)
125 (UNSPEC_VOLATILE_SSYNC 2)])
128 "move,mvi,mcld,mcst,dsp32,mult,alu0,shft,brcc,br,call,misc,sync,compare,dummy"
129 (const_string "misc"))
131 ;; Scheduling definitions
133 (define_automaton "bfin")
135 (define_cpu_unit "core" "bfin")
137 (define_insn_reservation "alu" 1
138 (eq_attr "type" "move,mvi,mcst,dsp32,alu0,shft,brcc,br,call,misc,sync,compare")
141 (define_insn_reservation "imul" 3
142 (eq_attr "type" "mult")
145 (define_insn_reservation "load" 1
146 (eq_attr "type" "mcld")
149 ;; Make sure genautomata knows about the maximum latency that can be produced
150 ;; by the adjust_cost function.
151 (define_insn_reservation "dummy" 5
152 (eq_attr "type" "mcld")
155 ;; Operand and operator predicates
157 (include "predicates.md")
160 ;;; FRIO branches have been optimized for code density
161 ;;; this comes at a slight cost of complexity when
162 ;;; a compiler needs to generate branches in the general
163 ;;; case. In order to generate the correct branching
164 ;;; mechanisms the compiler needs keep track of instruction
165 ;;; lengths. The follow table describes how to count instructions
166 ;;; for the FRIO architecture.
168 ;;; unconditional br are 12-bit imm pcrelative branches *2
169 ;;; conditional br are 10-bit imm pcrelative branches *2
171 ;;; 1024 10-bit imm *2 is 2048 (-1024..1022)
173 ;;; 4096 12-bit imm *2 is 8192 (-4096..4094)
174 ;;; NOTE : For brcc we generate instructions such as
175 ;;; if cc jmp; jump.[sl] offset
176 ;;; offset of jump.[sl] is from the jump instruction but
177 ;;; gcc calculates length from the if cc jmp instruction
178 ;;; furthermore gcc takes the end address of the branch instruction
179 ;;; as (pc) for a forward branch
180 ;;; hence our range is (-4094, 4092) instead of (-4096, 4094) for a br
182 ;;; The way the (pc) rtx works in these calculations is somewhat odd;
183 ;;; for backward branches it's the address of the current instruction,
184 ;;; for forward branches it's the previously known address of the following
185 ;;; instruction - we have to take this into account by reducing the range
186 ;;; for a forward branch.
188 ;; Lengths for type "mvi" insns are always defined by the instructions
190 (define_attr "length" ""
191 (cond [(eq_attr "type" "mcld")
192 (if_then_else (match_operand 1 "effective_address_32bit_p" "")
193 (const_int 4) (const_int 2))
195 (eq_attr "type" "mcst")
196 (if_then_else (match_operand 0 "effective_address_32bit_p" "")
197 (const_int 4) (const_int 2))
199 (eq_attr "type" "move") (const_int 2)
201 (eq_attr "type" "dsp32") (const_int 4)
202 (eq_attr "type" "call") (const_int 4)
204 (eq_attr "type" "br")
206 (le (minus (match_dup 0) (pc)) (const_int 4092))
207 (ge (minus (match_dup 0) (pc)) (const_int -4096)))
211 (eq_attr "type" "brcc")
213 (le (minus (match_dup 3) (pc)) (const_int 1020))
214 (ge (minus (match_dup 3) (pc)) (const_int -1024)))
217 (le (minus (match_dup 3) (pc)) (const_int 4092))
218 (ge (minus (match_dup 3) (pc)) (const_int -4094)))
227 (define_expand "movsicc"
228 [(set (match_operand:SI 0 "register_operand" "")
229 (if_then_else:SI (match_operand 1 "comparison_operator" "")
230 (match_operand:SI 2 "register_operand" "")
231 (match_operand:SI 3 "register_operand" "")))]
234 operands[1] = bfin_gen_compare (operands[1], SImode);
237 (define_insn "*movsicc_insn1"
238 [(set (match_operand:SI 0 "register_operand" "=da,da,da")
240 (eq:BI (match_operand:BI 3 "cc_operand" "C,C,C")
242 (match_operand:SI 1 "register_operand" "da,0,da")
243 (match_operand:SI 2 "register_operand" "0,da,da")))]
246 if !cc %0 =%1; /* movsicc-1a */
247 if cc %0 =%2; /* movsicc-1b */
248 if !cc %0 =%1; if cc %0=%2; /* movsicc-1 */"
249 [(set_attr "length" "2,2,4")
250 (set_attr "type" "move")])
252 (define_insn "*movsicc_insn2"
253 [(set (match_operand:SI 0 "register_operand" "=da,da,da")
255 (ne:BI (match_operand:BI 3 "cc_operand" "C,C,C")
257 (match_operand:SI 1 "register_operand" "0,da,da")
258 (match_operand:SI 2 "register_operand" "da,0,da")))]
261 if !cc %0 =%2; /* movsicc-2b */
262 if cc %0 =%1; /* movsicc-2a */
263 if cc %0 =%1; if !cc %0=%2; /* movsicc-1 */"
264 [(set_attr "length" "2,2,4")
265 (set_attr "type" "move")])
267 ;; Insns to load HIGH and LO_SUM
269 (define_insn "movsi_high"
270 [(set (match_operand:SI 0 "register_operand" "=x")
271 (high:SI (match_operand:SI 1 "immediate_operand" "i")))]
274 [(set_attr "type" "mvi")
275 (set_attr "length" "4")])
277 (define_insn "movstricthi_high"
278 [(set (match_operand:SI 0 "register_operand" "+x")
279 (ior:SI (and:SI (match_dup 0) (const_int 65535))
280 (match_operand:SI 1 "immediate_operand" "i")))]
283 [(set_attr "type" "mvi")
284 (set_attr "length" "4")])
286 (define_insn "movsi_low"
287 [(set (match_operand:SI 0 "register_operand" "=x")
288 (lo_sum:SI (match_operand:SI 1 "register_operand" "0")
289 (match_operand:SI 2 "immediate_operand" "i")))]
292 [(set_attr "type" "mvi")
293 (set_attr "length" "4")])
295 (define_insn "movsi_high_pic"
296 [(set (match_operand:SI 0 "register_operand" "=x")
297 (high:SI (unspec:SI [(match_operand:SI 1 "" "")]
301 [(set_attr "type" "mvi")
302 (set_attr "length" "4")])
304 (define_insn "movsi_low_pic"
305 [(set (match_operand:SI 0 "register_operand" "=x")
306 (lo_sum:SI (match_operand:SI 1 "register_operand" "0")
307 (unspec:SI [(match_operand:SI 2 "" "")]
310 "%h0 = %h2@GOT_HIGH;"
311 [(set_attr "type" "mvi")
312 (set_attr "length" "4")])
314 ;;; Move instructions
316 (define_insn_and_split "movdi_insn"
317 [(set (match_operand:DI 0 "nonimmediate_operand" "=x,mx,r")
318 (match_operand:DI 1 "general_operand" "iFx,r,mx"))]
319 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
322 [(set (match_dup 2) (match_dup 3))
323 (set (match_dup 4) (match_dup 5))]
325 rtx lo_half[2], hi_half[2];
326 split_di (operands, 2, lo_half, hi_half);
328 if (reg_overlap_mentioned_p (lo_half[0], hi_half[1]))
330 operands[2] = hi_half[0];
331 operands[3] = hi_half[1];
332 operands[4] = lo_half[0];
333 operands[5] = lo_half[1];
337 operands[2] = lo_half[0];
338 operands[3] = lo_half[1];
339 operands[4] = hi_half[0];
340 operands[5] = hi_half[1];
345 [(set (match_operand:BI 0 "nonimmediate_operand" "=x,x,d,mr,C,d,C")
346 (match_operand:BI 1 "general_operand" "x,xKs3,mr,d,d,C,P0"))]
356 R0 = R0 | R0; CC = AC0;"
357 [(set_attr "type" "move,mvi,mcld,mcst,compare,compare,alu0")
358 (set_attr "length" "2,2,*,*,2,2,4")])
360 (define_insn "movpdi"
361 [(set (match_operand:PDI 0 "nonimmediate_operand" "=e,<,e")
362 (match_operand:PDI 1 "general_operand" " e,e,>"))]
368 [(set_attr "type" "move,mcst,mcld")])
370 (define_insn "*pushsi_insn"
371 [(set (mem:SI (pre_dec:SI (reg:SI REG_SP)))
372 (match_operand:SI 0 "register_operand" "xy"))]
375 [(set_attr "type" "mcst")
376 (set_attr "length" "2")])
378 (define_insn "*popsi_insn"
379 [(set (match_operand:SI 0 "register_operand" "=xy")
380 (mem:SI (post_inc:SI (reg:SI REG_SP))))]
383 [(set_attr "type" "mcld")
384 (set_attr "length" "2")])
386 ;; The first alternative is used to make reload choose a limited register
387 ;; class when faced with a movsi_insn that had its input operand replaced
388 ;; with a PLUS. We generally require fewer secondary reloads this way.
389 (define_insn "*movsi_insn"
390 [(set (match_operand:SI 0 "nonimmediate_operand" "=da,x*y,da,x,x,x,da,mr")
391 (match_operand:SI 1 "general_operand" "da,x*y,xKs7,xKsh,xKuh,ix,mr,da"))]
393 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
403 [(set_attr "type" "move,move,mvi,mvi,mvi,*,mcld,mcst")
404 (set_attr "length" "2,2,2,4,4,*,*,*")])
406 (define_insn "*movv2hi_insn"
407 [(set (match_operand:V2HI 0 "nonimmediate_operand" "=da,d,m")
408 (match_operand:V2HI 1 "general_operand" "d,m,d"))]
410 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
412 [(set_attr "type" "move,mcld,mcst")
413 (set_attr "length" "2,*,*")])
415 (define_insn "*movhi_insn"
416 [(set (match_operand:HI 0 "nonimmediate_operand" "=x,da,x,d,mr")
417 (match_operand:HI 1 "general_operand" "x,xKs7,xKsh,mr,d"))]
418 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
425 [(set_attr "type" "move,mvi,mvi,mcld,mcst")
426 (set_attr "length" "2,2,4,*,*")])
428 (define_insn "*movqi_insn"
429 [(set (match_operand:QI 0 "nonimmediate_operand" "=x,da,x,d,mr")
430 (match_operand:QI 1 "general_operand" "x,xKs7,xKsh,mr,d"))]
431 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
438 [(set_attr "type" "move,mvi,mvi,mcld,mcst")
439 (set_attr "length" "2,2,4,*,*")])
441 (define_insn "*movsf_insn"
442 [(set (match_operand:SF 0 "nonimmediate_operand" "=x,x,da,mr")
443 (match_operand:SF 1 "general_operand" "x,Fx,mr,da"))]
444 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
450 [(set_attr "type" "move,*,mcld,mcst")])
452 (define_insn_and_split "movdf_insn"
453 [(set (match_operand:DF 0 "nonimmediate_operand" "=x,mx,r")
454 (match_operand:DF 1 "general_operand" "iFx,r,mx"))]
455 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
458 [(set (match_dup 2) (match_dup 3))
459 (set (match_dup 4) (match_dup 5))]
461 rtx lo_half[2], hi_half[2];
462 split_di (operands, 2, lo_half, hi_half);
464 if (reg_overlap_mentioned_p (lo_half[0], hi_half[1]))
466 operands[2] = hi_half[0];
467 operands[3] = hi_half[1];
468 operands[4] = lo_half[0];
469 operands[5] = lo_half[1];
473 operands[2] = lo_half[0];
474 operands[3] = lo_half[1];
475 operands[4] = hi_half[0];
476 operands[5] = hi_half[1];
480 ;; This is the main "hook" for PIC code. When generating
481 ;; PIC, movsi is responsible for determining when the source address
482 ;; needs PIC relocation and appropriately calling legitimize_pic_address
483 ;; to perform the actual relocation.
485 (define_expand "movsi"
486 [(set (match_operand:SI 0 "nonimmediate_operand" "")
487 (match_operand:SI 1 "general_operand" ""))]
489 "expand_move (operands, SImode);")
491 (define_expand "movv2hi"
492 [(set (match_operand:V2HI 0 "nonimmediate_operand" "")
493 (match_operand:V2HI 1 "general_operand" ""))]
495 "expand_move (operands, V2HImode);")
497 (define_expand "movdi"
498 [(set (match_operand:DI 0 "nonimmediate_operand" "")
499 (match_operand:DI 1 "general_operand" ""))]
501 "expand_move (operands, DImode);")
503 (define_expand "movsf"
504 [(set (match_operand:SF 0 "nonimmediate_operand" "")
505 (match_operand:SF 1 "general_operand" ""))]
507 "expand_move (operands, SFmode);")
509 (define_expand "movdf"
510 [(set (match_operand:DF 0 "nonimmediate_operand" "")
511 (match_operand:DF 1 "general_operand" ""))]
513 "expand_move (operands, DFmode);")
515 (define_expand "movhi"
516 [(set (match_operand:HI 0 "nonimmediate_operand" "")
517 (match_operand:HI 1 "general_operand" ""))]
519 "expand_move (operands, HImode);")
521 (define_expand "movqi"
522 [(set (match_operand:QI 0 "nonimmediate_operand" "")
523 (match_operand:QI 1 "general_operand" ""))]
525 " expand_move (operands, QImode); ")
527 ;; Some define_splits to break up SI/SFmode loads of immediate constants.
530 [(set (match_operand:SI 0 "register_operand" "")
531 (match_operand:SI 1 "symbolic_or_const_operand" ""))]
533 /* Always split symbolic operands; split integer constants that are
534 too large for a single instruction. */
535 && (GET_CODE (operands[1]) != CONST_INT
536 || (INTVAL (operands[1]) < -32768
537 || INTVAL (operands[1]) >= 65536
538 || (INTVAL (operands[1]) >= 32768 && PREG_P (operands[0]))))"
539 [(set (match_dup 0) (high:SI (match_dup 1)))
540 (set (match_dup 0) (lo_sum:SI (match_dup 0) (match_dup 1)))]
542 if (GET_CODE (operands[1]) == CONST_INT
543 && split_load_immediate (operands))
545 /* ??? Do something about TARGET_LOW_64K. */
549 [(set (match_operand:SF 0 "register_operand" "")
550 (match_operand:SF 1 "immediate_operand" ""))]
552 [(set (match_dup 2) (high:SI (match_dup 3)))
553 (set (match_dup 2) (lo_sum:SI (match_dup 2) (match_dup 3)))]
556 REAL_VALUE_TYPE value;
558 gcc_assert (GET_CODE (operands[1]) == CONST_DOUBLE);
560 REAL_VALUE_FROM_CONST_DOUBLE (value, operands[1]);
561 REAL_VALUE_TO_TARGET_SINGLE (value, values);
563 operands[2] = gen_rtx_REG (SImode, true_regnum (operands[0]));
564 operands[3] = GEN_INT (trunc_int_for_mode (values, SImode));
565 if (values >= -32768 && values < 65536)
567 emit_move_insn (operands[2], operands[3]);
570 if (split_load_immediate (operands + 2))
574 ;; Sadly, this can't be a proper named movstrict pattern, since the compiler
575 ;; expects to be able to use registers for operand 1.
576 ;; Note that the asm instruction is defined by the manual to take an unsigned
577 ;; constant, but it doesn't matter to the assembler, and the compiler only
578 ;; deals with sign-extended constants. Hence "Ksh".
579 (define_insn "*movstricthi"
580 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+x"))
581 (match_operand:HI 1 "immediate_operand" "Ksh"))]
584 [(set_attr "type" "mvi")
585 (set_attr "length" "4")])
587 ;; Sign and zero extensions
589 (define_insn "extendhisi2"
590 [(set (match_operand:SI 0 "register_operand" "=d, d")
591 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "d, m")))]
596 [(set_attr "type" "alu0,mcld")])
598 (define_insn "zero_extendhisi2"
599 [(set (match_operand:SI 0 "register_operand" "=d, d")
600 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "d, m")))]
605 [(set_attr "type" "alu0,mcld")])
607 (define_insn "zero_extendbisi2"
608 [(set (match_operand:SI 0 "register_operand" "=d")
609 (zero_extend:SI (match_operand:BI 1 "nonimmediate_operand" "C")))]
612 [(set_attr "type" "compare")])
614 (define_insn "extendqihi2"
615 [(set (match_operand:HI 0 "register_operand" "=d, d")
616 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "m, d")))]
621 [(set_attr "type" "mcld,alu0")])
623 (define_insn "extendqisi2"
624 [(set (match_operand:SI 0 "register_operand" "=d, d")
625 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "m, d")))]
630 [(set_attr "type" "mcld,alu0")])
633 (define_insn "zero_extendqihi2"
634 [(set (match_operand:HI 0 "register_operand" "=d, d")
635 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "m, d")))]
640 [(set_attr "type" "mcld,alu0")])
643 (define_insn "zero_extendqisi2"
644 [(set (match_operand:SI 0 "register_operand" "=d, d")
645 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "m, d")))]
650 [(set_attr "type" "mcld,alu0")])
652 ;; DImode logical operations
654 (define_code_macro any_logical [and ior xor])
655 (define_code_attr optab [(and "and")
658 (define_code_attr op [(and "&")
661 (define_code_attr high_result [(and "0")
665 (define_insn "<optab>di3"
666 [(set (match_operand:DI 0 "register_operand" "=d")
667 (any_logical:DI (match_operand:DI 1 "register_operand" "0")
668 (match_operand:DI 2 "register_operand" "d")))]
670 "%0 = %1 <op> %2;\\n\\t%H0 = %H1 <op> %H2;"
671 [(set_attr "length" "4")])
673 (define_insn "*<optab>di_zesidi_di"
674 [(set (match_operand:DI 0 "register_operand" "=d")
675 (any_logical:DI (zero_extend:DI
676 (match_operand:SI 2 "register_operand" "d"))
677 (match_operand:DI 1 "register_operand" "d")))]
679 "%0 = %1 <op> %2;\\n\\t%H0 = <high_result>;"
680 [(set_attr "length" "4")])
682 (define_insn "*<optab>di_sesdi_di"
683 [(set (match_operand:DI 0 "register_operand" "=d")
684 (any_logical:DI (sign_extend:DI
685 (match_operand:SI 2 "register_operand" "d"))
686 (match_operand:DI 1 "register_operand" "0")))
687 (clobber (match_scratch:SI 3 "=&d"))]
689 "%0 = %1 <op> %2;\\n\\t%3 = %2;\\n\\t%3 >>>= 31;\\n\\t%H0 = %H1 <op> %3;"
690 [(set_attr "length" "8")])
692 (define_insn "negdi2"
693 [(set (match_operand:DI 0 "register_operand" "=d")
694 (neg:DI (match_operand:DI 1 "register_operand" "d")))
695 (clobber (match_scratch:SI 2 "=&d"))
696 (clobber (reg:CC REG_CC))]
698 "%2 = 0; %2 = %2 - %1; cc = ac0; cc = !cc; %2 = cc;\\n\\t%0 = -%1; %H0 = -%H1; %H0 = %H0 - %2;"
699 [(set_attr "length" "16")])
701 (define_insn "one_cmpldi2"
702 [(set (match_operand:DI 0 "register_operand" "=d")
703 (not:DI (match_operand:DI 1 "register_operand" "d")))]
705 "%0 = ~%1;\\n\\t%H0 = ~%H1;"
706 [(set_attr "length" "4")])
708 ;; DImode zero and sign extend patterns
710 (define_insn_and_split "zero_extendsidi2"
711 [(set (match_operand:DI 0 "register_operand" "=d")
712 (zero_extend:DI (match_operand:SI 1 "register_operand" "d")))]
716 [(set (match_dup 3) (const_int 0))]
718 split_di (operands, 1, operands + 2, operands + 3);
719 if (REGNO (operands[0]) != REGNO (operands[1]))
720 emit_move_insn (operands[2], operands[1]);
723 (define_insn "zero_extendqidi2"
724 [(set (match_operand:DI 0 "register_operand" "=d")
725 (zero_extend:DI (match_operand:QI 1 "register_operand" "d")))]
727 "%0 = %T1 (Z);\\n\\t%H0 = 0;"
728 [(set_attr "length" "4")])
730 (define_insn "zero_extendhidi2"
731 [(set (match_operand:DI 0 "register_operand" "=d")
732 (zero_extend:DI (match_operand:HI 1 "register_operand" "d")))]
734 "%0 = %h1 (Z);\\n\\t%H0 = 0;"
735 [(set_attr "length" "4")])
737 (define_insn_and_split "extendsidi2"
738 [(set (match_operand:DI 0 "register_operand" "=d")
739 (sign_extend:DI (match_operand:SI 1 "register_operand" "d")))]
743 [(set (match_dup 3) (match_dup 1))
744 (set (match_dup 3) (ashiftrt:SI (match_dup 3) (const_int 31)))]
746 split_di (operands, 1, operands + 2, operands + 3);
747 if (REGNO (operands[0]) != REGNO (operands[1]))
748 emit_move_insn (operands[2], operands[1]);
751 (define_insn_and_split "extendqidi2"
752 [(set (match_operand:DI 0 "register_operand" "=d")
753 (sign_extend:DI (match_operand:QI 1 "register_operand" "d")))]
757 [(set (match_dup 2) (sign_extend:SI (match_dup 1)))
758 (set (match_dup 3) (sign_extend:SI (match_dup 1)))
759 (set (match_dup 3) (ashiftrt:SI (match_dup 3) (const_int 31)))]
761 split_di (operands, 1, operands + 2, operands + 3);
764 (define_insn_and_split "extendhidi2"
765 [(set (match_operand:DI 0 "register_operand" "=d")
766 (sign_extend:DI (match_operand:HI 1 "register_operand" "d")))]
770 [(set (match_dup 2) (sign_extend:SI (match_dup 1)))
771 (set (match_dup 3) (sign_extend:SI (match_dup 1)))
772 (set (match_dup 3) (ashiftrt:SI (match_dup 3) (const_int 31)))]
774 split_di (operands, 1, operands + 2, operands + 3);
777 ;; DImode arithmetic operations
779 (define_insn "adddi3"
780 [(set (match_operand:DI 0 "register_operand" "=&d,&d,&d")
781 (plus:DI (match_operand:DI 1 "register_operand" "%0,0,0")
782 (match_operand:DI 2 "nonmemory_operand" "Kn7,Ks7,d")))
783 (clobber (match_scratch:SI 3 "=&d,&d,&d"))
784 (clobber (reg:CC 34))]
787 %0 += %2; cc = ac0; %3 = cc; %H0 += -1; %H0 = %H0 + %3;
788 %0 += %2; cc = ac0; %3 = cc; %H0 = %H0 + %3;
789 %0 = %0 + %2; cc = ac0; %3 = cc; %H0 = %H0 + %H2; %H0 = %H0 + %3;"
790 [(set_attr "type" "alu0")
791 (set_attr "length" "10,8,10")])
793 (define_insn "subdi3"
794 [(set (match_operand:DI 0 "register_operand" "=&d")
795 (minus:DI (match_operand:DI 1 "register_operand" "0")
796 (match_operand:DI 2 "register_operand" "d")))
797 (clobber (reg:CC 34))]
799 "%0 = %1-%2;\\n\\tcc = ac0;\\n\\t%H0 = %H1-%H2;\\n\\tif cc jump 1f;\\n\\t%H0 += -1;\\n\\t1:"
800 [(set_attr "length" "10")])
802 (define_insn "*subdi_di_zesidi"
803 [(set (match_operand:DI 0 "register_operand" "=d")
804 (minus:DI (match_operand:DI 1 "register_operand" "0")
806 (match_operand:SI 2 "register_operand" "d"))))
807 (clobber (match_scratch:SI 3 "=&d"))
808 (clobber (reg:CC 34))]
810 "%0 = %1 - %2;\\n\\tcc = ac0;\\n\\tcc = ! cc;\\n\\t%3 = cc;\\n\\t%H0 = %H1 - %3;"
811 [(set_attr "length" "10")])
813 (define_insn "*subdi_zesidi_di"
814 [(set (match_operand:DI 0 "register_operand" "=d")
815 (minus:DI (zero_extend:DI
816 (match_operand:SI 2 "register_operand" "d"))
817 (match_operand:DI 1 "register_operand" "0")))
818 (clobber (match_scratch:SI 3 "=&d"))
819 (clobber (reg:CC 34))]
821 "%0 = %2 - %1;\\n\\tcc = ac0;\\n\\tcc = ! cc;\\n\\t%3 = cc;\\n\\t%3 = -%3;\\n\\t%H0 = %3 - %H1"
822 [(set_attr "length" "12")])
824 (define_insn "*subdi_di_sesidi"
825 [(set (match_operand:DI 0 "register_operand" "=d")
826 (minus:DI (match_operand:DI 1 "register_operand" "0")
828 (match_operand:SI 2 "register_operand" "d"))))
829 (clobber (match_scratch:SI 3 "=&d"))
830 (clobber (reg:CC 34))]
832 "%0 = %1 - %2;\\n\\tcc = ac0;\\n\\t%3 = %2;\\n\\t%3 >>>= 31;\\n\\t%H0 = %H1 - %3;\\n\\tif cc jump 1f;\\n\\t%H0 += -1;\\n\\t1:"
833 [(set_attr "length" "14")])
835 (define_insn "*subdi_sesidi_di"
836 [(set (match_operand:DI 0 "register_operand" "=d")
837 (minus:DI (sign_extend:DI
838 (match_operand:SI 2 "register_operand" "d"))
839 (match_operand:DI 1 "register_operand" "0")))
840 (clobber (match_scratch:SI 3 "=&d"))
841 (clobber (reg:CC 34))]
843 "%0 = %2 - %1;\\n\\tcc = ac0;\\n\\t%3 = %2;\\n\\t%3 >>>= 31;\\n\\t%H0 = %3 - %H1;\\n\\tif cc jump 1f;\\n\\t%H0 += -1;\\n\\t1:"
844 [(set_attr "length" "14")])
846 ;; Combined shift/add instructions
849 [(set (match_operand:SI 0 "register_operand" "=a,d")
850 (ashift:SI (plus:SI (match_operand:SI 1 "register_operand" "%0,0")
851 (match_operand:SI 2 "register_operand" "a,d"))
852 (match_operand:SI 3 "pos_scale_operand" "P1P2,P1P2")))]
854 "%0 = (%0 + %2) << %3;" /* "shadd %0,%2,%3;" */
855 [(set_attr "type" "alu0")])
858 [(set (match_operand:SI 0 "register_operand" "=a")
859 (plus:SI (match_operand:SI 1 "register_operand" "a")
860 (mult:SI (match_operand:SI 2 "register_operand" "a")
861 (match_operand:SI 3 "scale_by_operand" "i"))))]
863 "%0 = %1 + (%2 << %X3);"
864 [(set_attr "type" "alu0")])
867 [(set (match_operand:SI 0 "register_operand" "=a")
868 (plus:SI (match_operand:SI 1 "register_operand" "a")
869 (ashift:SI (match_operand:SI 2 "register_operand" "a")
870 (match_operand:SI 3 "pos_scale_operand" "i"))))]
872 "%0 = %1 + (%2 << %3);"
873 [(set_attr "type" "alu0")])
876 [(set (match_operand:SI 0 "register_operand" "=a")
877 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "a")
878 (match_operand:SI 2 "scale_by_operand" "i"))
879 (match_operand:SI 3 "register_operand" "a")))]
881 "%0 = %3 + (%1 << %X2);"
882 [(set_attr "type" "alu0")])
885 [(set (match_operand:SI 0 "register_operand" "=a")
886 (plus:SI (ashift:SI (match_operand:SI 1 "register_operand" "a")
887 (match_operand:SI 2 "pos_scale_operand" "i"))
888 (match_operand:SI 3 "register_operand" "a")))]
890 "%0 = %3 + (%1 << %2);"
891 [(set_attr "type" "alu0")])
893 (define_insn "mulhisi3"
894 [(set (match_operand:SI 0 "register_operand" "=d")
895 (mult:SI (sign_extend:SI (match_operand:HI 1 "register_operand" "%d"))
896 (sign_extend:SI (match_operand:HI 2 "register_operand" "d"))))]
898 "%0 = %h1 * %h2 (IS);"
899 [(set_attr "type" "dsp32")])
901 (define_insn "umulhisi3"
902 [(set (match_operand:SI 0 "register_operand" "=d")
903 (mult:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "%d"))
904 (zero_extend:SI (match_operand:HI 2 "register_operand" "d"))))]
906 "%0 = %h1 * %h2 (FU);"
907 [(set_attr "type" "dsp32")])
909 ;; The processor also supports ireg += mreg or ireg -= mreg, but these
910 ;; are unusable if we don't ensure that the corresponding lreg is zero.
911 ;; The same applies to the add/subtract constant versions involving
914 (define_insn "addsi3"
915 [(set (match_operand:SI 0 "register_operand" "=ad,a,d")
916 (plus:SI (match_operand:SI 1 "register_operand" "%0, a,d")
917 (match_operand:SI 2 "reg_or_7bit_operand" "Ks7, a,d")))]
923 [(set_attr "type" "alu0")
924 (set_attr "length" "2,2,2")])
926 (define_expand "subsi3"
927 [(set (match_operand:SI 0 "register_operand" "")
928 (minus:SI (match_operand:SI 1 "register_operand" "")
929 (match_operand:SI 2 "reg_or_7bit_operand" "")))]
934 [(set (match_operand:SI 0 "register_operand" "=da,d,a")
935 (minus:SI (match_operand:SI 1 "register_operand" "0,d,0")
936 (match_operand:SI 2 "reg_or_7bit_operand" "Ks7,d,a")))]
937 "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != -64"
939 static const char *const strings_subsi3[] = {
945 if (CONSTANT_P (operands[2]) && INTVAL (operands[2]) < 0) {
946 rtx tmp_op = operands[2];
947 operands[2] = GEN_INT (-INTVAL (operands[2]));
948 output_asm_insn ("%0 += %2;", operands);
949 operands[2] = tmp_op;
953 return strings_subsi3[which_alternative];
955 [(set_attr "type" "alu0")])
957 ;; Bit test instructions
959 (define_insn "*not_bittst"
960 [(set (match_operand:BI 0 "cc_operand" "=C")
961 (eq:BI (zero_extract:SI (match_operand:SI 1 "register_operand" "d")
963 (match_operand:SI 2 "immediate_operand" "Ku5"))
966 "cc = !BITTST (%1,%2);"
967 [(set_attr "type" "alu0")])
969 (define_insn "*bittst"
970 [(set (match_operand:BI 0 "cc_operand" "=C")
971 (ne:BI (zero_extract:SI (match_operand:SI 1 "register_operand" "d")
973 (match_operand:SI 2 "immediate_operand" "Ku5"))
976 "cc = BITTST (%1,%2);"
977 [(set_attr "type" "alu0")])
979 (define_insn_and_split "*bit_extract"
980 [(set (match_operand:SI 0 "register_operand" "=d")
981 (zero_extract:SI (match_operand:SI 1 "register_operand" "d")
983 (match_operand:SI 2 "immediate_operand" "Ku5")))
984 (clobber (reg:BI REG_CC))]
988 [(set (reg:BI REG_CC)
989 (ne:BI (zero_extract:SI (match_dup 1) (const_int 1) (match_dup 2))
992 (ne:SI (reg:BI REG_CC) (const_int 0)))])
994 (define_insn_and_split "*not_bit_extract"
995 [(set (match_operand:SI 0 "register_operand" "=d")
996 (zero_extract:SI (not:SI (match_operand:SI 1 "register_operand" "d"))
998 (match_operand:SI 2 "immediate_operand" "Ku5")))
999 (clobber (reg:BI REG_CC))]
1003 [(set (reg:BI REG_CC)
1004 (eq:BI (zero_extract:SI (match_dup 1) (const_int 1) (match_dup 2))
1007 (ne:SI (reg:BI REG_CC) (const_int 0)))])
1009 (define_insn "*andsi_insn"
1010 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
1011 (and:SI (match_operand:SI 1 "register_operand" "%0,d,d,d")
1012 (match_operand:SI 2 "rhs_andsi3_operand" "L,M1,M2,d")))]
1019 [(set_attr "type" "alu0")])
1021 (define_expand "andsi3"
1022 [(set (match_operand:SI 0 "register_operand" "")
1023 (and:SI (match_operand:SI 1 "register_operand" "")
1024 (match_operand:SI 2 "general_operand" "")))]
1027 if (highbits_operand (operands[2], SImode))
1029 operands[2] = GEN_INT (exact_log2 (-INTVAL (operands[2])));
1030 emit_insn (gen_ashrsi3 (operands[0], operands[1], operands[2]));
1031 emit_insn (gen_ashlsi3 (operands[0], operands[0], operands[2]));
1034 if (! rhs_andsi3_operand (operands[2], SImode))
1035 operands[2] = force_reg (SImode, operands[2]);
1038 (define_insn "iorsi3"
1039 [(set (match_operand:SI 0 "register_operand" "=d,d")
1040 (ior:SI (match_operand:SI 1 "register_operand" "%0,d")
1041 (match_operand:SI 2 "regorlog2_operand" "J,d")))]
1046 [(set_attr "type" "alu0")])
1048 (define_insn "xorsi3"
1049 [(set (match_operand:SI 0 "register_operand" "=d,d")
1050 (xor:SI (match_operand:SI 1 "register_operand" "%0,d")
1051 (match_operand:SI 2 "regorlog2_operand" "J,d")))]
1056 [(set_attr "type" "alu0")])
1058 (define_insn "smaxsi3"
1059 [(set (match_operand:SI 0 "register_operand" "=d")
1060 (smax:SI (match_operand:SI 1 "register_operand" "d")
1061 (match_operand:SI 2 "register_operand" "d")))]
1064 [(set_attr "type" "dsp32")])
1066 (define_insn "sminsi3"
1067 [(set (match_operand:SI 0 "register_operand" "=d")
1068 (smin:SI (match_operand:SI 1 "register_operand" "d")
1069 (match_operand:SI 2 "register_operand" "d")))]
1072 [(set_attr "type" "dsp32")])
1074 (define_insn "abssi2"
1075 [(set (match_operand:SI 0 "register_operand" "=d")
1076 (abs:SI (match_operand:SI 1 "register_operand" " d")))]
1079 [(set_attr "type" "dsp32")])
1082 (define_insn "negsi2"
1083 [(set (match_operand:SI 0 "register_operand" "=d")
1084 (neg:SI (match_operand:SI 1 "register_operand" " d")))]
1087 [(set_attr "type" "alu0")])
1089 (define_insn "one_cmplsi2"
1090 [(set (match_operand:SI 0 "register_operand" "=d")
1091 (not:SI (match_operand:SI 1 "register_operand" " d")))]
1094 [(set_attr "type" "alu0")])
1096 (define_insn "mulsi3"
1097 [(set (match_operand:SI 0 "register_operand" "=d")
1098 (mult:SI (match_operand:SI 1 "register_operand" "%0")
1099 (match_operand:SI 2 "register_operand" "d")))]
1102 [(set_attr "type" "mult")])
1104 (define_expand "ashlsi3"
1105 [(set (match_operand:SI 0 "register_operand" "")
1106 (ashift:SI (match_operand:SI 1 "register_operand" "")
1107 (match_operand:SI 2 "nonmemory_operand" "")))]
1110 if (GET_CODE (operands[2]) == CONST_INT
1111 && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) > 31)
1113 emit_insn (gen_movsi (operands[0], const0_rtx));
1118 (define_insn_and_split "*ashlsi3_insn"
1119 [(set (match_operand:SI 0 "register_operand" "=d,a,a,a")
1120 (ashift:SI (match_operand:SI 1 "register_operand" "0,a,a,a")
1121 (match_operand:SI 2 "nonmemory_operand" "dKu5,P1,P2,?P3P4")))]
1128 "PREG_P (operands[0]) && INTVAL (operands[2]) > 2"
1129 [(set (match_dup 0) (ashift:SI (match_dup 1) (const_int 2)))
1130 (set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 3)))]
1131 "operands[3] = GEN_INT (INTVAL (operands[2]) - 2);"
1132 [(set_attr "type" "shft")])
1134 (define_insn "ashrsi3"
1135 [(set (match_operand:SI 0 "register_operand" "=d")
1136 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
1137 (match_operand:SI 2 "nonmemory_operand" "dKu5")))]
1140 [(set_attr "type" "shft")])
1142 (define_insn "ror_one"
1143 [(set (match_operand:SI 0 "register_operand" "=d")
1144 (ior:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "d") (const_int 1))
1145 (ashift:SI (zero_extend:SI (reg:BI REG_CC)) (const_int 31))))
1146 (set (reg:BI REG_CC)
1147 (zero_extract:BI (match_dup 1) (const_int 1) (const_int 0)))]
1149 "%0 = ROT %1 BY -1;"
1150 [(set_attr "type" "shft")
1151 (set_attr "length" "4")])
1153 (define_insn "rol_one"
1154 [(set (match_operand:SI 0 "register_operand" "+d")
1155 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "d") (const_int 1))
1156 (zero_extend:SI (reg:BI REG_CC))))
1157 (set (reg:BI REG_CC)
1158 (zero_extract:BI (match_dup 1) (const_int 31) (const_int 0)))]
1161 [(set_attr "type" "shft")
1162 (set_attr "length" "4")])
1164 (define_expand "lshrdi3"
1165 [(set (match_operand:DI 0 "register_operand" "")
1166 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
1167 (match_operand:DI 2 "general_operand" "")))]
1170 rtx lo_half[2], hi_half[2];
1172 if (operands[2] != const1_rtx)
1174 if (! rtx_equal_p (operands[0], operands[1]))
1175 emit_move_insn (operands[0], operands[1]);
1177 split_di (operands, 2, lo_half, hi_half);
1179 emit_move_insn (bfin_cc_rtx, const0_rtx);
1180 emit_insn (gen_ror_one (hi_half[0], hi_half[0]));
1181 emit_insn (gen_ror_one (lo_half[0], lo_half[0]));
1185 (define_expand "ashrdi3"
1186 [(set (match_operand:DI 0 "register_operand" "")
1187 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
1188 (match_operand:DI 2 "general_operand" "")))]
1191 rtx lo_half[2], hi_half[2];
1193 if (operands[2] != const1_rtx)
1195 if (! rtx_equal_p (operands[0], operands[1]))
1196 emit_move_insn (operands[0], operands[1]);
1198 split_di (operands, 2, lo_half, hi_half);
1200 emit_insn (gen_compare_lt (gen_rtx_REG (BImode, REG_CC),
1201 hi_half[1], const0_rtx));
1202 emit_insn (gen_ror_one (hi_half[0], hi_half[0]));
1203 emit_insn (gen_ror_one (lo_half[0], lo_half[0]));
1207 (define_expand "ashldi3"
1208 [(set (match_operand:DI 0 "register_operand" "")
1209 (ashift:DI (match_operand:DI 1 "register_operand" "")
1210 (match_operand:DI 2 "general_operand" "")))]
1213 rtx lo_half[2], hi_half[2];
1215 if (operands[2] != const1_rtx)
1217 if (! rtx_equal_p (operands[0], operands[1]))
1218 emit_move_insn (operands[0], operands[1]);
1220 split_di (operands, 2, lo_half, hi_half);
1222 emit_move_insn (bfin_cc_rtx, const0_rtx);
1223 emit_insn (gen_rol_one (lo_half[0], lo_half[0]));
1224 emit_insn (gen_rol_one (hi_half[0], hi_half[0]));
1228 (define_insn "lshrsi3"
1229 [(set (match_operand:SI 0 "register_operand" "=d,a")
1230 (lshiftrt:SI (match_operand:SI 1 "register_operand" " 0,a")
1231 (match_operand:SI 2 "nonmemory_operand" "dKu5,P1P2")))]
1236 [(set_attr "type" "shft")])
1238 ;; A pattern to reload the equivalent of
1239 ;; (set (Dreg) (plus (FP) (large_constant)))
1241 ;; (set (dagreg) (plus (FP) (arbitrary_constant)))
1242 ;; using a scratch register
1243 (define_expand "reload_insi"
1244 [(parallel [(set (match_operand:SI 0 "register_operand" "=w")
1245 (match_operand:SI 1 "fp_plus_const_operand" ""))
1246 (clobber (match_operand:SI 2 "register_operand" "=&a"))])]
1249 rtx fp_op = XEXP (operands[1], 0);
1250 rtx const_op = XEXP (operands[1], 1);
1251 rtx primary = operands[0];
1252 rtx scratch = operands[2];
1254 emit_move_insn (scratch, const_op);
1255 emit_insn (gen_addsi3 (scratch, scratch, fp_op));
1256 emit_move_insn (primary, scratch);
1260 ;; Jump instructions
1264 (label_ref (match_operand 0 "" "")))]
1267 if (get_attr_length (insn) == 2)
1268 return "jump.s %0;";
1270 return "jump.l %0;";
1272 [(set_attr "type" "br")])
1274 (define_insn "indirect_jump"
1276 (match_operand:SI 0 "register_operand" "a"))]
1279 [(set_attr "type" "misc")])
1281 (define_expand "tablejump"
1282 [(parallel [(set (pc) (match_operand:SI 0 "register_operand" "a"))
1283 (use (label_ref (match_operand 1 "" "")))])]
1286 /* In PIC mode, the table entries are stored PC relative.
1287 Convert the relative address to an absolute address. */
1290 rtx op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
1292 operands[0] = expand_simple_binop (Pmode, PLUS, operands[0],
1293 op1, NULL_RTX, 0, OPTAB_DIRECT);
1297 (define_insn "*tablejump_internal"
1298 [(set (pc) (match_operand:SI 0 "register_operand" "a"))
1299 (use (label_ref (match_operand 1 "" "")))]
1302 [(set_attr "type" "misc")])
1304 ;; Call instructions..
1306 (define_expand "call"
1307 [(parallel [(call (match_operand:SI 0 "" "")
1308 (match_operand 1 "" ""))
1309 (use (match_operand 2 "" ""))])]
1312 bfin_expand_call (NULL_RTX, operands[0], operands[1], operands[2], 0);
1316 (define_expand "sibcall"
1317 [(parallel [(call (match_operand:SI 0 "" "")
1318 (match_operand 1 "" ""))
1319 (use (match_operand 2 "" ""))
1323 bfin_expand_call (NULL_RTX, operands[0], operands[1], operands[2], 1);
1327 (define_expand "call_value"
1328 [(parallel [(set (match_operand 0 "register_operand" "")
1329 (call (match_operand:SI 1 "" "")
1330 (match_operand 2 "" "")))
1331 (use (match_operand 3 "" ""))])]
1334 bfin_expand_call (operands[0], operands[1], operands[2], operands[3], 0);
1338 (define_expand "sibcall_value"
1339 [(parallel [(set (match_operand 0 "register_operand" "")
1340 (call (match_operand:SI 1 "" "")
1341 (match_operand 2 "" "")))
1342 (use (match_operand 3 "" ""))
1346 bfin_expand_call (operands[0], operands[1], operands[2], operands[3], 1);
1350 (define_insn "*call_symbol"
1351 [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "Q"))
1352 (match_operand 1 "general_operand" "g"))
1353 (use (match_operand 2 "" ""))]
1354 "! SIBLING_CALL_P (insn)
1356 && GET_CODE (operands[0]) == SYMBOL_REF
1357 && !bfin_longcall_p (operands[0], INTVAL (operands[2]))"
1359 [(set_attr "type" "call")
1360 (set_attr "length" "4")])
1362 (define_insn "*sibcall_symbol"
1363 [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "Q"))
1364 (match_operand 1 "general_operand" "g"))
1365 (use (match_operand 2 "" ""))
1367 "SIBLING_CALL_P (insn)
1369 && GET_CODE (operands[0]) == SYMBOL_REF
1370 && !bfin_longcall_p (operands[0], INTVAL (operands[2]))"
1372 [(set_attr "type" "br")
1373 (set_attr "length" "4")])
1375 (define_insn "*call_value_symbol"
1376 [(set (match_operand 0 "register_operand" "=d")
1377 (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "Q"))
1378 (match_operand 2 "general_operand" "g")))
1379 (use (match_operand 3 "" ""))]
1380 "! SIBLING_CALL_P (insn)
1382 && GET_CODE (operands[1]) == SYMBOL_REF
1383 && !bfin_longcall_p (operands[1], INTVAL (operands[3]))"
1385 [(set_attr "type" "call")
1386 (set_attr "length" "4")])
1388 (define_insn "*sibcall_value_symbol"
1389 [(set (match_operand 0 "register_operand" "=d")
1390 (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "Q"))
1391 (match_operand 2 "general_operand" "g")))
1392 (use (match_operand 3 "" ""))
1394 "SIBLING_CALL_P (insn)
1396 && GET_CODE (operands[1]) == SYMBOL_REF
1397 && !bfin_longcall_p (operands[1], INTVAL (operands[3]))"
1399 [(set_attr "type" "br")
1400 (set_attr "length" "4")])
1402 (define_insn "*call_insn"
1403 [(call (mem:SI (match_operand:SI 0 "register_no_elim_operand" "a"))
1404 (match_operand 1 "general_operand" "g"))
1405 (use (match_operand 2 "" ""))]
1406 "! SIBLING_CALL_P (insn)"
1408 [(set_attr "type" "call")
1409 (set_attr "length" "2")])
1411 (define_insn "*sibcall_insn"
1412 [(call (mem:SI (match_operand:SI 0 "register_no_elim_operand" "z"))
1413 (match_operand 1 "general_operand" "g"))
1414 (use (match_operand 2 "" ""))
1416 "SIBLING_CALL_P (insn)"
1418 [(set_attr "type" "br")
1419 (set_attr "length" "2")])
1421 (define_insn "*call_value_insn"
1422 [(set (match_operand 0 "register_operand" "=d")
1423 (call (mem:SI (match_operand:SI 1 "register_no_elim_operand" "a"))
1424 (match_operand 2 "general_operand" "g")))
1425 (use (match_operand 3 "" ""))]
1426 "! SIBLING_CALL_P (insn)"
1428 [(set_attr "type" "call")
1429 (set_attr "length" "2")])
1431 (define_insn "*sibcall_value_insn"
1432 [(set (match_operand 0 "register_operand" "=d")
1433 (call (mem:SI (match_operand:SI 1 "register_no_elim_operand" "z"))
1434 (match_operand 2 "general_operand" "g")))
1435 (use (match_operand 3 "" ""))
1437 "SIBLING_CALL_P (insn)"
1439 [(set_attr "type" "br")
1440 (set_attr "length" "2")])
1442 ;; Block move patterns
1444 ;; We cheat. This copies one more word than operand 2 indicates.
1446 (define_insn "rep_movsi"
1447 [(set (match_operand:SI 0 "register_operand" "=&a")
1448 (plus:SI (plus:SI (match_operand:SI 3 "register_operand" "0")
1449 (ashift:SI (match_operand:SI 2 "register_operand" "a")
1452 (set (match_operand:SI 1 "register_operand" "=&b")
1453 (plus:SI (plus:SI (match_operand:SI 4 "register_operand" "1")
1454 (ashift:SI (match_dup 2) (const_int 2)))
1456 (set (mem:BLK (match_dup 3))
1457 (mem:BLK (match_dup 4)))
1459 (clobber (match_scratch:HI 5 "=&d"))]
1461 "%5 = [%4++]; lsetup (1f, 1f) LC1 = %2; 1: MNOP || [%3++] = %5 || %5 = [%4++]; [%3++] = %5;"
1462 [(set_attr "type" "misc")
1463 (set_attr "length" "16")])
1465 (define_insn "rep_movhi"
1466 [(set (match_operand:SI 0 "register_operand" "=&a")
1467 (plus:SI (plus:SI (match_operand:SI 3 "register_operand" "0")
1468 (ashift:SI (match_operand:SI 2 "register_operand" "a")
1471 (set (match_operand:SI 1 "register_operand" "=&b")
1472 (plus:SI (plus:SI (match_operand:SI 4 "register_operand" "1")
1473 (ashift:SI (match_dup 2) (const_int 1)))
1475 (set (mem:BLK (match_dup 3))
1476 (mem:BLK (match_dup 4)))
1478 (clobber (match_scratch:HI 5 "=&d"))]
1480 "%h5 = W[%4++]; lsetup (1f, 1f) LC1 = %2; 1: MNOP || W [%3++] = %5 || %h5 = W [%4++]; W [%3++] = %5;"
1481 [(set_attr "type" "misc")
1482 (set_attr "length" "16")])
1484 (define_expand "movstrsi"
1485 [(match_operand:BLK 0 "general_operand" "")
1486 (match_operand:BLK 1 "general_operand" "")
1487 (match_operand:SI 2 "const_int_operand" "")
1488 (match_operand:SI 3 "const_int_operand" "")]
1491 if (bfin_expand_strmov (operands[0], operands[1], operands[2], operands[3]))
1496 ;; Conditional branch patterns
1497 ;; The Blackfin has only few condition codes: eq, lt, lte, ltu, leu
1499 ;; The only outcome of this pattern is that global variables
1500 ;; bfin_compare_op[01] are set for use in bcond patterns.
1502 (define_expand "cmpbi"
1503 [(set (cc0) (compare (match_operand:BI 0 "register_operand" "")
1504 (match_operand:BI 1 "immediate_operand" "")))]
1507 bfin_compare_op0 = operands[0];
1508 bfin_compare_op1 = operands[1];
1512 (define_expand "cmpsi"
1513 [(set (cc0) (compare (match_operand:SI 0 "register_operand" "")
1514 (match_operand:SI 1 "reg_or_const_int_operand" "")))]
1517 bfin_compare_op0 = operands[0];
1518 bfin_compare_op1 = operands[1];
1522 (define_insn "compare_eq"
1523 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1524 (eq:BI (match_operand:SI 1 "register_operand" "d,a")
1525 (match_operand:SI 2 "reg_or_const_int_operand" "dKs3,aKs3")))]
1528 [(set_attr "type" "compare")])
1530 (define_insn "compare_ne"
1531 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1532 (ne:BI (match_operand:SI 1 "register_operand" "d,a")
1533 (match_operand:SI 2 "reg_or_const_int_operand" "dKs3,aKs3")))]
1536 [(set_attr "type" "compare")])
1538 (define_insn "compare_lt"
1539 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1540 (lt:BI (match_operand:SI 1 "register_operand" "d,a")
1541 (match_operand:SI 2 "reg_or_const_int_operand" "dKs3,aKs3")))]
1544 [(set_attr "type" "compare")])
1546 (define_insn "compare_le"
1547 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1548 (le:BI (match_operand:SI 1 "register_operand" "d,a")
1549 (match_operand:SI 2 "reg_or_const_int_operand" "dKs3,aKs3")))]
1552 [(set_attr "type" "compare")])
1554 (define_insn "compare_leu"
1555 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1556 (leu:BI (match_operand:SI 1 "register_operand" "d,a")
1557 (match_operand:SI 2 "reg_or_const_int_operand" "dKu3,aKu3")))]
1560 [(set_attr "type" "compare")])
1562 (define_insn "compare_ltu"
1563 [(set (match_operand:BI 0 "cc_operand" "=C,C")
1564 (ltu:BI (match_operand:SI 1 "register_operand" "d,a")
1565 (match_operand:SI 2 "reg_or_const_int_operand" "dKu3,aKu3")))]
1568 [(set_attr "type" "compare")])
1570 (define_expand "beq"
1571 [(set (match_dup 1) (match_dup 2))
1573 (if_then_else (match_dup 3)
1574 (label_ref (match_operand 0 "" ""))
1578 rtx op0 = bfin_compare_op0, op1 = bfin_compare_op1;
1579 operands[1] = bfin_cc_rtx; /* hard register: CC */
1580 operands[2] = gen_rtx_EQ (BImode, op0, op1);
1581 /* If we have a BImode input, then we already have a compare result, and
1582 do not need to emit another comparison. */
1583 if (GET_MODE (bfin_compare_op0) == BImode)
1585 gcc_assert (bfin_compare_op1 == const0_rtx);
1586 emit_insn (gen_cbranchbi4 (operands[2], op0, op1, operands[0]));
1590 operands[3] = gen_rtx_NE (BImode, operands[1], const0_rtx);
1593 (define_expand "bne"
1594 [(set (match_dup 1) (match_dup 2))
1596 (if_then_else (match_dup 3)
1597 (label_ref (match_operand 0 "" ""))
1601 rtx op0 = bfin_compare_op0, op1 = bfin_compare_op1;
1602 /* If we have a BImode input, then we already have a compare result, and
1603 do not need to emit another comparison. */
1604 if (GET_MODE (bfin_compare_op0) == BImode)
1606 rtx cmp = gen_rtx_NE (BImode, op0, op1);
1608 gcc_assert (bfin_compare_op1 == const0_rtx);
1609 emit_insn (gen_cbranchbi4 (cmp, op0, op1, operands[0]));
1613 operands[1] = bfin_cc_rtx; /* hard register: CC */
1614 operands[2] = gen_rtx_EQ (BImode, op0, op1);
1615 operands[3] = gen_rtx_EQ (BImode, operands[1], const0_rtx);
1618 (define_expand "bgt"
1619 [(set (match_dup 1) (match_dup 2))
1621 (if_then_else (match_dup 3)
1622 (label_ref (match_operand 0 "" ""))
1626 operands[1] = bfin_cc_rtx;
1627 operands[2] = gen_rtx_LE (BImode, bfin_compare_op0, bfin_compare_op1);
1628 operands[3] = gen_rtx_EQ (BImode, operands[1], const0_rtx);
1631 (define_expand "bgtu"
1632 [(set (match_dup 1) (match_dup 2))
1634 (if_then_else (match_dup 3)
1635 (label_ref (match_operand 0 "" ""))
1639 operands[1] = bfin_cc_rtx;
1640 operands[2] = gen_rtx_LEU (BImode, bfin_compare_op0, bfin_compare_op1);
1641 operands[3] = gen_rtx_EQ (BImode, operands[1], const0_rtx);
1644 (define_expand "blt"
1645 [(set (match_dup 1) (match_dup 2))
1647 (if_then_else (match_dup 3)
1648 (label_ref (match_operand 0 "" ""))
1652 operands[1] = bfin_cc_rtx;
1653 operands[2] = gen_rtx_LT (BImode, bfin_compare_op0, bfin_compare_op1);
1654 operands[3] = gen_rtx_NE (BImode, operands[1], const0_rtx);
1657 (define_expand "bltu"
1658 [(set (match_dup 1) (match_dup 2))
1660 (if_then_else (match_dup 3)
1661 (label_ref (match_operand 0 "" ""))
1665 operands[1] = bfin_cc_rtx;
1666 operands[2] = gen_rtx_LTU (BImode, bfin_compare_op0, bfin_compare_op1);
1667 operands[3] = gen_rtx_NE (BImode, operands[1], const0_rtx);
1671 (define_expand "bge"
1672 [(set (match_dup 1) (match_dup 2))
1674 (if_then_else (match_dup 3)
1675 (label_ref (match_operand 0 "" ""))
1679 operands[1] = bfin_cc_rtx;
1680 operands[2] = gen_rtx_LT (BImode, bfin_compare_op0, bfin_compare_op1);
1681 operands[3] = gen_rtx_EQ (BImode, operands[1], const0_rtx);
1684 (define_expand "bgeu"
1685 [(set (match_dup 1) (match_dup 2))
1687 (if_then_else (match_dup 3)
1688 (label_ref (match_operand 0 "" ""))
1692 operands[1] = bfin_cc_rtx;
1693 operands[2] = gen_rtx_LTU (BImode, bfin_compare_op0, bfin_compare_op1);
1694 operands[3] = gen_rtx_EQ (BImode, operands[1], const0_rtx);
1697 (define_expand "ble"
1698 [(set (match_dup 1) (match_dup 2))
1700 (if_then_else (match_dup 3)
1701 (label_ref (match_operand 0 "" ""))
1705 operands[1] = bfin_cc_rtx;
1706 operands[2] = gen_rtx_LE (BImode, bfin_compare_op0, bfin_compare_op1);
1707 operands[3] = gen_rtx_NE (BImode, operands[1], const0_rtx);
1710 (define_expand "bleu"
1711 [(set (match_dup 1) (match_dup 2))
1713 (if_then_else (match_dup 3)
1714 (label_ref (match_operand 0 "" ""))
1719 operands[1] = bfin_cc_rtx;
1720 operands[2] = gen_rtx_LEU (BImode, bfin_compare_op0, bfin_compare_op1);
1721 operands[3] = gen_rtx_NE (BImode, operands[1], const0_rtx);
1724 (define_insn "cbranchbi4"
1727 (match_operator 0 "bfin_cbranch_operator"
1728 [(match_operand:BI 1 "cc_operand" "C")
1729 (match_operand:BI 2 "immediate_operand" "P0")])
1730 (label_ref (match_operand 3 "" ""))
1734 asm_conditional_branch (insn, operands, 0, 0);
1737 [(set_attr "type" "brcc")])
1739 ;; Special cbranch patterns to deal with the speculative load problem - see
1740 ;; bfin_reorg for details.
1742 (define_insn "cbranch_predicted_taken"
1745 (match_operator 0 "bfin_cbranch_operator"
1746 [(match_operand:BI 1 "cc_operand" "C")
1747 (match_operand:BI 2 "immediate_operand" "P0")])
1748 (label_ref (match_operand 3 "" ""))
1750 (unspec [(const_int 0)] UNSPEC_CBRANCH_TAKEN)]
1753 asm_conditional_branch (insn, operands, 0, 1);
1756 [(set_attr "type" "brcc")])
1758 (define_insn "cbranch_with_nops"
1761 (match_operator 0 "bfin_cbranch_operator"
1762 [(match_operand:BI 1 "cc_operand" "C")
1763 (match_operand:BI 2 "immediate_operand" "P0")])
1764 (label_ref (match_operand 3 "" ""))
1766 (unspec [(match_operand 4 "immediate_operand" "")] UNSPEC_CBRANCH_NOPS)]
1769 asm_conditional_branch (insn, operands, INTVAL (operands[4]), 0);
1772 [(set_attr "type" "brcc")
1773 (set_attr "length" "6")])
1776 (define_expand "seq"
1777 [(set (match_dup 1) (eq:BI (match_dup 2) (match_dup 3)))
1778 (set (match_operand:SI 0 "register_operand" "")
1779 (ne:SI (match_dup 1) (const_int 0)))]
1782 operands[2] = bfin_compare_op0;
1783 operands[3] = bfin_compare_op1;
1784 operands[1] = bfin_cc_rtx;
1787 (define_expand "slt"
1788 [(set (match_dup 1) (lt:BI (match_dup 2) (match_dup 3)))
1789 (set (match_operand:SI 0 "register_operand" "")
1790 (ne:SI (match_dup 1) (const_int 0)))]
1793 operands[2] = bfin_compare_op0;
1794 operands[3] = bfin_compare_op1;
1795 operands[1] = bfin_cc_rtx;
1798 (define_expand "sle"
1799 [(set (match_dup 1) (le:BI (match_dup 2) (match_dup 3)))
1800 (set (match_operand:SI 0 "register_operand" "")
1801 (ne:SI (match_dup 1) (const_int 0)))]
1804 operands[2] = bfin_compare_op0;
1805 operands[3] = bfin_compare_op1;
1806 operands[1] = bfin_cc_rtx;
1809 (define_expand "sltu"
1810 [(set (match_dup 1) (ltu:BI (match_dup 2) (match_dup 3)))
1811 (set (match_operand:SI 0 "register_operand" "")
1812 (ne:SI (match_dup 1) (const_int 0)))]
1815 operands[2] = bfin_compare_op0;
1816 operands[3] = bfin_compare_op1;
1817 operands[1] = bfin_cc_rtx;
1820 (define_expand "sleu"
1821 [(set (match_dup 1) (leu:BI (match_dup 2) (match_dup 3)))
1822 (set (match_operand:SI 0 "register_operand" "")
1823 (ne:SI (match_dup 1) (const_int 0)))]
1826 operands[2] = bfin_compare_op0;
1827 operands[3] = bfin_compare_op1;
1828 operands[1] = bfin_cc_rtx;
1836 ;;;;;;;;;;;;;;;;;;;; CC2dreg ;;;;;;;;;;;;;;;;;;;;;;;;;
1837 (define_insn "movsibi"
1838 [(set (match_operand:BI 0 "cc_operand" "=C")
1839 (ne:BI (match_operand:SI 1 "register_operand" "d")
1843 [(set_attr "length" "2")])
1845 (define_insn "movbisi"
1846 [(set (match_operand:SI 0 "register_operand" "=d")
1847 (ne:SI (match_operand:BI 1 "cc_operand" "C")
1851 [(set_attr "length" "2")])
1854 [(set (match_operand:BI 0 "cc_operand" "=C")
1855 (eq:BI (match_operand:BI 1 "cc_operand" " 0")
1858 "%0 = ! %0;" /* NOT CC;" */
1859 [(set_attr "type" "compare")])
1861 ;; Vector and DSP insns
1864 [(set (match_operand:SI 0 "register_operand" "=d")
1865 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "d")
1867 (lshiftrt:SI (match_operand:SI 2 "register_operand" "d")
1870 "%0 = ALIGN8(%1, %2);"
1871 [(set_attr "type" "dsp32")])
1874 [(set (match_operand:SI 0 "register_operand" "=d")
1875 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "d")
1877 (lshiftrt:SI (match_operand:SI 2 "register_operand" "d")
1880 "%0 = ALIGN16(%1, %2);"
1881 [(set_attr "type" "dsp32")])
1884 [(set (match_operand:SI 0 "register_operand" "=d")
1885 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "d")
1887 (lshiftrt:SI (match_operand:SI 2 "register_operand" "d")
1890 "%0 = ALIGN24(%1, %2);"
1891 [(set_attr "type" "dsp32")])
1893 ;; Prologue and epilogue.
1895 (define_expand "prologue"
1898 "bfin_expand_prologue (); DONE;")
1900 (define_expand "epilogue"
1903 "bfin_expand_epilogue (1, 0); DONE;")
1905 (define_expand "sibcall_epilogue"
1908 "bfin_expand_epilogue (0, 0); DONE;")
1910 (define_expand "eh_return"
1911 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")]
1912 UNSPEC_VOLATILE_EH_RETURN)]
1915 emit_move_insn (EH_RETURN_HANDLER_RTX, operands[0]);
1916 emit_insn (gen_eh_return_internal ());
1921 (define_insn_and_split "eh_return_internal"
1922 [(unspec_volatile [(reg:SI REG_P2)] UNSPEC_VOLATILE_EH_RETURN)]
1927 "bfin_expand_epilogue (1, 1); DONE;")
1930 [(set (mem:SI (plus:SI (reg:SI REG_SP) (const_int -4))) (reg:SI REG_RETS))
1931 (set (mem:SI (plus:SI (reg:SI REG_SP) (const_int -8))) (reg:SI REG_FP))
1932 (set (reg:SI REG_FP)
1933 (plus:SI (reg:SI REG_SP) (const_int -8)))
1934 (set (reg:SI REG_SP)
1935 (plus:SI (reg:SI REG_SP) (match_operand:SI 0 "immediate_operand" "i")))]
1938 [(set_attr "length" "4")])
1940 (define_insn "unlink"
1941 [(set (reg:SI REG_FP) (mem:SI (reg:SI REG_FP)))
1942 (set (reg:SI REG_RETS) (mem:SI (plus:SI (reg:SI REG_FP) (const_int 4))))
1943 (set (reg:SI REG_SP) (plus:SI (reg:SI REG_FP) (const_int 8)))]
1946 [(set_attr "length" "4")])
1948 ;; This pattern is slightly clumsy. The stack adjust must be the final SET in
1949 ;; the pattern, otherwise dwarf2out becomes very confused about which reg goes
1950 ;; where on the stack, since it goes through all elements of the parallel in
1952 (define_insn "push_multiple"
1953 [(match_parallel 0 "push_multiple_operation"
1954 [(unspec [(match_operand:SI 1 "immediate_operand" "i")] UNSPEC_PUSH_MULTIPLE)])]
1957 output_push_multiple (insn, operands);
1961 (define_insn "pop_multiple"
1962 [(match_parallel 0 "pop_multiple_operation"
1963 [(set (reg:SI REG_SP)
1964 (plus:SI (reg:SI REG_SP) (match_operand:SI 1 "immediate_operand" "i")))])]
1967 output_pop_multiple (insn, operands);
1971 (define_insn "return_internal"
1973 (unspec [(match_operand 0 "immediate_operand" "i")] UNSPEC_RETURN)]
1976 switch (INTVAL (operands[0]))
1982 case INTERRUPT_HANDLER:
1990 (define_insn "csync"
1991 [(unspec_volatile [(const_int 0)] UNSPEC_VOLATILE_CSYNC)]
1994 [(set_attr "type" "sync")])
1996 (define_insn "ssync"
1997 [(unspec_volatile [(const_int 0)] UNSPEC_VOLATILE_SSYNC)]
2000 [(set_attr "type" "sync")])
2002 (define_insn "trapifcc"
2003 [(trap_if (reg:BI REG_CC) (const_int 3))]
2005 "if !cc jump 4 (bp); excpt 3;"
2006 [(set_attr "type" "misc")
2007 (set_attr "length" "4")])
2009 ;;; Vector instructions
2011 (define_insn "addv2hi3"
2012 [(set (match_operand:V2HI 0 "register_operand" "=d")
2013 (plus:V2HI (match_operand:V2HI 1 "register_operand" "d")
2014 (match_operand:V2HI 2 "register_operand" "d")))]
2017 [(set_attr "type" "dsp32")])
2019 (define_insn "subv2hi3"
2020 [(set (match_operand:V2HI 0 "register_operand" "=d")
2021 (minus:V2HI (match_operand:V2HI 1 "register_operand" "d")
2022 (match_operand:V2HI 2 "register_operand" "d")))]
2025 [(set_attr "type" "dsp32")])
2027 (define_insn "sminv2hi3"
2028 [(set (match_operand:V2HI 0 "register_operand" "=d")
2029 (smin:V2HI (match_operand:V2HI 1 "register_operand" "d")
2030 (match_operand:V2HI 2 "register_operand" "d")))]
2032 "%0 = MIN (%1, %2) (V);"
2033 [(set_attr "type" "dsp32")])
2035 (define_insn "smaxv2hi3"
2036 [(set (match_operand:V2HI 0 "register_operand" "=d")
2037 (smax:V2HI (match_operand:V2HI 1 "register_operand" "d")
2038 (match_operand:V2HI 2 "register_operand" "d")))]
2040 "%0 = MAX (%1, %2) (V);"
2041 [(set_attr "type" "dsp32")])
2043 (define_insn "mulv2hi3"
2044 [(set (match_operand:V2HI 0 "register_operand" "=d")
2045 (mult:V2HI (match_operand:V2HI 1 "register_operand" "d")
2046 (match_operand:V2HI 2 "register_operand" "d")))]
2048 "%h0 = %h1 * %h2, %d0 = %d1 * %d2 (IS);"
2049 [(set_attr "type" "dsp32")])
2051 (define_insn "negv2hi2"
2052 [(set (match_operand:V2HI 0 "register_operand" "=d")
2053 (neg:V2HI (match_operand:V2HI 1 "register_operand" "d")))]
2056 [(set_attr "type" "dsp32")])
2058 (define_insn "absv2hi2"
2059 [(set (match_operand:V2HI 0 "register_operand" "=d")
2060 (abs:V2HI (match_operand:V2HI 1 "register_operand" "d")))]
2063 [(set_attr "type" "dsp32")])