1 ;; GCC machine description for Renesas H8/300
2 ;; Copyright (C) 1992-2020 Free Software Foundation, Inc.
4 ;; Contributed by Steve Chamberlain (sac@cygnus.com),
5 ;; Jim Wilson (wilson@cygnus.com), and Doug Evans (dje@cygnus.com).
7 ;; This file is part of GCC.
9 ;; GCC 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 3, or (at your option)
14 ;; GCC 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.
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GCC; see the file COPYING3. If not see
21 ;; <http://www.gnu.org/licenses/>.
23 ;; We compute exact length on each instruction for most of the time.
24 ;; In some case, most notably bit operations that may involve memory
25 ;; operands, the lengths in this file are "worst case".
27 ;; On the H8/300H and H8S, adds/subs operate on the 32bit "er"
28 ;; registers. Right now GCC doesn't expose the "e" half to the
29 ;; compiler, so using add/subs for addhi and subhi is safe. Long
30 ;; term, we want to expose the "e" half to the compiler (gives us 8
31 ;; more 16bit registers). At that point addhi and subhi can't use
34 ;; There's currently no way to have an insv/extzv expander for the H8/300H
35 ;; because word_mode is different for the H8/300 and H8/300H.
37 ;; Shifts/rotates by small constants should be handled by special
38 ;; patterns so we get the length and cc status correct.
40 ;; Bitfield operations no longer accept memory operands. We need
41 ;; to add variants which operate on memory back to the MD.
43 ;; ??? Implement remaining bit ops available on the h8300
45 ;; ----------------------------------------------------------------------
47 ;; ----------------------------------------------------------------------
70 ;; ----------------------------------------------------------------------
72 ;; ----------------------------------------------------------------------
74 (define_attr "cpu" "h8300,h8300h"
75 (const (symbol_ref "cpu_type")))
77 (define_attr "type" "branch,arith,bitbranch,call"
78 (const_string "arith"))
80 (define_attr "length_table" "none,add,logicb,movb,movw,movl,mova_zero,mova,unary,mov_imm4,short_immediate,bitfield,bitbranch"
81 (const_string "none"))
83 ;; The size of instructions in bytes.
85 (define_attr "length" ""
86 (cond [(eq_attr "type" "branch")
87 ;; In a forward delayed branch, (pc) represents the end of the
88 ;; delay sequence, not the end of the branch itself.
89 (if_then_else (and (ge (minus (match_dup 0) (pc))
91 (le (plus (minus (match_dup 0) (pc))
92 (symbol_ref "DELAY_SLOT_LENGTH (insn)"))
95 (if_then_else (and (eq_attr "cpu" "h8300h")
96 (and (ge (minus (pc) (match_dup 0))
98 (le (minus (pc) (match_dup 0))
102 (eq_attr "type" "bitbranch")
103 (if_then_else (and (ge (minus (match_dup 0) (pc))
105 (le (minus (match_dup 0) (pc))
107 (plus (symbol_ref "h8300_insn_length_from_table (insn, operands)")
109 (if_then_else (and (eq_attr "cpu" "h8300h")
110 (and (ge (minus (pc) (match_dup 0))
112 (le (minus (pc) (match_dup 0))
114 (plus (symbol_ref "h8300_insn_length_from_table (insn, operands)")
116 (plus (symbol_ref "h8300_insn_length_from_table (insn, operands)")
118 (eq_attr "length_table" "!none")
119 (symbol_ref "h8300_insn_length_from_table (insn, operands)")]
122 ;; Condition code settings.
124 ;; none - insn does not affect cc
125 ;; none_0hit - insn does not affect cc but it does modify operand 0
126 ;; This attribute is used to keep track of when operand 0 changes.
127 ;; See the description of NOTICE_UPDATE_CC for more info.
128 ;; set_znv - insn sets z,n,v to usable values (like a tst insn); c is unknown.
129 ;; set_zn - insn sets z,n to usable values; v,c are unknown.
130 ;; compare - compare instruction
131 ;; clobber - value of cc is unknown
133 (define_attr "cc" "none,none_0hit,set_znv,set_zn,compare,clobber"
134 (const_string "clobber"))
136 ;; Type of delay slot. NONE means the instruction has no delay slot.
137 ;; JUMP means it is an unconditional jump that (if short enough)
138 ;; could be implemented using bra/s.
140 (define_attr "delay_slot" "none,jump"
141 (const_string "none"))
143 ;; "yes" if the instruction can be put into a delay slot. It's not
144 ;; entirely clear that jsr is not valid in delay slots, but it
145 ;; definitely doesn't have the effect of causing the called function
146 ;; to return to the target of the delayed branch.
148 (define_attr "can_delay" "no,yes"
149 (cond [(eq_attr "type" "branch,bitbranch,call")
151 (geu (symbol_ref "get_attr_length (insn)") (const_int 2))
153 (const_string "yes")))
155 ;; Only allow jumps to have a delay slot if we think they might
156 ;; be short enough. This is just an optimization: we don't know
157 ;; for certain whether they will be or not.
159 (define_delay (and (eq_attr "delay_slot" "jump")
160 (eq (symbol_ref "get_attr_length (insn)") (const_int 2)))
161 [(eq_attr "can_delay" "yes")
165 ;; Provide the maximum length of an assembly instruction in an asm
166 ;; statement. The maximum length of 14 bytes is achieved on H8SX.
168 (define_asm_attributes
169 [(set (attr "length")
170 (cond [(match_test "TARGET_H8300H") (const_int 10)
171 (match_test "TARGET_H8300S") (const_int 10)]
174 (include "predicates.md")
175 (include "constraints.md")
177 ;; ----------------------------------------------------------------------
179 ;; ----------------------------------------------------------------------
181 ;; This mode iterator allows :P to be used for patterns that operate on
182 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
184 (define_mode_iterator P [(HI "Pmode == HImode") (SI "Pmode == SImode")])
186 (define_mode_iterator QHI [QI HI])
188 (define_mode_iterator HSI [HI SI])
190 (define_mode_iterator QHSI [QI HI SI])
192 (define_mode_iterator QHSIF [QI HI SI SF])
194 (define_code_iterator shifts [ashift ashiftrt lshiftrt])
196 (define_code_iterator ors [ior xor])
198 ;; ----------------------------------------------------------------------
200 ;; ----------------------------------------------------------------------
204 (define_insn "*movqi_h8nosx"
205 [(set (match_operand:QI 0 "general_operand_dst" "=r,r ,<,r,r,m")
206 (match_operand:QI 1 "general_operand_src" " I,r>,r,n,m,r"))]
208 && h8300_move_ok (operands[0], operands[1])"
216 [(set (attr "length")
217 (symbol_ref "compute_mov_length (operands)"))
218 (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
220 (define_insn "*movqi_h8sx"
221 [(set (match_operand:QI 0 "general_operand_dst" "=Z,rQ")
222 (match_operand:QI 1 "general_operand_src" "P4>X,rQi"))]
227 [(set_attr "length_table" "mov_imm4,movb")
228 (set_attr "cc" "set_znv")])
230 (define_expand "mov<mode>"
231 [(set (match_operand:QHSIF 0 "general_operand_dst" "")
232 (match_operand:QHSIF 1 "general_operand_src" ""))]
235 enum machine_mode mode = <MODE>mode;
238 /* Other H8 chips, except the H8/SX family can only handle a
239 single memory operand, which is checked by h8300_move_ok.
241 We could perhaps have h8300_move_ok handle the H8/SX better
242 and just remove the !TARGET_H8300SX conditional. */
243 if (!h8300_move_ok (operands[0], operands[1]))
244 operands[1] = copy_to_mode_reg (mode, operand1);
248 (define_insn "movstrictqi"
249 [(set (strict_low_part (match_operand:QI 0 "general_operand_dst" "+r,r"))
250 (match_operand:QI 1 "general_operand_src" "I,rmi>"))]
255 [(set_attr "length" "2,*")
256 (set_attr "length_table" "*,movb")
257 (set_attr "cc" "set_zn,set_znv")])
261 (define_insn "*movhi_h8nosx"
262 [(set (match_operand:HI 0 "general_operand_dst" "=r,r,<,r,r,m")
263 (match_operand:HI 1 "general_operand_src" "I,r>,r,i,m,r"))]
265 && h8300_move_ok (operands[0], operands[1])"
273 [(set (attr "length")
274 (symbol_ref "compute_mov_length (operands)"))
275 (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
277 (define_insn "*movhi_h8sx"
278 [(set (match_operand:HI 0 "general_operand_dst" "=r,r,Z,Q,rQ")
279 (match_operand:HI 1 "general_operand_src" "I,P3>X,P4>X,IP8>X,rQi"))]
287 [(set_attr "length_table" "*,*,mov_imm4,short_immediate,movw")
288 (set_attr "length" "2,2,*,*,*")
289 (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv")])
291 (define_insn "movstricthi"
292 [(set (strict_low_part (match_operand:HI 0 "general_operand_dst" "+r,r,r"))
293 (match_operand:HI 1 "general_operand_src" "I,P3>X,rmi"))]
299 [(set_attr "length" "2,2,*")
300 (set_attr "length_table" "*,*,movw")
301 (set_attr "cc" "set_zn,set_znv,set_znv")])
304 (define_insn "*movsi_h8300hs"
305 [(set (match_operand:SI 0 "general_operand_dst" "=r,r,r,<,r,r,m,*a,*a,r")
306 (match_operand:SI 1 "general_operand_src" "I,r,i,r,>,m,r,I,r,*a"))]
307 "(TARGET_H8300S || TARGET_H8300H) && !TARGET_H8300SX
308 && h8300_move_ok (operands[0], operands[1])"
310 switch (which_alternative)
313 return "sub.l %S0,%S0";
317 return "clrmac\;ldmac %1,macl";
319 return "stmac macl,%0";
321 if (GET_CODE (operands[1]) == CONST_INT)
323 int val = INTVAL (operands[1]);
325 /* Look for constants which can be made by adding an 8-bit
326 number to zero in one of the two low bytes. */
327 if (val == (val & 0xff))
329 operands[1] = GEN_INT ((char) val & 0xff);
330 return "sub.l\\t%S0,%S0\;add.b\\t%1,%w0";
333 if (val == (val & 0xff00))
335 operands[1] = GEN_INT ((char) (val >> 8) & 0xff);
336 return "sub.l\\t%S0,%S0\;add.b\\t%1,%x0";
339 /* Look for constants that can be obtained by subs, inc, and
341 switch (val & 0xffffffff)
344 return "sub.l\\t%S0,%S0\;subs\\t#1,%S0";
346 return "sub.l\\t%S0,%S0\;subs\\t#2,%S0";
348 return "sub.l\\t%S0,%S0\;subs\\t#4,%S0";
351 return "sub.l\\t%S0,%S0\;dec.w\\t#1,%f0";
353 return "sub.l\\t%S0,%S0\;dec.w\\t#2,%f0";
356 return "sub.l\\t%S0,%S0\;dec.w\\t#1,%e0";
358 return "sub.l\\t%S0,%S0\;dec.w\\t#2,%e0";
361 return "sub.l\\t%S0,%S0\;inc.w\\t#1,%e0";
363 return "sub.l\\t%S0,%S0\;inc.w\\t#2,%e0";
367 return "mov.l %S1,%S0";
369 [(set (attr "length")
370 (symbol_ref "compute_mov_length (operands)"))
371 (set_attr "cc" "set_zn,set_znv,clobber,set_znv,set_znv,set_znv,set_znv,none_0hit,none_0hit,set_znv")])
373 (define_insn "*movsi_h8sx"
374 [(set (match_operand:SI 0 "general_operand_dst" "=r,r,Q,rQ,*a,*a,r")
375 (match_operand:SI 1 "general_operand_src" "I,P3>X,IP8>X,rQi,I,r,*a"))]
383 clrmac\;ldmac %1,macl
385 [(set_attr "length_table" "*,*,short_immediate,movl,*,*,*")
386 (set_attr "length" "2,2,*,*,2,6,4")
387 (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,none_0hit,none_0hit,set_znv")])
389 (define_insn "*movsf_h8sx"
390 [(set (match_operand:SF 0 "general_operand_dst" "=r,rQ")
391 (match_operand:SF 1 "general_operand_src" "G,rQi"))]
396 [(set_attr "length" "2,*")
397 (set_attr "length_table" "*,movl")
398 (set_attr "cc" "set_zn,set_znv")])
402 (define_insn "*movsf_h8300hs"
403 [(set (match_operand:SF 0 "general_operand_dst" "=r,r,r,m,<,r")
404 (match_operand:SF 1 "general_operand_src" "G,r,im,r,r,>"))]
406 && (register_operand (operands[0], SFmode)
407 || register_operand (operands[1], SFmode))"
415 [(set (attr "length")
416 (symbol_ref "compute_mov_length (operands)"))
417 (set_attr "cc" "set_zn,set_znv,set_znv,set_znv,set_znv,set_znv")])
419 ;; ----------------------------------------------------------------------
421 ;; ----------------------------------------------------------------------
423 (define_insn "*push1_h8300hs_<QHI:mode>"
427 (plus:P (reg:P SP_REG) (const_int -4))))
428 (match_operand:QHI 0 "register_no_sp_elim_operand" "r"))]
431 [(set_attr "length" "4")])
434 ;; ----------------------------------------------------------------------
436 ;; ----------------------------------------------------------------------
438 (define_insn_and_split "*tst_extzv_1_n"
440 (compare (zero_extract:SI (match_operand:QI 0 "general_operand_src" "r,U,mn>")
442 (match_operand 1 "const_int_operand" "n,n,n"))
444 (clobber (match_scratch:QI 2 "=X,X,&r"))]
451 && !satisfies_constraint_U (operands[0])"
454 (parallel [(set (cc0) (compare (zero_extract:SI (match_dup 2)
458 (clobber (scratch:QI))])]
460 [(set_attr "length" "2,8,10")
461 (set_attr "cc" "set_zn,set_zn,set_zn")])
465 (compare (zero_extract:HSI (match_operand:HSI 0 "register_operand" "r")
467 (match_operand 1 "const_int_operand" "n"))
469 "INTVAL (operands[1]) <= 15"
471 [(set_attr "length" "2")
472 (set_attr "cc" "set_zn")])
474 (define_insn_and_split "*tstsi_upper_bit"
476 (compare (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
478 (match_operand 1 "const_int_operand" "n"))
480 (clobber (match_scratch:SI 2 "=&r"))]
481 "INTVAL (operands[1]) >= 16"
483 "&& reload_completed"
485 (ior:SI (and:SI (match_dup 2)
487 (lshiftrt:SI (match_dup 0)
490 (compare (zero_extract:SI (match_dup 2)
495 operands[3] = GEN_INT (INTVAL (operands[1]) - 16);
498 (define_insn "*tstsi_variable_bit"
500 (compare (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
502 (and:SI (match_operand:SI 1 "register_operand" "r")
507 [(set_attr "length" "2")
508 (set_attr "cc" "set_zn")])
510 (define_insn_and_split "*tstsi_variable_bit_qi"
512 (compare (zero_extract:SI (zero_extend:SI (match_operand:QI 0 "general_operand_src" "r,U,mn>"))
514 (and:SI (match_operand:SI 1 "register_operand" "r,r,r")
517 (clobber (match_scratch:QI 2 "=X,X,&r"))]
524 && !satisfies_constraint_U (operands[0])"
527 (parallel [(set (cc0)
528 (compare (zero_extract:SI (zero_extend:SI (match_dup 2))
530 (and:SI (match_dup 1)
533 (clobber (scratch:QI))])]
535 [(set_attr "length" "2,8,10")
536 (set_attr "cc" "set_zn,set_zn,set_zn")])
538 (define_insn "*tst<mode>"
540 (compare (match_operand:QHI 0 "register_operand" "r")
544 if (<MODE>mode == QImode)
545 return "mov.b %X0,%X0";
546 else if (<MODE>mode == HImode)
547 return "mov.w %T0,%T0";
550 [(set_attr "length" "2")
551 (set_attr "cc" "set_znv")])
553 (define_insn "*tsthi_upper"
555 (compare (and:HI (match_operand:HI 0 "register_operand" "r")
560 [(set_attr "length" "2")
561 (set_attr "cc" "set_znv")])
563 (define_insn "*tstsi"
565 (compare (match_operand:SI 0 "register_operand" "r")
569 [(set_attr "length" "2")
570 (set_attr "cc" "set_znv")])
572 (define_insn "*tstsi_upper"
574 (compare (and:SI (match_operand:SI 0 "register_operand" "r")
579 [(set_attr "length" "2")
580 (set_attr "cc" "set_znv")])
582 (define_insn "*cmpqi"
584 (compare (match_operand:QI 0 "h8300_dst_operand" "rQ")
585 (match_operand:QI 1 "h8300_src_operand" "rQi")))]
588 [(set_attr "length_table" "add")
589 (set_attr "cc" "compare")])
591 (define_insn "*cmphi_h8300hs_znvc"
593 (compare (match_operand:HI 0 "h8300_dst_operand" "rU,rQ")
594 (match_operand:HI 1 "h8300_src_operand" "P3>X,rQi")))]
597 switch (which_alternative)
601 return "cmp.w %T1,%T0";
603 return "cmp.w %T1:3,%T0";
605 return "cmp.w %T1,%T0";
610 [(set_attr "length_table" "short_immediate,add")
611 (set_attr "cc" "compare,compare")])
615 (compare (match_operand:SI 0 "h8300_dst_operand" "r,rQ")
616 (match_operand:SI 1 "h8300_src_operand" "P3>X,rQi")))]
619 switch (which_alternative)
623 return "cmp.l %S1,%S0";
625 return "cmp.l %S1:3,%S0";
627 return "cmp.l %S1,%S0";
632 [(set_attr "length" "2,*")
633 (set_attr "length_table" "*,add")
634 (set_attr "cc" "compare,compare")])
636 ;; ----------------------------------------------------------------------
638 ;; ----------------------------------------------------------------------
640 (define_expand "add<mode>3"
641 [(set (match_operand:QHSI 0 "register_operand" "")
642 (plus:QHSI (match_operand:QHSI 1 "register_operand" "")
643 (match_operand:QHSI 2 "h8300_src_operand" "")))]
647 (define_insn "*addqi3"
648 [(set (match_operand:QI 0 "h8300_dst_operand" "=rQ")
649 (plus:QI (match_operand:QI 1 "h8300_dst_operand" "%0")
650 (match_operand:QI 2 "h8300_src_operand" "rQi")))]
651 "h8300_operands_match_p (operands)"
653 [(set_attr "length_table" "add")
654 (set_attr "cc" "set_zn")])
656 (define_insn "*addhi3_h8300hs"
657 [(set (match_operand:HI 0 "register_operand" "=r,r,r,r,r")
658 (plus:HI (match_operand:HI 1 "register_operand" "%0,0,0,0,0")
659 (match_operand:HI 2 "h8300_src_operand" "L,N,J,n,r")))]
667 [(set_attr "length" "2,2,2,4,2")
668 (set_attr "cc" "none_0hit,none_0hit,clobber,set_zn,set_zn")])
670 (define_insn "*add<mode>3_incdec"
671 [(set (match_operand:HSI 0 "register_operand" "=r,r")
672 (unspec:HSI [(match_operand:HSI 1 "register_operand" "0,0")
673 (match_operand:HSI 2 "incdec_operand" "M,O")]
677 if (which_alternative == 0)
678 return <MODE>mode == HImode ? "inc.w\t%2,%T0" : "inc.l\t%2,%S0";
679 else if (which_alternative == 1)
680 return <MODE>mode == HImode ? "dec.w\t%G2,%T0" : "dec.l\t%G2,%S0";
683 [(set_attr "length" "2,2")
684 (set_attr "cc" "set_zn,set_zn")])
686 (define_insn "*addhi3_h8sx"
687 [(set (match_operand:HI 0 "h8300_dst_operand" "=rU,rU,r,rQ")
688 (plus:HI (match_operand:HI 1 "h8300_dst_operand" "%0,0,0,0")
689 (match_operand:HI 2 "h8300_src_operand" "P3>X,P3<X,J,rQi")))]
690 "TARGET_H8300SX && h8300_operands_match_p (operands)"
696 [(set_attr "length_table" "short_immediate,short_immediate,*,add")
697 (set_attr "length" "*,*,2,*")
698 (set_attr "cc" "set_zn")])
701 [(set (match_operand:HSI 0 "register_operand" "")
702 (plus:HSI (match_dup 0)
703 (match_operand:HSI 1 "two_insn_adds_subs_operand" "")))]
707 split_adds_subs (<MODE>mode, operands);
712 (define_insn "*addsi_h8300hs"
713 [(set (match_operand:SI 0 "h8300_dst_operand" "=rQ,rQ")
714 (plus:SI (match_operand:SI 1 "h8300_dst_operand" "%0,0")
715 (match_operand:SI 2 "h8300_src_operand" "i,rQ")))]
716 "h8300_operands_match_p (operands)"
718 return output_plussi (operands);
720 [(set (attr "length")
721 (symbol_ref "compute_plussi_length (operands)"))
723 (symbol_ref "compute_plussi_cc (operands)"))])
725 ;; ----------------------------------------------------------------------
726 ;; SUBTRACT INSTRUCTIONS
727 ;; ----------------------------------------------------------------------
729 (define_expand "sub<mode>3"
730 [(set (match_operand:QHSI 0 "register_operand" "")
731 (minus:QHSI (match_operand:QHSI 1 "register_operand" "")
732 (match_operand:QHSI 2 "h8300_src_operand" "")))]
737 (define_insn "*subqi3"
738 [(set (match_operand:QI 0 "h8300_dst_operand" "=rQ")
739 (minus:QI (match_operand:QI 1 "h8300_dst_operand" "0")
740 (match_operand:QI 2 "h8300_dst_operand" "rQ")))]
741 "h8300_operands_match_p (operands)"
743 [(set_attr "length_table" "add")
744 (set_attr "cc" "set_zn")])
746 (define_insn "*sub<mode>3_h8300hs"
747 [(set (match_operand:HSI 0 "h8300_dst_operand" "=rQ,rQ")
748 (minus:HSI (match_operand:HSI 1 "h8300_dst_operand" "0,0")
749 (match_operand:HSI 2 "h8300_src_operand" "rQ,i")))]
750 "h8300_operands_match_p (operands)"
752 if (<MODE>mode == HImode)
753 return "sub.w %T2,%T0";
754 else if (<MODE>mode == SImode)
755 return "sub.l %S2,%S0";
758 [(set_attr "length_table" "add")
759 (set_attr "cc" "set_zn")])
762 ;; ----------------------------------------------------------------------
763 ;; MULTIPLY INSTRUCTIONS
764 ;; ----------------------------------------------------------------------
766 ;; Note that the H8/300 can only handle umulqihi3.
768 (define_expand "mulqihi3"
769 [(set (match_operand:HI 0 "register_operand" "")
770 (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" ""))
771 ;; intentionally-mismatched modes
772 (match_operand:QI 2 "reg_or_nibble_operand" "")))]
775 if (GET_MODE (operands[2]) != VOIDmode)
776 operands[2] = gen_rtx_SIGN_EXTEND (HImode, operands[2]);
779 (define_insn "*mulqihi3_const"
780 [(set (match_operand:HI 0 "register_operand" "=r")
781 (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "%0"))
782 (match_operand:QI 2 "nibble_operand" "IP4>X")))]
785 [(set_attr "length" "4")
786 (set_attr "cc" "set_zn")])
788 (define_insn "*mulqihi3"
789 [(set (match_operand:HI 0 "register_operand" "=r")
790 (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "%0"))
791 (sign_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
794 [(set_attr "length" "4")
795 (set_attr "cc" "set_zn")])
797 (define_expand "mulhisi3"
798 [(set (match_operand:SI 0 "register_operand" "")
799 (mult:SI (sign_extend:SI (match_operand:HI 1 "register_operand" ""))
800 ;; intentionally-mismatched modes
801 (match_operand:HI 2 "reg_or_nibble_operand" "")))]
804 if (GET_MODE (operands[2]) != VOIDmode)
805 operands[2] = gen_rtx_SIGN_EXTEND (SImode, operands[2]);
808 (define_insn "*mulhisi3_const"
809 [(set (match_operand:SI 0 "register_operand" "=r")
810 (mult:SI (sign_extend:SI (match_operand:HI 1 "register_operand" "%0"))
811 (match_operand:SI 2 "nibble_operand" "IP4>X")))]
814 [(set_attr "length" "4")
815 (set_attr "cc" "set_zn")])
817 (define_insn "*mulhisi3"
818 [(set (match_operand:SI 0 "register_operand" "=r")
819 (mult:SI (sign_extend:SI (match_operand:HI 1 "register_operand" "%0"))
820 (sign_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
823 [(set_attr "length" "4")
824 (set_attr "cc" "set_zn")])
826 (define_expand "umulqihi3"
827 [(set (match_operand:HI 0 "register_operand" "")
828 (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" ""))
829 ;; intentionally-mismatched modes
830 (match_operand:QI 2 "reg_or_nibble_operand" "")))]
833 if (GET_MODE (operands[2]) != VOIDmode)
834 operands[2] = gen_rtx_ZERO_EXTEND (HImode, operands[2]);
837 (define_insn "*umulqihi3_const"
838 [(set (match_operand:HI 0 "register_operand" "=r")
839 (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "%0"))
840 (match_operand:QI 2 "nibble_operand" "IP4>X")))]
843 [(set_attr "length" "4")
844 (set_attr "cc" "set_zn")])
846 (define_insn "*umulqihi3"
847 [(set (match_operand:HI 0 "register_operand" "=r")
848 (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "%0"))
849 (zero_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
852 [(set_attr "length" "2")
853 (set_attr "cc" "none_0hit")])
855 (define_expand "umulhisi3"
856 [(set (match_operand:SI 0 "register_operand" "")
857 (mult:SI (zero_extend:SI (match_operand:HI 1 "register_operand" ""))
858 ;; intentionally-mismatched modes
859 (match_operand:HI 2 "reg_or_nibble_operand" "")))]
862 if (GET_MODE (operands[2]) != VOIDmode)
863 operands[2] = gen_rtx_ZERO_EXTEND (SImode, operands[2]);
866 (define_insn "*umulhisi3_const"
867 [(set (match_operand:SI 0 "register_operand" "=r")
868 (mult:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "%0"))
869 (match_operand:SI 2 "nibble_operand" "IP4>X")))]
872 [(set_attr "length" "4")
873 (set_attr "cc" "set_zn")])
875 (define_insn "*umulhisi3"
876 [(set (match_operand:SI 0 "register_operand" "=r")
877 (mult:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "%0"))
878 (zero_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
881 [(set_attr "length" "2")
882 (set_attr "cc" "none_0hit")])
884 ;; We could have used mulu.[wl] here, but mulu.[lw] is only available
885 ;; on a H8SX with a multiplier, whereas muls.w seems to be available
886 ;; on all H8SX variants.
888 (define_insn "mul<mode>3"
889 [(set (match_operand:HSI 0 "register_operand" "=r")
890 (mult:HSI (match_operand:HSI 1 "register_operand" "%0")
891 (match_operand:HSI 2 "reg_or_nibble_operand" "r IP4>X")))]
893 { return <MODE>mode == HImode ? "muls.w\\t%T2,%T0" : "muls.l\\t%S2,%S0"; }
894 [(set_attr "length" "4")
895 (set_attr "cc" "set_zn")])
897 (define_insn "smulsi3_highpart"
898 [(set (match_operand:SI 0 "register_operand" "=r")
902 (sign_extend:DI (match_operand:SI 1 "register_operand" "%0"))
903 (sign_extend:DI (match_operand:SI 2 "reg_or_nibble_operand" "r IP4>X")))
907 [(set_attr "length" "4")
908 (set_attr "cc" "set_zn")])
910 (define_insn "umulsi3_highpart"
911 [(set (match_operand:SI 0 "register_operand" "=r")
915 (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
916 (zero_extend:DI (match_operand:SI 2 "reg_or_nibble_operand" "r IP4>X")))
920 [(set_attr "length" "4")
921 (set_attr "cc" "none_0hit")])
923 ;; This is a "bridge" instruction. Combine can't cram enough insns
924 ;; together to crate a MAC instruction directly, but it can create
925 ;; this instruction, which then allows combine to create the real
928 ;; Unfortunately, if combine doesn't create a MAC instruction, this
929 ;; insn must generate reasonably correct code. Egad.
932 [(set (match_operand:SI 0 "register_operand" "=a")
935 (mem:HI (post_inc:SI (match_operand:SI 1 "register_operand" "r"))))
937 (mem:HI (post_inc:SI (match_operand:SI 2 "register_operand" "r"))))))]
939 "clrmac\;mac @%2+,@%1+"
940 [(set_attr "length" "6")
941 (set_attr "cc" "none_0hit")])
944 [(set (match_operand:SI 0 "register_operand" "=a")
946 (sign_extend:SI (mem:HI
947 (post_inc:SI (match_operand:SI 1 "register_operand" "r"))))
948 (sign_extend:SI (mem:HI
949 (post_inc:SI (match_operand:SI 2 "register_operand" "r")))))
950 (match_operand:SI 3 "register_operand" "0")))]
953 [(set_attr "length" "4")
954 (set_attr "cc" "none_0hit")])
956 ;; ----------------------------------------------------------------------
957 ;; DIVIDE/MOD INSTRUCTIONS
958 ;; ----------------------------------------------------------------------
960 (define_insn "udiv<mode>3"
961 [(set (match_operand:HSI 0 "register_operand" "=r")
962 (udiv:HSI (match_operand:HSI 1 "register_operand" "0")
963 (match_operand:HSI 2 "reg_or_nibble_operand" "r IP4>X")))]
965 { return <MODE>mode == HImode ? "divu.w\\t%T2,%T0" : "divu.l\\t%S2,%S0"; }
966 [(set_attr "length" "4")])
968 (define_insn "div<mode>3"
969 [(set (match_operand:HSI 0 "register_operand" "=r")
970 (div:HSI (match_operand:HSI 1 "register_operand" "0")
971 (match_operand:HSI 2 "reg_or_nibble_operand" "r IP4>X")))]
973 { return <MODE>mode == HImode ? "divs.w\\t%T2,%T0" : "divs.l\\t%S2,%S0"; }
974 [(set_attr "length" "4")])
976 (define_insn "udivmodqi4"
977 [(set (match_operand:QI 0 "register_operand" "=r")
980 (match_operand:HI 1 "register_operand" "0")
981 (zero_extend:HI (match_operand:QI 2 "register_operand" "r")))))
982 (set (match_operand:QI 3 "register_operand" "=r")
986 (zero_extend:HI (match_dup 2)))))]
989 if (find_reg_note (insn, REG_UNUSED, operands[3]))
990 return "divxu.b\\t%X2,%T0";
992 return "divxu.b\\t%X2,%T0\;mov.b\\t%t0,%s3";
994 [(set_attr "length" "4")])
996 (define_insn "divmodqi4"
997 [(set (match_operand:QI 0 "register_operand" "=r")
1000 (match_operand:HI 1 "register_operand" "0")
1001 (sign_extend:HI (match_operand:QI 2 "register_operand" "r")))))
1002 (set (match_operand:QI 3 "register_operand" "=r")
1006 (sign_extend:HI (match_dup 2)))))]
1009 if (find_reg_note (insn, REG_UNUSED, operands[3]))
1010 return "divxs.b\\t%X2,%T0";
1012 return "divxs.b\\t%X2,%T0\;mov.b\\t%t0,%s3";
1014 [(set_attr "length" "6")])
1016 (define_insn "udivmodhi4"
1017 [(set (match_operand:HI 0 "register_operand" "=r")
1020 (match_operand:SI 1 "register_operand" "0")
1021 (zero_extend:SI (match_operand:HI 2 "register_operand" "r")))))
1022 (set (match_operand:HI 3 "register_operand" "=r")
1026 (zero_extend:SI (match_dup 2)))))]
1029 if (find_reg_note (insn, REG_UNUSED, operands[3]))
1030 return "divxu.w\\t%T2,%S0";
1032 return "divxu.w\\t%T2,%S0\;mov.w\\t%e0,%f3";
1034 [(set_attr "length" "4")])
1036 (define_insn "divmodhi4"
1037 [(set (match_operand:HI 0 "register_operand" "=r")
1040 (match_operand:SI 1 "register_operand" "0")
1041 (sign_extend:SI (match_operand:HI 2 "register_operand" "r")))))
1042 (set (match_operand:HI 3 "register_operand" "=r")
1046 (sign_extend:SI (match_dup 2)))))]
1049 if (find_reg_note (insn, REG_UNUSED, operands[3]))
1050 return "divxs.w\\t%T2,%S0";
1052 return "divxs.w\\t%T2,%S0\;mov.w\\t%e0,%f3";
1054 [(set_attr "length" "6")])
1056 ;; ----------------------------------------------------------------------
1058 ;; ----------------------------------------------------------------------
1060 (define_insn "bclrqi_msx"
1061 [(set (match_operand:QI 0 "bit_register_indirect_operand" "=WU")
1062 (and:QI (match_operand:QI 1 "bit_register_indirect_operand" "%0")
1063 (match_operand:QI 2 "single_zero_operand" "Y0")))]
1064 "TARGET_H8300SX && rtx_equal_p (operands[0], operands[1])"
1066 [(set_attr "length" "8")])
1069 [(set (match_operand:HI 0 "bit_register_indirect_operand")
1070 (and:HI (match_operand:HI 1 "bit_register_indirect_operand")
1071 (match_operand:HI 2 "single_zero_operand")))]
1074 (and:QI (match_dup 1)
1077 if (abs (INTVAL (operands[2])) > 0xFF)
1079 operands[0] = adjust_address (operands[0], QImode, 0);
1080 operands[1] = adjust_address (operands[1], QImode, 0);
1081 operands[2] = GEN_INT ((INTVAL (operands[2])) >> 8);
1085 operands[0] = adjust_address (operands[0], QImode, 1);
1086 operands[1] = adjust_address (operands[1], QImode, 1);
1090 (define_insn "bclrhi_msx"
1091 [(set (match_operand:HI 0 "bit_register_indirect_operand" "=m")
1092 (and:HI (match_operand:HI 1 "bit_register_indirect_operand" "%0")
1093 (match_operand:HI 2 "single_zero_operand" "Y0")))]
1096 [(set_attr "length" "8")])
1098 (define_insn "*andqi3_2"
1099 [(set (match_operand:QI 0 "bit_operand" "=U,rQ,r")
1100 (and:QI (match_operand:QI 1 "bit_operand" "%0,0,WU")
1101 (match_operand:QI 2 "h8300_src_operand" "Y0,rQi,IP1>X")))]
1107 [(set_attr "length" "8,*,8")
1108 (set_attr "length_table" "*,logicb,*")
1109 (set_attr "cc" "none_0hit,set_znv,none_0hit")])
1111 (define_insn "andqi3_1"
1112 [(set (match_operand:QI 0 "bit_operand" "=U,r")
1113 (and:QI (match_operand:QI 1 "bit_operand" "%0,0")
1114 (match_operand:QI 2 "h8300_src_operand" "Y0,rn")))]
1115 "register_operand (operands[0], QImode)
1116 || single_zero_operand (operands[2], QImode)"
1120 [(set_attr "length" "2,8")
1121 (set_attr "cc" "none_0hit,set_znv")])
1123 (define_expand "and<mode>3"
1124 [(set (match_operand:QHSI 0 "register_operand" "")
1125 (and:QHSI (match_operand:QHSI 1 "register_operand" "")
1126 (match_operand:QHSI 2 "h8300_src_operand" "")))]
1130 (define_insn "*andor<mode>3"
1131 [(set (match_operand:QHSI 0 "register_operand" "=r")
1132 (ior:QHSI (and:QHSI (match_operand:QHSI 2 "register_operand" "r")
1133 (match_operand:QHSI 3 "single_one_operand" "n"))
1134 (match_operand:QHSI 1 "register_operand" "0")))]
1135 "(<MODE>mode == QImode
1136 || <MODE>mode == HImode
1137 || (<MODE>mode == SImode
1138 && (INTVAL (operands[3]) & 0xffff) != 0))"
1140 if (<MODE>mode == QImode)
1141 return "bld\\t%V3,%X2\;bor\\t%V3,%X0\;bst\\t%V3,%X0";
1143 if (<MODE>mode == HImode)
1145 operands[3] = GEN_INT (INTVAL (operands[3]) & 0xffff);
1146 if (INTVAL (operands[3]) > 128)
1148 operands[3] = GEN_INT (INTVAL (operands[3]) >> 8);
1149 return "bld\\t%V3,%t2\;bor\\t%V3,%t0\;bst\\t%V3,%t0";
1151 return "bld\\t%V3,%s2\;bor\\t%V3,%s0\;bst\\t%V3,%s0";
1154 if (<MODE>mode == SImode)
1156 operands[3] = GEN_INT (INTVAL (operands[3]) & 0xffff);
1157 if (INTVAL (operands[3]) > 128)
1159 operands[3] = GEN_INT (INTVAL (operands[3]) >> 8);
1160 return "bld\\t%V3,%x2\;bor\\t%V3,%x0\;bst\\t%V3,%x0";
1162 return "bld\\t%V3,%w2\;bor\\t%V3,%w0\;bst\\t%V3,%w0";
1168 [(set_attr "length" "6")])
1170 (define_insn "*andorsi3_shift_8"
1171 [(set (match_operand:SI 0 "register_operand" "=r")
1172 (ior:SI (and:SI (ashift:SI (match_operand:SI 2 "register_operand" "r")
1175 (match_operand:SI 1 "register_operand" "0")))]
1178 [(set_attr "length" "2")])
1180 ;; ----------------------------------------------------------------------
1181 ;; OR/XOR INSTRUCTIONS
1182 ;; ----------------------------------------------------------------------
1184 (define_insn "b<code>qi_msx"
1185 [(set (match_operand:QI 0 "bit_register_indirect_operand" "=WU")
1186 (ors:QI (match_operand:QI 1 "bit_register_indirect_operand" "%0")
1187 (match_operand:QI 2 "single_one_operand" "Y2")))]
1188 "TARGET_H8300SX && rtx_equal_p (operands[0], operands[1])"
1189 { return <CODE> == IOR ? "bset\\t%V2,%0" : "bnot\\t%V2,%0"; }
1190 [(set_attr "length" "8")])
1192 (define_insn "b<code>hi_msx"
1193 [(set (match_operand:HI 0 "bit_register_indirect_operand" "=m")
1194 (ors:HI (match_operand:HI 1 "bit_register_indirect_operand" "%0")
1195 (match_operand:HI 2 "single_one_operand" "Y2")))]
1197 { return <CODE> == IOR ? "bset\\t%V2,%0" : "bnot\\t%V2,%0"; }
1198 [(set_attr "length" "8")])
1200 (define_insn "<code>qi3_1"
1201 [(set (match_operand:QI 0 "bit_operand" "=U,rQ")
1202 (ors:QI (match_operand:QI 1 "bit_operand" "%0,0")
1203 (match_operand:QI 2 "h8300_src_operand" "Y2,rQi")))]
1204 "TARGET_H8300SX || register_operand (operands[0], QImode)
1205 || single_one_operand (operands[2], QImode)"
1207 if (which_alternative == 0)
1208 return <CODE> == IOR ? "bset\\t%V2,%R0" : "bnot\\t%V2,%R0";
1209 else if (which_alternative == 1)
1210 return <CODE> == IOR ? "or\\t%X2,%X0" : "xor\\t%X2,%X0";
1213 [(set_attr "length" "8,*")
1214 (set_attr "length_table" "*,logicb")
1215 (set_attr "cc" "none_0hit,set_znv")])
1217 (define_expand "<code><mode>3"
1218 [(set (match_operand:QHSI 0 "register_operand" "")
1219 (ors:QHSI (match_operand:QHSI 1 "register_operand" "")
1220 (match_operand:QHSI 2 "h8300_src_operand" "")))]
1224 ;; ----------------------------------------------------------------------
1225 ;; {AND,IOR,XOR}{HI3,SI3} PATTERNS
1226 ;; ----------------------------------------------------------------------
1228 (define_insn "*logical<mode>3"
1229 [(set (match_operand:HSI 0 "h8300_dst_operand" "=rQ")
1230 (match_operator:HSI 3 "bit_operator"
1231 [(match_operand:HSI 1 "h8300_dst_operand" "%0")
1232 (match_operand:HSI 2 "h8300_src_operand" "rQi")]))]
1233 "h8300_operands_match_p (operands)"
1234 { return output_logical_op (<MODE>mode, operands); }
1235 [(set (attr "length")
1236 (symbol_ref "compute_logical_op_length (<MODE>mode, operands)"))
1238 (symbol_ref "compute_logical_op_cc (<MODE>mode, operands)"))])
1240 ;; ----------------------------------------------------------------------
1241 ;; NEGATION INSTRUCTIONS
1242 ;; ----------------------------------------------------------------------
1244 (define_expand "neg<mode>2"
1245 [(set (match_operand:QHSIF 0 "register_operand" "")
1246 (neg:QHSIF (match_operand:QHSIF 1 "register_operand" "")))]
1250 (define_insn "*neg<mode>2"
1251 [(set (match_operand:QHSI 0 "h8300_dst_operand" "=rQ")
1252 (neg:QHSI (match_operand:QHSI 1 "h8300_dst_operand" "0")))]
1255 if (<MODE>mode == E_QImode)
1257 if (<MODE>mode == E_HImode)
1259 if (<MODE>mode == E_SImode)
1263 [(set_attr "length_table" "unary")
1264 (set_attr "cc" "set_zn")])
1267 (define_insn "*negsf2_h8300hs"
1268 [(set (match_operand:SF 0 "register_operand" "=r")
1269 (neg:SF (match_operand:SF 1 "register_operand" "0")))]
1271 "xor.w\\t#32768,%e0"
1272 [(set_attr "length" "4")])
1275 ;; ----------------------------------------------------------------------
1276 ;; ABSOLUTE VALUE INSTRUCTIONS
1277 ;; ----------------------------------------------------------------------
1279 (define_insn "abssf2"
1280 [(set (match_operand:SF 0 "register_operand" "=r")
1281 (abs:SF (match_operand:SF 1 "register_operand" "0")))]
1283 "and.w\\t#32767,%e0"
1284 [(set_attr "length" "4")])
1286 ;; ----------------------------------------------------------------------
1288 ;; ----------------------------------------------------------------------
1290 (define_insn "one_cmpl<mode>2"
1291 [(set (match_operand:QHSI 0 "h8300_dst_operand" "=rQ")
1292 (not:QHSI (match_operand:QHSI 1 "h8300_dst_operand" "0")))]
1295 if (<MODE>mode == E_QImode)
1297 if (<MODE>mode == E_HImode)
1299 if (<MODE>mode == E_SImode)
1303 [(set_attr "length_table" "unary")
1304 (set_attr "cc" "set_znv")])
1307 ;; ----------------------------------------------------------------------
1308 ;; JUMP INSTRUCTIONS
1309 ;; ----------------------------------------------------------------------
1311 ;; Conditional jump instructions
1313 (define_expand "cbranchqi4"
1314 [(use (match_operator 0 "ordered_comparison_operator"
1315 [(match_operand:QI 1 "h8300_dst_operand" "")
1316 (match_operand:QI 2 "h8300_src_operand" "")]))
1317 (use (match_operand 3 ""))]
1320 h8300_expand_branch (operands);
1324 (define_expand "cbranchhi4"
1325 [(use (match_operator 0 "ordered_comparison_operator"
1326 [(match_operand:HI 1 "h8300_dst_operand" "")
1327 (match_operand:HI 2 "h8300_src_operand" "")]))
1328 (use (match_operand 3 ""))]
1331 h8300_expand_branch (operands);
1335 (define_expand "cbranchsi4"
1336 [(use (match_operator 0 "ordered_comparison_operator"
1337 [(match_operand:SI 1 "h8300_dst_operand" "")
1338 (match_operand:SI 2 "h8300_src_operand" "")]))
1339 (use (match_operand 3 ""))]
1342 h8300_expand_branch (operands);
1346 (define_insn "branch_true"
1348 (if_then_else (match_operator 1 "comparison_operator"
1349 [(cc0) (const_int 0)])
1350 (label_ref (match_operand 0 "" ""))
1354 if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0
1355 && (GET_CODE (operands[1]) == GT
1356 || GET_CODE (operands[1]) == GE
1357 || GET_CODE (operands[1]) == LE
1358 || GET_CODE (operands[1]) == LT))
1360 cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
1364 if (get_attr_length (insn) == 2)
1366 else if (get_attr_length (insn) == 4)
1367 return "b%j1 %l0:16";
1369 return "b%k1 .Lh8BR%=\;jmp @%l0\\n.Lh8BR%=:";
1371 [(set_attr "type" "branch")
1372 (set_attr "cc" "none")])
1374 (define_insn "branch_false"
1376 (if_then_else (match_operator 1 "comparison_operator"
1377 [(cc0) (const_int 0)])
1379 (label_ref (match_operand 0 "" ""))))]
1382 if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0
1383 && (GET_CODE (operands[1]) == GT
1384 || GET_CODE (operands[1]) == GE
1385 || GET_CODE (operands[1]) == LE
1386 || GET_CODE (operands[1]) == LT))
1388 cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
1392 if (get_attr_length (insn) == 2)
1394 else if (get_attr_length (insn) == 4)
1395 return "b%k1 %l0:16";
1397 return "b%j1 .Lh8BR%=\;jmp @%l0\\n.Lh8BR%=:";
1399 [(set_attr "type" "branch")
1400 (set_attr "cc" "none")])
1402 (define_insn "*brabc"
1404 (if_then_else (eq (zero_extract (match_operand:QI 1 "bit_memory_operand" "WU")
1406 (match_operand:QI 2 "immediate_operand" "n"))
1408 (label_ref (match_operand 0 "" ""))
1412 switch (get_attr_length (insn)
1413 - h8300_insn_length_from_table (insn, operands))
1416 return "bra/bc %2,%R1,%l0";
1418 return "bra/bc %2,%R1,%l0:16";
1420 return "bra/bs %2,%R1,.Lh8BR%=\;jmp @%l0\\n.Lh8BR%=:";
1423 [(set_attr "type" "bitbranch")
1424 (set_attr "length_table" "bitbranch")
1425 (set_attr "cc" "none")])
1427 (define_insn "*brabs"
1429 (if_then_else (ne (zero_extract (match_operand:QI 1 "bit_memory_operand" "WU")
1431 (match_operand:QI 2 "immediate_operand" "n"))
1433 (label_ref (match_operand 0 "" ""))
1437 switch (get_attr_length (insn)
1438 - h8300_insn_length_from_table (insn, operands))
1441 return "bra/bs %2,%R1,%l0";
1443 return "bra/bs %2,%R1,%l0:16";
1445 return "bra/bc %2,%R1,.Lh8BR%=\;jmp @%l0\\n.Lh8BR%=:";
1448 [(set_attr "type" "bitbranch")
1449 (set_attr "length_table" "bitbranch")
1450 (set_attr "cc" "none")])
1452 ;; Unconditional and other jump instructions.
1456 (label_ref (match_operand 0 "" "")))]
1459 if (final_sequence != 0)
1461 if (get_attr_length (insn) == 2)
1465 /* The branch isn't short enough to use bra/s. Output the
1466 branch and delay slot in their normal order.
1468 If this is a backward branch, it will now be branching two
1469 bytes further than previously thought. The length-based
1470 test for bra vs. jump is very conservative though, so the
1471 branch will still be within range. */
1475 seq = final_sequence;
1477 final_scan_insn (seq->insn (1), asm_out_file, optimize, 1, & seen);
1478 final_scan_insn (seq->insn (0), asm_out_file, optimize, 1, & seen);
1479 seq->insn (1)->set_deleted ();
1483 else if (get_attr_length (insn) == 2)
1485 else if (get_attr_length (insn) == 4)
1486 return "bra %l0:16";
1490 [(set_attr "type" "branch")
1491 (set (attr "delay_slot")
1492 (if_then_else (match_test "TARGET_H8300SX")
1493 (const_string "jump")
1494 (const_string "none")))
1495 (set_attr "cc" "none")])
1497 ;; This is a define expand, because pointers may be either 16 or 32 bits.
1499 (define_expand "tablejump"
1500 [(parallel [(set (pc) (match_operand 0 "register_operand" ""))
1501 (use (label_ref (match_operand 1 "" "")))])]
1505 (define_insn "tablejump<mode>"
1506 [(set (pc) (match_operand:P 0 "register_operand" "r"))
1507 (use (label_ref (match_operand 1 "" "")))]
1510 if (<MODE>mode == E_HImode)
1512 if (<MODE>mode == E_SImode)
1516 [(set_attr "cc" "none")
1517 (set_attr "length" "2")])
1519 ;; This is a define expand, because pointers may be either 16 or 32 bits.
1521 (define_expand "indirect_jump"
1522 [(set (pc) (match_operand 0 "jump_address_operand" ""))]
1526 (define_insn "*indirect_jump_<mode>"
1527 [(set (pc) (match_operand:P 0 "jump_address_operand" "Vr"))]
1530 if (<MODE>mode == E_HImode)
1532 if (<MODE>mode == E_SImode)
1536 [(set_attr "cc" "none")
1537 (set_attr "length" "2")])
1539 ;; Call subroutine with no return value.
1541 ;; ??? Even though we use HImode here, this works on the H8/300H and H8S.
1543 (define_expand "call"
1544 [(call (match_operand:QI 0 "call_expander_operand" "")
1545 (match_operand 1 "general_operand" ""))]
1548 if (!register_operand (XEXP (operands[0], 0), Pmode)
1549 && GET_CODE (XEXP (operands[0], 0)) != SYMBOL_REF)
1550 XEXP (operands[0], 0) = force_reg (Pmode, XEXP (operands[0], 0));
1553 (define_insn "call_insn_<mode>"
1554 [(call (mem:QI (match_operand 0 "call_insn_operand" "Cr"))
1555 (match_operand:P 1 "general_operand" "g"))]
1559 xoperands[0] = gen_rtx_MEM (QImode, operands[0]);
1560 gcc_assert (GET_MODE (operands[0]) == Pmode);
1561 if (GET_CODE (XEXP (xoperands[0], 0)) == SYMBOL_REF
1562 && (SYMBOL_REF_FLAGS (XEXP (xoperands[0], 0)) & SYMBOL_FLAG_FUNCVEC_FUNCTION))
1563 output_asm_insn ("jsr\\t@%0:8", xoperands);
1565 output_asm_insn ("jsr\\t%0", xoperands);
1568 [(set_attr "type" "call")
1569 (set (attr "length")
1570 (if_then_else (match_operand:QI 0 "small_call_insn_operand" "")
1574 ;; Call subroutine, returning value in operand 0
1575 ;; (which must be a hard register).
1577 ;; ??? Even though we use HImode here, this works on the H8/300H and H8S.
1579 (define_expand "call_value"
1580 [(set (match_operand 0 "" "")
1581 (call (match_operand:QI 1 "call_expander_operand" "")
1582 (match_operand 2 "general_operand" "")))]
1585 if (!register_operand (XEXP (operands[1], 0), Pmode)
1586 && GET_CODE (XEXP (operands[1], 0)) != SYMBOL_REF)
1587 XEXP (operands[1], 0) = force_reg (Pmode, XEXP (operands[1], 0));
1590 (define_insn "call_value_insn_<mode>"
1591 [(set (match_operand 0 "" "=r")
1592 (call (mem:QI (match_operand 1 "call_insn_operand" "Cr"))
1593 (match_operand:P 2 "general_operand" "g")))]
1597 gcc_assert (GET_MODE (operands[1]) == Pmode);
1598 xoperands[0] = operands[0];
1599 xoperands[1] = gen_rtx_MEM (QImode, operands[1]);
1600 if (GET_CODE (XEXP (xoperands[1], 0)) == SYMBOL_REF
1601 && (SYMBOL_REF_FLAGS (XEXP (xoperands[1], 0)) & SYMBOL_FLAG_FUNCVEC_FUNCTION))
1602 output_asm_insn ("jsr\\t@%1:8", xoperands);
1604 output_asm_insn ("jsr\\t%1", xoperands);
1607 [(set_attr "type" "call")
1608 (set (attr "length")
1609 (if_then_else (match_operand:QI 0 "small_call_insn_operand" "")
1617 [(set_attr "cc" "none")
1618 (set_attr "length" "2")])
1620 ;; ----------------------------------------------------------------------
1621 ;; PROLOGUE/EPILOGUE-RELATED INSTRUCTIONS
1622 ;; ----------------------------------------------------------------------
1624 (define_expand "push_h8300hs_advanced"
1625 [(set (mem:SI (pre_dec:SI (reg:SI SP_REG)))
1626 (match_operand:SI 0 "register_operand" ""))]
1627 "TARGET_H8300H && TARGET_H8300S && !TARGET_NORMAL_MODE"
1630 (define_expand "push_h8300hs_normal"
1631 [(set (mem:SI (pre_dec:HI (reg:HI SP_REG)))
1632 (match_operand:SI 0 "register_operand" ""))]
1633 "TARGET_H8300H && TARGET_H8300S && TARGET_NORMAL_MODE"
1636 (define_expand "pop_h8300hs_advanced"
1637 [(set (match_operand:SI 0 "register_operand" "")
1638 (mem:SI (post_inc:SI (reg:SI SP_REG))))]
1639 "TARGET_H8300H && TARGET_H8300S && !TARGET_NORMAL_MODE"
1642 (define_expand "pop_h8300hs_normal"
1643 [(set (match_operand:SI 0 "register_operand" "")
1644 (mem:SI (post_inc:HI (reg:HI SP_REG))))]
1645 "TARGET_H8300H && TARGET_H8300S && TARGET_NORMAL_MODE"
1648 (define_insn "ldm_h8300sx"
1649 [(match_parallel 0 "h8300_ldm_parallel"
1650 [(set (match_operand:SI 1 "register_operand" "")
1651 (match_operand:SI 2 "memory_operand" ""))])]
1654 operands[3] = SET_DEST (XVECEXP (operands[0], 0,
1655 XVECLEN (operands[0], 0) - 2));
1656 return "ldm.l\t@er7+,%S1-%S3";
1658 [(set_attr "cc" "none")
1659 (set_attr "length" "4")])
1661 (define_insn "stm_h8300sx"
1662 [(match_parallel 0 "h8300_stm_parallel"
1663 [(set (match_operand:SI 1 "memory_operand" "")
1664 (match_operand:SI 2 "register_operand" ""))])]
1667 operands[3] = SET_SRC (XVECEXP (operands[0], 0,
1668 XVECLEN (operands[0], 0) - 2));
1669 return "stm.l\t%S2-%S3,@-er7";
1671 [(set_attr "cc" "none")
1672 (set_attr "length" "4")])
1674 (define_insn "return_h8sx"
1675 [(match_parallel 0 "h8300_return_parallel"
1677 (set (match_operand:SI 1 "register_operand" "")
1678 (match_operand:SI 2 "memory_operand" ""))])]
1681 operands[3] = SET_DEST (XVECEXP (operands[0], 0,
1682 XVECLEN (operands[0], 0) - 2));
1683 if (h8300_current_function_interrupt_function_p ()
1684 || h8300_current_function_monitor_function_p ())
1685 return "rte/l\t%S1-%S3";
1687 return "rts/l\t%S1-%S3";
1689 [(set_attr "cc" "none")
1690 (set_attr "can_delay" "no")
1691 (set_attr "length" "2")])
1693 (define_expand "return"
1695 "h8300_can_use_return_insn_p ()"
1698 (define_insn "*return_1"
1702 if (h8300_current_function_interrupt_function_p ()
1703 || h8300_current_function_monitor_function_p ())
1708 [(set_attr "cc" "none")
1709 (set_attr "can_delay" "no")
1710 (set_attr "length" "2")])
1712 (define_expand "prologue"
1716 h8300_expand_prologue ();
1720 (define_expand "epilogue"
1724 h8300_expand_epilogue ();
1728 (define_insn "monitor_prologue"
1729 [(unspec_volatile [(const_int 0)] UNSPEC_MONITOR)]
1732 if (TARGET_H8300H && TARGET_NORMAL_MODE)
1733 return "subs\\t#2,er7\;mov.l\\ter0,@-er7\;stc\\tccr,r0l\;mov.b\\tr0l,@(4,er7)\;mov.l\\t@er7+,er0\;orc\\t#128,ccr";
1734 else if (TARGET_H8300H)
1735 return "mov.l\\ter0,@-er7\;stc\\tccr,r0l\;mov.b\\tr0l,@(4,er7)\;mov.l\\t@er7+,er0\;orc\\t#128,ccr";
1736 else if (TARGET_H8300S && TARGET_NEXR )
1737 return "mov.l\\ter0,@-er7\;stc\tccr,r0l\;mov.b\tr0l,@(4,er7)\;mov.l\\t@er7+,er0\;orc\t#128,ccr";
1738 else if (TARGET_H8300S && TARGET_NEXR && TARGET_NORMAL_MODE)
1739 return "subs\\t#2,er7\;mov.l\\ter0,@-er7\;stc\tccr,r0l\;mov.b\tr0l,@(4,er7)\;mov.l\\t@er7+,er0\;orc\t#128,ccr";
1740 else if (TARGET_H8300S && TARGET_NORMAL_MODE)
1741 return "subs\\t#2,er7\;stc\texr,@-er7\;mov.l\\ter0,@-er7\;stc\tccr,r0l\;mov.b\tr0l,@(6,er7)\;mov.l\\t@er7+,er0\;orc\t#128,ccr";
1742 else if (TARGET_H8300S)
1743 return "stc\texr,@-er7\;mov.l\\ter0,@-er7\;stc\tccr,r0l\;mov.b\tr0l,@(6,er7)\;mov.l\\t@er7+,er0\;orc\t#128,ccr";
1746 [(set_attr "length" "20")])
1748 ;; ----------------------------------------------------------------------
1749 ;; EXTEND INSTRUCTIONS
1750 ;; ----------------------------------------------------------------------
1752 (define_expand "zero_extendqi<mode>2"
1753 [(set (match_operand:HSI 0 "register_operand" "")
1754 (zero_extend:HSI (match_operand:QI 1 "general_operand_src" "")))]
1758 operands[1] = force_reg (QImode, operands[1]);
1761 (define_insn "*zero_extendqihi2_h8300hs"
1762 [(set (match_operand:HI 0 "register_operand" "=r,r")
1763 (zero_extend:HI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1768 [(set_attr "length" "2,10")
1769 (set_attr "cc" "set_znv,set_znv")])
1771 ;; Split the zero extension of a general operand (actually a memory
1772 ;; operand) into a load of the operand and the actual zero extension
1773 ;; so that 1) the length will be accurate, and 2) the zero extensions
1774 ;; appearing at the end of basic blocks may be merged.
1777 [(set (match_operand:HI 0 "register_operand" "")
1778 (zero_extend:HI (match_operand:QI 1 "general_operand_src" "")))]
1783 (zero_extend:HI (match_dup 2)))]
1785 operands[2] = gen_rtx_REG (QImode, REGNO (operands[0]));
1788 (define_insn "*zero_extendqisi2_h8300hs"
1789 [(set (match_operand:SI 0 "register_operand" "=r,r")
1790 (zero_extend:SI (match_operand:QI 1 "general_operand_src" "0,g>")))]
1795 [(set (match_operand:SI 0 "register_operand" "")
1796 (zero_extend:SI (match_operand:QI 1 "general_operand_src" "")))]
1798 && reg_overlap_mentioned_p (operands[0], operands[1])
1799 && reload_completed"
1803 (zero_extend:HI (match_dup 2)))
1805 (zero_extend:SI (match_dup 3)))]
1807 operands[2] = gen_lowpart (QImode, operands[0]);
1808 operands[3] = gen_lowpart (HImode, operands[0]);
1812 [(set (match_operand:SI 0 "register_operand" "")
1813 (zero_extend:SI (match_operand:QI 1 "general_operand_src" "")))]
1815 && !reg_overlap_mentioned_p (operands[0], operands[1])
1816 && reload_completed"
1819 (set (strict_low_part (match_dup 2))
1822 operands[2] = gen_rtx_REG (QImode, REGNO (operands[0]));
1825 (define_insn "*zero_extendqisi2_h8sx"
1826 [(set (match_operand:SI 0 "register_operand" "=r")
1827 (zero_extend:SI (match_operand:QI 1 "register_operand" "0")))]
1830 [(set_attr "length" "2")
1831 (set_attr "cc" "set_znv")])
1833 (define_expand "zero_extendhisi2"
1834 [(set (match_operand:SI 0 "register_operand" "")
1835 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
1839 (define_insn "*zero_extendhisi2_h8300hs"
1840 [(set (match_operand:SI 0 "register_operand" "=r")
1841 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))]
1844 [(set_attr "length" "2")
1845 (set_attr "cc" "set_znv")])
1847 (define_expand "extendqi<mode>2"
1848 [(set (match_operand:HSI 0 "register_operand" "")
1849 (sign_extend:HSI (match_operand:QI 1 "register_operand" "")))]
1853 (define_insn "*extendqihi2_h8300hs"
1854 [(set (match_operand:HI 0 "register_operand" "=r")
1855 (sign_extend:HI (match_operand:QI 1 "register_operand" "0")))]
1858 [(set_attr "length" "2")
1859 (set_attr "cc" "set_znv")])
1861 ;; The following pattern is needed because without the pattern, the
1862 ;; combiner would split (sign_extend:SI (reg:QI)) into two 24-bit
1863 ;; shifts, one ashift and one ashiftrt.
1865 (define_insn_and_split "*extendqisi2_h8300hs"
1866 [(set (match_operand:SI 0 "register_operand" "=r")
1867 (sign_extend:SI (match_operand:QI 1 "register_operand" "0")))]
1870 "&& reload_completed"
1872 (sign_extend:HI (match_dup 1)))
1874 (sign_extend:SI (match_dup 2)))]
1876 operands[2] = gen_rtx_REG (HImode, REGNO (operands[0]));
1879 (define_insn "*extendqisi2_h8sx"
1880 [(set (match_operand:SI 0 "register_operand" "=r")
1881 (sign_extend:SI (match_operand:QI 1 "register_operand" "0")))]
1884 [(set_attr "length" "2")
1885 (set_attr "cc" "set_znv")])
1887 (define_expand "extendhisi2"
1888 [(set (match_operand:SI 0 "register_operand" "")
1889 (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
1893 (define_insn "*extendhisi2_h8300hs"
1894 [(set (match_operand:SI 0 "register_operand" "=r")
1895 (sign_extend:SI (match_operand:HI 1 "register_operand" "0")))]
1898 [(set_attr "length" "2")
1899 (set_attr "cc" "set_znv")])
1901 ;; ----------------------------------------------------------------------
1903 ;; ----------------------------------------------------------------------
1905 ;; We make some attempt to provide real efficient shifting. One example is
1906 ;; doing an 8-bit shift of a 16-bit value by moving a byte reg into the other
1907 ;; reg and moving 0 into the former reg.
1909 ;; We also try to achieve this in a uniform way. IE: We don't try to achieve
1910 ;; this in both rtl and at insn emit time. Ideally, we'd use rtl as that would
1911 ;; give the optimizer more cracks at the code. However, we wish to do things
1912 ;; like optimizing shifting the sign bit to bit 0 by rotating the other way.
1913 ;; There is rtl to handle this (rotate + and), but the H8/300 doesn't handle
1914 ;; 16-bit rotates. Also, if we emit complicated rtl, combine may not be able
1915 ;; to detect cases it can optimize.
1917 ;; For these and other fuzzy reasons, I've decided to go the less pretty but
1918 ;; easier "do it at insn emit time" route.
1921 (define_expand "ashl<mode>3"
1922 [(set (match_operand:QHSI 0 "register_operand" "")
1923 (ashift:QHSI (match_operand:QHSI 1 "register_operand" "")
1924 (match_operand:QI 2 "nonmemory_operand" "")))]
1927 if (expand_a_shift (<MODE>mode, ASHIFT, operands))
1931 (define_expand "ashr<mode>3"
1932 [(set (match_operand:QHSI 0 "register_operand" "")
1933 (ashiftrt:QHSI (match_operand:QHSI 1 "register_operand" "")
1934 (match_operand:QI 2 "nonmemory_operand" "")))]
1937 if (expand_a_shift (<MODE>mode, ASHIFTRT, operands))
1941 (define_expand "lshr<mode>3"
1942 [(set (match_operand:QHSI 0 "register_operand" "")
1943 (lshiftrt:QHSI (match_operand:QHSI 1 "register_operand" "")
1944 (match_operand:QI 2 "nonmemory_operand" "")))]
1947 if (expand_a_shift (<MODE>mode, LSHIFTRT, operands))
1951 ;; QI/HI/SI BIT SHIFTS
1952 ;; Sub-optimal WRT the scratch operand
1955 [(set (match_operand:QHSI 0 "h8300_dst_operand" "=rQ")
1956 (match_operator:QHSI 3 "h8sx_unary_shift_operator"
1957 [(match_operand:QHSI 1 "h8300_dst_operand" "0")
1958 (match_operand:QI 2 "const_int_operand" "")]))]
1959 "h8300_operands_match_p (operands)"
1961 if (<MODE>mode == E_QImode)
1962 return output_h8sx_shift (operands, 'b', 'X');
1963 if (<MODE>mode == E_HImode)
1964 return output_h8sx_shift (operands, 'w', 'T');
1965 if (<MODE>mode == E_SImode)
1966 return output_h8sx_shift (operands, 'l', 'S');
1969 [(set_attr "length_table" "unary")
1970 (set_attr "cc" "set_znv")])
1973 [(set (match_operand:QHSI 0 "register_operand" "=r")
1974 (match_operator:QHSI 3 "h8sx_binary_shift_operator"
1975 [(match_operand:QHSI 1 "register_operand" "0")
1976 (match_operand:QI 2 "nonmemory_operand" "r P5>X")]))]
1979 if (<MODE>mode == QImode)
1980 return output_h8sx_shift (operands, 'b', 'X');
1981 if (<MODE>mode == HImode)
1982 return output_h8sx_shift (operands, 'w', 'T');
1983 if (<MODE>mode == SImode)
1984 return output_h8sx_shift (operands, 'l', 'S');
1987 [(set_attr "length" "4")
1988 (set_attr "cc" "set_znv")])
1990 (define_insn "*shiftqi"
1991 [(set (match_operand:QI 0 "register_operand" "=r,r")
1992 (match_operator:QI 3 "nshift_operator"
1993 [(match_operand:QI 1 "register_operand" "0,0")
1994 (match_operand:QI 2 "nonmemory_operand" "R,rn")]))
1995 (clobber (match_scratch:QI 4 "=X,&r"))]
1998 return output_a_shift (operands);
2000 [(set (attr "length")
2001 (symbol_ref "compute_a_shift_length (insn, operands)"))
2003 (symbol_ref "compute_a_shift_cc (insn, operands)"))])
2005 (define_insn "*shifthi"
2006 [(set (match_operand:HI 0 "register_operand" "=r,r")
2007 (match_operator:HI 3 "nshift_operator"
2008 [(match_operand:HI 1 "register_operand" "0,0")
2009 (match_operand:QI 2 "nonmemory_operand" "S,rn")]))
2010 (clobber (match_scratch:QI 4 "=X,&r"))]
2013 return output_a_shift (operands);
2015 [(set (attr "length")
2016 (symbol_ref "compute_a_shift_length (insn, operands)"))
2018 (symbol_ref "compute_a_shift_cc (insn, operands)"))])
2020 (define_insn "*shiftsi"
2021 [(set (match_operand:SI 0 "register_operand" "=r,r")
2022 (match_operator:SI 3 "nshift_operator"
2023 [(match_operand:SI 1 "register_operand" "0,0")
2024 (match_operand:QI 2 "nonmemory_operand" "T,rn")]))
2025 (clobber (match_scratch:QI 4 "=X,&r"))]
2028 return output_a_shift (operands);
2030 [(set (attr "length")
2031 (symbol_ref "compute_a_shift_length (insn, operands)"))
2033 (symbol_ref "compute_a_shift_cc (insn, operands)"))])
2036 ;; Split a variable shift into a loop. If the register containing
2037 ;; the shift count dies, then we just use that register.
2040 [(set (match_operand 0 "register_operand" "")
2041 (match_operator 2 "nshift_operator"
2043 (match_operand:QI 1 "register_operand" "")]))
2044 (clobber (match_operand:QI 3 "register_operand" ""))]
2046 && find_regno_note (insn, REG_DEAD, REGNO (operands[1]))"
2047 [(set (cc0) (compare (match_dup 1) (const_int 0)))
2049 (if_then_else (le (cc0) (const_int 0))
2050 (label_ref (match_dup 5))
2055 (match_op_dup 2 [(match_dup 0) (const_int 1)]))
2056 (clobber (scratch:QI))])
2057 (set (match_dup 1) (plus:QI (match_dup 1) (const_int -1)))
2058 (set (cc0) (compare (match_dup 1) (const_int 0)))
2060 (if_then_else (ne (cc0) (const_int 0))
2061 (label_ref (match_dup 4))
2065 operands[4] = gen_label_rtx ();
2066 operands[5] = gen_label_rtx ();
2070 [(set (match_operand 0 "register_operand" "")
2071 (match_operator 2 "nshift_operator"
2073 (match_operand:QI 1 "register_operand" "")]))
2074 (clobber (match_operand:QI 3 "register_operand" ""))]
2076 && !find_regno_note (insn, REG_DEAD, REGNO (operands[1]))"
2079 (set (cc0) (compare (match_dup 3) (const_int 0)))
2081 (if_then_else (le (cc0) (const_int 0))
2082 (label_ref (match_dup 5))
2087 (match_op_dup 2 [(match_dup 0) (const_int 1)]))
2088 (clobber (scratch:QI))])
2089 (set (match_dup 3) (plus:QI (match_dup 3) (const_int -1)))
2090 (set (cc0) (compare (match_dup 3) (const_int 0)))
2092 (if_then_else (ne (cc0) (const_int 0))
2093 (label_ref (match_dup 4))
2097 operands[4] = gen_label_rtx ();
2098 operands[5] = gen_label_rtx ();
2101 ;; ----------------------------------------------------------------------
2103 ;; ----------------------------------------------------------------------
2105 (define_expand "rotl<mode>3"
2106 [(set (match_operand:QHSI 0 "register_operand" "")
2107 (rotate:QHSI (match_operand:QHSI 1 "register_operand" "")
2108 (match_operand:QI 2 "nonmemory_operand" "")))]
2111 if (expand_a_rotate (operands))
2115 (define_insn "rotl<mode>3_1"
2116 [(set (match_operand:QHSI 0 "register_operand" "=r")
2117 (rotate:QHSI (match_operand:QHSI 1 "register_operand" "0")
2118 (match_operand:QI 2 "immediate_operand" "")))]
2121 return output_a_rotate (ROTATE, operands);
2123 [(set (attr "length")
2124 (symbol_ref "compute_a_rotate_length (operands)"))])
2126 ;; -----------------------------------------------------------------
2128 ;; -----------------------------------------------------------------
2129 ;; The H8/300 has given 1/8th of its opcode space to bitfield
2130 ;; instructions so let's use them as well as we can.
2132 ;; You'll never believe all these patterns perform one basic action --
2133 ;; load a bit from the source, optionally invert the bit, then store it
2134 ;; in the destination (which is known to be zero).
2136 ;; Combine obviously need some work to better identify this situation and
2137 ;; canonicalize the form better.
2140 ;; Inverted loads with a 16bit destination.
2144 [(set (match_operand:HI 0 "register_operand" "=&r")
2145 (zero_extract:HI (xor:HI (match_operand:HI 1 "register_operand" "r")
2146 (match_operand:HI 3 "const_int_operand" "n"))
2148 (match_operand:HI 2 "const_int_operand" "n")))]
2150 && (1 << INTVAL (operands[2])) == INTVAL (operands[3])"
2151 "sub.w %0,%0\;bild %Z2,%Y1\;bst #0,%X0"
2152 [(set_attr "length" "8")])
2155 ;; Normal loads with a 32bit destination.
2158 (define_insn "*extzv_1_r_h8300hs"
2159 [(set (match_operand:SI 0 "register_operand" "=r,r")
2160 (zero_extract:SI (match_operand:SI 1 "register_operand" "?0,r")
2162 (match_operand 2 "const_int_operand" "n,n")))]
2163 "INTVAL (operands[2]) < 16"
2165 return output_simode_bld (0, operands);
2167 [(set_attr "cc" "set_znv,set_znv")
2168 (set_attr "length" "8,6")])
2171 ;; Inverted loads with a 32bit destination.
2174 (define_insn "*extzv_1_r_inv_h8300hs"
2175 [(set (match_operand:SI 0 "register_operand" "=r,r")
2176 (zero_extract:SI (xor:SI (match_operand:SI 1 "register_operand" "?0,r")
2177 (match_operand 3 "const_int_operand" "n,n"))
2179 (match_operand 2 "const_int_operand" "n,n")))]
2180 "INTVAL (operands[2]) < 16
2181 && (1 << INTVAL (operands[2])) == INTVAL (operands[3])"
2183 return output_simode_bld (1, operands);
2185 [(set_attr "cc" "set_znv,set_znv")
2186 (set_attr "length" "8,6")])
2188 (define_expand "insv"
2189 [(set (zero_extract:HI (match_operand:HI 0 "general_operand" "")
2190 (match_operand:HI 1 "general_operand" "")
2191 (match_operand:HI 2 "general_operand" ""))
2192 (match_operand:HI 3 "general_operand" ""))]
2195 if (GET_CODE (operands[1]) == CONST_INT
2196 && GET_CODE (operands[2]) == CONST_INT
2197 && INTVAL (operands[1]) <= 8
2198 && INTVAL (operands[2]) >= 0
2199 && INTVAL (operands[1]) + INTVAL (operands[2]) <= 8
2200 && memory_operand (operands[0], GET_MODE (operands[0])))
2202 /* If the source operand is zero, it's better to use AND rather
2203 than BFST. Likewise OR if the operand is all ones. */
2204 if (GET_CODE (operands[3]) == CONST_INT)
2206 HOST_WIDE_INT mask = (1 << INTVAL (operands[1])) - 1;
2207 if ((INTVAL (operands[3]) & mask) == 0)
2209 if ((INTVAL (operands[3]) & mask) == mask)
2212 if (! bit_memory_operand (operands[0], GET_MODE (operands[0])))
2214 if (!can_create_pseudo_p ())
2216 operands[0] = replace_equiv_address (operands[0], force_reg (Pmode,
2217 XEXP (operands[0], 0)));
2219 operands[3] = gen_lowpart (QImode, operands[3]);
2222 if (! register_operand (operands[3], QImode))
2224 if (!can_create_pseudo_p ())
2226 operands[3] = force_reg (QImode, operands[3]);
2228 emit_insn (gen_bfst (adjust_address (operands[0], QImode, 0),
2229 operands[3], operands[1], operands[2]));
2236 [(set (zero_extract:HI (match_operand:HI 0 "register_operand" "+r")
2238 (match_operand:HI 1 "immediate_operand" "n"))
2239 (match_operand:HI 2 "register_operand" "r"))]
2241 "bld #0,%R2\;bst %Z1,%Y0 ; i1"
2242 [(set_attr "length" "4")])
2244 (define_expand "extzv"
2245 [(set (match_operand:HI 0 "register_operand" "")
2246 (zero_extract:HI (match_operand:HI 1 "bit_operand" "")
2247 (match_operand:HI 2 "general_operand" "")
2248 (match_operand:HI 3 "general_operand" "")))]
2251 if (GET_CODE (operands[2]) == CONST_INT
2252 && GET_CODE (operands[3]) == CONST_INT
2253 && INTVAL (operands[2]) <= 8
2254 && INTVAL (operands[3]) >= 0
2255 && INTVAL (operands[2]) + INTVAL (operands[3]) <= 8
2256 && memory_operand (operands[1], QImode))
2260 /* Optimize the case where we're extracting into a paradoxical
2261 subreg. It's only necessary to extend to the inner reg. */
2262 if (GET_CODE (operands[0]) == SUBREG
2263 && subreg_lowpart_p (operands[0])
2264 && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0])))
2265 < GET_MODE_SIZE (GET_MODE (operands[0])))
2266 && (GET_MODE_CLASS (GET_MODE (SUBREG_REG (operands[0])))
2268 operands[0] = SUBREG_REG (operands[0]);
2270 if (!can_create_pseudo_p ())
2271 temp = gen_lowpart (QImode, operands[0]);
2273 temp = gen_reg_rtx (QImode);
2276 if (! bit_memory_operand (operands[1], QImode))
2278 if (!can_create_pseudo_p ())
2280 operands[1] = replace_equiv_address (operands[1],
2281 force_reg (Pmode, XEXP (operands[1], 0)));
2283 emit_insn (gen_bfld (temp, operands[1], operands[2], operands[3]));
2284 convert_move (operands[0], temp, 1);
2290 ;; BAND, BOR, and BXOR patterns
2293 [(set (match_operand:HI 0 "bit_operand" "=Ur")
2294 (match_operator:HI 4 "bit_operator"
2295 [(zero_extract:HI (match_operand:HI 1 "register_operand" "r")
2297 (match_operand:HI 2 "immediate_operand" "n"))
2298 (match_operand:HI 3 "bit_operand" "0")]))]
2300 "bld %Z2,%Y1\;b%c4 #0,%R0\;bst #0,%R0; bl1"
2301 [(set_attr "length" "6")])
2304 [(set (match_operand:HI 0 "bit_operand" "=Ur")
2305 (match_operator:HI 5 "bit_operator"
2306 [(zero_extract:HI (match_operand:HI 1 "register_operand" "r")
2308 (match_operand:HI 2 "immediate_operand" "n"))
2309 (zero_extract:HI (match_operand:HI 3 "register_operand" "r")
2311 (match_operand:HI 4 "immediate_operand" "n"))]))]
2313 "bld %Z2,%Y1\;b%c5 %Z4,%Y3\;bst #0,%R0; bl3"
2314 [(set_attr "length" "6")])
2317 [(set (match_operand:QI 0 "register_operand" "=r")
2318 (zero_extract:QI (match_operand:QI 1 "bit_memory_operand" "WU")
2319 (match_operand:QI 2 "immediate_operand" "n")
2320 (match_operand:QI 3 "immediate_operand" "n")))]
2321 "TARGET_H8300SX && INTVAL (operands[2]) + INTVAL (operands[3]) <= 8"
2323 operands[2] = GEN_INT ((1 << (INTVAL (operands[2]) + INTVAL (operands[3])))
2324 - (1 << INTVAL (operands[3])));
2325 return "bfld %2,%1,%R0";
2327 [(set_attr "cc" "none_0hit")
2328 (set_attr "length_table" "bitfield")])
2331 [(set (zero_extract:QI (match_operand:QI 0 "bit_memory_operand" "+WU")
2332 (match_operand:QI 2 "immediate_operand" "n")
2333 (match_operand:QI 3 "immediate_operand" "n"))
2334 (match_operand:QI 1 "register_operand" "r"))]
2335 "TARGET_H8300SX && INTVAL (operands[2]) + INTVAL (operands[3]) <= 8"
2337 operands[2] = GEN_INT ((1 << (INTVAL (operands[2]) + INTVAL (operands[3])))
2338 - (1 << INTVAL (operands[3])));
2339 return "bfst %R1,%2,%0";
2341 [(set_attr "cc" "none_0hit")
2342 (set_attr "length_table" "bitfield")])
2344 (define_expand "cstoreqi4"
2345 [(use (match_operator 1 "eqne_operator"
2346 [(match_operand:QI 2 "h8300_dst_operand" "")
2347 (match_operand:QI 3 "h8300_src_operand" "")]))
2348 (clobber (match_operand:HI 0 "register_operand"))]
2351 h8300_expand_store (operands);
2355 (define_expand "cstorehi4"
2356 [(use (match_operator 1 "eqne_operator"
2357 [(match_operand:HI 2 "h8300_dst_operand" "")
2358 (match_operand:HI 3 "h8300_src_operand" "")]))
2359 (clobber (match_operand:HI 0 "register_operand"))]
2362 h8300_expand_store (operands);
2366 (define_expand "cstoresi4"
2367 [(use (match_operator 1 "eqne_operator"
2368 [(match_operand:SI 2 "h8300_dst_operand" "")
2369 (match_operand:SI 3 "h8300_src_operand" "")]))
2370 (clobber (match_operand:HI 0 "register_operand"))]
2373 h8300_expand_store (operands);
2377 (define_insn "*bstzhireg"
2378 [(set (match_operand:HI 0 "register_operand" "=r")
2379 (match_operator:HI 1 "eqne_operator" [(cc0) (const_int 0)]))]
2381 "mulu.w #0,%T0\;b%k1 .Lh8BR%=\;inc.w #1,%T0\\n.Lh8BR%=:"
2382 [(set_attr "cc" "clobber")])
2384 (define_insn_and_split "*cmpstz"
2385 [(set (zero_extract:QI (match_operand:QI 0 "bit_memory_operand" "+WU,WU")
2387 (match_operand:QI 1 "immediate_operand" "n,n"))
2388 (match_operator:QI 2 "eqne_operator"
2389 [(match_operand 3 "h8300_dst_operand" "r,rQ")
2390 (match_operand 4 "h8300_src_operand" "I,rQi")]))]
2392 && (GET_MODE (operands[3]) == GET_MODE (operands[4])
2393 || GET_CODE (operands[4]) == CONST_INT)
2394 && GET_MODE_CLASS (GET_MODE (operands[3])) == MODE_INT
2395 && GET_MODE_SIZE (GET_MODE (operands[3])) <= 4"
2398 [(set (cc0) (match_dup 5))
2399 (set (zero_extract:QI (match_dup 0) (const_int 1) (match_dup 1))
2400 (match_op_dup:QI 2 [(cc0) (const_int 0)]))]
2402 operands[5] = gen_rtx_COMPARE (VOIDmode, operands[3], operands[4]);
2404 [(set_attr "cc" "set_znv,compare")])
2406 (define_insn "*bstz"
2407 [(set (zero_extract:QI (match_operand:QI 0 "bit_memory_operand" "+WU")
2409 (match_operand:QI 1 "immediate_operand" "n"))
2410 (eq:QI (cc0) (const_int 0)))]
2411 "TARGET_H8300SX && reload_completed"
2413 [(set_attr "cc" "none_0hit")
2414 (set_attr "length_table" "unary")])
2416 (define_insn "*bistz"
2417 [(set (zero_extract:QI (match_operand:QI 0 "bit_memory_operand" "+WU")
2419 (match_operand:QI 1 "immediate_operand" "n"))
2420 (ne:QI (cc0) (const_int 0)))]
2421 "TARGET_H8300SX && reload_completed"
2423 [(set_attr "cc" "none_0hit")
2424 (set_attr "length_table" "unary")])
2426 (define_insn_and_split "*cmpcondbset"
2427 [(set (match_operand:QI 0 "nonimmediate_operand" "=WU,WU")
2428 (if_then_else:QI (match_operator 1 "eqne_operator"
2429 [(match_operand 2 "h8300_dst_operand" "r,rQ")
2430 (match_operand 3 "h8300_src_operand" "I,rQi")])
2431 (ior:QI (match_operand:QI 4 "bit_memory_operand" "0,0")
2432 (match_operand:QI 5 "single_one_operand" "n,n"))
2437 [(set (cc0) (match_dup 6))
2439 (if_then_else:QI (match_op_dup 1 [(cc0) (const_int 0)])
2440 (ior:QI (match_dup 4) (match_dup 5))
2443 operands[6] = gen_rtx_COMPARE (VOIDmode, operands[2], operands[3]);
2445 [(set_attr "cc" "set_znv,compare")])
2447 (define_insn "*condbset"
2448 [(set (match_operand:QI 0 "bit_memory_operand" "=WU")
2449 (if_then_else:QI (match_operator:QI 2 "eqne_operator"
2450 [(cc0) (const_int 0)])
2451 (ior:QI (match_operand:QI 3 "bit_memory_operand" "0")
2452 (match_operand:QI 1 "single_one_operand" "n"))
2454 "TARGET_H8300SX && reload_completed"
2456 [(set_attr "cc" "none_0hit")
2457 (set_attr "length_table" "logicb")])
2459 (define_insn_and_split "*cmpcondbclr"
2460 [(set (match_operand:QI 0 "nonimmediate_operand" "=WU,WU")
2461 (if_then_else:QI (match_operator 1 "eqne_operator"
2462 [(match_operand 2 "h8300_dst_operand" "r,rQ")
2463 (match_operand 3 "h8300_src_operand" "I,rQi")])
2464 (and:QI (match_operand:QI 4 "bit_memory_operand" "0,0")
2465 (match_operand:QI 5 "single_zero_operand" "n,n"))
2470 [(set (cc0) (match_dup 6))
2472 (if_then_else:QI (match_op_dup 1 [(cc0) (const_int 0)])
2473 (and:QI (match_dup 4) (match_dup 5))
2476 operands[6] = gen_rtx_COMPARE (VOIDmode, operands[2], operands[3]);
2478 [(set_attr "cc" "set_znv,compare")])
2480 (define_insn "*condbclr"
2481 [(set (match_operand:QI 0 "bit_memory_operand" "=WU")
2482 (if_then_else:QI (match_operator:QI 2 "eqne_operator"
2483 [(cc0) (const_int 0)])
2484 (and:QI (match_operand:QI 3 "bit_memory_operand" "0")
2485 (match_operand:QI 1 "single_zero_operand" "n"))
2487 "TARGET_H8300SX && reload_completed"
2489 [(set_attr "cc" "none_0hit")
2490 (set_attr "length_table" "logicb")])
2492 (define_insn_and_split "*cmpcondbsetreg"
2493 [(set (match_operand:QI 0 "nonimmediate_operand" "=WU,WU")
2494 (if_then_else:QI (match_operator 1 "eqne_operator"
2495 [(match_operand 2 "h8300_dst_operand" "r,rQ")
2496 (match_operand 3 "h8300_src_operand" "I,rQi")])
2497 (ior:QI (match_operand:QI 4 "bit_memory_operand" "0,0")
2498 (ashift:QI (const_int 1)
2499 (match_operand:QI 5 "register_operand" "r,r")))
2504 [(set (cc0) (match_dup 6))
2506 (if_then_else:QI (match_op_dup 1 [(cc0) (const_int 0)])
2507 (ior:QI (match_dup 4)
2508 (ashift:QI (const_int 1)
2509 (match_operand:QI 5 "register_operand" "r,r")))
2512 operands[6] = gen_rtx_COMPARE (VOIDmode, operands[2], operands[3]);
2514 [(set_attr "cc" "set_znv,compare")])
2516 (define_insn "*condbsetreg"
2517 [(set (match_operand:QI 0 "bit_memory_operand" "=WU")
2518 (if_then_else:QI (match_operator:QI 2 "eqne_operator"
2519 [(cc0) (const_int 0)])
2520 (ior:QI (match_operand:QI 3 "bit_memory_operand" "0")
2521 (ashift:QI (const_int 1)
2522 (match_operand:QI 1 "register_operand" "r")))
2524 "TARGET_H8300SX && reload_completed"
2526 [(set_attr "cc" "none_0hit")
2527 (set_attr "length_table" "logicb")])
2529 (define_insn_and_split "*cmpcondbclrreg"
2530 [(set (match_operand:QI 0 "nonimmediate_operand" "=WU,WU")
2531 (if_then_else:QI (match_operator 1 "eqne_operator"
2532 [(match_operand 2 "h8300_dst_operand" "r,rQ")
2533 (match_operand 3 "h8300_src_operand" "I,rQi")])
2534 (and:QI (match_operand:QI 4 "bit_memory_operand" "0,0")
2535 (ashift:QI (const_int 1)
2536 (match_operand:QI 5 "register_operand" "r,r")))
2541 [(set (cc0) (match_dup 6))
2543 (if_then_else:QI (match_op_dup 1 [(cc0) (const_int 0)])
2544 (and:QI (match_dup 4)
2545 (ashift:QI (const_int 1)
2546 (match_operand:QI 5 "register_operand" "r,r")))
2549 operands[6] = gen_rtx_COMPARE (VOIDmode, operands[2], operands[3]);
2551 [(set_attr "cc" "set_znv,compare")])
2553 (define_insn "*condbclrreg"
2554 [(set (match_operand:QI 0 "bit_memory_operand" "=WU")
2555 (if_then_else:QI (match_operator:QI 2 "eqne_operator"
2556 [(cc0) (const_int 0)])
2557 (and:QI (match_operand:QI 3 "bit_memory_operand" "0")
2558 (ashift:QI (const_int 1)
2559 (match_operand:QI 1 "register_operand" "r")))
2561 "TARGET_H8300SX && reload_completed"
2563 [(set_attr "cc" "none_0hit")
2564 (set_attr "length_table" "logicb")])
2567 ;; -----------------------------------------------------------------
2569 ;; -----------------------------------------------------------------
2573 (define_insn "*insv_si_1_n"
2574 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
2576 (match_operand:SI 1 "const_int_operand" "n"))
2577 (match_operand:SI 2 "register_operand" "r"))]
2578 "INTVAL (operands[1]) < 16"
2579 "bld\\t#0,%w2\;bst\\t%Z1,%Y0"
2580 [(set_attr "length" "4")])
2582 (define_insn "*insv_si_1_n_lshiftrt"
2583 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
2585 (match_operand:SI 1 "const_int_operand" "n"))
2586 (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
2587 (match_operand:SI 3 "const_int_operand" "n")))]
2588 "INTVAL (operands[1]) < 16 && INTVAL (operands[3]) < 16"
2589 "bld\\t%Z3,%Y2\;bst\\t%Z1,%Y0"
2590 [(set_attr "length" "4")])
2592 (define_insn "*insv_si_1_n_lshiftrt_16"
2593 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
2595 (match_operand:SI 1 "const_int_operand" "n"))
2596 (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
2598 "INTVAL (operands[1]) < 16"
2599 "rotr.w\\t%e2\;rotl.w\\t%e2\;bst\\t%Z1,%Y0"
2600 [(set_attr "length" "6")])
2602 (define_insn "*insv_si_8_8"
2603 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
2606 (match_operand:SI 1 "register_operand" "r"))]
2609 [(set_attr "length" "2")])
2611 (define_insn "*insv_si_8_8_lshiftrt_8"
2612 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
2615 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
2619 [(set_attr "length" "2")])
2623 (define_insn "*extzv_8_8"
2624 [(set (match_operand:SI 0 "register_operand" "=r,r")
2625 (zero_extract:SI (match_operand:SI 1 "register_operand" "?0,r")
2630 mov.b\\t%x1,%w0\;extu.w\\t%f0\;extu.l\\t%S0
2631 sub.l\\t%S0,%S0\;mov.b\\t%x1,%w0"
2632 [(set_attr "cc" "set_znv,clobber")
2633 (set_attr "length" "6,4")])
2635 (define_insn "*extzv_8_16"
2636 [(set (match_operand:SI 0 "register_operand" "=r")
2637 (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
2641 "mov.w\\t%e1,%f0\;extu.w\\t%f0\;extu.l\\t%S0"
2642 [(set_attr "cc" "set_znv")
2643 (set_attr "length" "6")])
2645 (define_insn "*extzv_16_8"
2646 [(set (match_operand:SI 0 "register_operand" "=r")
2647 (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
2650 (clobber (match_scratch:SI 2 "=&r"))]
2652 "mov.w\\t%e1,%f2\;mov.b\\t%x1,%w0\;mov.b\\t%w2,%x0\;extu.l\\t%S0"
2653 [(set_attr "length" "8")
2654 (set_attr "cc" "set_znv")])
2656 ;; Extract the exponent of a float.
2658 (define_insn_and_split "*extzv_8_23"
2659 [(set (match_operand:SI 0 "register_operand" "=r")
2660 (zero_extract:SI (match_operand:SI 1 "register_operand" "0")
2665 "&& reload_completed"
2666 [(parallel [(set (match_dup 0)
2667 (ashift:SI (match_dup 0)
2669 (clobber (scratch:QI))])
2670 (parallel [(set (match_dup 0)
2671 (lshiftrt:SI (match_dup 0)
2673 (clobber (scratch:QI))])]
2678 ;; ((SImode) HImode) << 15
2680 (define_insn_and_split "*twoshifts_l16_r1"
2681 [(set (match_operand:SI 0 "register_operand" "=r")
2682 (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "0")
2684 (const_int 2147450880)))]
2687 "&& reload_completed"
2688 [(parallel [(set (match_dup 0)
2689 (ashift:SI (match_dup 0)
2691 (clobber (scratch:QI))])
2692 (parallel [(set (match_dup 0)
2693 (lshiftrt:SI (match_dup 0)
2695 (clobber (scratch:QI))])]
2698 ;; Transform (SImode << B) & 0xffff into (SImode) (HImode << B).
2700 (define_insn_and_split "*andsi3_ashift_n_lower"
2701 [(set (match_operand:SI 0 "register_operand" "=r,r")
2702 (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "0,0")
2703 (match_operand:QI 2 "const_int_operand" "S,n"))
2704 (match_operand:SI 3 "const_int_operand" "n,n")))
2705 (clobber (match_scratch:QI 4 "=X,&r"))]
2706 "INTVAL (operands[2]) <= 15
2707 && UINTVAL (operands[3]) == ((HOST_WIDE_INT_M1U << INTVAL (operands[2]))
2710 "&& reload_completed"
2711 [(parallel [(set (match_dup 5)
2712 (ashift:HI (match_dup 5)
2714 (clobber (match_dup 4))])
2716 (zero_extend:SI (match_dup 5)))]
2718 operands[5] = gen_rtx_REG (HImode, REGNO (operands[0]));
2721 ;; Accept (A >> 30) & 2 and the like.
2723 (define_insn "*andsi3_lshiftrt_n_sb"
2724 [(set (match_operand:SI 0 "register_operand" "=r")
2725 (and:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
2726 (match_operand:SI 2 "const_int_operand" "n"))
2727 (match_operand:SI 3 "single_one_operand" "n")))]
2728 "exact_log2 (INTVAL (operands[3])) < 16
2729 && INTVAL (operands[2]) + exact_log2 (INTVAL (operands[3])) == 31"
2731 operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
2732 return "shll.l\\t%S0\;xor.l\\t%S0,%S0\;bst\\t%Z3,%Y0";
2734 [(set_attr "length" "8")])
2736 (define_insn_and_split "*andsi3_lshiftrt_9_sb"
2737 [(set (match_operand:SI 0 "register_operand" "=r")
2738 (and:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
2740 (const_int 4194304)))]
2743 "&& reload_completed"
2745 (and:SI (lshiftrt:SI (match_dup 0)
2748 (parallel [(set (match_dup 0)
2749 (ashift:SI (match_dup 0)
2751 (clobber (scratch:QI))])]
2756 (define_insn "*addsi3_upper"
2757 [(set (match_operand:SI 0 "register_operand" "=r")
2758 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
2760 (match_operand:SI 2 "register_operand" "0")))]
2763 [(set_attr "length" "2")])
2765 (define_insn "*addsi3_lshiftrt_16_zexthi"
2766 [(set (match_operand:SI 0 "register_operand" "=r")
2767 (plus:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
2769 (zero_extend:SI (match_operand:HI 2 "register_operand" "0"))))]
2771 "add.w\\t%e1,%f0\;xor.w\\t%e0,%e0\;rotxl.w\\t%e0"
2772 [(set_attr "length" "6")])
2774 (define_insn_and_split "*addsi3_and_r_1"
2775 [(set (match_operand:SI 0 "register_operand" "=r")
2776 (plus:SI (and:SI (match_operand:SI 1 "register_operand" "r")
2778 (match_operand:SI 2 "register_operand" "0")))]
2781 "&& reload_completed"
2782 [(set (cc0) (compare (zero_extract:SI (match_dup 1)
2787 (if_then_else (eq (cc0)
2789 (label_ref (match_dup 3))
2792 (plus:SI (match_dup 2)
2796 operands[3] = gen_label_rtx ();
2799 (define_insn_and_split "*addsi3_and_not_r_1"
2800 [(set (match_operand:SI 0 "register_operand" "=r")
2801 (plus:SI (and:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
2803 (match_operand:SI 2 "register_operand" "0")))]
2806 "&& reload_completed"
2807 [(set (cc0) (compare (zero_extract:SI (match_dup 1)
2812 (if_then_else (ne (cc0)
2814 (label_ref (match_dup 3))
2817 (plus:SI (match_dup 2)
2821 operands[3] = gen_label_rtx ();
2826 (define_insn "*ixorhi3_zext"
2827 [(set (match_operand:HI 0 "register_operand" "=r")
2828 (match_operator:HI 1 "iorxor_operator"
2829 [(zero_extend:HI (match_operand:QI 2 "register_operand" "r"))
2830 (match_operand:HI 3 "register_operand" "0")]))]
2833 [(set_attr "length" "2")])
2837 (define_insn "*ixorsi3_zext_qi"
2838 [(set (match_operand:SI 0 "register_operand" "=r")
2839 (match_operator:SI 1 "iorxor_operator"
2840 [(zero_extend:SI (match_operand:QI 2 "register_operand" "r"))
2841 (match_operand:SI 3 "register_operand" "0")]))]
2844 [(set_attr "length" "2")])
2846 (define_insn "*ixorsi3_zext_hi"
2847 [(set (match_operand:SI 0 "register_operand" "=r")
2848 (match_operator:SI 1 "iorxor_operator"
2849 [(zero_extend:SI (match_operand:HI 2 "register_operand" "r"))
2850 (match_operand:SI 3 "register_operand" "0")]))]
2853 [(set_attr "length" "2")])
2855 (define_insn "*ixorsi3_ashift_16"
2856 [(set (match_operand:SI 0 "register_operand" "=r")
2857 (match_operator:SI 1 "iorxor_operator"
2858 [(ashift:SI (match_operand:SI 2 "register_operand" "r")
2860 (match_operand:SI 3 "register_operand" "0")]))]
2863 [(set_attr "length" "2")])
2865 (define_insn "*ixorsi3_lshiftrt_16"
2866 [(set (match_operand:SI 0 "register_operand" "=r")
2867 (match_operator:SI 1 "iorxor_operator"
2868 [(lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
2870 (match_operand:SI 3 "register_operand" "0")]))]
2873 [(set_attr "length" "2")])
2877 (define_insn "*iorhi3_ashift_8"
2878 [(set (match_operand:HI 0 "register_operand" "=r")
2879 (ior:HI (ashift:HI (match_operand:HI 1 "register_operand" "r")
2881 (match_operand:HI 2 "register_operand" "0")))]
2884 [(set_attr "length" "2")])
2886 (define_insn "*iorhi3_lshiftrt_8"
2887 [(set (match_operand:HI 0 "register_operand" "=r")
2888 (ior:HI (lshiftrt:HI (match_operand:HI 1 "register_operand" "r")
2890 (match_operand:HI 2 "register_operand" "0")))]
2893 [(set_attr "length" "2")])
2895 (define_insn "*iorhi3_two_qi"
2896 [(set (match_operand:HI 0 "register_operand" "=r")
2897 (ior:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "0"))
2898 (ashift:HI (match_operand:HI 2 "register_operand" "r")
2902 [(set_attr "length" "2")])
2904 (define_insn "*iorhi3_two_qi_mem"
2905 [(set (match_operand:HI 0 "register_operand" "=&r")
2906 (ior:HI (zero_extend:HI (match_operand:QI 1 "memory_operand" "m"))
2907 (ashift:HI (subreg:HI (match_operand:QI 2 "memory_operand" "m") 0)
2910 "mov.b\\t%X2,%t0\;mov.b\\t%X1,%s0"
2911 [(set_attr "length" "16")])
2914 [(set (match_operand:HI 0 "register_operand" "")
2915 (ior:HI (zero_extend:HI (match_operand:QI 1 "memory_operand" ""))
2916 (ashift:HI (subreg:HI (match_operand:QI 2 "memory_operand" "") 0)
2919 && byte_accesses_mergeable_p (XEXP (operands[2], 0), XEXP (operands[1], 0))"
2923 operands[3] = gen_rtx_MEM (HImode, XEXP (operands[2], 0));
2928 (define_insn "*iorsi3_two_hi"
2929 [(set (match_operand:SI 0 "register_operand" "=r")
2930 (ior:SI (zero_extend:SI (match_operand:HI 1 "register_operand" "0"))
2931 (ashift:SI (match_operand:SI 2 "register_operand" "r")
2935 [(set_attr "length" "2")])
2937 (define_insn_and_split "*iorsi3_two_qi_zext"
2938 [(set (match_operand:SI 0 "register_operand" "=&r")
2939 (ior:SI (zero_extend:SI (match_operand:QI 1 "memory_operand" "m"))
2940 (and:SI (ashift:SI (subreg:SI (match_operand:QI 2 "memory_operand" "m") 0)
2942 (const_int 65280))))]
2945 "&& reload_completed"
2947 (ior:HI (zero_extend:HI (match_dup 1))
2948 (ashift:HI (subreg:HI (match_dup 2) 0)
2951 (zero_extend:SI (match_dup 3)))]
2953 operands[3] = gen_rtx_REG (HImode, REGNO (operands[0]));
2956 (define_insn "*iorsi3_e2f"
2957 [(set (match_operand:SI 0 "register_operand" "=r")
2958 (ior:SI (and:SI (match_operand:SI 1 "register_operand" "0")
2960 (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
2964 [(set_attr "length" "2")])
2966 (define_insn_and_split "*iorsi3_two_qi_sext"
2967 [(set (match_operand:SI 0 "register_operand" "=r")
2968 (ior:SI (zero_extend:SI (match_operand:QI 1 "register_operand" "0"))
2969 (ashift:SI (sign_extend:SI (match_operand:QI 2 "register_operand" "r"))
2973 "&& reload_completed"
2975 (ior:HI (zero_extend:HI (match_dup 1))
2976 (ashift:HI (match_dup 4)
2979 (sign_extend:SI (match_dup 3)))]
2981 operands[3] = gen_rtx_REG (HImode, REGNO (operands[0]));
2982 operands[4] = gen_rtx_REG (HImode, REGNO (operands[2]));
2985 (define_insn "*iorsi3_w"
2986 [(set (match_operand:SI 0 "register_operand" "=r,&r")
2987 (ior:SI (and:SI (match_operand:SI 1 "register_operand" "0,0")
2989 (zero_extend:SI (match_operand:QI 2 "general_operand_src" "r,g>"))))]
2992 [(set_attr "length" "2,8")])
2994 (define_insn "*iorsi3_ashift_31"
2995 [(set (match_operand:SI 0 "register_operand" "=&r")
2996 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
2998 (match_operand:SI 2 "register_operand" "0")))]
3000 "rotxl.l\\t%S0\;bor\\t#0,%w1\;rotxr.l\\t%S0"
3001 [(set_attr "length" "6")
3002 (set_attr "cc" "set_znv")])
3004 (define_insn "*iorsi3_and_ashift"
3005 [(set (match_operand:SI 0 "register_operand" "=r")
3006 (ior:SI (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
3007 (match_operand:SI 2 "const_int_operand" "n"))
3008 (match_operand:SI 3 "single_one_operand" "n"))
3009 (match_operand:SI 4 "register_operand" "0")))]
3010 "(INTVAL (operands[3]) & ~0xffff) == 0"
3012 rtx srcpos = GEN_INT (exact_log2 (INTVAL (operands[3]))
3013 - INTVAL (operands[2]));
3014 rtx dstpos = GEN_INT (exact_log2 (INTVAL (operands[3])));
3015 operands[2] = srcpos;
3016 operands[3] = dstpos;
3017 return "bld\\t%Z2,%Y1\;bor\\t%Z3,%Y0\;bst\\t%Z3,%Y0";
3019 [(set_attr "length" "6")])
3021 (define_insn "*iorsi3_and_lshiftrt"
3022 [(set (match_operand:SI 0 "register_operand" "=r")
3023 (ior:SI (and:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3024 (match_operand:SI 2 "const_int_operand" "n"))
3025 (match_operand:SI 3 "single_one_operand" "n"))
3026 (match_operand:SI 4 "register_operand" "0")))]
3027 "((INTVAL (operands[3]) << INTVAL (operands[2])) & ~0xffff) == 0"
3029 rtx srcpos = GEN_INT (exact_log2 (INTVAL (operands[3]))
3030 + INTVAL (operands[2]));
3031 rtx dstpos = GEN_INT (exact_log2 (INTVAL (operands[3])));
3032 operands[2] = srcpos;
3033 operands[3] = dstpos;
3034 return "bld\\t%Z2,%Y1\;bor\\t%Z3,%Y0\;bst\\t%Z3,%Y0";
3036 [(set_attr "length" "6")])
3038 (define_insn "*iorsi3_zero_extract"
3039 [(set (match_operand:SI 0 "register_operand" "=r")
3040 (ior:SI (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
3042 (match_operand:SI 2 "const_int_operand" "n"))
3043 (match_operand:SI 3 "register_operand" "0")))]
3044 "INTVAL (operands[2]) < 16"
3045 "bld\\t%Z2,%Y1\;bor\\t#0,%w0\;bst\\t#0,%w0"
3046 [(set_attr "length" "6")])
3048 (define_insn "*iorsi3_and_lshiftrt_n_sb"
3049 [(set (match_operand:SI 0 "register_operand" "=r")
3050 (ior:SI (and:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3053 (match_operand:SI 2 "register_operand" "0")))]
3055 "rotl.l\\t%S1\;rotr.l\\t%S1\;bor\\t#1,%w0\;bst\\t#1,%w0"
3056 [(set_attr "length" "8")])
3058 (define_insn "*iorsi3_and_lshiftrt_9_sb"
3059 [(set (match_operand:SI 0 "register_operand" "=r")
3060 (ior:SI (and:SI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3062 (const_int 4194304))
3063 (match_operand:SI 2 "register_operand" "0")))
3064 (clobber (match_scratch:HI 3 "=&r"))]
3067 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3068 return "shll.l\\t%S1\;xor.w\\t%T3,%T3\;bst\\t#6,%s3\;or.w\\t%T3,%e0";
3070 return "rotl.l\\t%S1\;rotr.l\\t%S1\;xor.w\\t%T3,%T3\;bst\\t#6,%s3\;or.w\\t%T3,%e0";
3072 [(set_attr "length" "10")])
3074 ;; Used to OR the exponent of a float.
3076 (define_insn "*iorsi3_shift"
3077 [(set (match_operand:SI 0 "register_operand" "=r")
3078 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
3080 (match_operand:SI 2 "register_operand" "0")))
3081 (clobber (match_scratch:SI 3 "=&r"))]
3086 [(set (match_operand:SI 0 "register_operand" "")
3087 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "")
3090 (clobber (match_operand:SI 2 "register_operand" ""))]
3092 && find_regno_note (insn, REG_DEAD, REGNO (operands[1]))
3093 && REGNO (operands[0]) != REGNO (operands[1])"
3094 [(parallel [(set (match_dup 3)
3095 (ashift:HI (match_dup 3)
3097 (clobber (scratch:QI))])
3099 (ior:SI (ashift:SI (match_dup 1)
3103 operands[3] = gen_rtx_REG (HImode, REGNO (operands[1]));
3107 [(set (match_operand:SI 0 "register_operand" "")
3108 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "")
3111 (clobber (match_operand:SI 2 "register_operand" ""))]
3113 && !(find_regno_note (insn, REG_DEAD, REGNO (operands[1]))
3114 && REGNO (operands[0]) != REGNO (operands[1]))"
3117 (parallel [(set (match_dup 3)
3118 (ashift:HI (match_dup 3)
3120 (clobber (scratch:QI))])
3122 (ior:SI (ashift:SI (match_dup 2)
3126 operands[3] = gen_rtx_REG (HImode, REGNO (operands[2]));
3129 (define_insn "*iorsi2_and_1_lshiftrt_1"
3130 [(set (match_operand:SI 0 "register_operand" "=r")
3131 (ior:SI (and:SI (match_operand:SI 1 "register_operand" "0")
3133 (lshiftrt:SI (match_dup 1)
3136 "shlr.l\\t%S0\;bor\\t#0,%w0\;bst\\t#0,%w0"
3137 [(set_attr "length" "6")])
3139 (define_insn_and_split "*iorsi3_ashift_16_ashift_24"
3140 [(set (match_operand:SI 0 "register_operand" "=r")
3141 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "0")
3143 (ashift:SI (match_operand:SI 2 "register_operand" "r")
3147 "&& reload_completed"
3149 (ior:HI (ashift:HI (match_dup 4)
3152 (parallel [(set (match_dup 0)
3153 (ashift:SI (match_dup 0)
3155 (clobber (scratch:QI))])]
3157 operands[3] = gen_rtx_REG (HImode, REGNO (operands[0]));
3158 operands[4] = gen_rtx_REG (HImode, REGNO (operands[2]));
3161 (define_insn_and_split "*iorsi3_ashift_16_ashift_24_mem"
3162 [(set (match_operand:SI 0 "register_operand" "=&r")
3163 (ior:SI (and:SI (ashift:SI (subreg:SI (match_operand:QI 1 "memory_operand" "m") 0)
3165 (const_int 16711680))
3166 (ashift:SI (subreg:SI (match_operand:QI 2 "memory_operand" "m") 0)
3170 "&& reload_completed"
3172 (ior:HI (zero_extend:HI (match_dup 1))
3173 (ashift:HI (subreg:HI (match_dup 2) 0)
3175 (parallel [(set (match_dup 0)
3176 (ashift:SI (match_dup 0)
3178 (clobber (scratch:QI))])]
3180 operands[3] = gen_rtx_REG (HImode, REGNO (operands[0]));
3183 ;; Used to add the exponent of a float.
3185 (define_insn "*addsi3_shift"
3186 [(set (match_operand:SI 0 "register_operand" "=r")
3187 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
3188 (const_int 8388608))
3189 (match_operand:SI 2 "register_operand" "0")))
3190 (clobber (match_scratch:SI 3 "=&r"))]
3195 [(set (match_operand:SI 0 "register_operand" "")
3196 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
3197 (const_int 8388608))
3199 (clobber (match_operand:SI 2 "register_operand" ""))]
3201 && find_regno_note (insn, REG_DEAD, REGNO (operands[1]))
3202 && REGNO (operands[0]) != REGNO (operands[1])"
3203 [(parallel [(set (match_dup 3)
3204 (ashift:HI (match_dup 3)
3206 (clobber (scratch:QI))])
3208 (plus:SI (mult:SI (match_dup 1)
3212 operands[3] = gen_rtx_REG (HImode, REGNO (operands[1]));
3216 [(set (match_operand:SI 0 "register_operand" "")
3217 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
3218 (const_int 8388608))
3220 (clobber (match_operand:SI 2 "register_operand" ""))]
3222 && !(find_regno_note (insn, REG_DEAD, REGNO (operands[1]))
3223 && REGNO (operands[0]) != REGNO (operands[1]))"
3226 (parallel [(set (match_dup 3)
3227 (ashift:HI (match_dup 3)
3229 (clobber (scratch:QI))])
3231 (plus:SI (mult:SI (match_dup 2)
3235 operands[3] = gen_rtx_REG (HImode, REGNO (operands[2]));
3240 (define_insn_and_split "*ashiftsi_sextqi_7"
3241 [(set (match_operand:SI 0 "register_operand" "=r")
3242 (ashift:SI (sign_extend:SI (match_operand:QI 1 "register_operand" "0"))
3246 "&& reload_completed"
3247 [(parallel [(set (match_dup 2)
3248 (ashift:HI (match_dup 2)
3250 (clobber (scratch:QI))])
3252 (sign_extend:SI (match_dup 2)))
3253 (parallel [(set (match_dup 0)
3254 (ashiftrt:SI (match_dup 0)
3256 (clobber (scratch:QI))])]
3258 operands[2] = gen_rtx_REG (HImode, REGNO (operands[0]));
3261 ;; Storing a part of HImode to QImode.
3264 [(set (match_operand:QI 0 "general_operand_dst" "=rm<")
3265 (subreg:QI (lshiftrt:HI (match_operand:HI 1 "register_operand" "r")
3269 [(set_attr "cc" "set_znv")
3270 (set_attr "length" "8")])
3272 ;; Storing a part of SImode to QImode.
3275 [(set (match_operand:QI 0 "general_operand_dst" "=rm<")
3276 (subreg:QI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3280 [(set_attr "cc" "set_znv")
3281 (set_attr "length" "8")])
3284 [(set (match_operand:QI 0 "general_operand_dst" "=rm<")
3285 (subreg:QI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3287 (clobber (match_scratch:SI 2 "=&r"))]
3289 "mov.w\\t%e1,%f2\;mov.b\\t%w2,%R0"
3290 [(set_attr "cc" "set_znv")
3291 (set_attr "length" "10")])
3294 [(set (match_operand:QI 0 "general_operand_dst" "=rm<")
3295 (subreg:QI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
3297 (clobber (match_scratch:SI 2 "=&r"))]
3299 "mov.w\\t%e1,%f2\;mov.b\\t%x2,%R0"
3300 [(set_attr "cc" "set_znv")
3301 (set_attr "length" "10")])
3303 (define_insn_and_split ""
3305 (if_then_else (eq (zero_extract:SI (subreg:SI (match_operand:QI 0 "register_operand" "") 0)
3309 (label_ref (match_operand 1 "" ""))
3314 [(set (cc0) (compare (match_dup 0)
3317 (if_then_else (ge (cc0)
3319 (label_ref (match_dup 1))
3323 (define_insn_and_split ""
3325 (if_then_else (ne (zero_extract:SI (subreg:SI (match_operand:QI 0 "register_operand" "") 0)
3329 (label_ref (match_operand 1 "" ""))
3334 [(set (cc0) (compare (match_dup 0)
3337 (if_then_else (lt (cc0)
3339 (label_ref (match_dup 1))
3343 (include "peepholes.md")