;; Machine description for the TMS320C[34]x for GCC
|
;; Machine description for the TMS320C[34]x for GCC
|
;; Copyright (C) 1994, 1995, 1996, 1997, 1998,
|
;; Copyright (C) 1994, 1995, 1996, 1997, 1998,
|
;; 1999, 2000, 2002, 2004, 2005, 2007 Free Software Foundation, Inc.
|
;; 1999, 2000, 2002, 2004, 2005, 2007 Free Software Foundation, Inc.
|
|
|
;; Contributed by Michael Hayes (m.hayes@elec.canterbury.ac.nz)
|
;; Contributed by Michael Hayes (m.hayes@elec.canterbury.ac.nz)
|
;; and Herman Ten Brugge (Haj.Ten.Brugge@net.HCC.nl)
|
;; and Herman Ten Brugge (Haj.Ten.Brugge@net.HCC.nl)
|
|
|
;; This file is part of GCC.
|
;; This file is part of GCC.
|
|
|
;; GCC is free software; you can redistribute it and/or modify
|
;; GCC is free software; you can redistribute it and/or modify
|
;; it under the terms of the GNU General Public License as published by
|
;; it under the terms of the GNU General Public License as published by
|
;; the Free Software Foundation; either version 3, or (at your option)
|
;; the Free Software Foundation; either version 3, or (at your option)
|
;; any later version.
|
;; any later version.
|
|
|
;; GCC is distributed in the hope that it will be useful,
|
;; GCC is distributed in the hope that it will be useful,
|
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
|
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
|
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
;; GNU General Public License for more details.
|
;; GNU General Public License for more details.
|
|
|
;; You should have received a copy of the GNU General Public License
|
;; You should have received a copy of the GNU General Public License
|
;; along with GCC; see the file COPYING3. If not see
|
;; along with GCC; see the file COPYING3. If not see
|
;; .
|
;; .
|
|
|
;
|
;
|
; TODO :
|
; TODO :
|
; Try using PQImode again for addresses since C30 only uses
|
; Try using PQImode again for addresses since C30 only uses
|
; 24-bit addresses. Ideally GCC would emit different insns
|
; 24-bit addresses. Ideally GCC would emit different insns
|
; for QImode and Pmode, whether Pmode was QImode or PQImode.
|
; for QImode and Pmode, whether Pmode was QImode or PQImode.
|
; For addresses we wouldn't have to have a clobber of the CC
|
; For addresses we wouldn't have to have a clobber of the CC
|
; associated with each insn and we could use MPYI in address
|
; associated with each insn and we could use MPYI in address
|
; calculations without having to synthesize a proper 32 bit multiply.
|
; calculations without having to synthesize a proper 32 bit multiply.
|
|
|
; Additional C30/C40 instructions not coded:
|
; Additional C30/C40 instructions not coded:
|
; CALLcond, IACK, IDLE, LDE, LDFI, LDII, LDM, NORM, RETIcond
|
; CALLcond, IACK, IDLE, LDE, LDFI, LDII, LDM, NORM, RETIcond
|
; ROLC, RORC, SIGI, STFI, STII, SUBC, SWI
|
; ROLC, RORC, SIGI, STFI, STII, SUBC, SWI
|
|
|
; Additional C40 instructions not coded:
|
; Additional C40 instructions not coded:
|
; LDEP, LDPE, LWRct, LAJcond, RETIcondD
|
; LDEP, LDPE, LWRct, LAJcond, RETIcondD
|
|
|
;
|
;
|
; C4x MODES
|
; C4x MODES
|
;
|
;
|
; QImode char, short, int, long (32-bits)
|
; QImode char, short, int, long (32-bits)
|
; HImode long long (64-bits)
|
; HImode long long (64-bits)
|
; QFmode float, double (32-bits)
|
; QFmode float, double (32-bits)
|
; HFmode long double (40-bits)
|
; HFmode long double (40-bits)
|
; CCmode
|
; CCmode
|
; CC_NOOVmode
|
; CC_NOOVmode
|
|
|
;
|
;
|
; C4x PREDICATES:
|
; C4x PREDICATES:
|
;
|
;
|
; comparison_operator LT, GT, LE, GE, LTU, GTU, LEU, GEU, EQ, NE
|
; comparison_operator LT, GT, LE, GE, LTU, GTU, LEU, GEU, EQ, NE
|
; memory_operand memory [m]
|
; memory_operand memory [m]
|
; immediate_operand immediate constant [IKN]
|
; immediate_operand immediate constant [IKN]
|
; register_operand register [rf]
|
; register_operand register [rf]
|
; general_operand register, memory, constant [rfmI]
|
; general_operand register, memory, constant [rfmI]
|
|
|
; addr_reg_operand AR0-AR7, pseudo reg [a]
|
; addr_reg_operand AR0-AR7, pseudo reg [a]
|
; sp_reg_operand SP [b]
|
; sp_reg_operand SP [b]
|
; std_reg_operand AR0-AR7, IR0-IR1, RC, RS, RE, SP, pseudo [c]
|
; std_reg_operand AR0-AR7, IR0-IR1, RC, RS, RE, SP, pseudo [c]
|
; ext_reg_operand R0-R11, pseudo reg [f]
|
; ext_reg_operand R0-R11, pseudo reg [f]
|
; ext_low_reg_operand R0-R7, pseudo reg [q]
|
; ext_low_reg_operand R0-R7, pseudo reg [q]
|
; index_reg_operand IR0-IR1, pseudo reg [x]
|
; index_reg_operand IR0-IR1, pseudo reg [x]
|
; st_reg_operand ST [y]
|
; st_reg_operand ST [y]
|
; dp_reg_operand DP [z]
|
; dp_reg_operand DP [z]
|
; stik_const_operand 5-bit const [K]
|
; stik_const_operand 5-bit const [K]
|
; src_operand general operand [rfHmI]
|
; src_operand general operand [rfHmI]
|
; par_ind_operand indirect S mode (ARx + 0, 1, IRx) [S<>]
|
; par_ind_operand indirect S mode (ARx + 0, 1, IRx) [S<>]
|
; parallel_operand par_ind_operand or ext_low_reg_operand
|
; parallel_operand par_ind_operand or ext_low_reg_operand
|
; symbolic_address_operand
|
; symbolic_address_operand
|
; call_address_operand
|
; call_address_operand
|
|
|
; ADDI src2, src1, dst three operand op
|
; ADDI src2, src1, dst three operand op
|
; ADDI src, dst two operand op
|
; ADDI src, dst two operand op
|
|
|
; Note that the predicates are only used when selecting a pattern
|
; Note that the predicates are only used when selecting a pattern
|
; to determine if an operand is valid.
|
; to determine if an operand is valid.
|
|
|
; The constraints then select which of the possible valid operands
|
; The constraints then select which of the possible valid operands
|
; is present (and guide register selection). The actual assembly
|
; is present (and guide register selection). The actual assembly
|
; instruction is then selected on the basis of the constraints.
|
; instruction is then selected on the basis of the constraints.
|
|
|
; The extra constraint (valid_operands) is used to determine if
|
; The extra constraint (valid_operands) is used to determine if
|
; the combination of operands is legitimate for the pattern.
|
; the combination of operands is legitimate for the pattern.
|
|
|
;
|
;
|
; C4x CONSTRAINTS:
|
; C4x CONSTRAINTS:
|
;
|
;
|
; a address reg AR0-AR7
|
; a address reg AR0-AR7
|
; b stack pointer SP
|
; b stack pointer SP
|
; c other int reg AR0-AR7, IR0-IR1, RC, RS, RE
|
; c other int reg AR0-AR7, IR0-IR1, RC, RS, RE
|
; d fp reg R0-R11 (sets CC when dst)
|
; d fp reg R0-R11 (sets CC when dst)
|
; e
|
; e
|
; f fp reg R0-R11 (sets CC when dst)
|
; f fp reg R0-R11 (sets CC when dst)
|
; g general reg, memory, constant
|
; g general reg, memory, constant
|
; h fp reg (HFmode) R0-R11 (sets CC when dst)
|
; h fp reg (HFmode) R0-R11 (sets CC when dst)
|
; i immediate int constant
|
; i immediate int constant
|
; j
|
; j
|
; k block count BK
|
; k block count BK
|
; l
|
; l
|
; m memory
|
; m memory
|
; n immediate int constant with known numeric value
|
; n immediate int constant with known numeric value
|
; o offsettable memory
|
; o offsettable memory
|
; p memory address
|
; p memory address
|
; q low fp reg R0-R7 (sets CC when dst)
|
; q low fp reg R0-R7 (sets CC when dst)
|
; r general reg R0-R11, AR0-AR7, IR0-IR1, RC, RS, RE
|
; r general reg R0-R11, AR0-AR7, IR0-IR1, RC, RS, RE
|
; s immediate int constant (value not explicit)
|
; s immediate int constant (value not explicit)
|
; t R0-R1
|
; t R0-R1
|
; u R2-R3
|
; u R2-R3
|
; v repeat count reg RC
|
; v repeat count reg RC
|
; w
|
; w
|
; x index reg IR0-IR1
|
; x index reg IR0-IR1
|
; y status (CC) reg ST
|
; y status (CC) reg ST
|
; z data pointer DP
|
; z data pointer DP
|
|
|
; G fp zero
|
; G fp zero
|
; H fp 16-bit constant
|
; H fp 16-bit constant
|
; I signed 16-bit
|
; I signed 16-bit
|
; J signed 8-bit (C4x only)
|
; J signed 8-bit (C4x only)
|
; K signed 5-bit (C4x only)
|
; K signed 5-bit (C4x only)
|
; L unsigned 16-bit
|
; L unsigned 16-bit
|
; M unsigned 8-bit (C4x only)
|
; M unsigned 8-bit (C4x only)
|
; N ones complement of unsigned 16-bit
|
; N ones complement of unsigned 16-bit
|
; O 16 bit high constant
|
; O 16 bit high constant
|
; Q ARx + 9-bit signed disp
|
; Q ARx + 9-bit signed disp
|
; R ARx + 5-bit unsigned disp (C4x only)
|
; R ARx + 5-bit unsigned disp (C4x only)
|
; S ARx + 0, 1, IRx disp
|
; S ARx + 0, 1, IRx disp
|
; T direct memory operand
|
; T direct memory operand
|
; V non offsettable memory
|
; V non offsettable memory
|
; X any operand
|
; X any operand
|
; < memory operand with autodecrement addressing
|
; < memory operand with autodecrement addressing
|
; > memory operand with autoincrement addressing
|
; > memory operand with autoincrement addressing
|
; { memory operand with pre-modify addressing
|
; { memory operand with pre-modify addressing
|
; } memory operand with post-modify addressing
|
; } memory operand with post-modify addressing
|
|
|
; Note that the 'd', 'f', and 'h' constraints are equivalent.
|
; Note that the 'd', 'f', and 'h' constraints are equivalent.
|
; The m constraint is equivalent to 'QT<>{}'
|
; The m constraint is equivalent to 'QT<>{}'
|
|
|
; Note we cannot use the 'g' constraint with Pmode (i.e, QImode)
|
; Note we cannot use the 'g' constraint with Pmode (i.e, QImode)
|
; operations since LEGITIMATE_CONSTANT_P accepts SYMBOL_REF.
|
; operations since LEGITIMATE_CONSTANT_P accepts SYMBOL_REF.
|
; So instead we use 'rIm' for signed operands or 'rLm' for unsigned operands.
|
; So instead we use 'rIm' for signed operands or 'rLm' for unsigned operands.
|
|
|
; Note that the constraints are used to select the operands
|
; Note that the constraints are used to select the operands
|
; for a chosen pattern. The constraint that requires the fewest
|
; for a chosen pattern. The constraint that requires the fewest
|
; instructions to load an operand is chosen.
|
; instructions to load an operand is chosen.
|
|
|
; Note that the 'r' constraint is mostly only used for src integer register
|
; Note that the 'r' constraint is mostly only used for src integer register
|
; operands, while 'c' and 'd' constraints are generally only used for dst
|
; operands, while 'c' and 'd' constraints are generally only used for dst
|
; integer register operands (the 'r' constraint is the union of the 'c' and
|
; integer register operands (the 'r' constraint is the union of the 'c' and
|
; 'd' constraints). When a register satisfying the 'd' constraint
|
; 'd' constraints). When a register satisfying the 'd' constraint
|
; is used as a dst operand, the CC gets clobbered (except for LDIcond)---but
|
; is used as a dst operand, the CC gets clobbered (except for LDIcond)---but
|
; not for 'c'.
|
; not for 'c'.
|
|
|
; The 'f' constraint is only for float register operands---when
|
; The 'f' constraint is only for float register operands---when
|
; a register satisfying the 'f' constraint is used as a dst operand,
|
; a register satisfying the 'f' constraint is used as a dst operand,
|
; the CC gets clobbered (except for LDFcond).
|
; the CC gets clobbered (except for LDFcond).
|
|
|
; The ! in front of the 'b' constraint says to GCC to disparage the
|
; The ! in front of the 'b' constraint says to GCC to disparage the
|
; use of this constraint. The 'b' constraint applies only to the SP.
|
; use of this constraint. The 'b' constraint applies only to the SP.
|
|
|
; Note that we deal with the condition code CC like some of the RISC
|
; Note that we deal with the condition code CC like some of the RISC
|
; architectures (arm, sh, sparc) where it is stored in a general register,
|
; architectures (arm, sh, sparc) where it is stored in a general register,
|
; in this case the hard register ST (21). Unlike these other architectures
|
; in this case the hard register ST (21). Unlike these other architectures
|
; that do not set the CC with many instructions, the C[34]x architectures
|
; that do not set the CC with many instructions, the C[34]x architectures
|
; sets the CC for many instructions when the destination register is
|
; sets the CC for many instructions when the destination register is
|
; an extended precision register. While it would have been easier
|
; an extended precision register. While it would have been easier
|
; to use the generic cc0 register to store the CC, as with most of
|
; to use the generic cc0 register to store the CC, as with most of
|
; the other ported architectures, this constrains the setting and testing
|
; the other ported architectures, this constrains the setting and testing
|
; of the CC to be consecutive insns. Thus we would reduce the benefit
|
; of the CC to be consecutive insns. Thus we would reduce the benefit
|
; of scheduling instructions to avoid pipeline conflicts and filling of
|
; of scheduling instructions to avoid pipeline conflicts and filling of
|
; delayed branch slots.
|
; delayed branch slots.
|
|
|
; Since the C[34]x has many instructions that set the CC, we pay the
|
; Since the C[34]x has many instructions that set the CC, we pay the
|
; price of having to explicitly define which insns clobber the CC
|
; price of having to explicitly define which insns clobber the CC
|
; (rather than using the macro NOTICE_UPDATE_CC).
|
; (rather than using the macro NOTICE_UPDATE_CC).
|
|
|
; Note that many patterns say that the CC is clobbered when in fact
|
; Note that many patterns say that the CC is clobbered when in fact
|
; that it may not be (depending on the destination register).
|
; that it may not be (depending on the destination register).
|
; We have to cover ourselves if an extended precision register
|
; We have to cover ourselves if an extended precision register
|
; is allocated to the destination register.
|
; is allocated to the destination register.
|
; Unfortunately, it is not easy to tell GCC that the clobbering of CC
|
; Unfortunately, it is not easy to tell GCC that the clobbering of CC
|
; is register dependent. If we could tolerate the ST register being
|
; is register dependent. If we could tolerate the ST register being
|
; copied about, then we could store the CC in a pseudo register and
|
; copied about, then we could store the CC in a pseudo register and
|
; use constructs such as (clobber (match_scratch:CC N "&y,X")) to
|
; use constructs such as (clobber (match_scratch:CC N "&y,X")) to
|
; indicate that the 'y' class (ST register) is clobbered for the
|
; indicate that the 'y' class (ST register) is clobbered for the
|
; first combination of operands but not with the second.
|
; first combination of operands but not with the second.
|
; I tried this approach for a while but reload got unhappy since I
|
; I tried this approach for a while but reload got unhappy since I
|
; didn't allow it to move the CC around.
|
; didn't allow it to move the CC around.
|
|
|
; Note that fundamental operations, such as moves, must not clobber the
|
; Note that fundamental operations, such as moves, must not clobber the
|
; CC. Thus movqi chooses a move instruction that doesn't clobber the CC.
|
; CC. Thus movqi chooses a move instruction that doesn't clobber the CC.
|
; If GCC wants to combine a move with a compare, it is smart enough to
|
; If GCC wants to combine a move with a compare, it is smart enough to
|
; chose the move instruction that sets the CC.
|
; chose the move instruction that sets the CC.
|
|
|
; Unfortunately, the C[34]x instruction set does not have arithmetic or
|
; Unfortunately, the C[34]x instruction set does not have arithmetic or
|
; logical operations that never touch the CC. We thus have to assume
|
; logical operations that never touch the CC. We thus have to assume
|
; that the CC may be clobbered at all times. If we define patterns
|
; that the CC may be clobbered at all times. If we define patterns
|
; such as addqi without the clobber of CC, then GCC will be forced
|
; such as addqi without the clobber of CC, then GCC will be forced
|
; to use registers such as the auxiliary registers which can cause
|
; to use registers such as the auxiliary registers which can cause
|
; horrible pipeline conflicts. The tradeoff is that GCC can't now
|
; horrible pipeline conflicts. The tradeoff is that GCC can't now
|
; sneak in an add instruction between setting and testing of the CC.
|
; sneak in an add instruction between setting and testing of the CC.
|
|
|
; Most of the C[34]x instructions require operands of the following formats,
|
; Most of the C[34]x instructions require operands of the following formats,
|
; where imm represents an immediate constant, dir a direct memory reference,
|
; where imm represents an immediate constant, dir a direct memory reference,
|
; ind an indirect memory reference, and reg a register:
|
; ind an indirect memory reference, and reg a register:
|
|
|
; src2 (op2) src1 (op1) dst (op0)
|
; src2 (op2) src1 (op1) dst (op0)
|
; imm dir ind reg | imm dir ind reg | reg Notes
|
; imm dir ind reg | imm dir ind reg | reg Notes
|
;---------------------+----------------------+------
|
;---------------------+----------------------+------
|
; ILH T Q<> r | - - - 0 | r 2 operand
|
; ILH T Q<> r | - - - 0 | r 2 operand
|
; - - S<> r | - - S<> r | r
|
; - - S<> r | - - S<> r | r
|
; J - R - | - - R r | r C4x
|
; J - R - | - - R r | r C4x
|
|
|
; Arithmetic operations use the I, J constraints for immediate constants,
|
; Arithmetic operations use the I, J constraints for immediate constants,
|
; while logical operations use the L, J constraints. Floating point
|
; while logical operations use the L, J constraints. Floating point
|
; operations use the H constraint for immediate constants.
|
; operations use the H constraint for immediate constants.
|
|
|
; With most instructions the src2 and src1 operands are commutative
|
; With most instructions the src2 and src1 operands are commutative
|
; (except for SUB, SUBR, ANDN). The assembler considers
|
; (except for SUB, SUBR, ANDN). The assembler considers
|
; ADDI 10, R0, R1 and ADDI R0, 10, R1 to be equivalent.
|
; ADDI 10, R0, R1 and ADDI R0, 10, R1 to be equivalent.
|
; We thus match src2 and src1 with the src_operand predicate and
|
; We thus match src2 and src1 with the src_operand predicate and
|
; use valid_operands as the extra constraint to reject invalid
|
; use valid_operands as the extra constraint to reject invalid
|
; operand combinations. For example, ADDI @foo, @bar, R0.
|
; operand combinations. For example, ADDI @foo, @bar, R0.
|
|
|
; Note that we use the ? modifier so that reload doesn't preferentially
|
; Note that we use the ? modifier so that reload doesn't preferentially
|
; try the alternative where three registers are acceptable as
|
; try the alternative where three registers are acceptable as
|
; operands (whenever an operand requires reloading). Instead it will try
|
; operands (whenever an operand requires reloading). Instead it will try
|
; the 2 operand form which will produce better code since it won't require
|
; the 2 operand form which will produce better code since it won't require
|
; a new spill register.
|
; a new spill register.
|
|
|
; Note that the floating point representation of 0.0 on the C4x
|
; Note that the floating point representation of 0.0 on the C4x
|
; is 0x80000000 (-2147483648). This value produces a warning
|
; is 0x80000000 (-2147483648). This value produces a warning
|
; message on 32-bit machines about the decimal constant being so large
|
; message on 32-bit machines about the decimal constant being so large
|
; that it is unsigned.
|
; that it is unsigned.
|
|
|
; With two operand instructions patterns having two sets,
|
; With two operand instructions patterns having two sets,
|
; the compare set must come first to keep the combiner happy.
|
; the compare set must come first to keep the combiner happy.
|
; While the combiner seems to cope most of the time with the
|
; While the combiner seems to cope most of the time with the
|
; compare set coming second, it's best to have it first.
|
; compare set coming second, it's best to have it first.
|
|
|
;
|
;
|
; C4x CONSTANT attributes
|
; C4x CONSTANT attributes
|
;
|
;
|
(define_attr "cpu" "c4x,c3x"
|
(define_attr "cpu" "c4x,c3x"
|
(const
|
(const
|
(cond [(symbol_ref "TARGET_C3X") (const_string "c3x")]
|
(cond [(symbol_ref "TARGET_C3X") (const_string "c3x")]
|
(const_string "c4x"))))
|
(const_string "c4x"))))
|
|
|
;
|
;
|
; C4x INSN ATTRIBUTES:
|
; C4x INSN ATTRIBUTES:
|
;
|
;
|
; lda load address, non-clobber CC
|
; lda load address, non-clobber CC
|
; store memory store, non-clobber CC
|
; store memory store, non-clobber CC
|
; load_load parallel memory loads, non-clobber CC
|
; load_load parallel memory loads, non-clobber CC
|
; load_store parallel memory load and store, non-clobber CC
|
; load_store parallel memory load and store, non-clobber CC
|
; store_load parallel memory store and load, non-clobber CC
|
; store_load parallel memory store and load, non-clobber CC
|
; store_store parallel memory stores, non-clobber CC
|
; store_store parallel memory stores, non-clobber CC
|
; unary two operand arithmetic, non-clobber CC
|
; unary two operand arithmetic, non-clobber CC
|
; unarycc two operand arithmetic, clobber CC
|
; unarycc two operand arithmetic, clobber CC
|
; binary three operand arithmetic, non-clobber CC
|
; binary three operand arithmetic, non-clobber CC
|
; binarycc three operand arithmetic, clobber CC
|
; binarycc three operand arithmetic, clobber CC
|
; compare compare, clobber CC
|
; compare compare, clobber CC
|
; call function call
|
; call function call
|
; rets return from subroutine
|
; rets return from subroutine
|
; jump unconditional branch
|
; jump unconditional branch
|
; jmpc conditional branch
|
; jmpc conditional branch
|
; db decrement and branch (unconditional)
|
; db decrement and branch (unconditional)
|
; dbc decrement and branch (conditional)
|
; dbc decrement and branch (conditional)
|
; ldp load DP
|
; ldp load DP
|
; push stack push
|
; push stack push
|
; pop stack pop
|
; pop stack pop
|
; repeat block repeat
|
; repeat block repeat
|
; repeat_top block repeat top
|
; repeat_top block repeat top
|
; laj link and jump
|
; laj link and jump
|
; multi multiple instruction
|
; multi multiple instruction
|
; misc nop (default)
|
; misc nop (default)
|
|
|
; The only real instructions that affect things are the ones that modify
|
; The only real instructions that affect things are the ones that modify
|
; address registers and ones that call or jump. Note that the number
|
; address registers and ones that call or jump. Note that the number
|
; of operands refers to the RTL insn pattern, not the number of explicit
|
; of operands refers to the RTL insn pattern, not the number of explicit
|
; operands in the machine instruction.
|
; operands in the machine instruction.
|
;
|
;
|
(define_attr "type" "lda,store,unary,unarycc,binary,binarycc,compare,call,rets,jump,jmpc,db,dbc,misc,ldp,repeat,repeat_top,laj,load_load,load_store,store_load,store_store,push,pop,multi"
|
(define_attr "type" "lda,store,unary,unarycc,binary,binarycc,compare,call,rets,jump,jmpc,db,dbc,misc,ldp,repeat,repeat_top,laj,load_load,load_store,store_load,store_store,push,pop,multi"
|
(const_string "misc"))
|
(const_string "misc"))
|
|
|
|
|
; Some instructions operate on unsigned data constants, some on signed data
|
; Some instructions operate on unsigned data constants, some on signed data
|
; constants, or the ones complement of unsigned constants.
|
; constants, or the ones complement of unsigned constants.
|
; This differentiates them. Default to signed. This attribute
|
; This differentiates them. Default to signed. This attribute
|
; is used by the macro SMALL_CONST () (defined in c4x.h) to determine
|
; is used by the macro SMALL_CONST () (defined in c4x.h) to determine
|
; whether an immediate integer constant will fit within the instruction,
|
; whether an immediate integer constant will fit within the instruction,
|
; or will have to be loaded using direct addressing from memory.
|
; or will have to be loaded using direct addressing from memory.
|
; Note that logical operations assume unsigned integers whereas
|
; Note that logical operations assume unsigned integers whereas
|
; arithmetic operations assume signed integers. Note that the C4x
|
; arithmetic operations assume signed integers. Note that the C4x
|
; small immediate constant (J) used as src2 in three operand instructions
|
; small immediate constant (J) used as src2 in three operand instructions
|
; is always signed. not_uint16 refers to a number that fits into 16-bits
|
; is always signed. not_uint16 refers to a number that fits into 16-bits
|
; when one's complemented.
|
; when one's complemented.
|
;
|
;
|
(define_attr "data" "int16,uint16,high_16,not_uint16" (const_string "int16"))
|
(define_attr "data" "int16,uint16,high_16,not_uint16" (const_string "int16"))
|
|
|
(define_asm_attributes
|
(define_asm_attributes
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
;
|
;
|
; C4x DELAY SLOTS
|
; C4x DELAY SLOTS
|
;
|
;
|
; Define delay slot scheduling for branch and call instructions.
|
; Define delay slot scheduling for branch and call instructions.
|
; The C[34]x has three delay slots. Note that none of the three instructions
|
; The C[34]x has three delay slots. Note that none of the three instructions
|
; that follow a delayed branch can be a Bcond, BcondD, BR, BRD, DBcond,
|
; that follow a delayed branch can be a Bcond, BcondD, BR, BRD, DBcond,
|
; DBcondD, CALL, CALLcond, TRAPcond, RETIcond, RETScond, RPTB, RPTS, or IDLE.
|
; DBcondD, CALL, CALLcond, TRAPcond, RETIcond, RETScond, RPTB, RPTS, or IDLE.
|
;
|
;
|
; Annulled branches are a bit difficult because the next instructions
|
; Annulled branches are a bit difficult because the next instructions
|
; are preprocessed.
|
; are preprocessed.
|
; The table below shows what phase of the c4x is executed.
|
; The table below shows what phase of the c4x is executed.
|
; BccA[TF] label
|
; BccA[TF] label
|
; op1 fetch, decode and read executed
|
; op1 fetch, decode and read executed
|
; op2 fetch and decode executed
|
; op2 fetch and decode executed
|
; op3 fetch executed
|
; op3 fetch executed
|
; This means that we can allow any instruction in the last delay slot
|
; This means that we can allow any instruction in the last delay slot
|
; and only instructions which modify registers in the first two.
|
; and only instructions which modify registers in the first two.
|
; lda cannot be executed in the first delay slot
|
; lda cannot be executed in the first delay slot
|
; and ldpk cannot be executed in the first two delay slots.
|
; and ldpk cannot be executed in the first two delay slots.
|
|
|
(define_attr "onlyreg" "false,true"
|
(define_attr "onlyreg" "false,true"
|
(cond [(eq_attr "type" "unary,unarycc")
|
(cond [(eq_attr "type" "unary,unarycc")
|
(if_then_else (and (match_operand 0 "reg_imm_operand" "")
|
(if_then_else (and (match_operand 0 "reg_imm_operand" "")
|
(match_operand 1 "reg_imm_operand" ""))
|
(match_operand 1 "reg_imm_operand" ""))
|
(const_string "true") (const_string "false"))
|
(const_string "true") (const_string "false"))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (and (match_operand 0 "reg_imm_operand" "")
|
(if_then_else (and (match_operand 0 "reg_imm_operand" "")
|
(and (match_operand 1 "reg_imm_operand" "")
|
(and (match_operand 1 "reg_imm_operand" "")
|
(match_operand 2 "reg_imm_operand" "")))
|
(match_operand 2 "reg_imm_operand" "")))
|
(const_string "true") (const_string "false"))]
|
(const_string "true") (const_string "false"))]
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "onlyreg_nomod" "false,true"
|
(define_attr "onlyreg_nomod" "false,true"
|
(cond [(eq_attr "type" "unary,unarycc,compare,lda,store")
|
(cond [(eq_attr "type" "unary,unarycc,compare,lda,store")
|
(if_then_else (and (match_operand 0 "not_modify_reg" "")
|
(if_then_else (and (match_operand 0 "not_modify_reg" "")
|
(match_operand 1 "not_modify_reg" ""))
|
(match_operand 1 "not_modify_reg" ""))
|
(const_string "true") (const_string "false"))
|
(const_string "true") (const_string "false"))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (and (match_operand 0 "not_modify_reg" "")
|
(if_then_else (and (match_operand 0 "not_modify_reg" "")
|
(and (match_operand 1 "not_modify_reg" "")
|
(and (match_operand 1 "not_modify_reg" "")
|
(match_operand 2 "not_modify_reg" "")))
|
(match_operand 2 "not_modify_reg" "")))
|
(const_string "true") (const_string "false"))]
|
(const_string "true") (const_string "false"))]
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "not_repeat_reg" "false,true"
|
(define_attr "not_repeat_reg" "false,true"
|
(cond [(eq_attr "type" "unary,unarycc,compare,lda,ldp,store")
|
(cond [(eq_attr "type" "unary,unarycc,compare,lda,ldp,store")
|
(if_then_else (and (match_operand 0 "not_rc_reg" "")
|
(if_then_else (and (match_operand 0 "not_rc_reg" "")
|
(match_operand 1 "not_rc_reg" ""))
|
(match_operand 1 "not_rc_reg" ""))
|
(const_string "true") (const_string "false"))
|
(const_string "true") (const_string "false"))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (and (match_operand 0 "not_rc_reg" "")
|
(if_then_else (and (match_operand 0 "not_rc_reg" "")
|
(and (match_operand 1 "not_rc_reg" "")
|
(and (match_operand 1 "not_rc_reg" "")
|
(match_operand 2 "not_rc_reg" "")))
|
(match_operand 2 "not_rc_reg" "")))
|
(const_string "true") (const_string "false"))]
|
(const_string "true") (const_string "false"))]
|
(const_string "false")))
|
(const_string "false")))
|
|
|
/* Disable compare because the c4x contains a bug. The cmpi insn sets the CC
|
/* Disable compare because the c4x contains a bug. The cmpi insn sets the CC
|
in the read phase of the pipeline instead of the execution phase when
|
in the read phase of the pipeline instead of the execution phase when
|
two registers are compared. */
|
two registers are compared. */
|
(define_attr "in_annul_slot_1" "false,true"
|
(define_attr "in_annul_slot_1" "false,true"
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(eq_attr "type" "!jump,call,rets,jmpc,compare,db,dbc,repeat,repeat_top,laj,push,pop,lda,ldp,multi"))
|
(eq_attr "type" "!jump,call,rets,jmpc,compare,db,dbc,repeat,repeat_top,laj,push,pop,lda,ldp,multi"))
|
(eq_attr "onlyreg" "true"))
|
(eq_attr "onlyreg" "true"))
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "in_annul_slot_2" "false,true"
|
(define_attr "in_annul_slot_2" "false,true"
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
|
(eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
|
(eq_attr "onlyreg_nomod" "true"))
|
(eq_attr "onlyreg_nomod" "true"))
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
/* Disable ldp because the c4x contains a bug. The ldp insn modifies
|
/* Disable ldp because the c4x contains a bug. The ldp insn modifies
|
the dp register when the insn is anulled or not.
|
the dp register when the insn is anulled or not.
|
Also disable autoincrement insns because of a silicon bug. */
|
Also disable autoincrement insns because of a silicon bug. */
|
(define_attr "in_annul_slot_3" "false,true"
|
(define_attr "in_annul_slot_3" "false,true"
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(if_then_else (and (and (eq_attr "cpu" "c4x")
|
(eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
|
(eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
|
(eq_attr "onlyreg_nomod" "true"))
|
(eq_attr "onlyreg_nomod" "true"))
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "in_delay_slot" "false,true"
|
(define_attr "in_delay_slot" "false,true"
|
(if_then_else (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
|
(if_then_else (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "in_repeat_slot" "false,true"
|
(define_attr "in_repeat_slot" "false,true"
|
(if_then_else (and (eq_attr "cpu" "c4x")
|
(if_then_else (and (eq_attr "cpu" "c4x")
|
(and (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
|
(and (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,multi")
|
(eq_attr "not_repeat_reg" "true")))
|
(eq_attr "not_repeat_reg" "true")))
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_attr "in_dbc_slot" "false,true"
|
(define_attr "in_dbc_slot" "false,true"
|
(if_then_else (eq_attr "type" "!jump,call,rets,jmpc,unarycc,binarycc,compare,db,dbc,repeat,repeat_top,laj,multi")
|
(if_then_else (eq_attr "type" "!jump,call,rets,jmpc,unarycc,binarycc,compare,db,dbc,repeat,repeat_top,laj,multi")
|
(const_string "true")
|
(const_string "true")
|
(const_string "false")))
|
(const_string "false")))
|
|
|
(define_delay (eq_attr "type" "jmpc")
|
(define_delay (eq_attr "type" "jmpc")
|
[(eq_attr "in_delay_slot" "true")
|
[(eq_attr "in_delay_slot" "true")
|
(eq_attr "in_annul_slot_1" "true")
|
(eq_attr "in_annul_slot_1" "true")
|
(eq_attr "in_annul_slot_1" "true")
|
(eq_attr "in_annul_slot_1" "true")
|
|
|
(eq_attr "in_delay_slot" "true")
|
(eq_attr "in_delay_slot" "true")
|
(eq_attr "in_annul_slot_2" "true")
|
(eq_attr "in_annul_slot_2" "true")
|
(eq_attr "in_annul_slot_2" "true")
|
(eq_attr "in_annul_slot_2" "true")
|
|
|
(eq_attr "in_delay_slot" "true")
|
(eq_attr "in_delay_slot" "true")
|
(eq_attr "in_annul_slot_3" "true")
|
(eq_attr "in_annul_slot_3" "true")
|
(eq_attr "in_annul_slot_3" "true") ])
|
(eq_attr "in_annul_slot_3" "true") ])
|
|
|
|
|
(define_delay (eq_attr "type" "repeat_top")
|
(define_delay (eq_attr "type" "repeat_top")
|
[(eq_attr "in_repeat_slot" "true") (nil) (nil)
|
[(eq_attr "in_repeat_slot" "true") (nil) (nil)
|
(eq_attr "in_repeat_slot" "true") (nil) (nil)
|
(eq_attr "in_repeat_slot" "true") (nil) (nil)
|
(eq_attr "in_repeat_slot" "true") (nil) (nil)])
|
(eq_attr "in_repeat_slot" "true") (nil) (nil)])
|
|
|
(define_delay (eq_attr "type" "jump,db")
|
(define_delay (eq_attr "type" "jump,db")
|
[(eq_attr "in_delay_slot" "true") (nil) (nil)
|
[(eq_attr "in_delay_slot" "true") (nil) (nil)
|
(eq_attr "in_delay_slot" "true") (nil) (nil)
|
(eq_attr "in_delay_slot" "true") (nil) (nil)
|
(eq_attr "in_delay_slot" "true") (nil) (nil)])
|
(eq_attr "in_delay_slot" "true") (nil) (nil)])
|
|
|
|
|
; Decrement and branch conditional instructions cannot modify the
|
; Decrement and branch conditional instructions cannot modify the
|
; condition codes for the cycles in the delay slots.
|
; condition codes for the cycles in the delay slots.
|
;
|
;
|
(define_delay (eq_attr "type" "dbc")
|
(define_delay (eq_attr "type" "dbc")
|
[(eq_attr "in_dbc_slot" "true") (nil) (nil)
|
[(eq_attr "in_dbc_slot" "true") (nil) (nil)
|
(eq_attr "in_dbc_slot" "true") (nil) (nil)
|
(eq_attr "in_dbc_slot" "true") (nil) (nil)
|
(eq_attr "in_dbc_slot" "true") (nil) (nil)])
|
(eq_attr "in_dbc_slot" "true") (nil) (nil)])
|
|
|
; The LAJ instruction has three delay slots but the last slot is
|
; The LAJ instruction has three delay slots but the last slot is
|
; used for pushing the return address. Thus we can only use two slots.
|
; used for pushing the return address. Thus we can only use two slots.
|
;
|
;
|
(define_delay (eq_attr "type" "laj")
|
(define_delay (eq_attr "type" "laj")
|
[(eq_attr "in_delay_slot" "true") (nil) (nil)
|
[(eq_attr "in_delay_slot" "true") (nil) (nil)
|
(eq_attr "in_delay_slot" "true") (nil) (nil)])
|
(eq_attr "in_delay_slot" "true") (nil) (nil)])
|
|
|
;
|
;
|
; C4x UNSPEC NUMBERS
|
; C4x UNSPEC NUMBERS
|
;
|
;
|
(define_constants
|
(define_constants
|
[
|
[
|
(UNSPEC_BU 1)
|
(UNSPEC_BU 1)
|
(UNSPEC_RPTS 2)
|
(UNSPEC_RPTS 2)
|
(UNSPEC_LSH 3)
|
(UNSPEC_LSH 3)
|
(UNSPEC_CMPHI 4)
|
(UNSPEC_CMPHI 4)
|
(UNSPEC_RCPF 5)
|
(UNSPEC_RCPF 5)
|
(UNSPEC_RND 6)
|
(UNSPEC_RND 6)
|
(UNSPEC_RPTB_FILL 7)
|
(UNSPEC_RPTB_FILL 7)
|
(UNSPEC_LOADHF_INT 8)
|
(UNSPEC_LOADHF_INT 8)
|
(UNSPEC_STOREHF_INT 9)
|
(UNSPEC_STOREHF_INT 9)
|
(UNSPEC_RSQRF 10)
|
(UNSPEC_RSQRF 10)
|
(UNSPEC_LOADQF_INT 11)
|
(UNSPEC_LOADQF_INT 11)
|
(UNSPEC_STOREQF_INT 12)
|
(UNSPEC_STOREQF_INT 12)
|
(UNSPEC_LDIV 13)
|
(UNSPEC_LDIV 13)
|
(UNSPEC_PUSH_ST 14)
|
(UNSPEC_PUSH_ST 14)
|
(UNSPEC_POP_ST 15)
|
(UNSPEC_POP_ST 15)
|
(UNSPEC_PUSH_DP 16)
|
(UNSPEC_PUSH_DP 16)
|
(UNSPEC_POP_DP 17)
|
(UNSPEC_POP_DP 17)
|
(UNSPEC_POPQI 18)
|
(UNSPEC_POPQI 18)
|
(UNSPEC_POPQF 19)
|
(UNSPEC_POPQF 19)
|
(UNSPEC_ANDN_ST 20)
|
(UNSPEC_ANDN_ST 20)
|
(UNSPEC_RPTB_INIT 22)
|
(UNSPEC_RPTB_INIT 22)
|
(UNSPEC_TOIEEE 23)
|
(UNSPEC_TOIEEE 23)
|
(UNSPEC_FRIEEE 24)
|
(UNSPEC_FRIEEE 24)
|
])
|
])
|
|
|
;
|
;
|
; C4x PIPELINE MODEL
|
; C4x PIPELINE MODEL
|
;
|
;
|
; With the C3x, an external memory write (with no wait states) takes
|
; With the C3x, an external memory write (with no wait states) takes
|
; two cycles and an external memory read (with no wait states) takes
|
; two cycles and an external memory read (with no wait states) takes
|
; one cycle. However, an external read following an external write
|
; one cycle. However, an external read following an external write
|
; takes two cycles. With internal memory, reads and writes take
|
; takes two cycles. With internal memory, reads and writes take
|
; half a cycle.
|
; half a cycle.
|
; When a C4x address register is loaded it will not be available for
|
; When a C4x address register is loaded it will not be available for
|
; an extra machine cycle. Calculating with a C4x address register
|
; an extra machine cycle. Calculating with a C4x address register
|
; makes it unavailable for 2 machine cycles.
|
; makes it unavailable for 2 machine cycles.
|
;
|
;
|
; Just some dummy definitions. The real work is done in c4x_adjust_cost.
|
; Just some dummy definitions. The real work is done in c4x_adjust_cost.
|
; These are needed so the min/max READY_DELAY is known.
|
; These are needed so the min/max READY_DELAY is known.
|
|
|
(define_insn_reservation "any_insn" 1 (const_int 1) "nothing")
|
(define_insn_reservation "any_insn" 1 (const_int 1) "nothing")
|
(define_insn_reservation "slowest_insn" 3 (const_int 0) "nothing")
|
(define_insn_reservation "slowest_insn" 3 (const_int 0) "nothing")
|
|
|
; The attribute setar0 is set to 1 for insns where ar0 is a dst operand.
|
; The attribute setar0 is set to 1 for insns where ar0 is a dst operand.
|
; Note that the attributes unarycc and binarycc do not apply
|
; Note that the attributes unarycc and binarycc do not apply
|
; if ar0 is a dst operand (only loading an ext. prec. reg. sets CC)
|
; if ar0 is a dst operand (only loading an ext. prec. reg. sets CC)
|
(define_attr "setar0" ""
|
(define_attr "setar0" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar0" ""
|
(define_attr "setlda_ar0" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
; The attribute usear0 is set to 1 for insns where ar0 is used
|
; The attribute usear0 is set to 1 for insns where ar0 is used
|
; for addressing, as a src operand, or as a dst operand.
|
; for addressing, as a src operand, or as a dst operand.
|
(define_attr "usear0" ""
|
(define_attr "usear0" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar0_mem_operand" "")
|
(if_then_else (match_operand 0 "ar0_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar0_mem_operand" "")
|
(if_then_else (match_operand 1 "ar0_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar0_mem_operand" "")
|
(if_then_else (match_operand 2 "ar0_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
; The attribute readar0 is set to 1 for insns where ar0 is a src operand.
|
; The attribute readar0 is set to 1 for insns where ar0 is a src operand.
|
(define_attr "readar0" ""
|
(define_attr "readar0" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(if_then_else (match_operand 0 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar0_reg_operand" "")
|
(if_then_else (match_operand 1 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar0_reg_operand" "")
|
(if_then_else (match_operand 2 "ar0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar1" ""
|
(define_attr "setar1" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar1" ""
|
(define_attr "setlda_ar1" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear1" ""
|
(define_attr "usear1" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar1_mem_operand" "")
|
(if_then_else (match_operand 0 "ar1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar1_mem_operand" "")
|
(if_then_else (match_operand 1 "ar1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar1_mem_operand" "")
|
(if_then_else (match_operand 2 "ar1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar1" ""
|
(define_attr "readar1" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(if_then_else (match_operand 0 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar1_reg_operand" "")
|
(if_then_else (match_operand 1 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar1_reg_operand" "")
|
(if_then_else (match_operand 2 "ar1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar2" ""
|
(define_attr "setar2" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar2" ""
|
(define_attr "setlda_ar2" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear2" ""
|
(define_attr "usear2" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar2_mem_operand" "")
|
(if_then_else (match_operand 0 "ar2_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar2_mem_operand" "")
|
(if_then_else (match_operand 1 "ar2_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar2_mem_operand" "")
|
(if_then_else (match_operand 2 "ar2_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar2" ""
|
(define_attr "readar2" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(if_then_else (match_operand 0 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar2_reg_operand" "")
|
(if_then_else (match_operand 1 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar2_reg_operand" "")
|
(if_then_else (match_operand 2 "ar2_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar3" ""
|
(define_attr "setar3" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar3" ""
|
(define_attr "setlda_ar3" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear3" ""
|
(define_attr "usear3" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar3_mem_operand" "")
|
(if_then_else (match_operand 0 "ar3_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar3_mem_operand" "")
|
(if_then_else (match_operand 1 "ar3_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar3_mem_operand" "")
|
(if_then_else (match_operand 2 "ar3_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar3" ""
|
(define_attr "readar3" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(if_then_else (match_operand 0 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar3_reg_operand" "")
|
(if_then_else (match_operand 1 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar3_reg_operand" "")
|
(if_then_else (match_operand 2 "ar3_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar4" ""
|
(define_attr "setar4" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar4" ""
|
(define_attr "setlda_ar4" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear4" ""
|
(define_attr "usear4" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar4_mem_operand" "")
|
(if_then_else (match_operand 0 "ar4_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar4_mem_operand" "")
|
(if_then_else (match_operand 1 "ar4_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar4_mem_operand" "")
|
(if_then_else (match_operand 2 "ar4_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar4" ""
|
(define_attr "readar4" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(if_then_else (match_operand 0 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar4_reg_operand" "")
|
(if_then_else (match_operand 1 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar4_reg_operand" "")
|
(if_then_else (match_operand 2 "ar4_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar5" ""
|
(define_attr "setar5" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar5" ""
|
(define_attr "setlda_ar5" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear5" ""
|
(define_attr "usear5" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar5_mem_operand" "")
|
(if_then_else (match_operand 0 "ar5_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar5_mem_operand" "")
|
(if_then_else (match_operand 1 "ar5_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar5_mem_operand" "")
|
(if_then_else (match_operand 2 "ar5_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar5" ""
|
(define_attr "readar5" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(if_then_else (match_operand 0 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar5_reg_operand" "")
|
(if_then_else (match_operand 1 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar5_reg_operand" "")
|
(if_then_else (match_operand 2 "ar5_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar6" ""
|
(define_attr "setar6" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar6" ""
|
(define_attr "setlda_ar6" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear6" ""
|
(define_attr "usear6" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar6_mem_operand" "")
|
(if_then_else (match_operand 0 "ar6_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar6_mem_operand" "")
|
(if_then_else (match_operand 1 "ar6_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar6_mem_operand" "")
|
(if_then_else (match_operand 2 "ar6_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar6" ""
|
(define_attr "readar6" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(if_then_else (match_operand 0 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar6_reg_operand" "")
|
(if_then_else (match_operand 1 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar6_reg_operand" "")
|
(if_then_else (match_operand 2 "ar6_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setar7" ""
|
(define_attr "setar7" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ar7" ""
|
(define_attr "setlda_ar7" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usear7" ""
|
(define_attr "usear7" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ar7_mem_operand" "")
|
(if_then_else (match_operand 0 "ar7_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar7_mem_operand" "")
|
(if_then_else (match_operand 1 "ar7_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar7_mem_operand" "")
|
(if_then_else (match_operand 2 "ar7_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "db,dbc")
|
(eq_attr "type" "db,dbc")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readar7" ""
|
(define_attr "readar7" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(if_then_else (match_operand 0 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ar7_reg_operand" "")
|
(if_then_else (match_operand 1 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ar7_reg_operand" "")
|
(if_then_else (match_operand 2 "ar7_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setir0" ""
|
(define_attr "setir0" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ir0_reg_operand" "")
|
(if_then_else (match_operand 0 "ir0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ir0" ""
|
(define_attr "setlda_ir0" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ir0_reg_operand" "")
|
(if_then_else (match_operand 0 "ir0_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "useir0" ""
|
(define_attr "useir0" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ir0_mem_operand" "")
|
(if_then_else (match_operand 0 "ir0_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ir0_mem_operand" "")
|
(if_then_else (match_operand 1 "ir0_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ir0_mem_operand" "")
|
(if_then_else (match_operand 2 "ir0_mem_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setir1" ""
|
(define_attr "setir1" ""
|
(cond [(eq_attr "type" "unary,binary")
|
(cond [(eq_attr "type" "unary,binary")
|
(if_then_else (match_operand 0 "ir1_reg_operand" "")
|
(if_then_else (match_operand 0 "ir1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "setlda_ir1" ""
|
(define_attr "setlda_ir1" ""
|
(cond [(eq_attr "type" "lda")
|
(cond [(eq_attr "type" "lda")
|
(if_then_else (match_operand 0 "ir1_reg_operand" "")
|
(if_then_else (match_operand 0 "ir1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "useir1" ""
|
(define_attr "useir1" ""
|
(cond [(eq_attr "type" "compare,store")
|
(cond [(eq_attr "type" "compare,store")
|
(if_then_else (match_operand 0 "ir1_mem_operand" "")
|
(if_then_else (match_operand 0 "ir1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "ir1_mem_operand" "")
|
(if_then_else (match_operand 1 "ir1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "ir1_mem_operand" "")
|
(if_then_else (match_operand 2 "ir1_mem_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
; With the C3x, things are simpler but slower, i.e. more pipeline conflicts :(
|
; With the C3x, things are simpler but slower, i.e. more pipeline conflicts :(
|
; There are three functional groups:
|
; There are three functional groups:
|
; (1) AR0-AR7, IR0-IR1, BK
|
; (1) AR0-AR7, IR0-IR1, BK
|
; (2) DP
|
; (2) DP
|
; (3) SP
|
; (3) SP
|
;
|
;
|
; When a register in one of these functional groups is loaded,
|
; When a register in one of these functional groups is loaded,
|
; the contents of that or any other register in its group
|
; the contents of that or any other register in its group
|
; will not be available to the next instruction for 2 machine cycles.
|
; will not be available to the next instruction for 2 machine cycles.
|
; Similarly, when a register in one of the functional groups is read
|
; Similarly, when a register in one of the functional groups is read
|
; excepting (IR0-IR1, BK, DP) the contents of that or any other register
|
; excepting (IR0-IR1, BK, DP) the contents of that or any other register
|
; in its group will not be available to the next instruction for
|
; in its group will not be available to the next instruction for
|
; 1 machine cycle.
|
; 1 machine cycle.
|
;
|
;
|
; Let's ignore functional groups 2 and 3 for now, since they are not
|
; Let's ignore functional groups 2 and 3 for now, since they are not
|
; so important.
|
; so important.
|
|
|
(define_attr "setgroup1" ""
|
(define_attr "setgroup1" ""
|
(cond [(eq_attr "type" "lda,unary,binary")
|
(cond [(eq_attr "type" "lda,unary,binary")
|
(if_then_else (match_operand 0 "group1_reg_operand" "")
|
(if_then_else (match_operand 0 "group1_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "usegroup1" ""
|
(define_attr "usegroup1" ""
|
(cond [(eq_attr "type" "compare,store,store_store,store_load")
|
(cond [(eq_attr "type" "compare,store,store_store,store_load")
|
(if_then_else (match_operand 0 "group1_mem_operand" "")
|
(if_then_else (match_operand 0 "group1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc,load_load,load_store")
|
(eq_attr "type" "compare,lda,unary,unarycc,binary,binarycc,load_load,load_store")
|
(if_then_else (match_operand 1 "group1_mem_operand" "")
|
(if_then_else (match_operand 1 "group1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "store_store,load_store")
|
(eq_attr "type" "store_store,load_store")
|
(if_then_else (match_operand 2 "group1_mem_operand" "")
|
(if_then_else (match_operand 2 "group1_mem_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "load_load,store_load")
|
(eq_attr "type" "load_load,store_load")
|
(if_then_else (match_operand 3 "group1_mem_operand" "")
|
(if_then_else (match_operand 3 "group1_mem_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(define_attr "readarx" ""
|
(define_attr "readarx" ""
|
(cond [(eq_attr "type" "compare")
|
(cond [(eq_attr "type" "compare")
|
(if_then_else (match_operand 0 "arx_reg_operand" "")
|
(if_then_else (match_operand 0 "arx_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(eq_attr "type" "compare,store,lda,unary,unarycc,binary,binarycc")
|
(if_then_else (match_operand 1 "arx_reg_operand" "")
|
(if_then_else (match_operand 1 "arx_reg_operand" "")
|
(const_int 1) (const_int 0))
|
(const_int 1) (const_int 0))
|
(eq_attr "type" "binary,binarycc")
|
(eq_attr "type" "binary,binarycc")
|
(if_then_else (match_operand 2 "arx_reg_operand" "")
|
(if_then_else (match_operand 2 "arx_reg_operand" "")
|
(const_int 1) (const_int 0))]
|
(const_int 1) (const_int 0))]
|
(const_int 0)))
|
(const_int 0)))
|
|
|
(include "predicates.md")
|
(include "predicates.md")
|
|
|
;
|
;
|
; C4x INSN PATTERNS:
|
; C4x INSN PATTERNS:
|
;
|
;
|
; Note that the movMM and addP patterns can be called during reload
|
; Note that the movMM and addP patterns can be called during reload
|
; so we need to take special care with theses patterns since
|
; so we need to take special care with theses patterns since
|
; we cannot blindly clobber CC or generate new pseudo registers.
|
; we cannot blindly clobber CC or generate new pseudo registers.
|
|
|
;
|
;
|
; TWO OPERAND INTEGER INSTRUCTIONS
|
; TWO OPERAND INTEGER INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; LDP/LDPK
|
; LDP/LDPK
|
;
|
;
|
(define_insn "set_ldp"
|
(define_insn "set_ldp"
|
[(set (match_operand:QI 0 "dp_reg_operand" "=z")
|
[(set (match_operand:QI 0 "dp_reg_operand" "=z")
|
(high:QI (match_operand:QI 1 "" "")))]
|
(high:QI (match_operand:QI 1 "" "")))]
|
"! TARGET_SMALL"
|
"! TARGET_SMALL"
|
"* return (TARGET_C3X) ? \"ldp\\t%A1\" : \"ldpk\\t%A1\";"
|
"* return (TARGET_C3X) ? \"ldp\\t%A1\" : \"ldpk\\t%A1\";"
|
[(set_attr "type" "ldp")])
|
[(set_attr "type" "ldp")])
|
|
|
(define_insn "set_ldp_prologue"
|
(define_insn "set_ldp_prologue"
|
[(set (match_operand:QI 0 "dp_reg_operand" "=z")
|
[(set (match_operand:QI 0 "dp_reg_operand" "=z")
|
(high:QI (match_operand:QI 1 "" "")))]
|
(high:QI (match_operand:QI 1 "" "")))]
|
"TARGET_SMALL && TARGET_PARANOID"
|
"TARGET_SMALL && TARGET_PARANOID"
|
"* return (TARGET_C3X) ? \"ldp\\t@data_sec\" : \"ldpk\\t@data_sec\";"
|
"* return (TARGET_C3X) ? \"ldp\\t@data_sec\" : \"ldpk\\t@data_sec\";"
|
[(set_attr "type" "ldp")])
|
[(set_attr "type" "ldp")])
|
|
|
(define_insn "set_high"
|
(define_insn "set_high"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
(high:QI (match_operand:QI 1 "symbolic_address_operand" "")))]
|
(high:QI (match_operand:QI 1 "symbolic_address_operand" "")))]
|
"! TARGET_C3X && ! TARGET_TI"
|
"! TARGET_C3X && ! TARGET_TI"
|
"ldhi\\t^%H1,%0"
|
"ldhi\\t^%H1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_insn "set_lo_sum"
|
(define_insn "set_lo_sum"
|
[(set (match_operand:QI 0 "std_reg_operand" "+c")
|
[(set (match_operand:QI 0 "std_reg_operand" "+c")
|
(lo_sum:QI (match_dup 0)
|
(lo_sum:QI (match_dup 0)
|
(match_operand:QI 1 "symbolic_address_operand" "")))]
|
(match_operand:QI 1 "symbolic_address_operand" "")))]
|
"! TARGET_TI"
|
"! TARGET_TI"
|
"or\\t#%H1,%0"
|
"or\\t#%H1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(match_operand:QI 1 "symbolic_address_operand" ""))]
|
(match_operand:QI 1 "symbolic_address_operand" ""))]
|
"reload_completed && ! TARGET_C3X && ! TARGET_TI"
|
"reload_completed && ! TARGET_C3X && ! TARGET_TI"
|
[(set (match_dup 0) (high:QI (match_dup 1)))
|
[(set (match_dup 0) (high:QI (match_dup 1)))
|
(set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
|
(set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
|
"")
|
"")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)"
|
&& std_reg_operand (operands[0], QImode)"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
|
operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))]
|
(match_operand:QI 1 "const_int_operand" ""))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)"
|
&& std_reg_operand (operands[0], QImode)"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
|
operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"TARGET_C3X && ! TARGET_SMALL
|
"TARGET_C3X && ! TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)
|
&& std_reg_operand (operands[0], QImode)
|
&& c4x_shiftable_constant (operands[1]) < 0"
|
&& c4x_shiftable_constant (operands[1]) < 0"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
/* Generate two's complement value of 16 MSBs. */
|
/* Generate two's complement value of 16 MSBs. */
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
|
- 0x8000) ^ ~0x7fff);
|
- 0x8000) ^ ~0x7fff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[4] = GEN_INT (16);
|
operands[4] = GEN_INT (16);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))]
|
(match_operand:QI 1 "const_int_operand" ""))]
|
"TARGET_C3X && ! TARGET_SMALL
|
"TARGET_C3X && ! TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)
|
&& std_reg_operand (operands[0], QImode)
|
&& c4x_shiftable_constant (operands[1]) < 0"
|
&& c4x_shiftable_constant (operands[1]) < 0"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 4)))
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
/* Generate two's complement value of 16 MSBs. */
|
/* Generate two's complement value of 16 MSBs. */
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
|
- 0x8000) ^ ~0x7fff);
|
- 0x8000) ^ ~0x7fff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
|
operands[4] = GEN_INT (16);
|
operands[4] = GEN_INT (16);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"TARGET_C3X
|
"TARGET_C3X
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)
|
&& std_reg_operand (operands[0], QImode)
|
&& c4x_shiftable_constant (operands[1]) >= 0"
|
&& c4x_shiftable_constant (operands[1]) >= 0"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
/* Generate two's complement value of MSBs. */
|
/* Generate two's complement value of MSBs. */
|
int shift = c4x_shiftable_constant (operands[1]);
|
int shift = c4x_shiftable_constant (operands[1]);
|
|
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
|
- 0x8000) ^ ~0x7fff);
|
- 0x8000) ^ ~0x7fff);
|
operands[3] = GEN_INT (shift);
|
operands[3] = GEN_INT (shift);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))]
|
(match_operand:QI 1 "const_int_operand" ""))]
|
"TARGET_C3X
|
"TARGET_C3X
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& std_reg_operand (operands[0], QImode)
|
&& std_reg_operand (operands[0], QImode)
|
&& c4x_shiftable_constant (operands[1]) >= 0"
|
&& c4x_shiftable_constant (operands[1]) >= 0"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
|
(set (match_dup 0) (ashift:QI (match_dup 0) (match_dup 3)))]
|
"
|
"
|
{
|
{
|
/* Generate two's complement value of MSBs. */
|
/* Generate two's complement value of MSBs. */
|
int shift = c4x_shiftable_constant (operands[1]);
|
int shift = c4x_shiftable_constant (operands[1]);
|
|
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
|
operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
|
- 0x8000) ^ ~0x7fff);
|
- 0x8000) ^ ~0x7fff);
|
operands[3] = GEN_INT (shift);
|
operands[3] = GEN_INT (shift);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"! TARGET_SMALL
|
"! TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& ! std_reg_operand (operands[0], QImode)"
|
&& ! std_reg_operand (operands[0], QImode)"
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
(set (match_dup 0) (match_dup 4))
|
(set (match_dup 0) (match_dup 4))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = dp_reg;
|
operands[2] = dp_reg;
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[4] = change_address (operands[3], QImode,
|
operands[4] = change_address (operands[3], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[3], 0)));
|
XEXP (operands[3], 0)));
|
operands[3] = XEXP (operands[3], 0);
|
operands[3] = XEXP (operands[3], 0);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))]
|
(match_operand:QI 1 "const_int_operand" ""))]
|
"! TARGET_SMALL
|
"! TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& ! std_reg_operand (operands[0], QImode)"
|
&& ! std_reg_operand (operands[0], QImode)"
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
(set (match_dup 0) (match_dup 4))
|
(set (match_dup 0) (match_dup 4))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = dp_reg;
|
operands[2] = dp_reg;
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[4] = change_address (operands[3], QImode,
|
operands[4] = change_address (operands[3], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[3], 0)));
|
XEXP (operands[3], 0)));
|
operands[3] = XEXP (operands[3], 0);
|
operands[3] = XEXP (operands[3], 0);
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"TARGET_SMALL
|
"TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
|
&& ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
|
|| ! std_reg_operand (operands[0], QImode))"
|
|| ! std_reg_operand (operands[0], QImode))"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = change_address (operands[2], QImode,
|
operands[2] = change_address (operands[2], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[2], 0)));
|
XEXP (operands[2], 0)));
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" ""))]
|
(match_operand:QI 1 "const_int_operand" ""))]
|
"TARGET_SMALL
|
"TARGET_SMALL
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))
|
&& reload_completed
|
&& reload_completed
|
&& ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
|
&& ((TARGET_C3X && c4x_shiftable_constant (operands[1]) < 0)
|
|| ! std_reg_operand (operands[0], QImode))"
|
|| ! std_reg_operand (operands[0], QImode))"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = change_address (operands[2], QImode,
|
operands[2] = change_address (operands[2], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[2], 0)));
|
XEXP (operands[2], 0)));
|
}")
|
}")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(match_operand:HI 1 "const_int_operand" ""))
|
(match_operand:HI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 2) (match_dup 4))
|
[(set (match_dup 2) (match_dup 4))
|
(set (match_dup 3) (match_dup 5))]
|
(set (match_dup 3) (match_dup 5))]
|
"
|
"
|
{
|
{
|
operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
}")
|
}")
|
|
|
|
|
; We need to clobber the DP reg to be safe in case we
|
; We need to clobber the DP reg to be safe in case we
|
; need to load this address from memory
|
; need to load this address from memory
|
(define_insn "load_immed_address"
|
(define_insn "load_immed_address"
|
[(set (match_operand:QI 0 "reg_operand" "=a?x?c*r")
|
[(set (match_operand:QI 0 "reg_operand" "=a?x?c*r")
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"TARGET_LOAD_ADDRESS"
|
"TARGET_LOAD_ADDRESS"
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"reload_completed && ! TARGET_C3X && ! TARGET_TI"
|
"reload_completed && ! TARGET_C3X && ! TARGET_TI"
|
[(set (match_dup 0) (high:QI (match_dup 1)))
|
[(set (match_dup 0) (high:QI (match_dup 1)))
|
(set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
|
(set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
|
"")
|
"")
|
|
|
; CC has been selected to load a symbolic address. We force the address
|
; CC has been selected to load a symbolic address. We force the address
|
; into memory and then generate LDP and LDIU insns.
|
; into memory and then generate LDP and LDIU insns.
|
; This is also required for the C30 if we pretend that we can
|
; This is also required for the C30 if we pretend that we can
|
; easily load symbolic addresses into a register.
|
; easily load symbolic addresses into a register.
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"reload_completed
|
"reload_completed
|
&& ! TARGET_SMALL
|
&& ! TARGET_SMALL
|
&& (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
|
&& (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
[(set (match_dup 2) (high:QI (match_dup 3)))
|
(set (match_dup 0) (match_dup 4))
|
(set (match_dup 0) (match_dup 4))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = dp_reg;
|
operands[2] = dp_reg;
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[3] = force_const_mem (Pmode, operands[1]);
|
operands[4] = change_address (operands[3], QImode,
|
operands[4] = change_address (operands[3], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[3], 0)));
|
XEXP (operands[3], 0)));
|
operands[3] = XEXP (operands[3], 0);
|
operands[3] = XEXP (operands[3], 0);
|
}")
|
}")
|
|
|
; This pattern is similar to the above but does not emit a LDP
|
; This pattern is similar to the above but does not emit a LDP
|
; for the small memory model.
|
; for the small memory model.
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(match_operand:QI 1 "symbolic_address_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"reload_completed
|
"reload_completed
|
&& TARGET_SMALL
|
&& TARGET_SMALL
|
&& (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
|
&& (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
|
[(set (match_dup 0) (match_dup 2))
|
[(set (match_dup 0) (match_dup 2))
|
(use (match_dup 1))]
|
(use (match_dup 1))]
|
"
|
"
|
{
|
{
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
rtx dp_reg = gen_rtx_REG (Pmode, DP_REGNO);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = force_const_mem (Pmode, operands[1]);
|
operands[2] = change_address (operands[2], QImode,
|
operands[2] = change_address (operands[2], QImode,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
gen_rtx_LO_SUM (Pmode, dp_reg,
|
XEXP (operands[2], 0)));
|
XEXP (operands[2], 0)));
|
}")
|
}")
|
|
|
(define_insn "loadhi_big_constant"
|
(define_insn "loadhi_big_constant"
|
[(set (match_operand:HI 0 "reg_operand" "=c*d")
|
[(set (match_operand:HI 0 "reg_operand" "=c*d")
|
(match_operand:HI 1 "const_int_operand" ""))
|
(match_operand:HI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
;
|
;
|
; LDIU/LDA/STI/STIK
|
; LDIU/LDA/STI/STIK
|
;
|
;
|
; The following moves will not set the condition codes register.
|
; The following moves will not set the condition codes register.
|
;
|
;
|
|
|
; This must come before the general case
|
; This must come before the general case
|
(define_insn "*movqi_stik"
|
(define_insn "*movqi_stik"
|
[(set (match_operand:QI 0 "memory_operand" "=m")
|
[(set (match_operand:QI 0 "memory_operand" "=m")
|
(match_operand:QI 1 "stik_const_operand" "K"))]
|
(match_operand:QI 1 "stik_const_operand" "K"))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"stik\\t%1,%0"
|
"stik\\t%1,%0"
|
[(set_attr "type" "store")])
|
[(set_attr "type" "store")])
|
|
|
(define_insn "loadqi_big_constant"
|
(define_insn "loadqi_big_constant"
|
[(set (match_operand:QI 0 "reg_operand" "=c*d")
|
[(set (match_operand:QI 0 "reg_operand" "=c*d")
|
(match_operand:QI 1 "const_int_operand" ""))
|
(match_operand:QI 1 "const_int_operand" ""))
|
(clobber (reg:QI 16))]
|
(clobber (reg:QI 16))]
|
"! IS_INT16_CONST (INTVAL (operands[1]))
|
"! IS_INT16_CONST (INTVAL (operands[1]))
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))"
|
&& ! IS_HIGH_CONST (INTVAL (operands[1]))"
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; We must provide an alternative to store to memory in case we have to
|
; We must provide an alternative to store to memory in case we have to
|
; spill a register.
|
; spill a register.
|
(define_insn "movqi_noclobber"
|
(define_insn "movqi_noclobber"
|
[(set (match_operand:QI 0 "dst_operand" "=d,*c,m,r")
|
[(set (match_operand:QI 0 "dst_operand" "=d,*c,m,r")
|
(match_operand:QI 1 "src_hi_operand" "rIm,rIm,r,O"))]
|
(match_operand:QI 1 "src_hi_operand" "rIm,rIm,r,O"))]
|
"(REG_P (operands[0]) || REG_P (operands[1])
|
"(REG_P (operands[0]) || REG_P (operands[1])
|
|| GET_CODE (operands[0]) == SUBREG
|
|| GET_CODE (operands[0]) == SUBREG
|
|| GET_CODE (operands[1]) == SUBREG)
|
|| GET_CODE (operands[1]) == SUBREG)
|
&& ! symbolic_address_operand (operands[1], QImode)"
|
&& ! symbolic_address_operand (operands[1], QImode)"
|
"*
|
"*
|
if (which_alternative == 2)
|
if (which_alternative == 2)
|
return \"sti\\t%1,%0\";
|
return \"sti\\t%1,%0\";
|
|
|
if (! TARGET_C3X && which_alternative == 3)
|
if (! TARGET_C3X && which_alternative == 3)
|
{
|
{
|
operands[1] = GEN_INT ((INTVAL (operands[1]) >> 16) & 0xffff);
|
operands[1] = GEN_INT ((INTVAL (operands[1]) >> 16) & 0xffff);
|
return \"ldhi\\t%1,%0\";
|
return \"ldhi\\t%1,%0\";
|
}
|
}
|
|
|
/* The lda instruction cannot use the same register as source
|
/* The lda instruction cannot use the same register as source
|
and destination. */
|
and destination. */
|
if (! TARGET_C3X && which_alternative == 1
|
if (! TARGET_C3X && which_alternative == 1
|
&& ( IS_ADDR_REG (operands[0])
|
&& ( IS_ADDR_REG (operands[0])
|
|| IS_INDEX_REG (operands[0])
|
|| IS_INDEX_REG (operands[0])
|
|| IS_SP_REG (operands[0]))
|
|| IS_SP_REG (operands[0]))
|
&& (REGNO (operands[0]) != REGNO (operands[1])))
|
&& (REGNO (operands[0]) != REGNO (operands[1])))
|
return \"lda\\t%1,%0\";
|
return \"lda\\t%1,%0\";
|
return \"ldiu\\t%1,%0\";
|
return \"ldiu\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "unary,lda,store,unary")
|
[(set_attr "type" "unary,lda,store,unary")
|
(set_attr "data" "int16,int16,int16,high_16")])
|
(set_attr "data" "int16,int16,int16,high_16")])
|
|
|
;
|
;
|
; LDI
|
; LDI
|
;
|
;
|
|
|
; We shouldn't need these peepholes, but the combiner seems to miss them...
|
; We shouldn't need these peepholes, but the combiner seems to miss them...
|
(define_peephole
|
(define_peephole
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(match_operand:QI 1 "src_operand" "rIm"))
|
(match_operand:QI 1 "src_operand" "rIm"))
|
(set (reg:CC 21)
|
(set (reg:CC 21)
|
(compare:CC (match_dup 0) (const_int 0)))]
|
(compare:CC (match_dup 0) (const_int 0)))]
|
""
|
""
|
"ldi\\t%1,%0"
|
"ldi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_insn "*movqi_set"
|
(define_insn "*movqi_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QI 1 "src_operand" "rIm")
|
(compare:CC (match_operand:QI 1 "src_operand" "rIm")
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(match_dup 1))]
|
(match_dup 1))]
|
""
|
""
|
"ldi\\t%1,%0"
|
"ldi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
; This pattern probably gets in the way and requires a scratch register
|
; This pattern probably gets in the way and requires a scratch register
|
; when a simple compare with zero will suffice.
|
; when a simple compare with zero will suffice.
|
;(define_insn "*movqi_test"
|
;(define_insn "*movqi_test"
|
; [(set (reg:CC 21)
|
; [(set (reg:CC 21)
|
; (compare:CC (match_operand:QI 1 "src_operand" "rIm")
|
; (compare:CC (match_operand:QI 1 "src_operand" "rIm")
|
; (const_int 0)))
|
; (const_int 0)))
|
; (clobber (match_scratch:QI 0 "=d"))]
|
; (clobber (match_scratch:QI 0 "=d"))]
|
; ""
|
; ""
|
; "@
|
; "@
|
; ldi\\t%1,%0"
|
; ldi\\t%1,%0"
|
; [(set_attr "type" "unarycc")
|
; [(set_attr "type" "unarycc")
|
; (set_attr "data" "int16")])
|
; (set_attr "data" "int16")])
|
|
|
; If one of the operands is not a register, then we should
|
; If one of the operands is not a register, then we should
|
; emit two insns, using a scratch register. This will produce
|
; emit two insns, using a scratch register. This will produce
|
; better code in loops if the source operand is invariant, since
|
; better code in loops if the source operand is invariant, since
|
; the source reload can be optimized out. During reload we cannot
|
; the source reload can be optimized out. During reload we cannot
|
; use change_address or force_reg which will allocate new pseudo regs.
|
; use change_address or force_reg which will allocate new pseudo regs.
|
|
|
; Unlike most other insns, the move insns can't be split with
|
; Unlike most other insns, the move insns can't be split with
|
; different predicates, because register spilling and other parts of
|
; different predicates, because register spilling and other parts of
|
; the compiler, have memoized the insn number already.
|
; the compiler, have memoized the insn number already.
|
|
|
(define_expand "movqi"
|
(define_expand "movqi"
|
[(set (match_operand:QI 0 "general_operand" "")
|
[(set (match_operand:QI 0 "general_operand" "")
|
(match_operand:QI 1 "general_operand" ""))]
|
(match_operand:QI 1 "general_operand" ""))]
|
""
|
""
|
"
|
"
|
{
|
{
|
if (c4x_emit_move_sequence (operands, QImode))
|
if (c4x_emit_move_sequence (operands, QImode))
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
|
|
; As far as GCC is concerned, the moves are performed in parallel
|
; As far as GCC is concerned, the moves are performed in parallel
|
; thus it must be convinced that there is no aliasing.
|
; thus it must be convinced that there is no aliasing.
|
; It also assumes that the input operands are simultaneously loaded
|
; It also assumes that the input operands are simultaneously loaded
|
; and then the output operands are simultaneously stored.
|
; and then the output operands are simultaneously stored.
|
; With the C4x, if there are parallel stores to the same address
|
; With the C4x, if there are parallel stores to the same address
|
; both stores are executed.
|
; both stores are executed.
|
; If there is a parallel load and store to the same address,
|
; If there is a parallel load and store to the same address,
|
; the load is performed first.
|
; the load is performed first.
|
; The problem with this pattern is that reload can spoil
|
; The problem with this pattern is that reload can spoil
|
; the show when it eliminates a reference to the frame pointer.
|
; the show when it eliminates a reference to the frame pointer.
|
; This can invalidate the memory addressing mode, i.e., when
|
; This can invalidate the memory addressing mode, i.e., when
|
; the displacement is greater than 1.
|
; the displacement is greater than 1.
|
(define_insn "movqi_parallel"
|
(define_insn "movqi_parallel"
|
[(set (match_operand:QI 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
|
[(set (match_operand:QI 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
|
(match_operand:QI 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
|
(match_operand:QI 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
|
(set (match_operand:QI 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
|
(set (match_operand:QI 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
|
(match_operand:QI 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
|
(match_operand:QI 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
|
"TARGET_PARALLEL && valid_parallel_load_store (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_load_store (operands, QImode)"
|
"@
|
"@
|
ldi1\\t%1,%0\\n||\\tldi2\\t%3,%2
|
ldi1\\t%1,%0\\n||\\tldi2\\t%3,%2
|
sti1\\t%1,%0\\n||\\tsti2\\t%3,%2
|
sti1\\t%1,%0\\n||\\tsti2\\t%3,%2
|
ldi\\t%1,%0\\n||\\tsti\\t%3,%2
|
ldi\\t%1,%0\\n||\\tsti\\t%3,%2
|
ldi\\t%3,%2\\n||\\tsti\\t%1,%0"
|
ldi\\t%3,%2\\n||\\tsti\\t%1,%0"
|
[(set_attr "type" "load_load,store_store,load_store,store_load")])
|
[(set_attr "type" "load_load,store_store,load_store,store_load")])
|
|
|
;
|
;
|
; PUSH/POP
|
; PUSH/POP
|
;
|
;
|
(define_insn "pushqi"
|
(define_insn "pushqi"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(match_operand:QI 0 "reg_operand" "r"))]
|
(match_operand:QI 0 "reg_operand" "r"))]
|
""
|
""
|
"push\\t%0"
|
"push\\t%0"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
(define_insn "push_st"
|
(define_insn "push_st"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(unspec:QI [(reg:QI 21)] UNSPEC_PUSH_ST))
|
(unspec:QI [(reg:QI 21)] UNSPEC_PUSH_ST))
|
(use (reg:QI 21))]
|
(use (reg:QI 21))]
|
""
|
""
|
"push\\tst"
|
"push\\tst"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
(define_insn "push_dp"
|
(define_insn "push_dp"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(unspec:QI [(reg:QI 16)] UNSPEC_PUSH_DP))
|
(unspec:QI [(reg:QI 16)] UNSPEC_PUSH_DP))
|
(use (reg:QI 16))]
|
(use (reg:QI 16))]
|
""
|
""
|
"push\\tdp"
|
"push\\tdp"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
(define_insn "popqi"
|
(define_insn "popqi"
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"pop\\t%0"
|
"pop\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
(define_insn "pop_st"
|
(define_insn "pop_st"
|
[(set (unspec:QI [(reg:QI 21)] UNSPEC_POP_ST)
|
[(set (unspec:QI [(reg:QI 21)] UNSPEC_POP_ST)
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"pop\\tst"
|
"pop\\tst"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
(define_insn "pop_dp"
|
(define_insn "pop_dp"
|
[(set (unspec:QI [(reg:QI 16)] UNSPEC_POP_DP)
|
[(set (unspec:QI [(reg:QI 16)] UNSPEC_POP_DP)
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 16))]
|
(clobber (reg:CC 16))]
|
""
|
""
|
"pop\\tdp"
|
"pop\\tdp"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
(define_insn "popqi_unspec"
|
(define_insn "popqi_unspec"
|
[(set (unspec:QI [(match_operand:QI 0 "reg_operand" "=r")] UNSPEC_POPQI)
|
[(set (unspec:QI [(match_operand:QI 0 "reg_operand" "=r")] UNSPEC_POPQI)
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(clobber (match_dup 0))
|
(clobber (match_dup 0))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"pop\\t%0"
|
"pop\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
;
|
;
|
; ABSI
|
; ABSI
|
;
|
;
|
(define_expand "absqi2"
|
(define_expand "absqi2"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(abs:QI (match_operand:QI 1 "src_operand" "")))
|
(abs:QI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*absqi2_clobber"
|
(define_insn "*absqi2_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(abs:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
|
(abs:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"absi\\t%1,%0"
|
"absi\\t%1,%0"
|
[(set_attr "type" "unarycc,unary")
|
[(set_attr "type" "unarycc,unary")
|
(set_attr "data" "int16,int16")])
|
(set_attr "data" "int16,int16")])
|
|
|
(define_insn "*absqi2_noclobber"
|
(define_insn "*absqi2_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
(abs:QI (match_operand:QI 1 "src_operand" "rIm")))]
|
(abs:QI (match_operand:QI 1 "src_operand" "rIm")))]
|
""
|
""
|
"absi\\t%1,%0"
|
"absi\\t%1,%0"
|
[(set_attr "type" "unary")
|
[(set_attr "type" "unary")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(abs:QI (match_operand:QI 1 "src_operand" "")))
|
(abs:QI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(abs:QI (match_dup 1)))]
|
(abs:QI (match_dup 1)))]
|
"")
|
"")
|
|
|
(define_insn "*absqi2_test"
|
(define_insn "*absqi2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d"))]
|
(clobber (match_scratch:QI 0 "=d"))]
|
""
|
""
|
"absi\\t%1,%0"
|
"absi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_insn "*absqi2_set"
|
(define_insn "*absqi2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC_NOOV (abs:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(abs:QI (match_dup 1)))]
|
(abs:QI (match_dup 1)))]
|
""
|
""
|
"absi\\t%1,%0"
|
"absi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
;
|
;
|
; NEGI
|
; NEGI
|
;
|
;
|
(define_expand "negqi2"
|
(define_expand "negqi2"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(neg:QI (match_operand:QI 1 "src_operand" "")))
|
(neg:QI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*negqi2_clobber"
|
(define_insn "*negqi2_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm,rIm")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"negi\\t%1,%0"
|
"negi\\t%1,%0"
|
[(set_attr "type" "unarycc,unary")
|
[(set_attr "type" "unarycc,unary")
|
(set_attr "data" "int16,int16")])
|
(set_attr "data" "int16,int16")])
|
|
|
(define_insn "*negqi2_noclobber"
|
(define_insn "*negqi2_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm")))]
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm")))]
|
""
|
""
|
"negi\\t%1,%0"
|
"negi\\t%1,%0"
|
[(set_attr "type" "unary")
|
[(set_attr "type" "unary")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(neg:QI (match_operand:QI 1 "src_operand" "")))
|
(neg:QI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(neg:QI (match_dup 1)))]
|
(neg:QI (match_dup 1)))]
|
"")
|
"")
|
|
|
(define_insn "*negqi2_test"
|
(define_insn "*negqi2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d"))]
|
(clobber (match_scratch:QI 0 "=d"))]
|
""
|
""
|
"negi\\t%1,%0"
|
"negi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_insn "*negqi2_set"
|
(define_insn "*negqi2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC_NOOV (neg:QI (match_operand:QI 1 "src_operand" "rIm"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(neg:QI (match_dup 1)))]
|
(neg:QI (match_dup 1)))]
|
""
|
""
|
"negi\\t%1,%0"
|
"negi\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_insn "*negbqi2_clobber"
|
(define_insn "*negbqi2_clobber"
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm")))
|
(neg:QI (match_operand:QI 1 "src_operand" "rIm")))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"negb\\t%1,%0"
|
"negb\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
;
|
;
|
; NOT
|
; NOT
|
;
|
;
|
(define_expand "one_cmplqi2"
|
(define_expand "one_cmplqi2"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(not:QI (match_operand:QI 1 "lsrc_operand" "")))
|
(not:QI (match_operand:QI 1 "lsrc_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*one_cmplqi2_clobber"
|
(define_insn "*one_cmplqi2_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(not:QI (match_operand:QI 1 "lsrc_operand" "rLm,rLm")))
|
(not:QI (match_operand:QI 1 "lsrc_operand" "rLm,rLm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"not\\t%1,%0"
|
"not\\t%1,%0"
|
[(set_attr "type" "unarycc,unary")
|
[(set_attr "type" "unarycc,unary")
|
(set_attr "data" "uint16,uint16")])
|
(set_attr "data" "uint16,uint16")])
|
|
|
(define_insn "*one_cmplqi2_noclobber"
|
(define_insn "*one_cmplqi2_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
(not:QI (match_operand:QI 1 "lsrc_operand" "rLm")))]
|
(not:QI (match_operand:QI 1 "lsrc_operand" "rLm")))]
|
""
|
""
|
"not\\t%1,%0"
|
"not\\t%1,%0"
|
[(set_attr "type" "unary")
|
[(set_attr "type" "unary")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(not:QI (match_operand:QI 1 "lsrc_operand" "")))
|
(not:QI (match_operand:QI 1 "lsrc_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(not:QI (match_dup 1)))]
|
(not:QI (match_dup 1)))]
|
"")
|
"")
|
|
|
(define_insn "*one_cmplqi2_test"
|
(define_insn "*one_cmplqi2_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
|
(compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d"))]
|
(clobber (match_scratch:QI 0 "=d"))]
|
""
|
""
|
"not\\t%1,%0"
|
"not\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
(define_insn "*one_cmplqi2_set"
|
(define_insn "*one_cmplqi2_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
|
(compare:CC (not:QI (match_operand:QI 1 "lsrc_operand" "rLm"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(not:QI (match_dup 1)))]
|
(not:QI (match_dup 1)))]
|
""
|
""
|
"not\\t%1,%0"
|
"not\\t%1,%0"
|
[(set_attr "type" "unarycc")
|
[(set_attr "type" "unarycc")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
(define_insn "*one_cmplqi2_const_clobber"
|
(define_insn "*one_cmplqi2_const_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(match_operand:QI 1 "not_const_operand" "N,N"))
|
(match_operand:QI 1 "not_const_operand" "N,N"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"@
|
"@
|
not\\t%N1,%0
|
not\\t%N1,%0
|
not\\t%N1,%0"
|
not\\t%N1,%0"
|
[(set_attr "type" "unarycc,unary")
|
[(set_attr "type" "unarycc,unary")
|
(set_attr "data" "not_uint16,not_uint16")])
|
(set_attr "data" "not_uint16,not_uint16")])
|
|
|
; movqi can use this for loading an integer that can't normally
|
; movqi can use this for loading an integer that can't normally
|
; fit into a 16-bit signed integer. The drawback is that it cannot
|
; fit into a 16-bit signed integer. The drawback is that it cannot
|
; go into R0-R11 since that will clobber the CC and movqi shouldn't
|
; go into R0-R11 since that will clobber the CC and movqi shouldn't
|
; do that. This can cause additional reloading but in most cases
|
; do that. This can cause additional reloading but in most cases
|
; this will cause only an additional register move. With the large
|
; this will cause only an additional register move. With the large
|
; memory model we require an extra instruction to load DP anyway,
|
; memory model we require an extra instruction to load DP anyway,
|
; if we're loading the constant from memory. The big advantage of
|
; if we're loading the constant from memory. The big advantage of
|
; allowing constants that satisfy not_const_operand in movqi, is that
|
; allowing constants that satisfy not_const_operand in movqi, is that
|
; it allows andn to be generated more often.
|
; it allows andn to be generated more often.
|
; However, there is a problem if GCC has decided that it wants
|
; However, there is a problem if GCC has decided that it wants
|
; to use R0-R11, since we won't have a matching pattern...
|
; to use R0-R11, since we won't have a matching pattern...
|
; In interim, we prevent immed_const allowing `N' constants.
|
; In interim, we prevent immed_const allowing `N' constants.
|
(define_insn "*one_cmplqi2_const_noclobber"
|
(define_insn "*one_cmplqi2_const_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c")
|
(match_operand:QI 1 "not_const_operand" "N"))]
|
(match_operand:QI 1 "not_const_operand" "N"))]
|
""
|
""
|
"not\\t%N1,%0"
|
"not\\t%N1,%0"
|
[(set_attr "type" "unary")
|
[(set_attr "type" "unary")
|
(set_attr "data" "not_uint16")])
|
(set_attr "data" "not_uint16")])
|
|
|
;
|
;
|
; ROL
|
; ROL
|
;
|
;
|
(define_expand "rotlqi3"
|
(define_expand "rotlqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(rotate:QI (match_operand:QI 1 "reg_operand" "")
|
(rotate:QI (match_operand:QI 1 "reg_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")))
|
(match_operand:QI 2 "const_int_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"if (INTVAL (operands[2]) > 4)
|
"if (INTVAL (operands[2]) > 4)
|
FAIL; /* Open code as two shifts and an or */
|
FAIL; /* Open code as two shifts and an or */
|
if (INTVAL (operands[2]) > 1)
|
if (INTVAL (operands[2]) > 1)
|
{
|
{
|
int i;
|
int i;
|
rtx tmp;
|
rtx tmp;
|
|
|
/* If we have 4 or fewer shifts, then it is probably faster
|
/* If we have 4 or fewer shifts, then it is probably faster
|
to emit separate ROL instructions. A C3x requires
|
to emit separate ROL instructions. A C3x requires
|
at least 4 instructions (a C4x requires at least 3), to
|
at least 4 instructions (a C4x requires at least 3), to
|
perform a rotation by shifts. */
|
perform a rotation by shifts. */
|
|
|
tmp = operands[1];
|
tmp = operands[1];
|
for (i = 0; i < INTVAL (operands[2]) - 1; i++)
|
for (i = 0; i < INTVAL (operands[2]) - 1; i++)
|
{
|
{
|
tmp = gen_reg_rtx (QImode);
|
tmp = gen_reg_rtx (QImode);
|
emit_insn (gen_rotl_1_clobber (tmp, operands[1]));
|
emit_insn (gen_rotl_1_clobber (tmp, operands[1]));
|
operands[1] = tmp;
|
operands[1] = tmp;
|
}
|
}
|
emit_insn (gen_rotl_1_clobber (operands[0], tmp));
|
emit_insn (gen_rotl_1_clobber (operands[0], tmp));
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
(define_insn "rotl_1_clobber"
|
(define_insn "rotl_1_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(rotate:QI (match_operand:QI 1 "reg_operand" "0,0")
|
(rotate:QI (match_operand:QI 1 "reg_operand" "0,0")
|
(const_int 1)))
|
(const_int 1)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"rol\\t%0"
|
"rol\\t%0"
|
[(set_attr "type" "unarycc,unary")])
|
[(set_attr "type" "unarycc,unary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
;
|
;
|
; ROR
|
; ROR
|
;
|
;
|
(define_expand "rotrqi3"
|
(define_expand "rotrqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(rotatert:QI (match_operand:QI 1 "reg_operand" "")
|
(rotatert:QI (match_operand:QI 1 "reg_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")))
|
(match_operand:QI 2 "const_int_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"if (INTVAL (operands[2]) > 4)
|
"if (INTVAL (operands[2]) > 4)
|
FAIL; /* Open code as two shifts and an or */
|
FAIL; /* Open code as two shifts and an or */
|
if (INTVAL (operands[2]) > 1)
|
if (INTVAL (operands[2]) > 1)
|
{
|
{
|
int i;
|
int i;
|
rtx tmp;
|
rtx tmp;
|
|
|
/* If we have 4 or fewer shifts, then it is probably faster
|
/* If we have 4 or fewer shifts, then it is probably faster
|
to emit separate ROL instructions. A C3x requires
|
to emit separate ROL instructions. A C3x requires
|
at least 4 instructions (a C4x requires at least 3), to
|
at least 4 instructions (a C4x requires at least 3), to
|
perform a rotation by shifts. */
|
perform a rotation by shifts. */
|
|
|
tmp = operands[1];
|
tmp = operands[1];
|
for (i = 0; i < INTVAL (operands[2]) - 1; i++)
|
for (i = 0; i < INTVAL (operands[2]) - 1; i++)
|
{
|
{
|
tmp = gen_reg_rtx (QImode);
|
tmp = gen_reg_rtx (QImode);
|
emit_insn (gen_rotr_1_clobber (tmp, operands[1]));
|
emit_insn (gen_rotr_1_clobber (tmp, operands[1]));
|
operands[1] = tmp;
|
operands[1] = tmp;
|
}
|
}
|
emit_insn (gen_rotr_1_clobber (operands[0], tmp));
|
emit_insn (gen_rotr_1_clobber (operands[0], tmp));
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
(define_insn "rotr_1_clobber"
|
(define_insn "rotr_1_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(rotatert:QI (match_operand:QI 1 "reg_operand" "0,0")
|
(rotatert:QI (match_operand:QI 1 "reg_operand" "0,0")
|
(const_int 1)))
|
(const_int 1)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"ror\\t%0"
|
"ror\\t%0"
|
[(set_attr "type" "unarycc,unary")])
|
[(set_attr "type" "unarycc,unary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
|
|
;
|
;
|
; THREE OPERAND INTEGER INSTRUCTIONS
|
; THREE OPERAND INTEGER INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; ADDI
|
; ADDI
|
;
|
;
|
; This is used by reload when it calls gen_add2_insn for address arithmetic
|
; This is used by reload when it calls gen_add2_insn for address arithmetic
|
; so we must emit the pattern that doesn't clobber CC.
|
; so we must emit the pattern that doesn't clobber CC.
|
;
|
;
|
(define_expand "addqi3"
|
(define_expand "addqi3"
|
[(parallel [(set (match_operand:QI 0 "std_or_reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "std_or_reg_operand" "")
|
(plus:QI (match_operand:QI 1 "src_operand" "")
|
(plus:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (PLUS, operands, QImode);
|
"legitimize_operands (PLUS, operands, QImode);
|
if (reload_in_progress
|
if (reload_in_progress
|
|| (! IS_PSEUDO_REG (operands[0])
|
|| (! IS_PSEUDO_REG (operands[0])
|
&& ! IS_EXT_REG (operands[0])))
|
&& ! IS_EXT_REG (operands[0])))
|
{
|
{
|
emit_insn (gen_addqi3_noclobber (operands[0], operands[1], operands[2]));
|
emit_insn (gen_addqi3_noclobber (operands[0], operands[1], operands[2]));
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
; This pattern is required primarily for manipulating the stack pointer
|
; This pattern is required primarily for manipulating the stack pointer
|
; where GCC doesn't expect CC to be clobbered or for calculating
|
; where GCC doesn't expect CC to be clobbered or for calculating
|
; addresses during reload. Since this is a more specific pattern
|
; addresses during reload. Since this is a more specific pattern
|
; it needs to go first (otherwise we get into problems trying to decide
|
; it needs to go first (otherwise we get into problems trying to decide
|
; to add clobbers).
|
; to add clobbers).
|
(define_insn "addqi3_noclobber"
|
(define_insn "addqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*addqi3_clobber"
|
(define_insn "*addqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(plus:QI (match_operand:QI 1 "src_operand" "")
|
(plus:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(plus:QI (match_dup 1)
|
(plus:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
(define_insn "*addqi3_test"
|
(define_insn "*addqi3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
; gcc does this in combine.c we just reverse it here
|
; gcc does this in combine.c we just reverse it here
|
(define_insn "*cmp_neg"
|
(define_insn "*cmp_neg"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC_NOOV (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(neg: QI (match_operand:QI 2 "src_operand" "g,JR,rS<>"))))
|
(neg: QI (match_operand:QI 2 "src_operand" "g,JR,rS<>"))))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "g,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "g,JR,rS<>")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (reg:CC_NOOV 21)
|
(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_dup 0) (const_int 0)))]
|
(compare:CC_NOOV (match_dup 0) (const_int 0)))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*addqi3_set"
|
(define_insn "*addqi3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC_NOOV (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(plus:QI (match_dup 1) (match_dup 2)))]
|
(plus:QI (match_dup 1) (match_dup 2)))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
|
|
; This pattern is required during reload when eliminate_regs_in_insn
|
; This pattern is required during reload when eliminate_regs_in_insn
|
; effectively converts a move insn into an add insn when the src
|
; effectively converts a move insn into an add insn when the src
|
; operand is the frame pointer plus a constant. Without this
|
; operand is the frame pointer plus a constant. Without this
|
; pattern, gen_addqi3 can be called with a register for operand0
|
; pattern, gen_addqi3 can be called with a register for operand0
|
; that can clobber CC.
|
; that can clobber CC.
|
; For example, we may have (set (mem (reg ar0)) (reg 99))
|
; For example, we may have (set (mem (reg ar0)) (reg 99))
|
; with (set (reg 99) (plus (reg ar3) (const_int 8)))
|
; with (set (reg 99) (plus (reg ar3) (const_int 8)))
|
; Now since ar3, the frame pointer, is unchanging within the function,
|
; Now since ar3, the frame pointer, is unchanging within the function,
|
; (plus (reg ar3) (const_int 8)) is considered a constant.
|
; (plus (reg ar3) (const_int 8)) is considered a constant.
|
; eliminate_regs_in_insn substitutes this constant to give
|
; eliminate_regs_in_insn substitutes this constant to give
|
; (set (mem (reg ar0)) (plus (reg ar3) (const_int 8))).
|
; (set (mem (reg ar0)) (plus (reg ar3) (const_int 8))).
|
; This is an invalid C4x insn but if we don't provide a pattern
|
; This is an invalid C4x insn but if we don't provide a pattern
|
; for it, it will be considered to be a move insn for reloading.
|
; for it, it will be considered to be a move insn for reloading.
|
(define_insn "*addqi3_noclobber_reload"
|
(define_insn "*addqi3_noclobber_reload"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
"reload_in_progress"
|
"reload_in_progress"
|
"@
|
"@
|
addi\\t%2,%0
|
addi\\t%2,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0
|
addi3\\t%2,%1,%0"
|
addi3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
|
|
(define_insn "*addqi3_carry_clobber"
|
(define_insn "*addqi3_carry_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (PLUS, operands, QImode)"
|
"valid_operands (PLUS, operands, QImode)"
|
"@
|
"@
|
addc\\t%2,%0
|
addc\\t%2,%0
|
addc3\\t%2,%1,%0
|
addc3\\t%2,%1,%0
|
addc3\\t%2,%1,%0
|
addc3\\t%2,%1,%0
|
addc\\t%2,%0
|
addc\\t%2,%0
|
addc3\\t%2,%1,%0
|
addc3\\t%2,%1,%0
|
addc3\\t%2,%1,%0"
|
addc3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
|
|
;
|
;
|
; SUBI/SUBRI
|
; SUBI/SUBRI
|
;
|
;
|
(define_expand "subqi3"
|
(define_expand "subqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(minus:QI (match_operand:QI 1 "src_operand" "")
|
(minus:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MINUS, operands, QImode);")
|
"legitimize_operands (MINUS, operands, QImode);")
|
|
|
(define_insn "*subqi3_clobber"
|
(define_insn "*subqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0"
|
subi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(minus:QI (match_operand:QI 1 "src_operand" "")
|
(minus:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(minus:QI (match_dup 1)
|
(minus:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
(define_insn "*subqi3_test"
|
(define_insn "*subqi3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d,?d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d,?d"))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0"
|
subi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (reg:CC_NOOV 21)
|
(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_dup 0) (const_int 0)))]
|
(compare:CC_NOOV (match_dup 0) (const_int 0)))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0"
|
subi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*subqi3_set"
|
(define_insn "*subqi3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(minus:QI (match_dup 1)
|
(minus:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0"
|
subi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*subqi3_noclobber"
|
(define_insn "*subqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))]
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>")))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subi\\t%2,%0
|
subi\\t%2,%0
|
subri\\t%1,%0
|
subri\\t%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0
|
subi3\\t%2,%1,%0"
|
subi3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*subqi3_carry_clobber"
|
(define_insn "*subqi3_carry_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
|
(minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>,0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>,rIm,0,JR,rS<>")))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subb\\t%2,%0
|
subb\\t%2,%0
|
subrb\\t%1,%0
|
subrb\\t%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0
|
subb\\t%2,%0
|
subb\\t%2,%0
|
subrb\\t%1,%0
|
subrb\\t%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0"
|
subb3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*subqi3_carry_set"
|
(define_insn "*subqi3_carry_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(compare:CC_NOOV (minus:QI (match_operand:QI 1 "src_operand" "0,rIm,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,0,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(minus:QI (match_dup 1)
|
(minus:QI (match_dup 1)
|
(match_dup 2)))
|
(match_dup 2)))
|
(use (reg:CC_NOOV 21))]
|
(use (reg:CC_NOOV 21))]
|
"valid_operands (MINUS, operands, QImode)"
|
"valid_operands (MINUS, operands, QImode)"
|
"@
|
"@
|
subb\\t%2,%0
|
subb\\t%2,%0
|
subrb\\t%1,%0
|
subrb\\t%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0
|
subb3\\t%2,%1,%0"
|
subb3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
;
|
;
|
; MPYI
|
; MPYI
|
;
|
;
|
(define_expand "mulqi3"
|
(define_expand "mulqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(mult:QI (match_operand:QI 1 "src_operand" "")
|
(mult:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"if (TARGET_MPYI || (GET_CODE (operands[2]) == CONST_INT
|
"if (TARGET_MPYI || (GET_CODE (operands[2]) == CONST_INT
|
&& exact_log2 (INTVAL (operands[2])) >= 0))
|
&& exact_log2 (INTVAL (operands[2])) >= 0))
|
legitimize_operands (MULT, operands, QImode);
|
legitimize_operands (MULT, operands, QImode);
|
else
|
else
|
{
|
{
|
if (GET_CODE (operands[2]) == CONST_INT)
|
if (GET_CODE (operands[2]) == CONST_INT)
|
{
|
{
|
/* Let GCC try to synthesize the multiplication using shifts
|
/* Let GCC try to synthesize the multiplication using shifts
|
and adds. In most cases this will be more profitable than
|
and adds. In most cases this will be more profitable than
|
using the C3x MPYI. */
|
using the C3x MPYI. */
|
FAIL;
|
FAIL;
|
}
|
}
|
if (operands[1] == operands[2])
|
if (operands[1] == operands[2])
|
{
|
{
|
/* Do the squaring operation in-line. */
|
/* Do the squaring operation in-line. */
|
emit_insn (gen_sqrqi2_inline (operands[0], operands[1]));
|
emit_insn (gen_sqrqi2_inline (operands[0], operands[1]));
|
DONE;
|
DONE;
|
}
|
}
|
if (TARGET_INLINE)
|
if (TARGET_INLINE)
|
{
|
{
|
emit_insn (gen_mulqi3_inline (operands[0], operands[1],
|
emit_insn (gen_mulqi3_inline (operands[0], operands[1],
|
operands[2]));
|
operands[2]));
|
DONE;
|
DONE;
|
}
|
}
|
c4x_emit_libcall3 (smul_optab->handlers[(int) QImode].libfunc,
|
c4x_emit_libcall3 (smul_optab->handlers[(int) QImode].libfunc,
|
MULT, QImode, operands);
|
MULT, QImode, operands);
|
DONE;
|
DONE;
|
}
|
}
|
")
|
")
|
|
|
(define_insn "*mulqi3_clobber"
|
(define_insn "*mulqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MULT, operands, QImode)"
|
"valid_operands (MULT, operands, QImode)"
|
"*
|
"*
|
if (which_alternative == 0 || which_alternative == 3)
|
if (which_alternative == 0 || which_alternative == 3)
|
{
|
{
|
if (TARGET_C3X
|
if (TARGET_C3X
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
return \"ash\\t%L2,%0\";
|
return \"ash\\t%L2,%0\";
|
else
|
else
|
return \"mpyi\\t%2,%0\";
|
return \"mpyi\\t%2,%0\";
|
}
|
}
|
else
|
else
|
return \"mpyi3\\t%2,%1,%0\";"
|
return \"mpyi3\\t%2,%1,%0\";"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*mulqi3_test"
|
(define_insn "*mulqi3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (MULT, operands, QImode)"
|
"valid_operands (MULT, operands, QImode)"
|
"*
|
"*
|
if (which_alternative == 0)
|
if (which_alternative == 0)
|
{
|
{
|
if (TARGET_C3X
|
if (TARGET_C3X
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
return \"ash\\t%L2,%0\";
|
return \"ash\\t%L2,%0\";
|
else
|
else
|
return \"mpyi\\t%2,%0\";
|
return \"mpyi\\t%2,%0\";
|
}
|
}
|
else
|
else
|
return \"mpyi3\\t%2,%1,%0\";"
|
return \"mpyi3\\t%2,%1,%0\";"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*mulqi3_set"
|
(define_insn "*mulqi3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC_NOOV (mult:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(mult:QI (match_dup 1)
|
(mult:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (MULT, operands, QImode)"
|
"valid_operands (MULT, operands, QImode)"
|
"*
|
"*
|
if (which_alternative == 0)
|
if (which_alternative == 0)
|
{
|
{
|
if (TARGET_C3X
|
if (TARGET_C3X
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& GET_CODE (operands[2]) == CONST_INT
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
&& exact_log2 (INTVAL (operands[2])) >= 0)
|
return \"ash\\t%L2,%0\";
|
return \"ash\\t%L2,%0\";
|
else
|
else
|
return \"mpyi\\t%2,%0\";
|
return \"mpyi\\t%2,%0\";
|
}
|
}
|
else
|
else
|
return \"mpyi3\\t%2,%1,%0\";"
|
return \"mpyi3\\t%2,%1,%0\";"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
; The C3x multiply instruction assumes 24-bit signed integer operands
|
; The C3x multiply instruction assumes 24-bit signed integer operands
|
; and the 48-bit result is truncated to 32-bits.
|
; and the 48-bit result is truncated to 32-bits.
|
(define_insn "mulqi3_24_clobber"
|
(define_insn "mulqi3_24_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(mult:QI
|
(mult:QI
|
(sign_extend:QI
|
(sign_extend:QI
|
(and:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI
|
(sign_extend:QI
|
(and:QI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")
|
(and:QI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"@
|
"@
|
mpyi\\t%2,%0
|
mpyi\\t%2,%0
|
mpyi3\\t%2,%1,%0
|
mpyi3\\t%2,%1,%0
|
mpyi3\\t%2,%1,%0
|
mpyi3\\t%2,%1,%0
|
mpyi\\t%2,%0
|
mpyi\\t%2,%0
|
mpyi3\\t%2,%1,%0
|
mpyi3\\t%2,%1,%0
|
mpyi3\\t%2,%1,%0"
|
mpyi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
|
|
; Fast square function for C3x where TARGET_MPYI not asserted
|
; Fast square function for C3x where TARGET_MPYI not asserted
|
(define_expand "sqrqi2_inline"
|
(define_expand "sqrqi2_inline"
|
[(set (match_dup 7) (match_operand:QI 1 "src_operand" ""))
|
[(set (match_dup 7) (match_operand:QI 1 "src_operand" ""))
|
(parallel [(set (match_dup 3)
|
(parallel [(set (match_dup 3)
|
(lshiftrt:QI (match_dup 7) (const_int 16)))
|
(lshiftrt:QI (match_dup 7) (const_int 16)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 2)
|
(parallel [(set (match_dup 2)
|
(and:QI (match_dup 7) (const_int 65535)))
|
(and:QI (match_dup 7) (const_int 65535)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 4)
|
(parallel [(set (match_dup 4)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 2)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 2)
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI (and:QI (match_dup 2)
|
(sign_extend:QI (and:QI (match_dup 2)
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 5)
|
(parallel [(set (match_dup 5)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 2)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 2)
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI (and:QI (match_dup 3)
|
(sign_extend:QI (and:QI (match_dup 3)
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 6)
|
(parallel [(set (match_dup 6)
|
(ashift:QI (match_dup 5) (const_int 17)))
|
(ashift:QI (match_dup 5) (const_int 17)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(plus:QI (match_dup 4) (match_dup 6)))
|
(plus:QI (match_dup 4) (match_dup 6)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"
|
"
|
operands[2] = gen_reg_rtx (QImode); /* a = val & 0xffff */
|
operands[2] = gen_reg_rtx (QImode); /* a = val & 0xffff */
|
operands[3] = gen_reg_rtx (QImode); /* b = val >> 16 */
|
operands[3] = gen_reg_rtx (QImode); /* b = val >> 16 */
|
operands[4] = gen_reg_rtx (QImode); /* a * a */
|
operands[4] = gen_reg_rtx (QImode); /* a * a */
|
operands[5] = gen_reg_rtx (QImode); /* a * b */
|
operands[5] = gen_reg_rtx (QImode); /* a * b */
|
operands[6] = gen_reg_rtx (QImode); /* (a * b) << 17 */
|
operands[6] = gen_reg_rtx (QImode); /* (a * b) << 17 */
|
operands[7] = gen_reg_rtx (QImode); /* val */
|
operands[7] = gen_reg_rtx (QImode); /* val */
|
")
|
")
|
|
|
; Inlined integer multiply for C3x
|
; Inlined integer multiply for C3x
|
(define_expand "mulqi3_inline"
|
(define_expand "mulqi3_inline"
|
[(set (match_dup 12) (const_int -16))
|
[(set (match_dup 12) (const_int -16))
|
(set (match_dup 13) (match_operand:QI 1 "src_operand" ""))
|
(set (match_dup 13) (match_operand:QI 1 "src_operand" ""))
|
(set (match_dup 14) (match_operand:QI 2 "src_operand" ""))
|
(set (match_dup 14) (match_operand:QI 2 "src_operand" ""))
|
(parallel [(set (match_dup 4)
|
(parallel [(set (match_dup 4)
|
(lshiftrt:QI (match_dup 13) (neg:QI (match_dup 12))))
|
(lshiftrt:QI (match_dup 13) (neg:QI (match_dup 12))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 6)
|
(parallel [(set (match_dup 6)
|
(lshiftrt:QI (match_dup 14) (neg:QI (match_dup 12))))
|
(lshiftrt:QI (match_dup 14) (neg:QI (match_dup 12))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 3)
|
(parallel [(set (match_dup 3)
|
(and:QI (match_dup 13)
|
(and:QI (match_dup 13)
|
(const_int 65535)))
|
(const_int 65535)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 5)
|
(parallel [(set (match_dup 5)
|
(and:QI (match_dup 14)
|
(and:QI (match_dup 14)
|
(const_int 65535)))
|
(const_int 65535)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 7)
|
(parallel [(set (match_dup 7)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 4)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 4)
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI (and:QI (match_dup 5)
|
(sign_extend:QI (and:QI (match_dup 5)
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 8)
|
(parallel [(set (match_dup 8)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 3)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 3)
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI (and:QI (match_dup 5)
|
(sign_extend:QI (and:QI (match_dup 5)
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 9)
|
(parallel [(set (match_dup 9)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 3)
|
(mult:QI (sign_extend:QI (and:QI (match_dup 3)
|
(const_int 16777215)))
|
(const_int 16777215)))
|
(sign_extend:QI (and:QI (match_dup 6)
|
(sign_extend:QI (and:QI (match_dup 6)
|
(const_int 16777215)))))
|
(const_int 16777215)))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 10)
|
(parallel [(set (match_dup 10)
|
(plus:QI (match_dup 7) (match_dup 9)))
|
(plus:QI (match_dup 7) (match_dup 9)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 11)
|
(parallel [(set (match_dup 11)
|
(ashift:QI (match_dup 10) (const_int 16)))
|
(ashift:QI (match_dup 10) (const_int 16)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(plus:QI (match_dup 8) (match_dup 11)))
|
(plus:QI (match_dup 8) (match_dup 11)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"TARGET_C3X"
|
"TARGET_C3X"
|
"
|
"
|
operands[3] = gen_reg_rtx (QImode); /* a = arg1 & 0xffff */
|
operands[3] = gen_reg_rtx (QImode); /* a = arg1 & 0xffff */
|
operands[4] = gen_reg_rtx (QImode); /* b = arg1 >> 16 */
|
operands[4] = gen_reg_rtx (QImode); /* b = arg1 >> 16 */
|
operands[5] = gen_reg_rtx (QImode); /* a = arg2 & 0xffff */
|
operands[5] = gen_reg_rtx (QImode); /* a = arg2 & 0xffff */
|
operands[6] = gen_reg_rtx (QImode); /* b = arg2 >> 16 */
|
operands[6] = gen_reg_rtx (QImode); /* b = arg2 >> 16 */
|
operands[7] = gen_reg_rtx (QImode); /* b * c */
|
operands[7] = gen_reg_rtx (QImode); /* b * c */
|
operands[8] = gen_reg_rtx (QImode); /* a * c */
|
operands[8] = gen_reg_rtx (QImode); /* a * c */
|
operands[9] = gen_reg_rtx (QImode); /* a * d */
|
operands[9] = gen_reg_rtx (QImode); /* a * d */
|
operands[10] = gen_reg_rtx (QImode); /* b * c + a * d */
|
operands[10] = gen_reg_rtx (QImode); /* b * c + a * d */
|
operands[11] = gen_reg_rtx (QImode); /* (b *c + a * d) << 16 */
|
operands[11] = gen_reg_rtx (QImode); /* (b *c + a * d) << 16 */
|
operands[12] = gen_reg_rtx (QImode); /* -16 */
|
operands[12] = gen_reg_rtx (QImode); /* -16 */
|
operands[13] = gen_reg_rtx (QImode); /* arg1 */
|
operands[13] = gen_reg_rtx (QImode); /* arg1 */
|
operands[14] = gen_reg_rtx (QImode); /* arg2 */
|
operands[14] = gen_reg_rtx (QImode); /* arg2 */
|
")
|
")
|
|
|
;
|
;
|
; MPYSHI (C4x only)
|
; MPYSHI (C4x only)
|
;
|
;
|
(define_expand "smulqi3_highpart"
|
(define_expand "smulqi3_highpart"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(sign_extend:HI (match_operand:QI 1 "src_operand" ""))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" ""))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "")))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "")))
|
(const_int 32))))
|
(const_int 32))))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MULT, operands, QImode);
|
"legitimize_operands (MULT, operands, QImode);
|
if (TARGET_C3X)
|
if (TARGET_C3X)
|
{
|
{
|
c4x_emit_libcall_mulhi (smulhi3_libfunc, SIGN_EXTEND, QImode, operands);
|
c4x_emit_libcall_mulhi (smulhi3_libfunc, SIGN_EXTEND, QImode, operands);
|
DONE;
|
DONE;
|
}
|
}
|
")
|
")
|
|
|
(define_insn "*smulqi3_highpart_clobber"
|
(define_insn "*smulqi3_highpart_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>"))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>"))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(const_int 32))))
|
(const_int 32))))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"@
|
"@
|
mpyshi\\t%2,%0
|
mpyshi\\t%2,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi\\t%2,%0
|
mpyshi\\t%2,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0"
|
mpyshi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
(set_attr "data" "int16,int16,int16,int16,int16,int16")])
|
(set_attr "data" "int16,int16,int16,int16,int16,int16")])
|
|
|
(define_insn "*smulqi3_highpart_noclobber"
|
(define_insn "*smulqi3_highpart_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))
|
(sign_extend:HI (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))
|
(const_int 32))))]
|
(const_int 32))))]
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"@
|
"@
|
mpyshi\\t%2,%0
|
mpyshi\\t%2,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0
|
mpyshi3\\t%2,%1,%0"
|
mpyshi3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary")
|
(set_attr "data" "int16,int16,int16")])
|
(set_attr "data" "int16,int16,int16")])
|
|
|
;
|
;
|
; MPYUHI (C4x only)
|
; MPYUHI (C4x only)
|
;
|
;
|
(define_expand "umulqi3_highpart"
|
(define_expand "umulqi3_highpart"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(zero_extend:HI (match_operand:QI 1
|
(zero_extend:HI (match_operand:QI 1
|
"nonimmediate_src_operand" ""))
|
"nonimmediate_src_operand" ""))
|
(zero_extend:HI (match_operand:QI 2
|
(zero_extend:HI (match_operand:QI 2
|
"nonimmediate_lsrc_operand" "")))
|
"nonimmediate_lsrc_operand" "")))
|
(const_int 32))))
|
(const_int 32))))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MULT, operands, QImode);
|
"legitimize_operands (MULT, operands, QImode);
|
if (TARGET_C3X)
|
if (TARGET_C3X)
|
{
|
{
|
c4x_emit_libcall_mulhi (umulhi3_libfunc, ZERO_EXTEND, QImode, operands);
|
c4x_emit_libcall_mulhi (umulhi3_libfunc, ZERO_EXTEND, QImode, operands);
|
DONE;
|
DONE;
|
}
|
}
|
")
|
")
|
|
|
(define_insn "*umulqi3_highpart_clobber"
|
(define_insn "*umulqi3_highpart_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(zero_extend:HI (match_operand:QI 1
|
(zero_extend:HI (match_operand:QI 1
|
"nonimmediate_src_operand" "%0,rR,rS<>,0,rR,rS<>"))
|
"nonimmediate_src_operand" "%0,rR,rS<>,0,rR,rS<>"))
|
(zero_extend:HI (match_operand:QI 2
|
(zero_extend:HI (match_operand:QI 2
|
"nonimmediate_lsrc_operand" "rm,R,rS<>,rm,R,rS<>")))
|
"nonimmediate_lsrc_operand" "rm,R,rS<>,rm,R,rS<>")))
|
(const_int 32))))
|
(const_int 32))))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"@
|
"@
|
mpyuhi\\t%2,%0
|
mpyuhi\\t%2,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi\\t%2,%0
|
mpyuhi\\t%2,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0"
|
mpyuhi3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
(set_attr "data" "uint16,uint16,uint16,uint16,uint16,uint16")])
|
(set_attr "data" "uint16,uint16,uint16,uint16,uint16,uint16")])
|
|
|
(define_insn "*umulqi3_highpart_noclobber"
|
(define_insn "*umulqi3_highpart_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(truncate:QI
|
(truncate:QI
|
(lshiftrt:HI
|
(lshiftrt:HI
|
(mult:HI
|
(mult:HI
|
(zero_extend:HI (match_operand:QI 1
|
(zero_extend:HI (match_operand:QI 1
|
"nonimmediate_src_operand" "0,rR,rS<>"))
|
"nonimmediate_src_operand" "0,rR,rS<>"))
|
(zero_extend:HI (match_operand:QI 2
|
(zero_extend:HI (match_operand:QI 2
|
"nonimmediate_lsrc_operand" "rm,R,rS<>")))
|
"nonimmediate_lsrc_operand" "rm,R,rS<>")))
|
(const_int 32))))]
|
(const_int 32))))]
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"! TARGET_C3X && valid_operands (MULT, operands, QImode)"
|
"@
|
"@
|
mpyuhi\\t%2,%0
|
mpyuhi\\t%2,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0
|
mpyuhi3\\t%2,%1,%0"
|
mpyuhi3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary")
|
(set_attr "data" "uint16,uint16,uint16")])
|
(set_attr "data" "uint16,uint16,uint16")])
|
|
|
;
|
;
|
; AND
|
; AND
|
;
|
;
|
(define_expand "andqi3"
|
(define_expand "andqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(and:QI (match_operand:QI 1 "src_operand" "")
|
(and:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "tsrc_operand" "")))
|
(match_operand:QI 2 "tsrc_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (AND, operands, QImode);")
|
"legitimize_operands (AND, operands, QImode);")
|
|
|
|
|
(define_insn "*andqi3_255_clobber"
|
(define_insn "*andqi3_255_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(and:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(and:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 255)))
|
(const_int 255)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lbu0\\t%1,%0"
|
"lbu0\\t%1,%0"
|
[(set_attr "type" "unarycc,unary")])
|
[(set_attr "type" "unarycc,unary")])
|
|
|
(define_insn "*andqi3_255_noclobber"
|
(define_insn "*andqi3_255_noclobber"
|
[(set (match_operand:QI 0 "reg_operand" "=c")
|
[(set (match_operand:QI 0 "reg_operand" "=c")
|
(and:QI (match_operand:QI 1 "src_operand" "mr")
|
(and:QI (match_operand:QI 1 "src_operand" "mr")
|
(const_int 255)))]
|
(const_int 255)))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lbu0\\t%1,%0"
|
"lbu0\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
|
|
(define_insn "*andqi3_65535_clobber"
|
(define_insn "*andqi3_65535_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(and:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(and:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 65535)))
|
(const_int 65535)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lhu0\\t%1,%0"
|
"lhu0\\t%1,%0"
|
[(set_attr "type" "unarycc,unary")])
|
[(set_attr "type" "unarycc,unary")])
|
|
|
(define_insn "*andqi3_65535_noclobber"
|
(define_insn "*andqi3_65535_noclobber"
|
[(set (match_operand:QI 0 "reg_operand" "=c")
|
[(set (match_operand:QI 0 "reg_operand" "=c")
|
(and:QI (match_operand:QI 1 "src_operand" "mr")
|
(and:QI (match_operand:QI 1 "src_operand" "mr")
|
(const_int 65535)))]
|
(const_int 65535)))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lhu0\\t%1,%0"
|
"lhu0\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_insn "*andqi3_clobber"
|
(define_insn "*andqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,d,?d,c,c,c,?c")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>,0,0,rR,rS<>")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>,0,0,rR,rS<>")
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>,N,rLm,JR,rS<>")))
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>,N,rLm,JR,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
and\\t%2,%0
|
and\\t%2,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
and\\t%2,%0
|
and\\t%2,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0"
|
and3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc,binary,binary,binary,binary")
|
(set_attr "data" "not_uint16,uint16,int16,uint16,not_uint16,uint16,int16,uint16")])
|
(set_attr "data" "not_uint16,uint16,int16,uint16,not_uint16,uint16,int16,uint16")])
|
|
|
(define_insn "*andqi3_noclobber"
|
(define_insn "*andqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c,?c")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))]
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
and\\t%2,%0
|
and\\t%2,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0"
|
and3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary,binary")
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
|
|
(define_insn "andn_st"
|
(define_insn "andn_st"
|
[(set (unspec:QI [(reg:QI 21)] 20)
|
[(set (unspec:QI [(reg:QI 21)] 20)
|
(and:QI (unspec:QI [(reg:QI 21)] UNSPEC_ANDN_ST)
|
(and:QI (unspec:QI [(reg:QI 21)] UNSPEC_ANDN_ST)
|
(match_operand:QI 0 "" "N")))
|
(match_operand:QI 0 "" "N")))
|
(use (match_dup 0))
|
(use (match_dup 0))
|
(use (reg:CC 21))
|
(use (reg:CC 21))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"andn\\t%N0,st"
|
"andn\\t%N0,st"
|
[(set_attr "type" "misc")
|
[(set_attr "type" "misc")
|
(set_attr "data" "not_uint16")])
|
(set_attr "data" "not_uint16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(and:QI (match_operand:QI 1 "src_operand" "")
|
(and:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "tsrc_operand" "")))
|
(match_operand:QI 2 "tsrc_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(and:QI (match_dup 1)
|
(and:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
(define_insn "*andqi3_test"
|
(define_insn "*andqi3_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,r,rR,rS<>")
|
(compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,r,rR,rS<>")
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,X,X,?X"))]
|
(clobber (match_scratch:QI 0 "=d,X,X,?X"))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
tstb\\t%2,%1
|
tstb\\t%2,%1
|
tstb3\\t%2,%1
|
tstb3\\t%2,%1
|
tstb3\\t%2,%1"
|
tstb3\\t%2,%1"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (reg:CC 21)
|
(set (reg:CC 21)
|
(compare:CC (match_dup 0) (const_int 0)))]
|
(compare:CC (match_dup 0) (const_int 0)))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
and\\t%2,%0
|
and\\t%2,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0"
|
and3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
|
|
(define_insn "*andqi3_set"
|
(define_insn "*andqi3_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(compare:CC (and:QI (match_operand:QI 1 "src_operand" "%0,0,rR,rS<>")
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
|
(match_operand:QI 2 "tsrc_operand" "N,rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d,?d")
|
(and:QI (match_dup 1)
|
(and:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%N2,%0
|
andn\\t%N2,%0
|
and\\t%2,%0
|
and\\t%2,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0
|
and3\\t%2,%1,%0"
|
and3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
(set_attr "data" "not_uint16,uint16,int16,uint16")])
|
|
|
;
|
;
|
; ANDN
|
; ANDN
|
;
|
;
|
; NB, this insn doesn't have commutative operands, but valid_operands
|
; NB, this insn doesn't have commutative operands, but valid_operands
|
; assumes that the code AND does. We might have to kludge this if
|
; assumes that the code AND does. We might have to kludge this if
|
; we make valid_operands stricter.
|
; we make valid_operands stricter.
|
(define_insn "*andnqi3_clobber"
|
(define_insn "*andnqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>"))
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%2,%0
|
andn\\t%2,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn\\t%2,%0
|
andn\\t%2,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0"
|
andn3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
|
|
(define_insn "*andnqi3_noclobber"
|
(define_insn "*andnqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>")))]
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>")))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%2,%0
|
andn\\t%2,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0"
|
andn3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" ""))
|
(and:QI (not:QI (match_operand:QI 2 "lsrc_operand" ""))
|
(match_operand:QI 1 "src_operand" "")))
|
(match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(and:QI (not:QI (match_dup 2))
|
(and:QI (not:QI (match_dup 2))
|
(match_dup 1)))]
|
(match_dup 1)))]
|
"")
|
"")
|
|
|
(define_insn "*andnqi3_test"
|
(define_insn "*andnqi3_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%2,%0
|
andn\\t%2,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0"
|
andn3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_insn "*andnqi3_set"
|
(define_insn "*andnqi3_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(compare:CC (and:QI (not:QI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(match_operand:QI 1 "src_operand" "0,rR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(and:QI (not:QI (match_dup 2))
|
(and:QI (not:QI (match_dup 2))
|
(match_dup 1)))]
|
(match_dup 1)))]
|
"valid_operands (AND, operands, QImode)"
|
"valid_operands (AND, operands, QImode)"
|
"@
|
"@
|
andn\\t%2,%0
|
andn\\t%2,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0
|
andn3\\t%2,%1,%0"
|
andn3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
;
|
;
|
; OR
|
; OR
|
;
|
;
|
(define_expand "iorqi3"
|
(define_expand "iorqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(ior:QI (match_operand:QI 1 "src_operand" "")
|
(ior:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (IOR, operands, QImode);")
|
"legitimize_operands (IOR, operands, QImode);")
|
|
|
(define_insn "*iorqi3_clobber"
|
(define_insn "*iorqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (IOR, operands, QImode)"
|
"valid_operands (IOR, operands, QImode)"
|
"@
|
"@
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0"
|
or3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(ior:QI (match_operand:QI 1 "src_operand" "")
|
(ior:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(ior:QI (match_dup 1)
|
(ior:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
(define_insn "*iorqi3_test"
|
(define_insn "*iorqi3_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (IOR, operands, QImode)"
|
"valid_operands (IOR, operands, QImode)"
|
"@
|
"@
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0"
|
or3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
[(parallel [(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (reg:CC 21)
|
(set (reg:CC 21)
|
(compare:CC (match_dup 0) (const_int 0)))]
|
(compare:CC (match_dup 0) (const_int 0)))]
|
"valid_operands (IOR, operands, QImode)"
|
"valid_operands (IOR, operands, QImode)"
|
"@
|
"@
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0"
|
or3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_insn "*iorqi3_set"
|
(define_insn "*iorqi3_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC (ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(ior:QI (match_dup 1)
|
(ior:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (IOR, operands, QImode)"
|
"valid_operands (IOR, operands, QImode)"
|
"@
|
"@
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0"
|
or3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
; This pattern is used for loading symbol references in several parts.
|
; This pattern is used for loading symbol references in several parts.
|
(define_insn "iorqi3_noclobber"
|
(define_insn "iorqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(ior:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
|
"valid_operands (IOR, operands, QImode)"
|
"valid_operands (IOR, operands, QImode)"
|
"@
|
"@
|
or\\t%2,%0
|
or\\t%2,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0
|
or3\\t%2,%1,%0"
|
or3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
;
|
;
|
; XOR
|
; XOR
|
;
|
;
|
(define_expand "xorqi3"
|
(define_expand "xorqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(xor:QI (match_operand:QI 1 "src_operand" "")
|
(xor:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (XOR, operands, QImode);")
|
"legitimize_operands (XOR, operands, QImode);")
|
|
|
(define_insn "*xorqi3_clobber"
|
(define_insn "*xorqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (XOR, operands, QImode)"
|
"valid_operands (XOR, operands, QImode)"
|
"@
|
"@
|
xor\\t%2,%0
|
xor\\t%2,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor\\t%2,%0
|
xor\\t%2,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0"
|
xor3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16,uint16,int16,uint16")])
|
|
|
(define_insn "*xorqi3_noclobber"
|
(define_insn "*xorqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))]
|
"valid_operands (XOR, operands, QImode)"
|
"valid_operands (XOR, operands, QImode)"
|
"@
|
"@
|
xor\\t%2,%0
|
xor\\t%2,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0"
|
xor3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")
|
[(set_attr "type" "binary,binary,binary")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(xor:QI (match_operand:QI 1 "src_operand" "")
|
(xor:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(match_operand:QI 2 "lsrc_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(xor:QI (match_dup 1)
|
(xor:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
(define_insn "*xorqi3_test"
|
(define_insn "*xorqi3_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
(clobber (match_scratch:QI 0 "=d,d,d"))]
|
"valid_operands (XOR, operands, QImode)"
|
"valid_operands (XOR, operands, QImode)"
|
"@
|
"@
|
xor\\t%2,%0
|
xor\\t%2,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0"
|
xor3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
(define_insn "*xorqi3_set"
|
(define_insn "*xorqi3_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(compare:CC (xor:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d,d,d")
|
(xor:QI (match_dup 1)
|
(xor:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (XOR, operands, QImode)"
|
"valid_operands (XOR, operands, QImode)"
|
"@
|
"@
|
xor\\t%2,%0
|
xor\\t%2,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0
|
xor3\\t%2,%1,%0"
|
xor3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
[(set_attr "type" "binarycc,binarycc,binarycc")
|
(set_attr "data" "uint16,int16,uint16")])
|
(set_attr "data" "uint16,int16,uint16")])
|
|
|
;
|
;
|
; LSH/ASH (left)
|
; LSH/ASH (left)
|
;
|
;
|
; The C3x and C4x have two shift instructions ASH and LSH
|
; The C3x and C4x have two shift instructions ASH and LSH
|
; If the shift count is positive, a left shift is performed
|
; If the shift count is positive, a left shift is performed
|
; otherwise a right shift is performed. The number of bits
|
; otherwise a right shift is performed. The number of bits
|
; shifted is determined by the seven LSBs of the shift count.
|
; shifted is determined by the seven LSBs of the shift count.
|
; If the absolute value of the count is 32 or greater, the result
|
; If the absolute value of the count is 32 or greater, the result
|
; using the LSH instruction is zero; with the ASH insn the result
|
; using the LSH instruction is zero; with the ASH insn the result
|
; is zero or negative 1. Note that the ISO C standard allows
|
; is zero or negative 1. Note that the ISO C standard allows
|
; the result to be machine dependent whenever the shift count
|
; the result to be machine dependent whenever the shift count
|
; exceeds the size of the object.
|
; exceeds the size of the object.
|
(define_expand "ashlqi3"
|
(define_expand "ashlqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(ashift:QI (match_operand:QI 1 "src_operand" "")
|
(ashift:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (ASHIFT, operands, QImode);")
|
"legitimize_operands (ASHIFT, operands, QImode);")
|
|
|
(define_insn "*ashlqi3_clobber"
|
(define_insn "*ashlqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (ASHIFT, operands, QImode)"
|
"valid_operands (ASHIFT, operands, QImode)"
|
"@
|
"@
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0"
|
ash3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*ashlqi3_set"
|
(define_insn "*ashlqi3_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC
|
(compare:CC
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "reg_operand" "=d,d,d")
|
(set (match_operand:QI 0 "reg_operand" "=d,d,d")
|
(ashift:QI (match_dup 1)
|
(ashift:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (ASHIFT, operands, QImode)"
|
"valid_operands (ASHIFT, operands, QImode)"
|
"@
|
"@
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0"
|
ash3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "ashlqi3_noclobber"
|
(define_insn "ashlqi3_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
(match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
|
"valid_operands (ASHIFT, operands, QImode)"
|
"valid_operands (ASHIFT, operands, QImode)"
|
"@
|
"@
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0"
|
ash3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
[(set (match_operand:QI 0 "std_reg_operand" "")
|
(ashift:QI (match_operand:QI 1 "src_operand" "")
|
(ashift:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0)
|
[(set (match_dup 0)
|
(ashift:QI (match_dup 1)
|
(ashift:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"")
|
"")
|
|
|
; This is only used by lshrhi3_reg where we need a LSH insn that will
|
; This is only used by lshrhi3_reg where we need a LSH insn that will
|
; shift both ways.
|
; shift both ways.
|
(define_insn "*lshlqi3_clobber"
|
(define_insn "*lshlqi3_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(ashift:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(unspec:QI [(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")] UNSPEC_LSH)))
|
(unspec:QI [(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")] UNSPEC_LSH)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (ASHIFT, operands, QImode)"
|
"valid_operands (ASHIFT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%2,%0
|
lsh\\t%2,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh\\t%2,%0
|
lsh\\t%2,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0"
|
lsh3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
;
|
;
|
; LSH (right)
|
; LSH (right)
|
;
|
;
|
; Logical right shift on the C[34]x works by negating the shift count,
|
; Logical right shift on the C[34]x works by negating the shift count,
|
; then emitting a right shift with the shift count negated. This means
|
; then emitting a right shift with the shift count negated. This means
|
; that all actual shift counts in the RTL will be positive.
|
; that all actual shift counts in the RTL will be positive.
|
;
|
;
|
(define_expand "lshrqi3"
|
(define_expand "lshrqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (LSHIFTRT, operands, QImode);")
|
"legitimize_operands (LSHIFTRT, operands, QImode);")
|
|
|
|
|
(define_insn "*lshrqi3_24_clobber"
|
(define_insn "*lshrqi3_24_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 24)))
|
(const_int 24)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lbu3\\t%1,%0"
|
"lbu3\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
(define_insn "*ashrqi3_24_clobber"
|
(define_insn "*ashrqi3_24_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 24)))
|
(const_int 24)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lb3\\t%1,%0"
|
"lb3\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
(define_insn "lshrqi3_16_clobber"
|
(define_insn "lshrqi3_16_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 16)))
|
(const_int 16)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lhu1\\t%1,%0"
|
"lhu1\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
(define_insn "*ashrqi3_16_clobber"
|
(define_insn "*ashrqi3_16_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "mr,mr")
|
(const_int 16)))
|
(const_int 16)))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"lh1\\t%1,%0"
|
"lh1\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
; When the shift count is greater than the size of the word
|
; When the shift count is greater than the size of the word
|
; the result can be implementation specific
|
; the result can be implementation specific
|
(define_insn "*lshrqi3_const_clobber"
|
(define_insn "*lshrqi3_const_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
|
(match_operand:QI 2 "const_int_operand" "n,n,J,J")))
|
(match_operand:QI 2 "const_int_operand" "n,n,J,J")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%n2,%0
|
lsh\\t%n2,%0
|
lsh\\t%n2,%0
|
lsh\\t%n2,%0
|
lsh3\\t%n2,%1,%0
|
lsh3\\t%n2,%1,%0
|
lsh3\\t%n2,%1,%0"
|
lsh3\\t%n2,%1,%0"
|
[(set_attr "type" "binarycc,binary,binarycc,binary")])
|
[(set_attr "type" "binarycc,binary,binarycc,binary")])
|
|
|
(define_insn "*lshrqi3_const_noclobber"
|
(define_insn "*lshrqi3_const_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(match_operand:QI 2 "const_int_operand" "n,J")))]
|
(match_operand:QI 2 "const_int_operand" "n,J")))]
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%n2,%0
|
lsh\\t%n2,%0
|
lsh3\\t%n2,%1,%0"
|
lsh3\\t%n2,%1,%0"
|
[(set_attr "type" "binary,binary")])
|
[(set_attr "type" "binary,binary")])
|
|
|
; When the shift count is greater than the size of the word
|
; When the shift count is greater than the size of the word
|
; the result can be implementation specific
|
; the result can be implementation specific
|
(define_insn "*lshrqi3_const_set"
|
(define_insn "*lshrqi3_const_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC
|
(compare:CC
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(match_operand:QI 2 "const_int_operand" "n,J"))
|
(match_operand:QI 2 "const_int_operand" "n,J"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "reg_operand" "=?d,d")
|
(set (match_operand:QI 0 "reg_operand" "=?d,d")
|
(lshiftrt:QI (match_dup 1)
|
(lshiftrt:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%n2,%0
|
lsh\\t%n2,%0
|
lsh3\\t%n2,%1,%0"
|
lsh3\\t%n2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
(define_insn "*lshrqi3_nonconst_clobber"
|
(define_insn "*lshrqi3_nonconst_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%2,%0
|
lsh\\t%2,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh\\t%2,%0
|
lsh\\t%2,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0"
|
lsh3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*lshrqi3_nonconst_noclobber"
|
(define_insn "*lshrqi3_nonconst_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(lshiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"valid_operands (LSHIFTRT, operands, QImode)"
|
"@
|
"@
|
lsh\\t%2,%0
|
lsh\\t%2,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0
|
lsh3\\t%2,%1,%0"
|
lsh3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
;
|
;
|
; ASH (right)
|
; ASH (right)
|
;
|
;
|
; Arithmetic right shift on the C[34]x works by negating the shift count,
|
; Arithmetic right shift on the C[34]x works by negating the shift count,
|
; then emitting a right shift with the shift count negated. This means
|
; then emitting a right shift with the shift count negated. This means
|
; that all actual shift counts in the RTL will be positive.
|
; that all actual shift counts in the RTL will be positive.
|
|
|
(define_expand "ashrqi3"
|
(define_expand "ashrqi3"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (ASHIFTRT, operands, QImode);")
|
"legitimize_operands (ASHIFTRT, operands, QImode);")
|
|
|
; When the shift count is greater than the size of the word
|
; When the shift count is greater than the size of the word
|
; the result can be implementation specific
|
; the result can be implementation specific
|
(define_insn "*ashrqi3_const_clobber"
|
(define_insn "*ashrqi3_const_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c,?d,?c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,0,r,r")
|
(match_operand:QI 2 "const_int_operand" "n,n,J,J")))
|
(match_operand:QI 2 "const_int_operand" "n,n,J,J")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"@
|
"@
|
ash\\t%n2,%0
|
ash\\t%n2,%0
|
ash\\t%n2,%0
|
ash\\t%n2,%0
|
ash3\\t%n2,%1,%0
|
ash3\\t%n2,%1,%0
|
ash3\\t%n2,%1,%0"
|
ash3\\t%n2,%1,%0"
|
[(set_attr "type" "binarycc,binary,binarycc,binary")])
|
[(set_attr "type" "binarycc,binary,binarycc,binary")])
|
|
|
(define_insn "*ashrqi3_const_noclobber"
|
(define_insn "*ashrqi3_const_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,?c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(match_operand:QI 2 "const_int_operand" "n,J")))]
|
(match_operand:QI 2 "const_int_operand" "n,J")))]
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"@
|
"@
|
ash\\t%n2,%0
|
ash\\t%n2,%0
|
ash3\\t%n2,%1,%0"
|
ash3\\t%n2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
; When the shift count is greater than the size of the word
|
; When the shift count is greater than the size of the word
|
; the result can be implementation specific
|
; the result can be implementation specific
|
(define_insn "*ashrqi3_const_set"
|
(define_insn "*ashrqi3_const_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC
|
(compare:CC
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,r")
|
(match_operand:QI 2 "const_int_operand" "n,J"))
|
(match_operand:QI 2 "const_int_operand" "n,J"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "reg_operand" "=?d,d")
|
(set (match_operand:QI 0 "reg_operand" "=?d,d")
|
(ashiftrt:QI (match_dup 1)
|
(ashiftrt:QI (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"@
|
"@
|
ash\\t%n2,%0
|
ash\\t%n2,%0
|
ash3\\t%n2,%1,%0"
|
ash3\\t%n2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
(define_insn "*ashrqi3_nonconst_clobber"
|
(define_insn "*ashrqi3_nonconst_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,d,?d,c,c,?c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>,0,rR,rS<>")
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>,rm,R,rS<>"))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"@
|
"@
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0"
|
ash3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
(define_insn "*ashrqi3_nonconst_noclobber"
|
(define_insn "*ashrqi3_nonconst_noclobber"
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
[(set (match_operand:QI 0 "std_reg_operand" "=c,c,?c")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(ashiftrt:QI (match_operand:QI 1 "src_operand" "0,rR,rS<>")
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
|
(neg:QI (match_operand:QI 2 "src_operand" "rm,R,rS<>"))))]
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"valid_operands (ASHIFTRT, operands, QImode)"
|
"@
|
"@
|
ash\\t%2,%0
|
ash\\t%2,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0
|
ash3\\t%2,%1,%0"
|
ash3\\t%2,%1,%0"
|
[(set_attr "type" "binary,binary,binary")])
|
[(set_attr "type" "binary,binary,binary")])
|
; Default to int16 data attr.
|
; Default to int16 data attr.
|
|
|
;
|
;
|
; CMPI
|
; CMPI
|
;
|
;
|
; Unfortunately the C40 doesn't allow cmpi3 7, *ar0++ so the next best
|
; Unfortunately the C40 doesn't allow cmpi3 7, *ar0++ so the next best
|
; thing would be to get the small constant loaded into a register (say r0)
|
; thing would be to get the small constant loaded into a register (say r0)
|
; so that it could be hoisted out of the loop so that we only
|
; so that it could be hoisted out of the loop so that we only
|
; would need to do cmpi3 *ar0++, r0. Now the loop optimization pass
|
; would need to do cmpi3 *ar0++, r0. Now the loop optimization pass
|
; comes before the flow pass (which finds autoincrements) so we're stuck.
|
; comes before the flow pass (which finds autoincrements) so we're stuck.
|
; Ideally, GCC requires another loop optimization pass (preferably after
|
; Ideally, GCC requires another loop optimization pass (preferably after
|
; reload) so that it can hoist invariants out of loops.
|
; reload) so that it can hoist invariants out of loops.
|
; The current solution modifies legitimize_operands () so that small
|
; The current solution modifies legitimize_operands () so that small
|
; constants are forced into a pseudo register.
|
; constants are forced into a pseudo register.
|
;
|
;
|
(define_expand "cmpqi"
|
(define_expand "cmpqi"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QI 0 "src_operand" "")
|
(compare:CC (match_operand:QI 0 "src_operand" "")
|
(match_operand:QI 1 "src_operand" "")))]
|
(match_operand:QI 1 "src_operand" "")))]
|
""
|
""
|
"legitimize_operands (COMPARE, operands, QImode);
|
"legitimize_operands (COMPARE, operands, QImode);
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op1 = operands[1];
|
c4x_compare_op1 = operands[1];
|
DONE;")
|
DONE;")
|
|
|
(define_insn "*cmpqi_test"
|
(define_insn "*cmpqi_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QI 0 "src_operand" "r,rR,rS<>")
|
(compare:CC (match_operand:QI 0 "src_operand" "r,rR,rS<>")
|
(match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
|
(match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
|
"valid_operands (COMPARE, operands, QImode)"
|
"valid_operands (COMPARE, operands, QImode)"
|
"@
|
"@
|
cmpi\\t%1,%0
|
cmpi\\t%1,%0
|
cmpi3\\t%1,%0
|
cmpi3\\t%1,%0
|
cmpi3\\t%1,%0"
|
cmpi3\\t%1,%0"
|
[(set_attr "type" "compare,compare,compare")])
|
[(set_attr "type" "compare,compare,compare")])
|
|
|
(define_insn "*cmpqi_test_noov"
|
(define_insn "*cmpqi_test_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:QI 0 "src_operand" "r,rR,rS<>")
|
(compare:CC_NOOV (match_operand:QI 0 "src_operand" "r,rR,rS<>")
|
(match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
|
(match_operand:QI 1 "src_operand" "rIm,JR,rS<>")))]
|
"valid_operands (COMPARE, operands, QImode)"
|
"valid_operands (COMPARE, operands, QImode)"
|
"@
|
"@
|
cmpi\\t%1,%0
|
cmpi\\t%1,%0
|
cmpi3\\t%1,%0
|
cmpi3\\t%1,%0
|
cmpi3\\t%1,%0"
|
cmpi3\\t%1,%0"
|
[(set_attr "type" "compare,compare,compare")])
|
[(set_attr "type" "compare,compare,compare")])
|
|
|
|
|
;
|
;
|
; BIT-FIELD INSTRUCTIONS
|
; BIT-FIELD INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; LBx/LHw (C4x only)
|
; LBx/LHw (C4x only)
|
;
|
;
|
(define_expand "extv"
|
(define_expand "extv"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(sign_extract:QI (match_operand:QI 1 "src_operand" "")
|
(sign_extract:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")
|
(match_operand:QI 3 "const_int_operand" "")))
|
(match_operand:QI 3 "const_int_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
|
"if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
|
|| (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
|
|| (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
|
FAIL;
|
FAIL;
|
")
|
")
|
|
|
(define_insn "*extv_clobber"
|
(define_insn "*extv_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(sign_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
|
(sign_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
|
(match_operand:QI 2 "const_int_operand" "n,n")
|
(match_operand:QI 2 "const_int_operand" "n,n")
|
(match_operand:QI 3 "const_int_operand" "n,n")))
|
(match_operand:QI 3 "const_int_operand" "n,n")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lb%3\\t%1,%0\";
|
return \"lb%3\\t%1,%0\";
|
}
|
}
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lh%3\\t%1,%0\";
|
return \"lh%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc,binary")
|
[(set_attr "type" "binarycc,binary")
|
(set_attr "data" "int16,int16")])
|
(set_attr "data" "int16,int16")])
|
|
|
(define_insn "*extv_clobber_test"
|
(define_insn "*extv_clobber_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d"))]
|
(clobber (match_scratch:QI 0 "=d"))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lb%3\\t%1,%0\";
|
return \"lb%3\\t%1,%0\";
|
}
|
}
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lh%3\\t%1,%0\";
|
return \"lh%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc")
|
[(set_attr "type" "binarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
(define_insn "*extv_clobber_set"
|
(define_insn "*extv_clobber_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(compare:CC (sign_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "reg_operand" "=d")
|
(set (match_operand:QI 0 "reg_operand" "=d")
|
(sign_extract:QI (match_dup 1)
|
(sign_extract:QI (match_dup 1)
|
(match_dup 2)
|
(match_dup 2)
|
(match_dup 3)))]
|
(match_dup 3)))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lb%3\\t%1,%0\";
|
return \"lb%3\\t%1,%0\";
|
}
|
}
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lh%3\\t%1,%0\";
|
return \"lh%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc")
|
[(set_attr "type" "binarycc")
|
(set_attr "data" "int16")])
|
(set_attr "data" "int16")])
|
|
|
;
|
;
|
; LBUx/LHUw (C4x only)
|
; LBUx/LHUw (C4x only)
|
;
|
;
|
(define_expand "extzv"
|
(define_expand "extzv"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(zero_extract:QI (match_operand:QI 1 "src_operand" "")
|
(zero_extract:QI (match_operand:QI 1 "src_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")
|
(match_operand:QI 2 "const_int_operand" "")
|
(match_operand:QI 3 "const_int_operand" "")))
|
(match_operand:QI 3 "const_int_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
|
"if ((INTVAL (operands[2]) != 8 && INTVAL (operands[2]) != 16)
|
|| (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
|
|| (INTVAL (operands[3]) % INTVAL (operands[2]) != 0))
|
FAIL;
|
FAIL;
|
")
|
")
|
|
|
(define_insn "*extzv_clobber"
|
(define_insn "*extzv_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(zero_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
|
(zero_extract:QI (match_operand:QI 1 "src_operand" "rLm,rLm")
|
(match_operand:QI 2 "const_int_operand" "n,n")
|
(match_operand:QI 2 "const_int_operand" "n,n")
|
(match_operand:QI 3 "const_int_operand" "n,n")))
|
(match_operand:QI 3 "const_int_operand" "n,n")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lbu%3\\t%1,%0\";
|
return \"lbu%3\\t%1,%0\";
|
}
|
}
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lhu%3\\t%1,%0\";
|
return \"lhu%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc,binary")
|
[(set_attr "type" "binarycc,binary")
|
(set_attr "data" "uint16,uint16")])
|
(set_attr "data" "uint16,uint16")])
|
|
|
(define_insn "*extzv_test"
|
(define_insn "*extzv_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QI 0 "=d"))]
|
(clobber (match_scratch:QI 0 "=d"))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lbu%3\\t%1,%0\";
|
return \"lbu%3\\t%1,%0\";
|
}
|
}
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lhu%3\\t%1,%0\";
|
return \"lhu%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc")
|
[(set_attr "type" "binarycc")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
(define_insn "*extzv_set"
|
(define_insn "*extzv_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(compare:CC (zero_extract:QI (match_operand:QI 1 "src_operand" "rLm")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 2 "const_int_operand" "n")
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(match_operand:QI 3 "const_int_operand" "n"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(zero_extract:QI (match_dup 1)
|
(zero_extract:QI (match_dup 1)
|
(match_dup 2)
|
(match_dup 2)
|
(match_dup 3)))]
|
(match_dup 3)))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[2]) == 8 || INTVAL (operands[2]) == 16)
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
&& (INTVAL (operands[3]) % INTVAL (operands[2]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[2]) == 8)
|
if (INTVAL (operands[2]) == 8)
|
{
|
{
|
/* 8 bit extract. */
|
/* 8 bit extract. */
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
|
return \"lbu%3\\t%1,%0\";
|
return \"lbu%3\\t%1,%0\";
|
}
|
}
|
/* 16 bit extract. */
|
/* 16 bit extract. */
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
operands[3] = GEN_INT (INTVAL (operands[3]) / 16);
|
return \"lhu%3\\t%1,%0\";
|
return \"lhu%3\\t%1,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc")
|
[(set_attr "type" "binarycc")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
;
|
;
|
; MBx/MHw (C4x only)
|
; MBx/MHw (C4x only)
|
;
|
;
|
(define_expand "insv"
|
(define_expand "insv"
|
[(parallel [(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "const_int_operand" "")
|
(match_operand:QI 1 "const_int_operand" "")
|
(match_operand:QI 2 "const_int_operand" ""))
|
(match_operand:QI 2 "const_int_operand" ""))
|
(match_operand:QI 3 "src_operand" ""))
|
(match_operand:QI 3 "src_operand" ""))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"if (! (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
"if (! (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
|
|| (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8)))
|
|| (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8)))
|
FAIL;
|
FAIL;
|
")
|
")
|
|
|
(define_insn "*insv_clobber"
|
(define_insn "*insv_clobber"
|
[(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "+d,c")
|
[(set (zero_extract:QI (match_operand:QI 0 "reg_operand" "+d,c")
|
(match_operand:QI 1 "const_int_operand" "n,n")
|
(match_operand:QI 1 "const_int_operand" "n,n")
|
(match_operand:QI 2 "const_int_operand" "n,n"))
|
(match_operand:QI 2 "const_int_operand" "n,n"))
|
(match_operand:QI 3 "src_operand" "rLm,rLm"))
|
(match_operand:QI 3 "src_operand" "rLm,rLm"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
&& (((INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0))
|
|| (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8))"
|
|| (INTVAL (operands[1]) == 24 && INTVAL (operands[2]) == 8))"
|
"*
|
"*
|
if (INTVAL (operands[1]) == 8)
|
if (INTVAL (operands[1]) == 8)
|
{
|
{
|
/* 8 bit insert. */
|
/* 8 bit insert. */
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
|
return \"mb%2\\t%3,%0\";
|
return \"mb%2\\t%3,%0\";
|
}
|
}
|
else if (INTVAL (operands[1]) == 16)
|
else if (INTVAL (operands[1]) == 16)
|
{
|
{
|
/* 16 bit insert. */
|
/* 16 bit insert. */
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
|
return \"mh%2\\t%3,%0\";
|
return \"mh%2\\t%3,%0\";
|
}
|
}
|
/* 24 bit insert. */
|
/* 24 bit insert. */
|
return \"lwl1\\t%3,%0\";
|
return \"lwl1\\t%3,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc,binary")
|
[(set_attr "type" "binarycc,binary")
|
(set_attr "data" "uint16,uint16")])
|
(set_attr "data" "uint16,uint16")])
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (zero_extract:QI (match_operand:QI 0 "ext_reg_operand" "+d")
|
[(parallel [(set (zero_extract:QI (match_operand:QI 0 "ext_reg_operand" "+d")
|
(match_operand:QI 1 "const_int_operand" "n")
|
(match_operand:QI 1 "const_int_operand" "n")
|
(match_operand:QI 2 "const_int_operand" "n"))
|
(match_operand:QI 2 "const_int_operand" "n"))
|
(match_operand:QI 3 "src_operand" "rLm"))
|
(match_operand:QI 3 "src_operand" "rLm"))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (reg:CC 21)
|
(set (reg:CC 21)
|
(compare:CC (match_dup 0) (const_int 0)))]
|
(compare:CC (match_dup 0) (const_int 0)))]
|
"! TARGET_C3X
|
"! TARGET_C3X
|
&& (INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
&& (INTVAL (operands[1]) == 8 || INTVAL (operands[1]) == 16)
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0)"
|
&& (INTVAL (operands[2]) % INTVAL (operands[1]) == 0)"
|
"*
|
"*
|
if (INTVAL (operands[1]) == 8)
|
if (INTVAL (operands[1]) == 8)
|
{
|
{
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
|
return \"mb%2\\t%3,%0\";
|
return \"mb%2\\t%3,%0\";
|
}
|
}
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
|
operands[2] = GEN_INT (INTVAL (operands[2]) / 16);
|
return \"mh%2\\t%3,%0\";
|
return \"mh%2\\t%3,%0\";
|
"
|
"
|
[(set_attr "type" "binarycc")
|
[(set_attr "type" "binarycc")
|
(set_attr "data" "uint16")])
|
(set_attr "data" "uint16")])
|
|
|
|
|
; TWO OPERAND FLOAT INSTRUCTIONS
|
; TWO OPERAND FLOAT INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; LDF/STF
|
; LDF/STF
|
;
|
;
|
; If one of the operands is not a register, then we should
|
; If one of the operands is not a register, then we should
|
; emit two insns, using a scratch register. This will produce
|
; emit two insns, using a scratch register. This will produce
|
; better code in loops if the source operand is invariant, since
|
; better code in loops if the source operand is invariant, since
|
; the source reload can be optimized out. During reload we cannot
|
; the source reload can be optimized out. During reload we cannot
|
; use change_address or force_reg.
|
; use change_address or force_reg.
|
(define_expand "movqf"
|
(define_expand "movqf"
|
[(set (match_operand:QF 0 "src_operand" "")
|
[(set (match_operand:QF 0 "src_operand" "")
|
(match_operand:QF 1 "src_operand" ""))]
|
(match_operand:QF 1 "src_operand" ""))]
|
""
|
""
|
"
|
"
|
{
|
{
|
if (c4x_emit_move_sequence (operands, QFmode))
|
if (c4x_emit_move_sequence (operands, QFmode))
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
; This can generate invalid stack slot displacements
|
; This can generate invalid stack slot displacements
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))]
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 3) (match_dup 1))
|
[(set (match_dup 3) (match_dup 1))
|
(set (match_dup 0) (match_dup 2))]
|
(set (match_dup 0) (match_dup 2))]
|
"operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
|
"operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
|
operands[3] = copy_rtx (operands[2]);
|
operands[3] = copy_rtx (operands[2]);
|
PUT_MODE (operands[3], QFmode);")
|
PUT_MODE (operands[3], QFmode);")
|
|
|
|
|
(define_insn "storeqf_int"
|
(define_insn "storeqf_int"
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))]
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"reload_completed"
|
"reload_completed"
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
(match_dup 1))
|
(match_dup 1))
|
(parallel [(set (match_dup 0)
|
(parallel [(set (match_dup 0)
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(mem:QI (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"")
|
"")
|
|
|
|
|
; We need accurate death notes for this...
|
; We need accurate death notes for this...
|
;(define_peephole
|
;(define_peephole
|
; [(set (match_operand:QF 0 "reg_operand" "=f")
|
; [(set (match_operand:QF 0 "reg_operand" "=f")
|
; (match_operand:QF 1 "memory_operand" "m"))
|
; (match_operand:QF 1 "memory_operand" "m"))
|
; (set (mem:QF (pre_inc:QI (reg:QI 20)))
|
; (set (mem:QF (pre_inc:QI (reg:QI 20)))
|
; (match_dup 0))
|
; (match_dup 0))
|
; (parallel [(set (match_operand:QI 2 "reg_operand" "r")
|
; (parallel [(set (match_operand:QI 2 "reg_operand" "r")
|
; (mem:QI (post_dec:QI (reg:QI 20))))
|
; (mem:QI (post_dec:QI (reg:QI 20))))
|
; (clobber (reg:CC 21))])]
|
; (clobber (reg:CC 21))])]
|
; ""
|
; ""
|
; "ldiu\\t%1,%0")
|
; "ldiu\\t%1,%0")
|
|
|
(define_insn "storeqf_int_clobber"
|
(define_insn "storeqf_int_clobber"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "=r")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "=r")
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))
|
(unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
|
|
; This can generate invalid stack slot displacements
|
; This can generate invalid stack slot displacements
|
(define_split
|
(define_split
|
[(set (match_operand:QF 0 "reg_operand" "")
|
[(set (match_operand:QF 0 "reg_operand" "")
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))]
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 2) (match_dup 1))
|
[(set (match_dup 2) (match_dup 1))
|
(set (match_dup 0) (match_dup 3))]
|
(set (match_dup 0) (match_dup 3))]
|
"operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
|
"operands[2] = assign_stack_temp (QImode, GET_MODE_SIZE (QImode), 0);
|
operands[3] = copy_rtx (operands[2]);
|
operands[3] = copy_rtx (operands[2]);
|
PUT_MODE (operands[3], QFmode);")
|
PUT_MODE (operands[3], QFmode);")
|
|
|
|
|
(define_insn "loadqf_int"
|
(define_insn "loadqf_int"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))]
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"reload_completed"
|
"reload_completed"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(match_dup 1))
|
(match_dup 1))
|
(parallel [(set (match_dup 0)
|
(parallel [(set (match_dup 0)
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"")
|
"")
|
|
|
(define_insn "loadqf_int_clobber"
|
(define_insn "loadqf_int_clobber"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "=f")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))
|
(unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; We must provide an alternative to store to memory in case we have to
|
; We must provide an alternative to store to memory in case we have to
|
; spill a register.
|
; spill a register.
|
(define_insn "movqf_noclobber"
|
(define_insn "movqf_noclobber"
|
[(set (match_operand:QF 0 "dst_operand" "=f,m")
|
[(set (match_operand:QF 0 "dst_operand" "=f,m")
|
(match_operand:QF 1 "src_operand" "fHm,f"))]
|
(match_operand:QF 1 "src_operand" "fHm,f"))]
|
"REG_P (operands[0]) || REG_P (operands[1])"
|
"REG_P (operands[0]) || REG_P (operands[1])"
|
"@
|
"@
|
ldfu\\t%1,%0
|
ldfu\\t%1,%0
|
stf\\t%1,%0"
|
stf\\t%1,%0"
|
[(set_attr "type" "unary,store")])
|
[(set_attr "type" "unary,store")])
|
|
|
;(define_insn "*movqf_clobber"
|
;(define_insn "*movqf_clobber"
|
; [(set (match_operand:QF 0 "reg_operand" "=f")
|
; [(set (match_operand:QF 0 "reg_operand" "=f")
|
; (match_operand:QF 1 "src_operand" "fHm"))
|
; (match_operand:QF 1 "src_operand" "fHm"))
|
; (clobber (reg:CC 21))]
|
; (clobber (reg:CC 21))]
|
; "0"
|
; "0"
|
; "ldf\\t%1,%0"
|
; "ldf\\t%1,%0"
|
; [(set_attr "type" "unarycc")])
|
; [(set_attr "type" "unarycc")])
|
|
|
(define_insn "*movqf_test"
|
(define_insn "*movqf_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QF 1 "src_operand" "fHm")
|
(compare:CC (match_operand:QF 1 "src_operand" "fHm")
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:QF 0 "=f"))]
|
(clobber (match_scratch:QF 0 "=f"))]
|
""
|
""
|
"ldf\\t%1,%0"
|
"ldf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*movqf_set"
|
(define_insn "*movqf_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QF 1 "src_operand" "fHm")
|
(compare:CC (match_operand:QF 1 "src_operand" "fHm")
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(match_dup 1))]
|
(match_dup 1))]
|
""
|
""
|
"ldf\\t%1,%0"
|
"ldf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
(define_insn "*movqf_parallel"
|
(define_insn "*movqf_parallel"
|
[(set (match_operand:QF 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
|
[(set (match_operand:QF 0 "parallel_operand" "=q,S<>!V,q,S<>!V")
|
(match_operand:QF 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
|
(match_operand:QF 1 "parallel_operand" "S<>!V,q,S<>!V,q"))
|
(set (match_operand:QF 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
|
(set (match_operand:QF 2 "parallel_operand" "=q,S<>!V,S<>!V,q")
|
(match_operand:QF 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
|
(match_operand:QF 3 "parallel_operand" "S<>!V,q,q,S<>!V"))]
|
"TARGET_PARALLEL && valid_parallel_load_store (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_load_store (operands, QFmode)"
|
"@
|
"@
|
ldf1\\t%1,%0\\n||\\tldf2\\t%3,%2
|
ldf1\\t%1,%0\\n||\\tldf2\\t%3,%2
|
stf1\\t%1,%0\\n||\\tstf2\\t%3,%2
|
stf1\\t%1,%0\\n||\\tstf2\\t%3,%2
|
ldf\\t%1,%0\\n||\\tstf\\t%3,%2
|
ldf\\t%1,%0\\n||\\tstf\\t%3,%2
|
ldf\\t%3,%2\\n||\\tstf\\t%1,%0"
|
ldf\\t%3,%2\\n||\\tstf\\t%1,%0"
|
[(set_attr "type" "load_load,store_store,load_store,store_load")])
|
[(set_attr "type" "load_load,store_store,load_store,store_load")])
|
|
|
|
|
;
|
;
|
; PUSH/POP
|
; PUSH/POP
|
;
|
;
|
(define_insn "pushqf"
|
(define_insn "pushqf"
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
(match_operand:QF 0 "reg_operand" "f"))]
|
(match_operand:QF 0 "reg_operand" "f"))]
|
""
|
""
|
"pushf\\t%0"
|
"pushf\\t%0"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
(define_insn "popqf"
|
(define_insn "popqf"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"popf\\t%0"
|
"popf\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
(define_insn "popqf_unspec"
|
(define_insn "popqf_unspec"
|
[(set (unspec:QF [(match_operand:QF 0 "reg_operand" "=f")] UNSPEC_POPQF)
|
[(set (unspec:QF [(match_operand:QF 0 "reg_operand" "=f")] UNSPEC_POPQF)
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(mem:QF (post_dec:QI (reg:QI 20))))
|
(clobber (match_dup 0))
|
(clobber (match_dup 0))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"popf\\t%0"
|
"popf\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
;
|
;
|
; ABSF
|
; ABSF
|
;
|
;
|
(define_expand "absqf2"
|
(define_expand "absqf2"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(abs:QF (match_operand:QF 1 "src_operand" "")))
|
(abs:QF (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*absqf2_clobber"
|
(define_insn "*absqf2_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(abs:QF (match_operand:QF 1 "src_operand" "fHm")))
|
(abs:QF (match_operand:QF 1 "src_operand" "fHm")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*absqf2_test"
|
(define_insn "*absqf2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(clobber (match_scratch:QF 0 "=f"))]
|
(clobber (match_scratch:QF 0 "=f"))]
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*absqf2_set"
|
(define_insn "*absqf2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(compare:CC_NOOV (abs:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(abs:QF (match_dup 1)))]
|
(abs:QF (match_dup 1)))]
|
|
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; NEGF
|
; NEGF
|
;
|
;
|
(define_expand "negqf2"
|
(define_expand "negqf2"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(neg:QF (match_operand:QF 1 "src_operand" "")))
|
(neg:QF (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*negqf2_clobber"
|
(define_insn "*negqf2_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(neg:QF (match_operand:QF 1 "src_operand" "fHm")))
|
(neg:QF (match_operand:QF 1 "src_operand" "fHm")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*negqf2_test"
|
(define_insn "*negqf2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(clobber (match_scratch:QF 0 "=f"))]
|
(clobber (match_scratch:QF 0 "=f"))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*negqf2_set"
|
(define_insn "*negqf2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(compare:CC_NOOV (neg:QF (match_operand:QF 1 "src_operand" "fHm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(neg:QF (match_dup 1)))]
|
(neg:QF (match_dup 1)))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; FLOAT
|
; FLOAT
|
;
|
;
|
(define_insn "floatqiqf2"
|
(define_insn "floatqiqf2"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(float:QF (match_operand:QI 1 "src_operand" "rIm")))
|
(float:QF (match_operand:QI 1 "src_operand" "rIm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"float\\t%1,%0"
|
"float\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*floatqiqf2_set"
|
(define_insn "*floatqiqf2_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (float:QF (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC (float:QF (match_operand:QI 1 "src_operand" "rIm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(set (match_operand:QF 0 "reg_operand" "=f")
|
(float:QF (match_dup 1)))]
|
(float:QF (match_dup 1)))]
|
""
|
""
|
"float\\t%1,%0"
|
"float\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
; Unsigned conversions are a little tricky because we need to
|
; Unsigned conversions are a little tricky because we need to
|
; add the value for the high bit if necessary.
|
; add the value for the high bit if necessary.
|
;
|
;
|
;
|
;
|
(define_expand "floatunsqiqf2"
|
(define_expand "floatunsqiqf2"
|
[(set (match_dup 2) (match_dup 3))
|
[(set (match_dup 2) (match_dup 3))
|
(parallel [(set (reg:CC 21)
|
(parallel [(set (reg:CC 21)
|
(compare:CC (float:QF (match_operand:QI 1 "src_operand" ""))
|
(compare:CC (float:QF (match_operand:QI 1 "src_operand" ""))
|
(match_dup 3)))
|
(match_dup 3)))
|
(set (match_dup 4)
|
(set (match_dup 4)
|
(float:QF (match_dup 1)))])
|
(float:QF (match_dup 1)))])
|
(set (match_dup 2)
|
(set (match_dup 2)
|
(if_then_else:QF (lt (reg:CC 21) (const_int 0))
|
(if_then_else:QF (lt (reg:CC 21) (const_int 0))
|
(match_dup 5)
|
(match_dup 5)
|
(match_dup 2)))
|
(match_dup 2)))
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(plus:QF (match_dup 2) (match_dup 4)))
|
(plus:QF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"operands[2] = gen_reg_rtx (QFmode);
|
"operands[2] = gen_reg_rtx (QFmode);
|
operands[3] = CONST0_RTX (QFmode);
|
operands[3] = CONST0_RTX (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[5] = gen_reg_rtx (QFmode);
|
operands[5] = gen_reg_rtx (QFmode);
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
|
|
|
(define_expand "floatunsqihf2"
|
(define_expand "floatunsqihf2"
|
[(set (match_dup 2) (match_dup 3))
|
[(set (match_dup 2) (match_dup 3))
|
(parallel [(set (reg:CC 21)
|
(parallel [(set (reg:CC 21)
|
(compare:CC (float:HF (match_operand:QI 1 "src_operand" ""))
|
(compare:CC (float:HF (match_operand:QI 1 "src_operand" ""))
|
(match_dup 3)))
|
(match_dup 3)))
|
(set (match_dup 4)
|
(set (match_dup 4)
|
(float:HF (match_dup 1)))])
|
(float:HF (match_dup 1)))])
|
(set (match_dup 2)
|
(set (match_dup 2)
|
(if_then_else:HF (lt (reg:CC 21) (const_int 0))
|
(if_then_else:HF (lt (reg:CC 21) (const_int 0))
|
(match_dup 5)
|
(match_dup 5)
|
(match_dup 2)))
|
(match_dup 2)))
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(plus:HF (match_dup 2) (match_dup 4)))
|
(plus:HF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"operands[2] = gen_reg_rtx (HFmode);
|
"operands[2] = gen_reg_rtx (HFmode);
|
operands[3] = CONST0_RTX (HFmode);
|
operands[3] = CONST0_RTX (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[5] = gen_reg_rtx (HFmode);
|
operands[5] = gen_reg_rtx (HFmode);
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
|
|
|
(define_insn "floatqihf2"
|
(define_insn "floatqihf2"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(float:HF (match_operand:QI 1 "src_operand" "rIm")))
|
(float:HF (match_operand:QI 1 "src_operand" "rIm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"float\\t%1,%0"
|
"float\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*floatqihf2_set"
|
(define_insn "*floatqihf2_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (float:HF (match_operand:QI 1 "src_operand" "rIm"))
|
(compare:CC (float:HF (match_operand:QI 1 "src_operand" "rIm"))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(match_operand:QF 2 "fp_zero_operand" "G")))
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(float:HF (match_dup 1)))]
|
(float:HF (match_dup 1)))]
|
""
|
""
|
"float\\t%1,%0"
|
"float\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; FIX
|
; FIX
|
;
|
;
|
(define_insn "fixqfqi_clobber"
|
(define_insn "fixqfqi_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
[(set (match_operand:QI 0 "reg_operand" "=d,c")
|
(fix:QI (match_operand:QF 1 "src_operand" "fHm,fHm")))
|
(fix:QI (match_operand:QF 1 "src_operand" "fHm,fHm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"fix\\t%1,%0"
|
"fix\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*fixqfqi_set"
|
(define_insn "*fixqfqi_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (fix:QI (match_operand:QF 1 "src_operand" "fHm"))
|
(compare:CC (fix:QI (match_operand:QF 1 "src_operand" "fHm"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(fix:QI (match_dup 1)))]
|
(fix:QI (match_dup 1)))]
|
""
|
""
|
"fix\\t%1,%0"
|
"fix\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; The C[34]x fix instruction implements a floor, not a straight trunc,
|
; The C[34]x fix instruction implements a floor, not a straight trunc,
|
; so we have to invert the number, fix it, and reinvert it if negative
|
; so we have to invert the number, fix it, and reinvert it if negative
|
;
|
;
|
(define_expand "fix_truncqfqi2"
|
(define_expand "fix_truncqfqi2"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(fix:QI (match_operand:QF 1 "src_operand" "")))
|
(fix:QI (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 3) (neg:QF (match_dup 1)))
|
(parallel [(set (match_dup 3) (neg:QF (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
|
(parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (reg:CC_NOOV 21)
|
(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
|
(compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
|
(set (match_dup 5) (neg:QI (match_dup 4)))])
|
(set (match_dup 5) (neg:QI (match_dup 4)))])
|
(set (match_dup 2)
|
(set (match_dup 2)
|
(if_then_else:QI (le (reg:CC 21) (const_int 0))
|
(if_then_else:QI (le (reg:CC 21) (const_int 0))
|
(match_dup 5)
|
(match_dup 5)
|
(match_dup 2)))
|
(match_dup 2)))
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
|
""
|
""
|
"if (TARGET_FAST_FIX)
|
"if (TARGET_FAST_FIX)
|
{
|
{
|
emit_insn (gen_fixqfqi_clobber (operands[0], operands[1]));
|
emit_insn (gen_fixqfqi_clobber (operands[0], operands[1]));
|
DONE;
|
DONE;
|
}
|
}
|
operands[2] = gen_reg_rtx (QImode);
|
operands[2] = gen_reg_rtx (QImode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QImode);
|
")
|
")
|
|
|
(define_expand "fix_truncqfhi2"
|
(define_expand "fix_truncqfhi2"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(fix:HI (match_operand:QF 1 "src_operand" "")))
|
(fix:HI (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (fix_truncqfhi2_libfunc, FIX, HImode, QFmode, 2, operands);
|
"c4x_emit_libcall (fix_truncqfhi2_libfunc, FIX, HImode, QFmode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
(define_expand "fixuns_truncqfqi2"
|
(define_expand "fixuns_truncqfqi2"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(fix:QI (match_operand:QF 1 "src_operand" "fHm")))
|
(fix:QI (match_operand:QF 1 "src_operand" "fHm")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 3)
|
(parallel [(set (match_dup 3)
|
(minus:QF (match_dup 1) (match_dup 5)))
|
(minus:QF (match_dup 1) (match_dup 5)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (reg:CC 21)
|
(parallel [(set (reg:CC 21)
|
(compare:CC (fix:QI (match_dup 3))
|
(compare:CC (fix:QI (match_dup 3))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_dup 4)
|
(set (match_dup 4)
|
(fix:QI (match_dup 3)))])
|
(fix:QI (match_dup 3)))])
|
(parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
|
(parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
|
(use (reg:CC 21))])
|
(use (reg:CC 21))])
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
|
""
|
""
|
"operands[2] = gen_reg_rtx (QImode);
|
"operands[2] = gen_reg_rtx (QImode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QFmode);
|
operands[5] = gen_reg_rtx (QFmode);
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
|
|
|
(define_expand "fixuns_truncqfhi2"
|
(define_expand "fixuns_truncqfhi2"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(unsigned_fix:HI (match_operand:QF 1 "src_operand" "")))
|
(unsigned_fix:HI (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (fixuns_truncqfhi2_libfunc, UNSIGNED_FIX,
|
"c4x_emit_libcall (fixuns_truncqfhi2_libfunc, UNSIGNED_FIX,
|
HImode, QFmode, 2, operands);
|
HImode, QFmode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
;
|
;
|
; RCPF
|
; RCPF
|
;
|
;
|
(define_insn "rcpfqf_clobber"
|
(define_insn "rcpfqf_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RCPF))
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RCPF))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rcpf\\t%1,%0"
|
"rcpf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; RSQRF
|
; RSQRF
|
;
|
;
|
(define_insn "*rsqrfqf_clobber"
|
(define_insn "*rsqrfqf_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RSQRF))
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RSQRF))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rsqrf\\t%1,%0"
|
"rsqrf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; RNDF
|
; RNDF
|
;
|
;
|
(define_insn "*rndqf_clobber"
|
(define_insn "*rndqf_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RND))
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RND))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rnd\\t%1,%0"
|
"rnd\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
; Inlined float square root for C4x
|
; Inlined float square root for C4x
|
(define_expand "sqrtqf2_inline"
|
(define_expand "sqrtqf2_inline"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(unspec:QF [(match_operand:QF 1 "src_operand" "")] UNSPEC_RSQRF))
|
(unspec:QF [(match_operand:QF 1 "src_operand" "")] UNSPEC_RSQRF))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 5) (match_dup 1)))
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 5) (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 6) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 2) (mult:QF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 1)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(unspec:QF [(match_dup 4)] UNSPEC_RND))
|
(unspec:QF [(match_dup 4)] UNSPEC_RND))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"if (! reload_in_progress
|
"if (! reload_in_progress
|
&& ! reg_operand (operands[1], QFmode))
|
&& ! reg_operand (operands[1], QFmode))
|
operands[1] = force_reg (QFmode, operands[1]);
|
operands[1] = force_reg (QFmode, operands[1]);
|
operands[2] = gen_reg_rtx (QFmode);
|
operands[2] = gen_reg_rtx (QFmode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[5] = CONST_DOUBLE_ATOF (\"0.5\", QFmode);
|
operands[5] = CONST_DOUBLE_ATOF (\"0.5\", QFmode);
|
operands[6] = CONST_DOUBLE_ATOF (\"1.5\", QFmode);")
|
operands[6] = CONST_DOUBLE_ATOF (\"1.5\", QFmode);")
|
|
|
(define_expand "sqrtqf2"
|
(define_expand "sqrtqf2"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(sqrt:QF (match_operand:QF 1 "src_operand" "")))
|
(sqrt:QF (match_operand:QF 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X && TARGET_INLINE"
|
"! TARGET_C3X && TARGET_INLINE"
|
"emit_insn (gen_sqrtqf2_inline (operands[0], operands[1]));
|
"emit_insn (gen_sqrtqf2_inline (operands[0], operands[1]));
|
DONE;")
|
DONE;")
|
|
|
;
|
;
|
; TOIEEE / FRIEEE
|
; TOIEEE / FRIEEE
|
;
|
;
|
(define_insn "toieee"
|
(define_insn "toieee"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_TOIEEE))
|
(unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_TOIEEE))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"toieee\\t%1,%0")
|
"toieee\\t%1,%0")
|
|
|
(define_insn "frieee"
|
(define_insn "frieee"
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
[(set (match_operand:QF 0 "reg_operand" "=f")
|
(unspec:QF [(match_operand:QF 1 "memory_operand" "m")] UNSPEC_FRIEEE))
|
(unspec:QF [(match_operand:QF 1 "memory_operand" "m")] UNSPEC_FRIEEE))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"frieee\\t%1,%0")
|
"frieee\\t%1,%0")
|
|
|
;
|
;
|
; THREE OPERAND FLOAT INSTRUCTIONS
|
; THREE OPERAND FLOAT INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; ADDF
|
; ADDF
|
;
|
;
|
(define_expand "addqf3"
|
(define_expand "addqf3"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(plus:QF (match_operand:QF 1 "src_operand" "")
|
(plus:QF (match_operand:QF 1 "src_operand" "")
|
(match_operand:QF 2 "src_operand" "")))
|
(match_operand:QF 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (PLUS, operands, QFmode);")
|
"legitimize_operands (PLUS, operands, QFmode);")
|
|
|
(define_insn "*addqf3_clobber"
|
(define_insn "*addqf3_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (PLUS, operands, QFmode)"
|
"valid_operands (PLUS, operands, QFmode)"
|
"@
|
"@
|
addf\\t%2,%0
|
addf\\t%2,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0"
|
addf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*addqf3_test"
|
(define_insn "*addqf3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(clobber (match_scratch:QF 0 "=f,f,?f"))]
|
(clobber (match_scratch:QF 0 "=f,f,?f"))]
|
"valid_operands (PLUS, operands, QFmode)"
|
"valid_operands (PLUS, operands, QFmode)"
|
"@
|
"@
|
addf\\t%2,%0
|
addf\\t%2,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0"
|
addf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*addqf3_set"
|
(define_insn "*addqf3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(compare:CC_NOOV (plus:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(plus:QF (match_dup 1)
|
(plus:QF (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (PLUS, operands, QFmode)"
|
"valid_operands (PLUS, operands, QFmode)"
|
"@
|
"@
|
addf\\t%2,%0
|
addf\\t%2,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0
|
addf3\\t%2,%1,%0"
|
addf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
;
|
;
|
; SUBF/SUBRF
|
; SUBF/SUBRF
|
;
|
;
|
(define_expand "subqf3"
|
(define_expand "subqf3"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(minus:QF (match_operand:QF 1 "src_operand" "")
|
(minus:QF (match_operand:QF 1 "src_operand" "")
|
(match_operand:QF 2 "src_operand" "")))
|
(match_operand:QF 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MINUS, operands, QFmode);")
|
"legitimize_operands (MINUS, operands, QFmode);")
|
|
|
(define_insn "*subqf3_clobber"
|
(define_insn "*subqf3_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
|
(minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>")))
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MINUS, operands, QFmode)"
|
"valid_operands (MINUS, operands, QFmode)"
|
"@
|
"@
|
subf\\t%2,%0
|
subf\\t%2,%0
|
subrf\\t%1,%0
|
subrf\\t%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0"
|
subf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*subqf3_test"
|
(define_insn "*subqf3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
|
(clobber (match_scratch:QF 0 "=f,f,f,?f"))]
|
(clobber (match_scratch:QF 0 "=f,f,f,?f"))]
|
"valid_operands (MINUS, operands, QFmode)"
|
"valid_operands (MINUS, operands, QFmode)"
|
"@
|
"@
|
subf\\t%2,%0
|
subf\\t%2,%0
|
subrf\\t%1,%0
|
subrf\\t%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0"
|
subf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*subqf3_set"
|
(define_insn "*subqf3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(compare:CC_NOOV (minus:QF (match_operand:QF 1 "src_operand" "0,fHm,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,0,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G,G")))
|
(set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
|
(set (match_operand:QF 0 "reg_operand" "=f,f,f,?f")
|
(minus:QF (match_dup 1)
|
(minus:QF (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (MINUS, operands, QFmode)"
|
"valid_operands (MINUS, operands, QFmode)"
|
"@
|
"@
|
subf\\t%2,%0
|
subf\\t%2,%0
|
subrf\\t%1,%0
|
subrf\\t%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0
|
subf3\\t%2,%1,%0"
|
subf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
;
|
;
|
; MPYF
|
; MPYF
|
;
|
;
|
(define_expand "mulqf3"
|
(define_expand "mulqf3"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(mult:QF (match_operand:QF 1 "src_operand" "")
|
(mult:QF (match_operand:QF 1 "src_operand" "")
|
(match_operand:QF 2 "src_operand" "")))
|
(match_operand:QF 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MULT, operands, QFmode);")
|
"legitimize_operands (MULT, operands, QFmode);")
|
|
|
(define_insn "*mulqf3_clobber"
|
(define_insn "*mulqf3_clobber"
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
[(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MULT, operands, QFmode)"
|
"valid_operands (MULT, operands, QFmode)"
|
"@
|
"@
|
mpyf\\t%2,%0
|
mpyf\\t%2,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0"
|
mpyf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*mulqf3_test"
|
(define_insn "*mulqf3_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(clobber (match_scratch:QF 0 "=f,f,?f"))]
|
(clobber (match_scratch:QF 0 "=f,f,?f"))]
|
"valid_operands (MULT, operands, QFmode)"
|
"valid_operands (MULT, operands, QFmode)"
|
"@
|
"@
|
mpyf\\t%2,%0
|
mpyf\\t%2,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0"
|
mpyf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
(define_insn "*mulqf3_set"
|
(define_insn "*mulqf3_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(compare:CC_NOOV (mult:QF (match_operand:QF 1 "src_operand" "%0,fR,fS<>")
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 2 "src_operand" "fHm,R,fS<>"))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(match_operand:QF 3 "fp_zero_operand" "G,G,G")))
|
(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(set (match_operand:QF 0 "reg_operand" "=f,f,?f")
|
(mult:QF (match_dup 1)
|
(mult:QF (match_dup 1)
|
(match_dup 2)))]
|
(match_dup 2)))]
|
"valid_operands (MULT, operands, QFmode)"
|
"valid_operands (MULT, operands, QFmode)"
|
"@
|
"@
|
mpyf\\t%2,%0
|
mpyf\\t%2,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0
|
mpyf3\\t%2,%1,%0"
|
mpyf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
;
|
;
|
; CMPF
|
; CMPF
|
;
|
;
|
(define_expand "cmpqf"
|
(define_expand "cmpqf"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QF 0 "src_operand" "")
|
(compare:CC (match_operand:QF 0 "src_operand" "")
|
(match_operand:QF 1 "src_operand" "")))]
|
(match_operand:QF 1 "src_operand" "")))]
|
""
|
""
|
"legitimize_operands (COMPARE, operands, QFmode);
|
"legitimize_operands (COMPARE, operands, QFmode);
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op1 = operands[1];
|
c4x_compare_op1 = operands[1];
|
DONE;")
|
DONE;")
|
|
|
(define_insn "*cmpqf"
|
(define_insn "*cmpqf"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:QF 0 "src_operand" "f,fR,fS<>")
|
(compare:CC (match_operand:QF 0 "src_operand" "f,fR,fS<>")
|
(match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
|
(match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
|
"valid_operands (COMPARE, operands, QFmode)"
|
"valid_operands (COMPARE, operands, QFmode)"
|
"@
|
"@
|
cmpf\\t%1,%0
|
cmpf\\t%1,%0
|
cmpf3\\t%1,%0
|
cmpf3\\t%1,%0
|
cmpf3\\t%1,%0"
|
cmpf3\\t%1,%0"
|
[(set_attr "type" "compare,compare,compare")])
|
[(set_attr "type" "compare,compare,compare")])
|
|
|
(define_insn "*cmpqf_noov"
|
(define_insn "*cmpqf_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:QF 0 "src_operand" "f,fR,fS<>")
|
(compare:CC_NOOV (match_operand:QF 0 "src_operand" "f,fR,fS<>")
|
(match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
|
(match_operand:QF 1 "src_operand" "fHm,R,fS<>")))]
|
"valid_operands (COMPARE, operands, QFmode)"
|
"valid_operands (COMPARE, operands, QFmode)"
|
"@
|
"@
|
cmpf\\t%1,%0
|
cmpf\\t%1,%0
|
cmpf3\\t%1,%0
|
cmpf3\\t%1,%0
|
cmpf3\\t%1,%0"
|
cmpf3\\t%1,%0"
|
[(set_attr "type" "compare,compare,compare")])
|
[(set_attr "type" "compare,compare,compare")])
|
|
|
; Inlined float divide for C4x
|
; Inlined float divide for C4x
|
(define_expand "divqf3_inline"
|
(define_expand "divqf3_inline"
|
[(parallel [(set (match_dup 3)
|
[(parallel [(set (match_dup 3)
|
(unspec:QF [(match_operand:QF 2 "src_operand" "")] UNSPEC_RCPF))
|
(unspec:QF [(match_operand:QF 2 "src_operand" "")] UNSPEC_RCPF))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:QF (match_dup 5) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
|
(parallel [(set (match_dup 3) (mult:QF (match_dup 3) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3)
|
(parallel [(set (match_dup 3)
|
(mult:QF (match_operand:QF 1 "src_operand" "")
|
(mult:QF (match_operand:QF 1 "src_operand" "")
|
(match_dup 3)))
|
(match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(unspec:QF [(match_dup 3)] UNSPEC_RND))
|
(unspec:QF [(match_dup 3)] UNSPEC_RND))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"if (! reload_in_progress
|
"if (! reload_in_progress
|
&& ! reg_operand (operands[2], QFmode))
|
&& ! reg_operand (operands[2], QFmode))
|
operands[2] = force_reg (QFmode, operands[2]);
|
operands[2] = force_reg (QFmode, operands[2]);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[3] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[4] = gen_reg_rtx (QFmode);
|
operands[5] = CONST2_RTX (QFmode);")
|
operands[5] = CONST2_RTX (QFmode);")
|
|
|
(define_expand "divqf3"
|
(define_expand "divqf3"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(div:QF (match_operand:QF 1 "src_operand" "")
|
(div:QF (match_operand:QF 1 "src_operand" "")
|
(match_operand:QF 2 "src_operand" "")))
|
(match_operand:QF 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X && TARGET_INLINE"
|
"! TARGET_C3X && TARGET_INLINE"
|
"emit_insn (gen_divqf3_inline (operands[0], operands[1], operands[2]));
|
"emit_insn (gen_divqf3_inline (operands[0], operands[1], operands[2]));
|
DONE;")
|
DONE;")
|
|
|
;
|
;
|
; CONDITIONAL MOVES
|
; CONDITIONAL MOVES
|
;
|
;
|
|
|
; ??? We should make these pattern fail if the src operand combination
|
; ??? We should make these pattern fail if the src operand combination
|
; is not valid. Although reload will fix things up, it will introduce
|
; is not valid. Although reload will fix things up, it will introduce
|
; extra load instructions that won't be hoisted out of a loop.
|
; extra load instructions that won't be hoisted out of a loop.
|
|
|
(define_insn "*ldi_conditional"
|
(define_insn "*ldi_conditional"
|
[(set (match_operand:QI 0 "reg_operand" "=r,r")
|
[(set (match_operand:QI 0 "reg_operand" "=r,r")
|
(if_then_else:QI (match_operator 1 "comparison_operator"
|
(if_then_else:QI (match_operator 1 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(match_operand:QI 2 "src_operand" "rIm,0")
|
(match_operand:QI 2 "src_operand" "rIm,0")
|
(match_operand:QI 3 "src_operand" "0,rIm")))]
|
(match_operand:QI 3 "src_operand" "0,rIm")))]
|
"valid_operands (IF_THEN_ELSE, operands, QImode)"
|
"valid_operands (IF_THEN_ELSE, operands, QImode)"
|
"@
|
"@
|
ldi%1\\t%2,%0
|
ldi%1\\t%2,%0
|
ldi%I1\\t%3,%0"
|
ldi%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_insn "*ldi_conditional_noov"
|
(define_insn "*ldi_conditional_noov"
|
[(set (match_operand:QI 0 "reg_operand" "=r,r")
|
[(set (match_operand:QI 0 "reg_operand" "=r,r")
|
(if_then_else:QI (match_operator 1 "comparison_operator"
|
(if_then_else:QI (match_operator 1 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(match_operand:QI 2 "src_operand" "rIm,0")
|
(match_operand:QI 2 "src_operand" "rIm,0")
|
(match_operand:QI 3 "src_operand" "0,rIm")))]
|
(match_operand:QI 3 "src_operand" "0,rIm")))]
|
"GET_CODE (operands[1]) != LE
|
"GET_CODE (operands[1]) != LE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != GT
|
&& GET_CODE (operands[1]) != GT
|
&& valid_operands (IF_THEN_ELSE, operands, QImode)"
|
&& valid_operands (IF_THEN_ELSE, operands, QImode)"
|
"@
|
"@
|
ldi%1\\t%2,%0
|
ldi%1\\t%2,%0
|
ldi%I1\\t%3,%0"
|
ldi%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_insn "*ldi_on_overflow"
|
(define_insn "*ldi_on_overflow"
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
[(set (match_operand:QI 0 "reg_operand" "=r")
|
(unspec:QI [(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LDIV))
|
(unspec:QI [(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LDIV))
|
(use (reg:CC 21))]
|
(use (reg:CC 21))]
|
""
|
""
|
"ldiv\\t%1,%0"
|
"ldiv\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
; Move operand 2 to operand 0 if condition (operand 1) is true
|
; Move operand 2 to operand 0 if condition (operand 1) is true
|
; else move operand 3 to operand 0.
|
; else move operand 3 to operand 0.
|
; The temporary register is required below because some of the operands
|
; The temporary register is required below because some of the operands
|
; might be identical (namely 0 and 2).
|
; might be identical (namely 0 and 2).
|
;
|
;
|
(define_expand "movqicc"
|
(define_expand "movqicc"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(if_then_else:QI (match_operand 1 "comparison_operator" "")
|
(if_then_else:QI (match_operand 1 "comparison_operator" "")
|
(match_operand:QI 2 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")
|
(match_operand:QI 3 "src_operand" "")))]
|
(match_operand:QI 3 "src_operand" "")))]
|
""
|
""
|
"{
|
"{
|
enum rtx_code code = GET_CODE (operands[1]);
|
enum rtx_code code = GET_CODE (operands[1]);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
if (ccreg == NULL_RTX) FAIL;
|
if (ccreg == NULL_RTX) FAIL;
|
emit_insn (gen_rtx_SET (QImode, operands[0],
|
emit_insn (gen_rtx_SET (QImode, operands[0],
|
gen_rtx_IF_THEN_ELSE (QImode,
|
gen_rtx_IF_THEN_ELSE (QImode,
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
operands[2], operands[3])));
|
operands[2], operands[3])));
|
DONE;}")
|
DONE;}")
|
|
|
(define_insn "*ldf_conditional"
|
(define_insn "*ldf_conditional"
|
[(set (match_operand:QF 0 "reg_operand" "=f,f")
|
[(set (match_operand:QF 0 "reg_operand" "=f,f")
|
(if_then_else:QF (match_operator 1 "comparison_operator"
|
(if_then_else:QF (match_operator 1 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(match_operand:QF 2 "src_operand" "fHm,0")
|
(match_operand:QF 2 "src_operand" "fHm,0")
|
(match_operand:QF 3 "src_operand" "0,fHm")))]
|
(match_operand:QF 3 "src_operand" "0,fHm")))]
|
"valid_operands (IF_THEN_ELSE, operands, QFmode)"
|
"valid_operands (IF_THEN_ELSE, operands, QFmode)"
|
"@
|
"@
|
ldf%1\\t%2,%0
|
ldf%1\\t%2,%0
|
ldf%I1\\t%3,%0"
|
ldf%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_insn "*ldf_conditional_noov"
|
(define_insn "*ldf_conditional_noov"
|
[(set (match_operand:QF 0 "reg_operand" "=f,f")
|
[(set (match_operand:QF 0 "reg_operand" "=f,f")
|
(if_then_else:QF (match_operator 1 "comparison_operator"
|
(if_then_else:QF (match_operator 1 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(match_operand:QF 2 "src_operand" "fHm,0")
|
(match_operand:QF 2 "src_operand" "fHm,0")
|
(match_operand:QF 3 "src_operand" "0,fHm")))]
|
(match_operand:QF 3 "src_operand" "0,fHm")))]
|
"GET_CODE (operands[1]) != LE
|
"GET_CODE (operands[1]) != LE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != GT
|
&& GET_CODE (operands[1]) != GT
|
&& valid_operands (IF_THEN_ELSE, operands, QFmode)"
|
&& valid_operands (IF_THEN_ELSE, operands, QFmode)"
|
"@
|
"@
|
ldf%1\\t%2,%0
|
ldf%1\\t%2,%0
|
ldf%I1\\t%3,%0"
|
ldf%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_expand "movqfcc"
|
(define_expand "movqfcc"
|
[(set (match_operand:QF 0 "reg_operand" "")
|
[(set (match_operand:QF 0 "reg_operand" "")
|
(if_then_else:QF (match_operand 1 "comparison_operator" "")
|
(if_then_else:QF (match_operand 1 "comparison_operator" "")
|
(match_operand:QF 2 "src_operand" "")
|
(match_operand:QF 2 "src_operand" "")
|
(match_operand:QF 3 "src_operand" "")))]
|
(match_operand:QF 3 "src_operand" "")))]
|
""
|
""
|
"{
|
"{
|
enum rtx_code code = GET_CODE (operands[1]);
|
enum rtx_code code = GET_CODE (operands[1]);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
if (ccreg == NULL_RTX) FAIL;
|
if (ccreg == NULL_RTX) FAIL;
|
emit_insn (gen_rtx_SET (QFmode, operands[0],
|
emit_insn (gen_rtx_SET (QFmode, operands[0],
|
gen_rtx_IF_THEN_ELSE (QFmode,
|
gen_rtx_IF_THEN_ELSE (QFmode,
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
operands[2], operands[3])));
|
operands[2], operands[3])));
|
DONE;}")
|
DONE;}")
|
|
|
(define_insn "*ldhf_conditional"
|
(define_insn "*ldhf_conditional"
|
[(set (match_operand:HF 0 "reg_operand" "=h,h")
|
[(set (match_operand:HF 0 "reg_operand" "=h,h")
|
(if_then_else:HF (match_operator 1 "comparison_operator"
|
(if_then_else:HF (match_operator 1 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(match_operand:HF 2 "src_operand" "hH,0")
|
(match_operand:HF 2 "src_operand" "hH,0")
|
(match_operand:HF 3 "src_operand" "0,hH")))]
|
(match_operand:HF 3 "src_operand" "0,hH")))]
|
""
|
""
|
"@
|
"@
|
ldf%1\\t%2,%0
|
ldf%1\\t%2,%0
|
ldf%I1\\t%3,%0"
|
ldf%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_insn "*ldhf_conditional_noov"
|
(define_insn "*ldhf_conditional_noov"
|
[(set (match_operand:HF 0 "reg_operand" "=h,h")
|
[(set (match_operand:HF 0 "reg_operand" "=h,h")
|
(if_then_else:HF (match_operator 1 "comparison_operator"
|
(if_then_else:HF (match_operator 1 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(match_operand:HF 2 "src_operand" "hH,0")
|
(match_operand:HF 2 "src_operand" "hH,0")
|
(match_operand:HF 3 "src_operand" "0,hH")))]
|
(match_operand:HF 3 "src_operand" "0,hH")))]
|
"GET_CODE (operands[1]) != LE
|
"GET_CODE (operands[1]) != LE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != GE
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != LT
|
&& GET_CODE (operands[1]) != GT"
|
&& GET_CODE (operands[1]) != GT"
|
"@
|
"@
|
ldf%1\\t%2,%0
|
ldf%1\\t%2,%0
|
ldf%I1\\t%3,%0"
|
ldf%I1\\t%3,%0"
|
[(set_attr "type" "binary")])
|
[(set_attr "type" "binary")])
|
|
|
(define_expand "movhfcc"
|
(define_expand "movhfcc"
|
[(set (match_operand:HF 0 "reg_operand" "")
|
[(set (match_operand:HF 0 "reg_operand" "")
|
(if_then_else:HF (match_operand 1 "comparison_operator" "")
|
(if_then_else:HF (match_operand 1 "comparison_operator" "")
|
(match_operand:HF 2 "src_operand" "")
|
(match_operand:HF 2 "src_operand" "")
|
(match_operand:HF 3 "src_operand" "")))]
|
(match_operand:HF 3 "src_operand" "")))]
|
""
|
""
|
"{
|
"{
|
enum rtx_code code = GET_CODE (operands[1]);
|
enum rtx_code code = GET_CODE (operands[1]);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
if (ccreg == NULL_RTX) FAIL;
|
if (ccreg == NULL_RTX) FAIL;
|
emit_insn (gen_rtx_SET (HFmode, operands[0],
|
emit_insn (gen_rtx_SET (HFmode, operands[0],
|
gen_rtx_IF_THEN_ELSE (HFmode,
|
gen_rtx_IF_THEN_ELSE (HFmode,
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
|
operands[2], operands[3])));
|
operands[2], operands[3])));
|
DONE;}")
|
DONE;}")
|
|
|
(define_expand "seq"
|
(define_expand "seq"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (eq (match_dup 1) (const_int 0))
|
(if_then_else:QI (eq (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "sne"
|
(define_expand "sne"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (ne (match_dup 1) (const_int 0))
|
(if_then_else:QI (ne (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "slt"
|
(define_expand "slt"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (lt (match_dup 1) (const_int 0))
|
(if_then_else:QI (lt (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "sltu"
|
(define_expand "sltu"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (ltu (match_dup 1) (const_int 0))
|
(if_then_else:QI (ltu (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "sgt"
|
(define_expand "sgt"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (gt (match_dup 1) (const_int 0))
|
(if_then_else:QI (gt (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "sgtu"
|
(define_expand "sgtu"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (gtu (match_dup 1) (const_int 0))
|
(if_then_else:QI (gtu (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "sle"
|
(define_expand "sle"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (le (match_dup 1) (const_int 0))
|
(if_then_else:QI (le (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "sleu"
|
(define_expand "sleu"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (leu (match_dup 1) (const_int 0))
|
(if_then_else:QI (leu (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "sge"
|
(define_expand "sge"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (ge (match_dup 1) (const_int 0))
|
(if_then_else:QI (ge (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "sgeu"
|
(define_expand "sgeu"
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (geu (match_dup 1) (const_int 0))
|
(if_then_else:QI (geu (match_dup 1) (const_int 0))
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operator:QI 1 "comparison_operator" [(reg:CC 21) (const_int 0)]))]
|
(match_operator:QI 1 "comparison_operator" [(reg:CC 21) (const_int 0)]))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0) (const_int 0))
|
[(set (match_dup 0) (const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (match_op_dup 1 [(reg:CC 21) (const_int 0)])
|
(if_then_else:QI (match_op_dup 1 [(reg:CC 21) (const_int 0)])
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
"")
|
"")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:QI 0 "reg_operand" "")
|
[(set (match_operand:QI 0 "reg_operand" "")
|
(match_operator:QI 1 "comparison_operator" [(reg:CC_NOOV 21) (const_int 0)]))]
|
(match_operator:QI 1 "comparison_operator" [(reg:CC_NOOV 21) (const_int 0)]))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0) (const_int 0))
|
[(set (match_dup 0) (const_int 0))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(if_then_else:QI (match_op_dup 1 [(reg:CC_NOOV 21) (const_int 0)])
|
(if_then_else:QI (match_op_dup 1 [(reg:CC_NOOV 21) (const_int 0)])
|
(const_int 1)
|
(const_int 1)
|
(match_dup 0)))]
|
(match_dup 0)))]
|
"")
|
"")
|
|
|
(define_insn "*bu"
|
(define_insn "*bu"
|
[(set (pc)
|
[(set (pc)
|
(unspec [(match_operand:QI 0 "reg_operand" "r")] UNSPEC_BU))]
|
(unspec [(match_operand:QI 0 "reg_operand" "r")] UNSPEC_BU))]
|
""
|
""
|
"bu%#\\t%0"
|
"bu%#\\t%0"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
(define_expand "caseqi"
|
(define_expand "caseqi"
|
[(parallel [(set (match_dup 5)
|
[(parallel [(set (match_dup 5)
|
(minus:QI (match_operand:QI 0 "reg_operand" "")
|
(minus:QI (match_operand:QI 0 "reg_operand" "")
|
(match_operand:QI 1 "src_operand" "")))
|
(match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (reg:CC 21)
|
(set (reg:CC 21)
|
(compare:CC (match_dup 5)
|
(compare:CC (match_dup 5)
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(set (pc)
|
(set (pc)
|
(if_then_else (gtu (reg:CC 21)
|
(if_then_else (gtu (reg:CC 21)
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 4 "" ""))
|
(label_ref (match_operand 4 "" ""))
|
(pc)))
|
(pc)))
|
(parallel [(set (match_dup 6)
|
(parallel [(set (match_dup 6)
|
(plus:QI (match_dup 5)
|
(plus:QI (match_dup 5)
|
(label_ref:QI (match_operand 3 "" ""))))
|
(label_ref:QI (match_operand 3 "" ""))))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (match_dup 7)
|
(set (match_dup 7)
|
(mem:QI (match_dup 6)))
|
(mem:QI (match_dup 6)))
|
(set (pc) (match_dup 7))]
|
(set (pc) (match_dup 7))]
|
""
|
""
|
"operands[5] = gen_reg_rtx (QImode);
|
"operands[5] = gen_reg_rtx (QImode);
|
operands[6] = gen_reg_rtx (QImode);
|
operands[6] = gen_reg_rtx (QImode);
|
operands[7] = gen_reg_rtx (QImode);")
|
operands[7] = gen_reg_rtx (QImode);")
|
|
|
;
|
;
|
; PARALLEL FLOAT INSTRUCTIONS
|
; PARALLEL FLOAT INSTRUCTIONS
|
;
|
;
|
; This patterns are under development
|
; This patterns are under development
|
|
|
;
|
;
|
; ABSF/STF
|
; ABSF/STF
|
;
|
;
|
|
|
(define_insn "*absqf2_movqf_clobber"
|
(define_insn "*absqf2_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(abs:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(abs:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"absf\\t%1,%0\\n||\\tstf\\t%3,%2"
|
"absf\\t%1,%0\\n||\\tstf\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; ADDF/STF
|
; ADDF/STF
|
;
|
;
|
|
|
(define_insn "*addqf3_movqf_clobber"
|
(define_insn "*addqf3_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
|
(plus:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
|
(plus:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
|
(match_operand:QF 2 "parallel_operand" "S<>,q")))
|
(match_operand:QF 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QF 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QF 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"addf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
"addf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; FLOAT/STF
|
; FLOAT/STF
|
;
|
;
|
|
|
(define_insn "*floatqiqf2_movqf_clobber"
|
(define_insn "*floatqiqf2_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(float:QF (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(float:QF (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"float\\t%1,%0\\n||\\tstf\\t%3,%2"
|
"float\\t%1,%0\\n||\\tstf\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; MPYF/ADDF
|
; MPYF/ADDF
|
;
|
;
|
|
|
(define_insn "*mulqf3_addqf3_clobber"
|
(define_insn "*mulqf3_addqf3_clobber"
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t,t,t")
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t,t,t")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
|
(match_operand:QF 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
|
(match_operand:QF 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u,u,u,u")
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u,u,u,u")
|
(plus:QF (match_operand:QF 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
|
(plus:QF (match_operand:QF 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
|
(match_operand:QF 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
|
(match_operand:QF 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
|
"TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
|
"mpyf3\\t%2,%1,%0\\n||\\taddf3\\t%5,%4,%3"
|
"mpyf3\\t%2,%1,%0\\n||\\taddf3\\t%5,%4,%3"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
|
|
;
|
;
|
; MPYF/STF
|
; MPYF/STF
|
;
|
;
|
|
|
(define_insn "*mulqf3_movqf_clobber"
|
(define_insn "*mulqf3_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q,q")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "%q,S<>")
|
(match_operand:QF 2 "parallel_operand" "S<>,q")))
|
(match_operand:QF 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QF 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QF 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"mpyf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
"mpyf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; MPYF/SUBF
|
; MPYF/SUBF
|
;
|
;
|
|
|
(define_insn "*mulqf3_subqf3_clobber"
|
(define_insn "*mulqf3_subqf3_clobber"
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t")
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t,t")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "S<>,q")
|
(mult:QF (match_operand:QF 1 "parallel_operand" "S<>,q")
|
(match_operand:QF 2 "parallel_operand" "q,S<>")))
|
(match_operand:QF 2 "parallel_operand" "q,S<>")))
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u,u")
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u,u")
|
(minus:QF (match_operand:QF 4 "parallel_operand" "S<>,q")
|
(minus:QF (match_operand:QF 4 "parallel_operand" "S<>,q")
|
(match_operand:QF 5 "parallel_operand" "q,S<>")))
|
(match_operand:QF 5 "parallel_operand" "q,S<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
|
"TARGET_PARALLEL_MPY && valid_parallel_operands_6 (operands, QFmode)"
|
"mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%5,%4,%3"
|
"mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%5,%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; MPYF/LDF 0
|
; MPYF/LDF 0
|
;
|
;
|
|
|
(define_insn "*mulqf3_clrqf_clobber"
|
(define_insn "*mulqf3_clrqf_clobber"
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t")
|
[(set (match_operand:QF 0 "r0r1_reg_operand" "=t")
|
(mult:QF (match_operand:QF 1 "par_ind_operand" "%S<>")
|
(mult:QF (match_operand:QF 1 "par_ind_operand" "%S<>")
|
(match_operand:QF 2 "par_ind_operand" "S<>")))
|
(match_operand:QF 2 "par_ind_operand" "S<>")))
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u")
|
(set (match_operand:QF 3 "r2r3_reg_operand" "=u")
|
(match_operand:QF 4 "fp_zero_operand" "G"))
|
(match_operand:QF 4 "fp_zero_operand" "G"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL_MPY"
|
"TARGET_PARALLEL_MPY"
|
"mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%3,%3,%3"
|
"mpyf3\\t%2,%1,%0\\n||\\tsubf3\\t%3,%3,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; NEGF/STF
|
; NEGF/STF
|
;
|
;
|
|
|
(define_insn "*negqf2_movqf_clobber"
|
(define_insn "*negqf2_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(neg:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(neg:QF (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"negf\\t%1,%0\\n||\\tstf\\t%3,%2"
|
"negf\\t%1,%0\\n||\\tstf\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; SUBF/STF
|
; SUBF/STF
|
;
|
;
|
|
|
(define_insn "*subqf3_movqf_clobber"
|
(define_insn "*subqf3_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(minus:QF (match_operand:QF 1 "ext_low_reg_operand" "q")
|
(minus:QF (match_operand:QF 1 "ext_low_reg_operand" "q")
|
(match_operand:QF 2 "par_ind_operand" "S<>")))
|
(match_operand:QF 2 "par_ind_operand" "S<>")))
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 3 "par_ind_operand" "=S<>")
|
(match_operand:QF 4 "ext_low_reg_operand" "q"))
|
(match_operand:QF 4 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QFmode)"
|
"subf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
"subf3\\t%2,%1,%0\\n||\\tstf\\t%4,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; TOIEEE/STF
|
; TOIEEE/STF
|
;
|
;
|
|
|
(define_insn "*toieee_movqf_clobber"
|
(define_insn "*toieee_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_TOIEEE))
|
(unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_TOIEEE))
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"toieee\\t%1,%0\\n||\\tstf\\t%3,%2"
|
"toieee\\t%1,%0\\n||\\tstf\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; FRIEEE/STF
|
; FRIEEE/STF
|
;
|
;
|
|
|
(define_insn "*frieee_movqf_clobber"
|
(define_insn "*frieee_movqf_clobber"
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
|
(unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_FRIEEE))
|
(unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_FRIEEE))
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QF 2 "par_ind_operand" "=S<>")
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(match_operand:QF 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QFmode)"
|
"frieee\\t%1,%0\\n||\\tstf\\t%3,%2"
|
"frieee\\t%1,%0\\n||\\tstf\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; PARALLEL INTEGER INSTRUCTIONS
|
; PARALLEL INTEGER INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; ABSI/STI
|
; ABSI/STI
|
;
|
;
|
|
|
(define_insn "*absqi2_movqi_clobber"
|
(define_insn "*absqi2_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(abs:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(abs:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"absi\\t%1,%0\\n||\\tsti\\t%3,%2"
|
"absi\\t%1,%0\\n||\\tsti\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; ADDI/STI
|
; ADDI/STI
|
;
|
;
|
|
|
(define_insn "*addqi3_movqi_clobber"
|
(define_insn "*addqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
(plus:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(plus:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"addi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"addi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; AND/STI
|
; AND/STI
|
;
|
;
|
|
|
(define_insn "*andqi3_movqi_clobber"
|
(define_insn "*andqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
(and:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(and:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"and3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"and3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; ASH(left)/STI
|
; ASH(left)/STI
|
;
|
;
|
|
|
(define_insn "*ashlqi3_movqi_clobber"
|
(define_insn "*ashlqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(ashift:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(ashift:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(match_operand:QI 2 "ext_low_reg_operand" "q")))
|
(match_operand:QI 2 "ext_low_reg_operand" "q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; ASH(right)/STI
|
; ASH(right)/STI
|
;
|
;
|
|
|
(define_insn "*ashrqi3_movqi_clobber"
|
(define_insn "*ashrqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(ashiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(ashiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
|
(neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"ash3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; FIX/STI
|
; FIX/STI
|
;
|
;
|
|
|
(define_insn "*fixqfqi2_movqi_clobber"
|
(define_insn "*fixqfqi2_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(fix:QI (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(fix:QI (match_operand:QF 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"fix\\t%1,%0\\n||\\tsti\\t%3,%2"
|
"fix\\t%1,%0\\n||\\tsti\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; LSH(right)/STI
|
; LSH(right)/STI
|
;
|
;
|
|
|
(define_insn "*lshrqi3_movqi_clobber"
|
(define_insn "*lshrqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(lshiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(lshiftrt:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
|
(neg:QI (match_operand:QI 2 "ext_low_reg_operand" "q"))))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"lsh3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"lsh3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; MPYI/ADDI
|
; MPYI/ADDI
|
;
|
;
|
|
|
(define_insn "*mulqi3_addqi3_clobber"
|
(define_insn "*mulqi3_addqi3_clobber"
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t,t,t")
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t,t,t")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "%S<>!V,q,S<>!V,q")
|
(match_operand:QI 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
|
(match_operand:QI 2 "parallel_operand" "q,S<>!V,S<>!V,q")))
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u,u,u,u")
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u,u,u,u")
|
(plus:QI (match_operand:QI 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
|
(plus:QI (match_operand:QI 4 "parallel_operand" "%S<>!V,q,q,S<>!V")
|
(match_operand:QI 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
|
(match_operand:QI 5 "parallel_operand" "q,S<>!V,q,S<>!V")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL_MPY && TARGET_MPYI
|
"TARGET_PARALLEL_MPY && TARGET_MPYI
|
&& valid_parallel_operands_6 (operands, QImode)"
|
&& valid_parallel_operands_6 (operands, QImode)"
|
"mpyi3\\t%2,%1,%0\\n||\\taddi3\\t%5,%4,%3"
|
"mpyi3\\t%2,%1,%0\\n||\\taddi3\\t%5,%4,%3"
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc,binarycc")])
|
|
|
|
|
;
|
;
|
; MPYI/STI
|
; MPYI/STI
|
;
|
;
|
|
|
(define_insn "*mulqi3_movqi_clobber"
|
(define_insn "*mulqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && TARGET_MPYI
|
"TARGET_PARALLEL && TARGET_MPYI
|
&& valid_parallel_operands_5 (operands, QImode)"
|
&& valid_parallel_operands_5 (operands, QImode)"
|
"mpyi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"mpyi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; MPYI/SUBI
|
; MPYI/SUBI
|
;
|
;
|
|
|
(define_insn "*mulqi3_subqi3_clobber"
|
(define_insn "*mulqi3_subqi3_clobber"
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t")
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t,t")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "S<>,q")
|
(mult:QI (match_operand:QI 1 "parallel_operand" "S<>,q")
|
(match_operand:QI 2 "parallel_operand" "q,S<>")))
|
(match_operand:QI 2 "parallel_operand" "q,S<>")))
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u,u")
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u,u")
|
(minus:QI (match_operand:QI 4 "parallel_operand" "S<>,q")
|
(minus:QI (match_operand:QI 4 "parallel_operand" "S<>,q")
|
(match_operand:QI 5 "parallel_operand" "q,S<>")))
|
(match_operand:QI 5 "parallel_operand" "q,S<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL_MPY && TARGET_MPYI
|
"TARGET_PARALLEL_MPY && TARGET_MPYI
|
&& valid_parallel_operands_6 (operands, QImode)"
|
&& valid_parallel_operands_6 (operands, QImode)"
|
"mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%5,%4,%3"
|
"mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%5,%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; MPYI/LDI 0
|
; MPYI/LDI 0
|
;
|
;
|
|
|
(define_insn "*mulqi3_clrqi_clobber"
|
(define_insn "*mulqi3_clrqi_clobber"
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t")
|
[(set (match_operand:QI 0 "r0r1_reg_operand" "=t")
|
(mult:QI (match_operand:QI 1 "par_ind_operand" "%S<>")
|
(mult:QI (match_operand:QI 1 "par_ind_operand" "%S<>")
|
(match_operand:QI 2 "par_ind_operand" "S<>")))
|
(match_operand:QI 2 "par_ind_operand" "S<>")))
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u")
|
(set (match_operand:QI 3 "r2r3_reg_operand" "=u")
|
(const_int 0))
|
(const_int 0))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL_MPY && TARGET_MPYI"
|
"TARGET_PARALLEL_MPY && TARGET_MPYI"
|
"mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%3,%3,%3"
|
"mpyi3\\t%2,%1,%0\\n||\\tsubi3\\t%3,%3,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; NEGI/STI
|
; NEGI/STI
|
;
|
;
|
|
|
(define_insn "*negqi2_movqi_clobber"
|
(define_insn "*negqi2_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(neg:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(neg:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"negi\\t%1,%0\\n||\\tsti\\t%3,%2"
|
"negi\\t%1,%0\\n||\\tsti\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; NOT/STI
|
; NOT/STI
|
;
|
;
|
|
|
(define_insn "*notqi2_movqi_clobber"
|
(define_insn "*notqi2_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(not:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(not:QI (match_operand:QI 1 "par_ind_operand" "S<>")))
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 2 "par_ind_operand" "=S<>")
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(match_operand:QI 3 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_4 (operands, QImode)"
|
"not\\t%1,%0\\n||\\tsti\\t%3,%2"
|
"not\\t%1,%0\\n||\\tsti\\t%3,%2"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; OR/STI
|
; OR/STI
|
;
|
;
|
|
|
(define_insn "*iorqi3_movqi_clobber"
|
(define_insn "*iorqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
(ior:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(ior:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"or3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"or3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; SUBI/STI
|
; SUBI/STI
|
;
|
;
|
|
|
(define_insn "*subqi3_movqi_clobber"
|
(define_insn "*subqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q")
|
(minus:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(minus:QI (match_operand:QI 1 "par_ind_operand" "S<>")
|
(match_operand:QI 2 "ext_low_reg_operand" "q")))
|
(match_operand:QI 2 "ext_low_reg_operand" "q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"subi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"subi3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc")])
|
[(set_attr "type" "binarycc")])
|
|
|
;
|
;
|
; XOR/STI
|
; XOR/STI
|
;
|
;
|
|
|
(define_insn "*xorqi3_movqi_clobber"
|
(define_insn "*xorqi3_movqi_clobber"
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
[(set (match_operand:QI 0 "ext_low_reg_operand" "=q,q")
|
(xor:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(xor:QI (match_operand:QI 1 "parallel_operand" "%q,S<>")
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(match_operand:QI 2 "parallel_operand" "S<>,q")))
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(set (match_operand:QI 3 "par_ind_operand" "=S<>,S<>")
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(match_operand:QI 4 "ext_low_reg_operand" "q,q"))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"TARGET_PARALLEL && valid_parallel_operands_5 (operands, QImode)"
|
"xor3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
"xor3\\t%2,%1,%0\\n||\\tsti\\t%4,%3"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; BRANCH/CALL INSTRUCTIONS
|
; BRANCH/CALL INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; Branch instructions
|
; Branch instructions
|
;
|
;
|
(define_insn "*b"
|
(define_insn "*b"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"*
|
"*
|
return c4x_output_cbranch (\"b%0\", insn);"
|
return c4x_output_cbranch (\"b%0\", insn);"
|
[(set_attr "type" "jmpc")])
|
[(set_attr "type" "jmpc")])
|
|
|
(define_insn "*b_rev"
|
(define_insn "*b_rev"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(pc)
|
(pc)
|
(label_ref (match_operand 1 "" ""))))]
|
(label_ref (match_operand 1 "" ""))))]
|
""
|
""
|
"*
|
"*
|
return c4x_output_cbranch (\"b%I0\", insn);"
|
return c4x_output_cbranch (\"b%I0\", insn);"
|
[(set_attr "type" "jmpc")])
|
[(set_attr "type" "jmpc")])
|
|
|
(define_insn "*b_noov"
|
(define_insn "*b_noov"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))]
|
(pc)))]
|
"GET_CODE (operands[0]) != LE
|
"GET_CODE (operands[0]) != LE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != GT"
|
&& GET_CODE (operands[0]) != GT"
|
"*
|
"*
|
return c4x_output_cbranch (\"b%0\", insn);"
|
return c4x_output_cbranch (\"b%0\", insn);"
|
[(set_attr "type" "jmpc")])
|
[(set_attr "type" "jmpc")])
|
|
|
(define_insn "*b_noov_rev"
|
(define_insn "*b_noov_rev"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(pc)
|
(pc)
|
(label_ref (match_operand 1 "" ""))))]
|
(label_ref (match_operand 1 "" ""))))]
|
"GET_CODE (operands[0]) != LE
|
"GET_CODE (operands[0]) != LE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != GT"
|
&& GET_CODE (operands[0]) != GT"
|
"*
|
"*
|
return c4x_output_cbranch (\"b%I0\", insn);"
|
return c4x_output_cbranch (\"b%I0\", insn);"
|
[(set_attr "type" "jmpc")])
|
[(set_attr "type" "jmpc")])
|
|
|
(define_expand "beq"
|
(define_expand "beq"
|
[(set (pc) (if_then_else (eq (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (eq (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (EQ, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "bne"
|
(define_expand "bne"
|
[(set (pc) (if_then_else (ne (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (ne (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (NE, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "blt"
|
(define_expand "blt"
|
[(set (pc) (if_then_else (lt (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (lt (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (LT, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "bltu"
|
(define_expand "bltu"
|
[(set (pc) (if_then_else (ltu (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (ltu (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (LTU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "bgt"
|
(define_expand "bgt"
|
[(set (pc) (if_then_else (gt (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (gt (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (GT, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "bgtu"
|
(define_expand "bgtu"
|
[(set (pc) (if_then_else (gtu (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (gtu (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (GTU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "ble"
|
(define_expand "ble"
|
[(set (pc) (if_then_else (le (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (le (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (LE, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "bleu"
|
(define_expand "bleu"
|
[(set (pc) (if_then_else (leu (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (leu (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (LEU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_expand "bge"
|
(define_expand "bge"
|
[(set (pc) (if_then_else (ge (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (ge (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
|
"operands[1] = c4x_gen_compare_reg (GE, c4x_compare_op0, c4x_compare_op1);
|
if (operands[1] == NULL_RTX) FAIL;")
|
if (operands[1] == NULL_RTX) FAIL;")
|
|
|
(define_expand "bgeu"
|
(define_expand "bgeu"
|
[(set (pc) (if_then_else (geu (match_dup 1) (const_int 0))
|
[(set (pc) (if_then_else (geu (match_dup 1) (const_int 0))
|
(label_ref (match_operand 0 "" ""))
|
(label_ref (match_operand 0 "" ""))
|
(pc)))]
|
(pc)))]
|
""
|
""
|
"operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
|
"operands[1] = c4x_gen_compare_reg (GEU, c4x_compare_op0, c4x_compare_op1);")
|
|
|
(define_insn "*b_reg"
|
(define_insn "*b_reg"
|
[(set (pc) (match_operand:QI 0 "reg_operand" "r"))]
|
[(set (pc) (match_operand:QI 0 "reg_operand" "r"))]
|
""
|
""
|
"bu%#\\t%0"
|
"bu%#\\t%0"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
(define_expand "indirect_jump"
|
(define_expand "indirect_jump"
|
[(set (pc) (match_operand:QI 0 "reg_operand" ""))]
|
[(set (pc) (match_operand:QI 0 "reg_operand" ""))]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "tablejump"
|
(define_insn "tablejump"
|
[(set (pc) (match_operand:QI 0 "src_operand" "r"))
|
[(set (pc) (match_operand:QI 0 "src_operand" "r"))
|
(use (label_ref (match_operand 1 "" "")))]
|
(use (label_ref (match_operand 1 "" "")))]
|
""
|
""
|
"bu%#\\t%0"
|
"bu%#\\t%0"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
;
|
;
|
; CALL
|
; CALL
|
;
|
;
|
(define_insn "*call_c3x"
|
(define_insn "*call_c3x"
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
(match_operand:QI 1 "general_operand" ""))
|
(match_operand:QI 1 "general_operand" ""))
|
(clobber (reg:QI 31))]
|
(clobber (reg:QI 31))]
|
;; Operand 1 not really used on the C4x. The C30 doesn't have reg 31.
|
;; Operand 1 not really used on the C4x. The C30 doesn't have reg 31.
|
|
|
"TARGET_C3X"
|
"TARGET_C3X"
|
"call%U0\\t%C0"
|
"call%U0\\t%C0"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
; LAJ requires R11 (31) for the return address
|
; LAJ requires R11 (31) for the return address
|
(define_insn "*laj"
|
(define_insn "*laj"
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
(match_operand:QI 1 "general_operand" ""))
|
(match_operand:QI 1 "general_operand" ""))
|
(clobber (reg:QI 31))]
|
(clobber (reg:QI 31))]
|
;; Operand 1 not really used on the C4x.
|
;; Operand 1 not really used on the C4x.
|
|
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"*
|
"*
|
if (final_sequence)
|
if (final_sequence)
|
return c4x_check_laj_p (insn)
|
return c4x_check_laj_p (insn)
|
? \"nop\\n\\tlaj%U0\\t%C0\" : \"laj%U0\\t%C0\";
|
? \"nop\\n\\tlaj%U0\\t%C0\" : \"laj%U0\\t%C0\";
|
else
|
else
|
return \"call%U0\\t%C0\";"
|
return \"call%U0\\t%C0\";"
|
[(set_attr "type" "laj")])
|
[(set_attr "type" "laj")])
|
|
|
(define_expand "call"
|
(define_expand "call"
|
[(parallel [(call (match_operand:QI 0 "" "")
|
[(parallel [(call (match_operand:QI 0 "" "")
|
(match_operand:QI 1 "general_operand" ""))
|
(match_operand:QI 1 "general_operand" ""))
|
(clobber (reg:QI 31))])]
|
(clobber (reg:QI 31))])]
|
""
|
""
|
"
|
"
|
{
|
{
|
if (GET_CODE (operands[0]) == MEM
|
if (GET_CODE (operands[0]) == MEM
|
&& ! call_address_operand (XEXP (operands[0], 0), Pmode))
|
&& ! call_address_operand (XEXP (operands[0], 0), Pmode))
|
operands[0] = gen_rtx_MEM (GET_MODE (operands[0]),
|
operands[0] = gen_rtx_MEM (GET_MODE (operands[0]),
|
force_reg (Pmode, XEXP (operands[0], 0)));
|
force_reg (Pmode, XEXP (operands[0], 0)));
|
}")
|
}")
|
|
|
(define_insn "nodb_call"
|
(define_insn "nodb_call"
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
[(call (mem:QI (match_operand:QI 0 "call_address_operand" "Ur"))
|
(const_int 0))]
|
(const_int 0))]
|
""
|
""
|
"call%U0\\t%C0"
|
"call%U0\\t%C0"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
(define_insn "*callv_c3x"
|
(define_insn "*callv_c3x"
|
[(set (match_operand 0 "" "=r")
|
[(set (match_operand 0 "" "=r")
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
|
(match_operand:QI 2 "general_operand" "")))
|
(match_operand:QI 2 "general_operand" "")))
|
(clobber (reg:QI 31))]
|
(clobber (reg:QI 31))]
|
;; Operand 0 and 2 not really used for the C4x.
|
;; Operand 0 and 2 not really used for the C4x.
|
;; The C30 doesn't have reg 31.
|
;; The C30 doesn't have reg 31.
|
|
|
"TARGET_C3X"
|
"TARGET_C3X"
|
"call%U1\\t%C1"
|
"call%U1\\t%C1"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
; LAJ requires R11 (31) for the return address
|
; LAJ requires R11 (31) for the return address
|
(define_insn "*lajv"
|
(define_insn "*lajv"
|
[(set (match_operand 0 "" "=r")
|
[(set (match_operand 0 "" "=r")
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" "Ur"))
|
(match_operand:QI 2 "general_operand" "")))
|
(match_operand:QI 2 "general_operand" "")))
|
(clobber (reg:QI 31))]
|
(clobber (reg:QI 31))]
|
;; Operand 0 and 2 not really used in the C30 instruction.
|
;; Operand 0 and 2 not really used in the C30 instruction.
|
|
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"*
|
"*
|
if (final_sequence)
|
if (final_sequence)
|
return c4x_check_laj_p (insn)
|
return c4x_check_laj_p (insn)
|
? \"nop\\n\\tlaj%U1\\t%C1\" : \"laj%U1\\t%C1\";
|
? \"nop\\n\\tlaj%U1\\t%C1\" : \"laj%U1\\t%C1\";
|
else
|
else
|
return \"call%U1\\t%C1\";"
|
return \"call%U1\\t%C1\";"
|
[(set_attr "type" "laj")])
|
[(set_attr "type" "laj")])
|
|
|
(define_expand "call_value"
|
(define_expand "call_value"
|
[(parallel [(set (match_operand 0 "" "")
|
[(parallel [(set (match_operand 0 "" "")
|
(call (match_operand:QI 1 "" "")
|
(call (match_operand:QI 1 "" "")
|
(match_operand:QI 2 "general_operand" "")))
|
(match_operand:QI 2 "general_operand" "")))
|
(clobber (reg:QI 31))])]
|
(clobber (reg:QI 31))])]
|
""
|
""
|
"
|
"
|
{
|
{
|
if (GET_CODE (operands[0]) == MEM
|
if (GET_CODE (operands[0]) == MEM
|
&& ! call_address_operand (XEXP (operands[1], 0), Pmode))
|
&& ! call_address_operand (XEXP (operands[1], 0), Pmode))
|
operands[0] = gen_rtx_MEM (GET_MODE (operands[1]),
|
operands[0] = gen_rtx_MEM (GET_MODE (operands[1]),
|
force_reg (Pmode, XEXP (operands[1], 0)));
|
force_reg (Pmode, XEXP (operands[1], 0)));
|
}")
|
}")
|
|
|
(define_insn "return"
|
(define_insn "return"
|
[(return)]
|
[(return)]
|
"! c4x_null_epilogue_p ()"
|
"! c4x_null_epilogue_p ()"
|
"rets"
|
"rets"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "return_from_epilogue"
|
(define_insn "return_from_epilogue"
|
[(return)]
|
[(return)]
|
"reload_completed && ! c4x_interrupt_function_p ()"
|
"reload_completed && ! c4x_interrupt_function_p ()"
|
"rets"
|
"rets"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "return_from_interrupt_epilogue"
|
(define_insn "return_from_interrupt_epilogue"
|
[(return)]
|
[(return)]
|
"reload_completed && c4x_interrupt_function_p ()"
|
"reload_completed && c4x_interrupt_function_p ()"
|
"reti"
|
"reti"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "*return_cc"
|
(define_insn "*return_cc"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (match_operator 0 "comparison_operator"
|
(if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(return)
|
(return)
|
(pc)))]
|
(pc)))]
|
"! c4x_null_epilogue_p ()"
|
"! c4x_null_epilogue_p ()"
|
"rets%0"
|
"rets%0"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "*return_cc_noov"
|
(define_insn "*return_cc_noov"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (match_operator 0 "comparison_operator"
|
(if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(return)
|
(return)
|
(pc)))]
|
(pc)))]
|
"GET_CODE (operands[0]) != LE
|
"GET_CODE (operands[0]) != LE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != GT
|
&& GET_CODE (operands[0]) != GT
|
&& ! c4x_null_epilogue_p ()"
|
&& ! c4x_null_epilogue_p ()"
|
"rets%0"
|
"rets%0"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "*return_cc_inverse"
|
(define_insn "*return_cc_inverse"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (match_operator 0 "comparison_operator"
|
(if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(pc)
|
(pc)
|
(return)))]
|
(return)))]
|
"! c4x_null_epilogue_p ()"
|
"! c4x_null_epilogue_p ()"
|
"rets%I0"
|
"rets%I0"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "*return_cc_noov_inverse"
|
(define_insn "*return_cc_noov_inverse"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (match_operator 0 "comparison_operator"
|
(if_then_else (match_operator 0 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(pc)
|
(pc)
|
(return)))]
|
(return)))]
|
"GET_CODE (operands[0]) != LE
|
"GET_CODE (operands[0]) != LE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != GT
|
&& GET_CODE (operands[0]) != GT
|
&& ! c4x_null_epilogue_p ()"
|
&& ! c4x_null_epilogue_p ()"
|
"rets%I0"
|
"rets%I0"
|
[(set_attr "type" "rets")])
|
[(set_attr "type" "rets")])
|
|
|
(define_insn "jump"
|
(define_insn "jump"
|
[(set (pc) (label_ref (match_operand 0 "" "")))]
|
[(set (pc) (label_ref (match_operand 0 "" "")))]
|
""
|
""
|
"br%#\\t%l0"
|
"br%#\\t%l0"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
(define_insn "trap"
|
(define_insn "trap"
|
[(trap_if (const_int 1) (const_int 31))]
|
[(trap_if (const_int 1) (const_int 31))]
|
""
|
""
|
"trapu\\t31"
|
"trapu\\t31"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
(define_expand "conditional_trap"
|
(define_expand "conditional_trap"
|
[(trap_if (match_operand 0 "comparison_operator" "")
|
[(trap_if (match_operand 0 "comparison_operator" "")
|
(match_operand 1 "const_int_operand" ""))]
|
(match_operand 1 "const_int_operand" ""))]
|
""
|
""
|
"{
|
"{
|
enum rtx_code code = GET_CODE (operands[1]);
|
enum rtx_code code = GET_CODE (operands[1]);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
rtx ccreg = c4x_gen_compare_reg (code, c4x_compare_op0, c4x_compare_op1);
|
if (ccreg == NULL_RTX) FAIL;
|
if (ccreg == NULL_RTX) FAIL;
|
if (GET_MODE (ccreg) == CCmode)
|
if (GET_MODE (ccreg) == CCmode)
|
emit_insn (gen_cond_trap_cc (operands[0], operands[1]));
|
emit_insn (gen_cond_trap_cc (operands[0], operands[1]));
|
else
|
else
|
emit_insn (gen_cond_trap_cc_noov (operands[0], operands[1]));
|
emit_insn (gen_cond_trap_cc_noov (operands[0], operands[1]));
|
DONE;}")
|
DONE;}")
|
|
|
(define_insn "cond_trap_cc"
|
(define_insn "cond_trap_cc"
|
[(trap_if (match_operator 0 "comparison_operator"
|
[(trap_if (match_operator 0 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(match_operand 1 "const_int_operand" ""))]
|
(match_operand 1 "const_int_operand" ""))]
|
""
|
""
|
"trap%0\\t31"
|
"trap%0\\t31"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
(define_insn "cond_trap_cc_noov"
|
(define_insn "cond_trap_cc_noov"
|
[(trap_if (match_operator 0 "comparison_operator"
|
[(trap_if (match_operator 0 "comparison_operator"
|
[(reg:CC_NOOV 21) (const_int 0)])
|
[(reg:CC_NOOV 21) (const_int 0)])
|
(match_operand 1 "const_int_operand" ""))]
|
(match_operand 1 "const_int_operand" ""))]
|
"GET_CODE (operands[0]) != LE
|
"GET_CODE (operands[0]) != LE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != GE
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != LT
|
&& GET_CODE (operands[0]) != GT"
|
&& GET_CODE (operands[0]) != GT"
|
"trap%0\\t31"
|
"trap%0\\t31"
|
[(set_attr "type" "call")])
|
[(set_attr "type" "call")])
|
|
|
;
|
;
|
; DBcond
|
; DBcond
|
;
|
;
|
; Note we have to emit a dbu instruction if there are no delay slots
|
; Note we have to emit a dbu instruction if there are no delay slots
|
; to fill.
|
; to fill.
|
; Also note that GCC will try to reverse a loop to see if it can
|
; Also note that GCC will try to reverse a loop to see if it can
|
; utilize this instruction. However, if there are more than one
|
; utilize this instruction. However, if there are more than one
|
; memory reference in the loop, it cannot guarantee that reversing
|
; memory reference in the loop, it cannot guarantee that reversing
|
; the loop will work :( (see check_dbra_loop() in loop.c)
|
; the loop will work :( (see check_dbra_loop() in loop.c)
|
; Note that the C3x only decrements the 24 LSBs of the address register
|
; Note that the C3x only decrements the 24 LSBs of the address register
|
; and the 8 MSBs are untouched. The C4x uses all 32-bits. We thus
|
; and the 8 MSBs are untouched. The C4x uses all 32-bits. We thus
|
; have an option to disable this instruction.
|
; have an option to disable this instruction.
|
(define_insn "*db"
|
(define_insn "*db"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"*
|
"*
|
if (which_alternative == 0)
|
if (which_alternative == 0)
|
return \"dbu%#\\t%0,%l1\";
|
return \"dbu%#\\t%0,%l1\";
|
else if (which_alternative == 1)
|
else if (which_alternative == 1)
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
else if (which_alternative == 2)
|
else if (which_alternative == 2)
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
else
|
else
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
"
|
"
|
[(set_attr "type" "db,jmpc,jmpc,jmpc")])
|
[(set_attr "type" "db,jmpc,jmpc,jmpc")])
|
|
|
(define_insn "*db_noclobber"
|
(define_insn "*db_noclobber"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a")
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "+a")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))]
|
(const_int -1)))]
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"dbu%#\\t%0,%l1"
|
"dbu%#\\t%0,%l1"
|
[(set_attr "type" "db")])
|
[(set_attr "type" "db")])
|
|
|
(define_split
|
(define_split
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "")
|
(if_then_else (ne (match_operand:QI 0 "addr_reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
[(parallel [(set (pc)
|
[(parallel [(set (pc)
|
(if_then_else (ne (match_dup 0)
|
(if_then_else (ne (match_dup 0)
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_dup 1))
|
(label_ref (match_dup 1))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))])]
|
(const_int -1)))])]
|
"")
|
"")
|
|
|
|
|
; This insn is used for some loop tests, typically loops reversed when
|
; This insn is used for some loop tests, typically loops reversed when
|
; strength reduction is used. It is actually created when the instruction
|
; strength reduction is used. It is actually created when the instruction
|
; combination phase combines the special loop test. Since this insn
|
; combination phase combines the special loop test. Since this insn
|
; is both a jump insn and has an output, it must deal with its own
|
; is both a jump insn and has an output, it must deal with its own
|
; reloads, hence the `m' constraints.
|
; reloads, hence the `m' constraints.
|
|
|
; The C4x does the decrement and then compares the result against zero.
|
; The C4x does the decrement and then compares the result against zero.
|
; It branches if the result was greater than or equal to zero.
|
; It branches if the result was greater than or equal to zero.
|
; In the RTL the comparison and decrement are assumed to happen
|
; In the RTL the comparison and decrement are assumed to happen
|
; at the same time so we bias the iteration counter with by -1
|
; at the same time so we bias the iteration counter with by -1
|
; when we make the test.
|
; when we make the test.
|
(define_insn "decrement_and_branch_until_zero"
|
(define_insn "decrement_and_branch_until_zero"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a,?*d,??*r,!m")
|
(const_int -1))
|
(const_int -1))
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"TARGET_DB && (find_reg_note (insn, REG_NONNEG, 0) || TARGET_LOOP_UNSIGNED)"
|
"TARGET_DB && (find_reg_note (insn, REG_NONNEG, 0) || TARGET_LOOP_UNSIGNED)"
|
"*
|
"*
|
if (which_alternative == 0)
|
if (which_alternative == 0)
|
return \"dbu%#\\t%0,%l1\";
|
return \"dbu%#\\t%0,%l1\";
|
else if (which_alternative == 1)
|
else if (which_alternative == 1)
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
else if (which_alternative == 2)
|
else if (which_alternative == 2)
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
else
|
else
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
"
|
"
|
[(set_attr "type" "db,jmpc,jmpc,jmpc")])
|
[(set_attr "type" "db,jmpc,jmpc,jmpc")])
|
|
|
(define_insn "*decrement_and_branch_until_zero_noclobber"
|
(define_insn "*decrement_and_branch_until_zero_noclobber"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
|
(const_int -1))
|
(const_int -1))
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))]
|
(const_int -1)))]
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"dbu%#\\t%0,%l1"
|
"dbu%#\\t%0,%l1"
|
[(set_attr "type" "db")])
|
[(set_attr "type" "db")])
|
|
|
(define_split
|
(define_split
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "")
|
(if_then_else (ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "")
|
(const_int -1))
|
(const_int -1))
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
"reload_completed && TARGET_DB && TARGET_LOOP_UNSIGNED"
|
[(parallel [(set (pc)
|
[(parallel [(set (pc)
|
(if_then_else (ge (plus:QI (match_dup 0)
|
(if_then_else (ge (plus:QI (match_dup 0)
|
(const_int -1))
|
(const_int -1))
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_dup 1))
|
(label_ref (match_dup 1))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))])]
|
(const_int -1)))])]
|
"")
|
"")
|
|
|
;
|
;
|
; MISC INSTRUCTIONS
|
; MISC INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; NOP
|
; NOP
|
;
|
;
|
(define_insn "nop"
|
(define_insn "nop"
|
[(const_int 0)]
|
[(const_int 0)]
|
""
|
""
|
"nop")
|
"nop")
|
; Default to misc type attr.
|
; Default to misc type attr.
|
|
|
(define_insn "return_indirect_internal"
|
(define_insn "return_indirect_internal"
|
[(return)
|
[(return)
|
(use (match_operand:QI 0 "reg_operand" ""))]
|
(use (match_operand:QI 0 "reg_operand" ""))]
|
"reload_completed"
|
"reload_completed"
|
"bu%#\\t%0"
|
"bu%#\\t%0"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
(define_expand "prologue"
|
(define_expand "prologue"
|
[(const_int 1)]
|
[(const_int 1)]
|
""
|
""
|
"c4x_expand_prologue (); DONE;")
|
"c4x_expand_prologue (); DONE;")
|
|
|
(define_expand "epilogue"
|
(define_expand "epilogue"
|
[(const_int 1)]
|
[(const_int 1)]
|
""
|
""
|
"c4x_expand_epilogue (); DONE;")
|
"c4x_expand_epilogue (); DONE;")
|
|
|
;
|
;
|
; RPTB
|
; RPTB
|
;
|
;
|
(define_insn "rptb_top"
|
(define_insn "rptb_top"
|
[(use (label_ref (match_operand 0 "" "")))
|
[(use (label_ref (match_operand 0 "" "")))
|
(use (label_ref (match_operand 1 "" "")))
|
(use (label_ref (match_operand 1 "" "")))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 26))]
|
(clobber (reg:QI 26))]
|
""
|
""
|
"*
|
"*
|
return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
|
return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
|
? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
|
? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
|
"
|
"
|
[(set_attr "type" "repeat_top")])
|
[(set_attr "type" "repeat_top")])
|
|
|
(define_insn "rpts_top"
|
(define_insn "rpts_top"
|
[(unspec [(use (label_ref (match_operand 0 "" "")))
|
[(unspec [(use (label_ref (match_operand 0 "" "")))
|
(use (label_ref (match_operand 1 "" "")))] UNSPEC_RPTS)
|
(use (label_ref (match_operand 1 "" "")))] UNSPEC_RPTS)
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 26))]
|
(clobber (reg:QI 26))]
|
""
|
""
|
"*
|
"*
|
return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
|
return ! final_sequence && c4x_rptb_rpts_p (insn, operands[0])
|
? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
|
? \"rpts\\trc\" : \"rptb%#\\t%l1-1\";
|
"
|
"
|
[(set_attr "type" "repeat")])
|
[(set_attr "type" "repeat")])
|
|
|
; This pattern needs to be emitted at the start of the loop to
|
; This pattern needs to be emitted at the start of the loop to
|
; say that RS and RE are loaded.
|
; say that RS and RE are loaded.
|
(define_insn "rptb_init"
|
(define_insn "rptb_init"
|
[(unspec [(match_operand:QI 0 "register_operand" "va")] UNSPEC_RPTB_INIT)
|
[(unspec [(match_operand:QI 0 "register_operand" "va")] UNSPEC_RPTB_INIT)
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 26))]
|
(clobber (reg:QI 26))]
|
""
|
""
|
""
|
""
|
[(set_attr "type" "repeat")])
|
[(set_attr "type" "repeat")])
|
|
|
|
|
; operand 0 is the loop count pseudo register
|
; operand 0 is the loop count pseudo register
|
; operand 1 is the number of loop iterations or 0 if it is unknown
|
; operand 1 is the number of loop iterations or 0 if it is unknown
|
; operand 2 is the maximum number of loop iterations
|
; operand 2 is the maximum number of loop iterations
|
; operand 3 is the number of levels of enclosed loops
|
; operand 3 is the number of levels of enclosed loops
|
(define_expand "doloop_begin"
|
(define_expand "doloop_begin"
|
[(use (match_operand 0 "register_operand" ""))
|
[(use (match_operand 0 "register_operand" ""))
|
(use (match_operand:QI 1 "const_int_operand" ""))
|
(use (match_operand:QI 1 "const_int_operand" ""))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 3 "const_int_operand" ""))]
|
(use (match_operand:QI 3 "const_int_operand" ""))]
|
""
|
""
|
"if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
|
"if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
|
FAIL;
|
FAIL;
|
emit_insn (gen_rptb_init (operands[0]));
|
emit_insn (gen_rptb_init (operands[0]));
|
DONE;
|
DONE;
|
")
|
")
|
|
|
|
|
; The RS (25) and RE (26) registers must be unviolate from the top of the loop
|
; The RS (25) and RE (26) registers must be unviolate from the top of the loop
|
; to here.
|
; to here.
|
(define_insn "rptb_end"
|
(define_insn "rptb_end"
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ge (match_operand:QI 0 "register_operand" "+v,?a,!*d,!*x*k,!m")
|
(if_then_else (ge (match_operand:QI 0 "register_operand" "+v,?a,!*d,!*x*k,!m")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 25))
|
(use (reg:QI 25))
|
(use (reg:QI 26))
|
(use (reg:QI 26))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"*
|
"*
|
if (which_alternative == 0)
|
if (which_alternative == 0)
|
return c4x_rptb_nop_p (insn) ? \"nop\" : \"\";
|
return c4x_rptb_nop_p (insn) ? \"nop\" : \"\";
|
else if (which_alternative == 1 && TARGET_DB)
|
else if (which_alternative == 1 && TARGET_DB)
|
return \"dbu%#\\t%0,%l1\";
|
return \"dbu%#\\t%0,%l1\";
|
else if (which_alternative == 2)
|
else if (which_alternative == 2)
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tbge\", insn);
|
else if (which_alternative == 3 || (which_alternative == 1 && ! TARGET_DB))
|
else if (which_alternative == 3 || (which_alternative == 1 && ! TARGET_DB))
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
return c4x_output_cbranch (\"subi\\t1,%0\\n\\tcmpi\\t0,%0\\n\\tbge\", insn);
|
else
|
else
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
return c4x_output_cbranch (\"push\\tr0\\n\\tldi\\t%0,r0\\n\\tsubi\\t1,r0\\n\\tsti\\tr0,%0\\n\\tpop\\tr0\\n\\tbhs\", insn);
|
"
|
"
|
[(set_attr "type" "repeat,db,jmpc,jmpc,jmpc")])
|
[(set_attr "type" "repeat,db,jmpc,jmpc,jmpc")])
|
|
|
(define_split
|
(define_split
|
[(set (pc)
|
[(set (pc)
|
(if_then_else (ge (match_operand:QI 0 "addr_reg_operand" "")
|
(if_then_else (ge (match_operand:QI 0 "addr_reg_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 3 "const_int_operand" ""))
|
(use (match_operand:QI 3 "const_int_operand" ""))
|
(use (match_operand:QI 4 "const_int_operand" ""))
|
(use (match_operand:QI 4 "const_int_operand" ""))
|
(use (reg:QI 25))
|
(use (reg:QI 25))
|
(use (reg:QI 26))
|
(use (reg:QI 26))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (pc)
|
[(parallel [(set (pc)
|
(if_then_else (ge (match_dup 0)
|
(if_then_else (ge (match_dup 0)
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_dup 1))
|
(label_ref (match_dup 1))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))])]
|
(const_int -1)))])]
|
"")
|
"")
|
|
|
; operand 0 is the loop count pseudo register
|
; operand 0 is the loop count pseudo register
|
; operand 1 is the number of loop iterations or 0 if it is unknown
|
; operand 1 is the number of loop iterations or 0 if it is unknown
|
; operand 2 is the maximum number of loop iterations
|
; operand 2 is the maximum number of loop iterations
|
; operand 3 is the number of levels of enclosed loops
|
; operand 3 is the number of levels of enclosed loops
|
; operand 4 is the label to jump to at the top of the loop
|
; operand 4 is the label to jump to at the top of the loop
|
(define_expand "doloop_end"
|
(define_expand "doloop_end"
|
[(use (match_operand 0 "register_operand" ""))
|
[(use (match_operand 0 "register_operand" ""))
|
(use (match_operand:QI 1 "const_int_operand" ""))
|
(use (match_operand:QI 1 "const_int_operand" ""))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 2 "const_int_operand" ""))
|
(use (match_operand:QI 3 "const_int_operand" ""))
|
(use (match_operand:QI 3 "const_int_operand" ""))
|
(use (label_ref (match_operand 4 "" "")))]
|
(use (label_ref (match_operand 4 "" "")))]
|
""
|
""
|
"if (! TARGET_LOOP_UNSIGNED
|
"if (! TARGET_LOOP_UNSIGNED
|
&& (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > ((unsigned) 1 << 31))
|
&& (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > ((unsigned) 1 << 31))
|
FAIL;
|
FAIL;
|
if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
|
if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
|
{
|
{
|
/* The C30 maximum iteration count for DB is 2^24. */
|
/* The C30 maximum iteration count for DB is 2^24. */
|
if (! TARGET_DB)
|
if (! TARGET_DB)
|
FAIL;
|
FAIL;
|
emit_jump_insn (gen_decrement_and_branch_until_zero (operands[0],
|
emit_jump_insn (gen_decrement_and_branch_until_zero (operands[0],
|
operands[4]));
|
operands[4]));
|
DONE;
|
DONE;
|
}
|
}
|
emit_jump_insn (gen_rptb_end (operands[0], operands[4]));
|
emit_jump_insn (gen_rptb_end (operands[0], operands[4]));
|
DONE;
|
DONE;
|
")
|
")
|
|
|
(define_expand "decrement_and_branch_on_count"
|
(define_expand "decrement_and_branch_on_count"
|
[(parallel [(set (pc)
|
[(parallel [(set (pc)
|
(if_then_else (ge (match_operand:QI 0 "register_operand" "")
|
(if_then_else (ge (match_operand:QI 0 "register_operand" "")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 25))
|
(use (reg:QI 25))
|
(use (reg:QI 26))
|
(use (reg:QI 26))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"0"
|
"0"
|
"")
|
"")
|
|
|
(define_expand "movmemqi_small"
|
(define_expand "movmemqi_small"
|
[(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
|
[(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
|
(mem:BLK (match_operand:BLK 1 "src_operand" "")))
|
(mem:BLK (match_operand:BLK 1 "src_operand" "")))
|
(use (match_operand:QI 2 "immediate_operand" ""))
|
(use (match_operand:QI 2 "immediate_operand" ""))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(clobber (match_operand:QI 4 "ext_low_reg_operand" ""))])]
|
(clobber (match_operand:QI 4 "ext_low_reg_operand" ""))])]
|
""
|
""
|
"
|
"
|
{
|
{
|
rtx src, dst, tmp;
|
rtx src, dst, tmp;
|
rtx src_mem, dst_mem;
|
rtx src_mem, dst_mem;
|
int len;
|
int len;
|
int i;
|
int i;
|
|
|
dst = operands[0];
|
dst = operands[0];
|
src = operands[1];
|
src = operands[1];
|
len = INTVAL (operands[2]);
|
len = INTVAL (operands[2]);
|
tmp = operands[4];
|
tmp = operands[4];
|
|
|
src_mem = gen_rtx_MEM (QImode, src);
|
src_mem = gen_rtx_MEM (QImode, src);
|
dst_mem = gen_rtx_MEM (QImode, dst);
|
dst_mem = gen_rtx_MEM (QImode, dst);
|
|
|
if (TARGET_PARALLEL)
|
if (TARGET_PARALLEL)
|
{
|
{
|
emit_insn (gen_movqi (tmp, src_mem));
|
emit_insn (gen_movqi (tmp, src_mem));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
for (i = 1; i < len; i++)
|
for (i = 1; i < len; i++)
|
{
|
{
|
emit_insn (gen_movqi_parallel (tmp, src_mem, dst_mem, tmp));
|
emit_insn (gen_movqi_parallel (tmp, src_mem, dst_mem, tmp));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
}
|
}
|
emit_insn (gen_movqi (dst_mem, tmp));
|
emit_insn (gen_movqi (dst_mem, tmp));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
}
|
}
|
else
|
else
|
{
|
{
|
for (i = 0; i < len; i++)
|
for (i = 0; i < len; i++)
|
{
|
{
|
emit_insn (gen_movqi (tmp, src_mem));
|
emit_insn (gen_movqi (tmp, src_mem));
|
emit_insn (gen_movqi (dst_mem, tmp));
|
emit_insn (gen_movqi (dst_mem, tmp));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (src, src, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
emit_insn (gen_addqi3_noclobber (dst, dst, const1_rtx));
|
}
|
}
|
}
|
}
|
DONE;
|
DONE;
|
}
|
}
|
")
|
")
|
|
|
|
|
;
|
;
|
; BLOCK MOVE
|
; BLOCK MOVE
|
; We should probably get RC loaded when using RPTB automagically...
|
; We should probably get RC loaded when using RPTB automagically...
|
; There's probably no need to call _memcpy() if we don't get
|
; There's probably no need to call _memcpy() if we don't get
|
; an immediate operand for the size. We could do a better job here
|
; an immediate operand for the size. We could do a better job here
|
; than most memcpy() implementations.
|
; than most memcpy() implementations.
|
; operand 2 is the number of bytes
|
; operand 2 is the number of bytes
|
; operand 3 is the shared alignment
|
; operand 3 is the shared alignment
|
; operand 4 is a scratch register
|
; operand 4 is a scratch register
|
|
|
(define_insn "movmemqi_large"
|
(define_insn "movmemqi_large"
|
[(set (mem:BLK (match_operand:QI 0 "addr_reg_operand" "a"))
|
[(set (mem:BLK (match_operand:QI 0 "addr_reg_operand" "a"))
|
(mem:BLK (match_operand:QI 1 "addr_reg_operand" "a")))
|
(mem:BLK (match_operand:QI 1 "addr_reg_operand" "a")))
|
(use (match_operand:QI 2 "immediate_operand" "i"))
|
(use (match_operand:QI 2 "immediate_operand" "i"))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(clobber (match_operand:QI 4 "ext_low_reg_operand" "=&q"))
|
(clobber (match_operand:QI 4 "ext_low_reg_operand" "=&q"))
|
(clobber (match_scratch:QI 5 "=0"))
|
(clobber (match_scratch:QI 5 "=0"))
|
(clobber (match_scratch:QI 6 "=1"))
|
(clobber (match_scratch:QI 6 "=1"))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 25))
|
(clobber (reg:QI 26))
|
(clobber (reg:QI 26))
|
(clobber (reg:QI 27))]
|
(clobber (reg:QI 27))]
|
""
|
""
|
"*
|
"*
|
{
|
{
|
int i;
|
int i;
|
int len = INTVAL (operands[2]);
|
int len = INTVAL (operands[2]);
|
|
|
output_asm_insn (\"ldiu\\t*%1++,%4\", operands);
|
output_asm_insn (\"ldiu\\t*%1++,%4\", operands);
|
if (len < 8)
|
if (len < 8)
|
{
|
{
|
for (i = 1; i < len; i++)
|
for (i = 1; i < len; i++)
|
{
|
{
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
}
|
}
|
}
|
}
|
else
|
else
|
{
|
{
|
if (TARGET_RPTS_CYCLES (len))
|
if (TARGET_RPTS_CYCLES (len))
|
{
|
{
|
output_asm_insn (\"rpts\\t%2-2\", operands);
|
output_asm_insn (\"rpts\\t%2-2\", operands);
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
}
|
}
|
else
|
else
|
{
|
{
|
output_asm_insn (\"ldiu\\t%2-2,rc\", operands);
|
output_asm_insn (\"ldiu\\t%2-2,rc\", operands);
|
output_asm_insn (\"rptb\\t$+1\", operands);
|
output_asm_insn (\"rptb\\t$+1\", operands);
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"sti\\t%4,*%0++\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
|
}
|
}
|
}
|
}
|
return \"sti\\t%4,*%0++\";
|
return \"sti\\t%4,*%0++\";
|
}"
|
}"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; Operand 2 is the count, operand 3 is the alignment.
|
; Operand 2 is the count, operand 3 is the alignment.
|
(define_expand "movmemqi"
|
(define_expand "movmemqi"
|
[(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
|
[(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
|
(mem:BLK (match_operand:BLK 1 "src_operand" "")))
|
(mem:BLK (match_operand:BLK 1 "src_operand" "")))
|
(use (match_operand:QI 2 "immediate_operand" ""))
|
(use (match_operand:QI 2 "immediate_operand" ""))
|
(use (match_operand:QI 3 "immediate_operand" ""))])]
|
(use (match_operand:QI 3 "immediate_operand" ""))])]
|
""
|
""
|
"
|
"
|
{
|
{
|
rtx tmp;
|
rtx tmp;
|
if (GET_CODE (operands[2]) != CONST_INT
|
if (GET_CODE (operands[2]) != CONST_INT
|
|| INTVAL (operands[2]) > 32767
|
|| INTVAL (operands[2]) > 32767
|
|| INTVAL (operands[2]) <= 0)
|
|| INTVAL (operands[2]) <= 0)
|
{
|
{
|
FAIL; /* Try to call _memcpy */
|
FAIL; /* Try to call _memcpy */
|
}
|
}
|
|
|
operands[0] = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
|
operands[0] = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
|
operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
|
operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
|
tmp = gen_reg_rtx (QImode);
|
tmp = gen_reg_rtx (QImode);
|
/* Disabled because of reload problems. */
|
/* Disabled because of reload problems. */
|
if (0 && INTVAL (operands[2]) < 8)
|
if (0 && INTVAL (operands[2]) < 8)
|
emit_insn (gen_movmemqi_small (operands[0], operands[1], operands[2],
|
emit_insn (gen_movmemqi_small (operands[0], operands[1], operands[2],
|
operands[3], tmp));
|
operands[3], tmp));
|
else
|
else
|
{
|
{
|
emit_insn (gen_movmemqi_large (operands[0], operands[1], operands[2],
|
emit_insn (gen_movmemqi_large (operands[0], operands[1], operands[2],
|
operands[3], tmp));
|
operands[3], tmp));
|
}
|
}
|
DONE;
|
DONE;
|
}")
|
}")
|
|
|
|
|
(define_insn "*cmpstrnqi"
|
(define_insn "*cmpstrnqi"
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
[(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(compare:QI (mem:BLK (match_operand:QI 1 "addr_reg_operand" "+a"))
|
(compare:QI (mem:BLK (match_operand:QI 1 "addr_reg_operand" "+a"))
|
(mem:BLK (match_operand:QI 2 "addr_reg_operand" "+a"))))
|
(mem:BLK (match_operand:QI 2 "addr_reg_operand" "+a"))))
|
(use (match_operand:QI 3 "immediate_operand" "i"))
|
(use (match_operand:QI 3 "immediate_operand" "i"))
|
(use (match_operand:QI 4 "immediate_operand" ""))
|
(use (match_operand:QI 4 "immediate_operand" ""))
|
(clobber (match_operand:QI 5 "std_reg_operand" "=&c"))
|
(clobber (match_operand:QI 5 "std_reg_operand" "=&c"))
|
(clobber (reg:QI 21))]
|
(clobber (reg:QI 21))]
|
""
|
""
|
"*
|
"*
|
{
|
{
|
output_asm_insn (\"ldi\\t%3-1,%5\", operands);
|
output_asm_insn (\"ldi\\t%3-1,%5\", operands);
|
output_asm_insn (\"$1:\tsubi3\\t*%1++,*%2++,%0\", operands);
|
output_asm_insn (\"$1:\tsubi3\\t*%1++,*%2++,%0\", operands);
|
output_asm_insn (\"dbeq\\t%5,$1\", operands);
|
output_asm_insn (\"dbeq\\t%5,$1\", operands);
|
return \"\";
|
return \"\";
|
}")
|
}")
|
|
|
(define_expand "cmpstrnqi"
|
(define_expand "cmpstrnqi"
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(compare:QI (match_operand:BLK 1 "general_operand" "")
|
(compare:QI (match_operand:BLK 1 "general_operand" "")
|
(match_operand:BLK 2 "general_operand" "")))
|
(match_operand:BLK 2 "general_operand" "")))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(use (match_operand:QI 3 "immediate_operand" ""))
|
(use (match_operand:QI 4 "immediate_operand" ""))
|
(use (match_operand:QI 4 "immediate_operand" ""))
|
(clobber (match_dup 5))
|
(clobber (match_dup 5))
|
(clobber (reg:QI 21))])]
|
(clobber (reg:QI 21))])]
|
""
|
""
|
"
|
"
|
{
|
{
|
if (GET_CODE (operands[3]) != CONST_INT
|
if (GET_CODE (operands[3]) != CONST_INT
|
|| INTVAL (operands[3]) > 32767
|
|| INTVAL (operands[3]) > 32767
|
|| INTVAL (operands[3]) <= 0)
|
|| INTVAL (operands[3]) <= 0)
|
{
|
{
|
FAIL;
|
FAIL;
|
}
|
}
|
operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
|
operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
|
operands[2] = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
|
operands[2] = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
|
operands[5] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QImode);
|
}")
|
}")
|
|
|
;
|
;
|
; TWO OPERAND LONG DOUBLE INSTRUCTIONS
|
; TWO OPERAND LONG DOUBLE INSTRUCTIONS
|
;
|
;
|
|
|
(define_expand "movhf"
|
(define_expand "movhf"
|
[(set (match_operand:HF 0 "src_operand" "")
|
[(set (match_operand:HF 0 "src_operand" "")
|
(match_operand:HF 1 "src_operand" ""))]
|
(match_operand:HF 1 "src_operand" ""))]
|
""
|
""
|
"if (c4x_emit_move_sequence (operands, HFmode))
|
"if (c4x_emit_move_sequence (operands, HFmode))
|
DONE;")
|
DONE;")
|
|
|
(define_insn "*movhf_noclobber_reg"
|
(define_insn "*movhf_noclobber_reg"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(match_operand:HF 1 "src_operand" "Hh"))]
|
(match_operand:HF 1 "src_operand" "Hh"))]
|
"GET_CODE (operands[1]) != MEM"
|
"GET_CODE (operands[1]) != MEM"
|
"ldfu\\t%1,%0"
|
"ldfu\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_insn "*movhf_noclobber"
|
(define_insn "*movhf_noclobber"
|
[(set (match_operand:HF 0 "dst_operand" "=h,m")
|
[(set (match_operand:HF 0 "dst_operand" "=h,m")
|
(match_operand:HF 1 "src_operand" "Hm,h"))]
|
(match_operand:HF 1 "src_operand" "Hm,h"))]
|
"reg_operand (operands[0], HFmode) ^ reg_operand (operands[1], HFmode)"
|
"reg_operand (operands[0], HFmode) ^ reg_operand (operands[1], HFmode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi")])
|
[(set_attr "type" "multi,multi")])
|
|
|
(define_insn "*movhf_test"
|
(define_insn "*movhf_test"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HF 1 "reg_operand" "h")
|
(compare:CC (match_operand:HF 1 "reg_operand" "h")
|
(const_int 0)))
|
(const_int 0)))
|
(clobber (match_scratch:HF 0 "=h"))]
|
(clobber (match_scratch:HF 0 "=h"))]
|
""
|
""
|
"ldf\\t%1,%0"
|
"ldf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*movhf_set"
|
(define_insn "*movhf_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HF 1 "reg_operand" "h")
|
(compare:CC (match_operand:HF 1 "reg_operand" "h")
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(match_dup 1))]
|
(match_dup 1))]
|
""
|
""
|
"ldf\\t%1,%0"
|
"ldf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HF 0 "reg_operand" "")
|
[(set (match_operand:HF 0 "reg_operand" "")
|
(match_operand:HF 1 "memory_operand" ""))]
|
(match_operand:HF 1 "memory_operand" ""))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 0) (float_extend:HF (match_dup 2)))
|
[(set (match_dup 0) (float_extend:HF (match_dup 2)))
|
(set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
|
(set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
|
(match_dup 3)] UNSPEC_LOADHF_INT))]
|
(match_dup 3)] UNSPEC_LOADHF_INT))]
|
"operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
|
"operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[3], QImode);")
|
PUT_MODE (operands[3], QImode);")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HF 0 "reg_operand" "")
|
[(set (match_operand:HF 0 "reg_operand" "")
|
(match_operand:HF 1 "const_operand" ""))]
|
(match_operand:HF 1 "const_operand" ""))]
|
"reload_completed && 0"
|
"reload_completed && 0"
|
[(set (match_dup 0) (float_extend:HF (match_dup 2)))
|
[(set (match_dup 0) (float_extend:HF (match_dup 2)))
|
(set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
|
(set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
|
(match_dup 3)] UNSPEC_LOADHF_INT))]
|
(match_dup 3)] UNSPEC_LOADHF_INT))]
|
"operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
|
"operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[3], QImode);")
|
PUT_MODE (operands[3], QImode);")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HF 0 "memory_operand" "")
|
[(set (match_operand:HF 0 "memory_operand" "")
|
(match_operand:HF 1 "reg_operand" ""))]
|
(match_operand:HF 1 "reg_operand" ""))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 2) (float_truncate:QF (match_dup 1)))
|
[(set (match_dup 2) (float_truncate:QF (match_dup 1)))
|
(set (match_dup 3) (unspec:QI [(match_dup 1)] UNSPEC_STOREHF_INT))]
|
(set (match_dup 3) (unspec:QI [(match_dup 1)] UNSPEC_STOREHF_INT))]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HFmode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HFmode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[2], QFmode);
|
PUT_MODE (operands[3], QImode);")
|
PUT_MODE (operands[3], QImode);")
|
|
|
(define_insn "*loadhf_float"
|
(define_insn "*loadhf_float"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(float_extend:HF (match_operand:QF 1 "src_operand" "fHm")))]
|
(float_extend:HF (match_operand:QF 1 "src_operand" "fHm")))]
|
""
|
""
|
"ldfu\\t%1,%0"
|
"ldfu\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_insn "*loadhf_int"
|
(define_insn "*loadhf_int"
|
[(set (match_operand:HF 0 "reg_operand" "+h")
|
[(set (match_operand:HF 0 "reg_operand" "+h")
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LOADHF_INT))]
|
(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LOADHF_INT))]
|
""
|
""
|
"ldiu\\t%1,%0"
|
"ldiu\\t%1,%0"
|
[(set_attr "type" "unary")])
|
[(set_attr "type" "unary")])
|
|
|
(define_insn "*storehf_float"
|
(define_insn "*storehf_float"
|
[(set (match_operand:QF 0 "memory_operand" "=m")
|
[(set (match_operand:QF 0 "memory_operand" "=m")
|
(float_truncate:QF (match_operand:HF 1 "reg_operand" "h")))]
|
(float_truncate:QF (match_operand:HF 1 "reg_operand" "h")))]
|
""
|
""
|
"stf\\t%1,%0"
|
"stf\\t%1,%0"
|
[(set_attr "type" "store")])
|
[(set_attr "type" "store")])
|
|
|
(define_insn "*storehf_int"
|
(define_insn "*storehf_int"
|
[(set (match_operand:QI 0 "memory_operand" "=m")
|
[(set (match_operand:QI 0 "memory_operand" "=m")
|
(unspec:QI [(match_operand:HF 1 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
|
(unspec:QI [(match_operand:HF 1 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
|
""
|
""
|
"sti\\t%1,%0"
|
"sti\\t%1,%0"
|
[(set_attr "type" "store")])
|
[(set_attr "type" "store")])
|
|
|
(define_insn "extendqfhf2"
|
(define_insn "extendqfhf2"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(float_extend:HF (match_operand:QF 1 "reg_operand" "h")))]
|
(float_extend:HF (match_operand:QF 1 "reg_operand" "h")))]
|
""
|
""
|
"ldfu\\t%1,%0"
|
"ldfu\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "trunchfqf2"
|
(define_insn "trunchfqf2"
|
[(set (match_operand:QF 0 "reg_operand" "=h")
|
[(set (match_operand:QF 0 "reg_operand" "=h")
|
(float_truncate:QF (match_operand:HF 1 "reg_operand" "0")))
|
(float_truncate:QF (match_operand:HF 1 "reg_operand" "0")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"andn\\t0ffh,%0"
|
"andn\\t0ffh,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; PUSH/POP
|
; PUSH/POP
|
;
|
;
|
(define_insn "pushhf"
|
(define_insn "pushhf"
|
[(set (mem:HF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:HF (pre_inc:QI (reg:QI 20)))
|
(match_operand:HF 0 "reg_operand" "h"))]
|
(match_operand:HF 0 "reg_operand" "h"))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (mem:HF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:HF (pre_inc:QI (reg:QI 20)))
|
(match_operand:HF 0 "reg_operand" ""))]
|
(match_operand:HF 0 "reg_operand" ""))]
|
"reload_completed"
|
"reload_completed"
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
(float_truncate:QF (match_dup 0)))
|
(float_truncate:QF (match_dup 0)))
|
(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(unspec:QI [(match_dup 0)] UNSPEC_STOREHF_INT))]
|
(unspec:QI [(match_dup 0)] UNSPEC_STOREHF_INT))]
|
"")
|
"")
|
|
|
(define_insn "pushhf_trunc"
|
(define_insn "pushhf_trunc"
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QF (pre_inc:QI (reg:QI 20)))
|
(float_truncate:QF (match_operand:HF 0 "reg_operand" "h")))]
|
(float_truncate:QF (match_operand:HF 0 "reg_operand" "h")))]
|
""
|
""
|
"pushf\\t%0"
|
"pushf\\t%0"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
(define_insn "pushhf_int"
|
(define_insn "pushhf_int"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20)))
|
(unspec:QI [(match_operand:HF 0 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
|
(unspec:QI [(match_operand:HF 0 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
|
""
|
""
|
"push\\t%0"
|
"push\\t%0"
|
[(set_attr "type" "push")])
|
[(set_attr "type" "push")])
|
|
|
; we cannot use this because the popf will destroy the low 8 bits
|
; we cannot use this because the popf will destroy the low 8 bits
|
;(define_insn "pophf"
|
;(define_insn "pophf"
|
; [(set (match_operand:HF 0 "reg_operand" "=h")
|
; [(set (match_operand:HF 0 "reg_operand" "=h")
|
; (mem:HF (post_dec:QI (reg:QI 20))))
|
; (mem:HF (post_dec:QI (reg:QI 20))))
|
; (clobber (reg:CC 21))]
|
; (clobber (reg:CC 21))]
|
; ""
|
; ""
|
; "#"
|
; "#"
|
; [(set_attr "type" "multi")])
|
; [(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HF 0 "reg_operand" "")
|
[(set (match_operand:HF 0 "reg_operand" "")
|
(mem:HF (post_dec:QI (reg:QI 20))))
|
(mem:HF (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
|
(float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
|
(float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 0)
|
(parallel [(set (match_dup 0)
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
|
(mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"")
|
"")
|
|
|
(define_insn "*pophf_int"
|
(define_insn "*pophf_int"
|
[(set (match_operand:HF 0 "reg_operand" "+h")
|
[(set (match_operand:HF 0 "reg_operand" "+h")
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(unspec:HF [(subreg:QI (match_dup 0) 0)
|
(mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
|
(mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"pop\\t%0"
|
"pop\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
(define_insn "*pophf_float"
|
(define_insn "*pophf_float"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
|
(float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"popf\\t%0"
|
"popf\\t%0"
|
[(set_attr "type" "pop")])
|
[(set_attr "type" "pop")])
|
|
|
;
|
;
|
; FIX
|
; FIX
|
;
|
;
|
(define_expand "fixuns_trunchfqi2"
|
(define_expand "fixuns_trunchfqi2"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 3)
|
(parallel [(set (match_dup 3)
|
(minus:HF (match_dup 1) (match_dup 5)))
|
(minus:HF (match_dup 1) (match_dup 5)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (reg:CC 21)
|
(parallel [(set (reg:CC 21)
|
(compare:CC (fix:QI (match_dup 3))
|
(compare:CC (fix:QI (match_dup 3))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_dup 4)
|
(set (match_dup 4)
|
(fix:QI (match_dup 3)))])
|
(fix:QI (match_dup 3)))])
|
(parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
|
(parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
|
(use (reg:CC 21))])
|
(use (reg:CC 21))])
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
|
""
|
""
|
"operands[2] = gen_reg_rtx (QImode);
|
"operands[2] = gen_reg_rtx (QImode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (HFmode);
|
operands[5] = gen_reg_rtx (HFmode);
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
|
emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
|
|
|
(define_expand "fix_trunchfqi2"
|
(define_expand "fix_trunchfqi2"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "")))
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 3) (neg:HF (match_dup 1)))
|
(parallel [(set (match_dup 3) (neg:HF (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
|
(parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (reg:CC_NOOV 21)
|
(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
|
(compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
|
(set (match_dup 5) (neg:QI (match_dup 4)))])
|
(set (match_dup 5) (neg:QI (match_dup 4)))])
|
(set (match_dup 2)
|
(set (match_dup 2)
|
(if_then_else:QI (le (reg:CC 21) (const_int 0))
|
(if_then_else:QI (le (reg:CC 21) (const_int 0))
|
(match_dup 5)
|
(match_dup 5)
|
(match_dup 2)))
|
(match_dup 2)))
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
|
(set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
|
""
|
""
|
"if (TARGET_FAST_FIX)
|
"if (TARGET_FAST_FIX)
|
{
|
{
|
emit_insn (gen_fixhfqi_clobber (operands[0], operands[1]));
|
emit_insn (gen_fixhfqi_clobber (operands[0], operands[1]));
|
DONE;
|
DONE;
|
}
|
}
|
operands[2] = gen_reg_rtx (QImode);
|
operands[2] = gen_reg_rtx (QImode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[4] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QImode);
|
operands[5] = gen_reg_rtx (QImode);
|
")
|
")
|
|
|
(define_insn "*fixhfqi_set"
|
(define_insn "*fixhfqi_set"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(compare:CC (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(set (match_operand:QI 0 "ext_reg_operand" "=d")
|
(fix:QI (match_dup 1)))]
|
(fix:QI (match_dup 1)))]
|
""
|
""
|
"fix\\t%1,%0"
|
"fix\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "fixhfqi_clobber"
|
(define_insn "fixhfqi_clobber"
|
[(set (match_operand:QI 0 "reg_operand" "=dc")
|
[(set (match_operand:QI 0 "reg_operand" "=dc")
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"fix\\t%1,%0"
|
"fix\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_expand "fix_trunchfhi2"
|
(define_expand "fix_trunchfhi2"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(fix:HI (match_operand:HF 1 "reg_operand" "")))
|
(fix:HI (match_operand:HF 1 "reg_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (fix_trunchfhi2_libfunc, FIX, HImode, HFmode, 2, operands);
|
"c4x_emit_libcall (fix_trunchfhi2_libfunc, FIX, HImode, HFmode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
(define_expand "fixuns_trunchfhi2"
|
(define_expand "fixuns_trunchfhi2"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(unsigned_fix:HI (match_operand:HF 1 "reg_operand" "")))
|
(unsigned_fix:HI (match_operand:HF 1 "reg_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (fixuns_trunchfhi2_libfunc, UNSIGNED_FIX,
|
"c4x_emit_libcall (fixuns_trunchfhi2_libfunc, UNSIGNED_FIX,
|
HImode, HFmode, 2, operands);
|
HImode, HFmode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
;
|
;
|
; ABSF
|
; ABSF
|
;
|
;
|
(define_expand "abshf2"
|
(define_expand "abshf2"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(abs:HF (match_operand:HF 1 "reg_or_const_operand" "")))
|
(abs:HF (match_operand:HF 1 "reg_or_const_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*abshf2_clobber"
|
(define_insn "*abshf2_clobber"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*abshf2_test"
|
(define_insn "*abshf2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_operand" "h"))
|
(compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_operand" "h"))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(clobber (match_scratch:HF 0 "=h"))]
|
(clobber (match_scratch:HF 0 "=h"))]
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*abshf2_set"
|
(define_insn "*abshf2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(compare:CC_NOOV (abs:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(abs:HF (match_dup 1)))]
|
(abs:HF (match_dup 1)))]
|
|
|
""
|
""
|
"absf\\t%1,%0"
|
"absf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; NEGF
|
; NEGF
|
;
|
;
|
(define_expand "neghf2"
|
(define_expand "neghf2"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(neg:HF (match_operand:HF 1 "reg_or_const_operand" "")))
|
(neg:HF (match_operand:HF 1 "reg_or_const_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"")
|
"")
|
|
|
(define_insn "*neghf2_clobber"
|
(define_insn "*neghf2_clobber"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*neghf2_test"
|
(define_insn "*neghf2_test"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(clobber (match_scratch:HF 0 "=h"))]
|
(clobber (match_scratch:HF 0 "=h"))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
(define_insn "*neghf2_set"
|
(define_insn "*neghf2_set"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(compare:CC_NOOV (neg:HF (match_operand:HF 1 "reg_or_const_operand" "hH"))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(match_operand:HF 2 "fp_zero_operand" "G")))
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(set (match_operand:HF 0 "reg_operand" "=h")
|
(neg:HF (match_dup 1)))]
|
(neg:HF (match_dup 1)))]
|
""
|
""
|
"negf\\t%1,%0"
|
"negf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; RCPF
|
; RCPF
|
;
|
;
|
(define_insn "*rcpfhf_clobber"
|
(define_insn "*rcpfhf_clobber"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RCPF))
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RCPF))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rcpf\\t%1,%0"
|
"rcpf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; RSQRF
|
; RSQRF
|
;
|
;
|
(define_insn "*rsqrfhf_clobber"
|
(define_insn "*rsqrfhf_clobber"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RSQRF))
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RSQRF))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rsqrf\\t%1,%0"
|
"rsqrf\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
;
|
;
|
; RNDF
|
; RNDF
|
;
|
;
|
(define_insn "*rndhf_clobber"
|
(define_insn "*rndhf_clobber"
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
[(set (match_operand:HF 0 "reg_operand" "=h")
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RND))
|
(unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RND))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"rnd\\t%1,%0"
|
"rnd\\t%1,%0"
|
[(set_attr "type" "unarycc")])
|
[(set_attr "type" "unarycc")])
|
|
|
|
|
; Inlined float square root for C4x
|
; Inlined float square root for C4x
|
(define_expand "sqrthf2_inline"
|
(define_expand "sqrthf2_inline"
|
[(parallel [(set (match_dup 2)
|
[(parallel [(set (match_dup 2)
|
(unspec:HF [(match_operand:HF 1 "reg_operand" "")] UNSPEC_RSQRF))
|
(unspec:HF [(match_operand:HF 1 "reg_operand" "")] UNSPEC_RSQRF))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 5) (match_dup 1)))
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 5) (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 6) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
|
(parallel [(set (match_dup 2) (mult:HF (match_dup 2) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(mult:HF (match_dup 2) (match_dup 1)))
|
(mult:HF (match_dup 2) (match_dup 1)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"
|
"
|
operands[2] = gen_reg_rtx (HFmode);
|
operands[2] = gen_reg_rtx (HFmode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[5] = CONST_DOUBLE_ATOF (\"0.5\", HFmode);
|
operands[5] = CONST_DOUBLE_ATOF (\"0.5\", HFmode);
|
operands[6] = CONST_DOUBLE_ATOF (\"1.5\", HFmode);
|
operands[6] = CONST_DOUBLE_ATOF (\"1.5\", HFmode);
|
")
|
")
|
|
|
|
|
(define_expand "sqrthf2"
|
(define_expand "sqrthf2"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(sqrt:HF (match_operand:HF 1 "reg_operand" "")))
|
(sqrt:HF (match_operand:HF 1 "reg_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X && TARGET_INLINE"
|
"! TARGET_C3X && TARGET_INLINE"
|
"emit_insn (gen_sqrthf2_inline (operands[0], operands[1]));
|
"emit_insn (gen_sqrthf2_inline (operands[0], operands[1]));
|
DONE;")
|
DONE;")
|
|
|
;
|
;
|
; THREE OPERAND LONG DOUBLE INSTRUCTIONS
|
; THREE OPERAND LONG DOUBLE INSTRUCTIONS
|
;
|
;
|
|
|
;
|
;
|
; ADDF
|
; ADDF
|
;
|
;
|
(define_insn "addhf3"
|
(define_insn "addhf3"
|
[(set (match_operand:HF 0 "reg_operand" "=h,?h")
|
[(set (match_operand:HF 0 "reg_operand" "=h,?h")
|
(plus:HF (match_operand:HF 1 "reg_operand" "%0,h")
|
(plus:HF (match_operand:HF 1 "reg_operand" "%0,h")
|
(match_operand:HF 2 "reg_or_const_operand" "H,h")))
|
(match_operand:HF 2 "reg_or_const_operand" "H,h")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"@
|
"@
|
addf\\t%2,%0
|
addf\\t%2,%0
|
addf3\\t%2,%1,%0"
|
addf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; SUBF
|
; SUBF
|
;
|
;
|
(define_insn "subhf3"
|
(define_insn "subhf3"
|
[(set (match_operand:HF 0 "reg_operand" "=h,h,?h")
|
[(set (match_operand:HF 0 "reg_operand" "=h,h,?h")
|
(minus:HF (match_operand:HF 1 "reg_or_const_operand" "0,H,h")
|
(minus:HF (match_operand:HF 1 "reg_or_const_operand" "0,H,h")
|
(match_operand:HF 2 "reg_or_const_operand" "H,0,h")))
|
(match_operand:HF 2 "reg_or_const_operand" "H,0,h")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"@
|
"@
|
subf\\t%2,%0
|
subf\\t%2,%0
|
subrf\\t%1,%0
|
subrf\\t%1,%0
|
subf3\\t%2,%1,%0"
|
subf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc,binarycc")])
|
|
|
;
|
;
|
; MULF
|
; MULF
|
;
|
;
|
; The C3x MPYF only uses 24-bit precision while the C4x uses 32-bit precision.
|
; The C3x MPYF only uses 24-bit precision while the C4x uses 32-bit precision.
|
;
|
;
|
(define_expand "mulhf3"
|
(define_expand "mulhf3"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
|
(mult:HF (match_operand:HF 1 "reg_operand" "h")
|
(mult:HF (match_operand:HF 1 "reg_operand" "h")
|
(match_operand:HF 2 "reg_operand" "h")))
|
(match_operand:HF 2 "reg_operand" "h")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"")
|
"")
|
|
|
(define_insn "*mulhf3_c40"
|
(define_insn "*mulhf3_c40"
|
[(set (match_operand:HF 0 "reg_operand" "=h,?h")
|
[(set (match_operand:HF 0 "reg_operand" "=h,?h")
|
(mult:HF (match_operand:HF 1 "reg_operand" "%0,h")
|
(mult:HF (match_operand:HF 1 "reg_operand" "%0,h")
|
(match_operand:HF 2 "reg_or_const_operand" "hH,h")))
|
(match_operand:HF 2 "reg_or_const_operand" "hH,h")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"@
|
"@
|
mpyf\\t%2,%0
|
mpyf\\t%2,%0
|
mpyf3\\t%2,%1,%0"
|
mpyf3\\t%2,%1,%0"
|
[(set_attr "type" "binarycc,binarycc")])
|
[(set_attr "type" "binarycc,binarycc")])
|
|
|
;
|
;
|
; CMPF
|
; CMPF
|
;
|
;
|
(define_expand "cmphf"
|
(define_expand "cmphf"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HF 0 "reg_operand" "")
|
(compare:CC (match_operand:HF 0 "reg_operand" "")
|
(match_operand:HF 1 "reg_or_const_operand" "")))]
|
(match_operand:HF 1 "reg_or_const_operand" "")))]
|
""
|
""
|
"c4x_compare_op0 = operands[0];
|
"c4x_compare_op0 = operands[0];
|
c4x_compare_op1 = operands[1];
|
c4x_compare_op1 = operands[1];
|
DONE;")
|
DONE;")
|
|
|
(define_insn "*cmphf"
|
(define_insn "*cmphf"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HF 0 "reg_operand" "h")
|
(compare:CC (match_operand:HF 0 "reg_operand" "h")
|
(match_operand:HF 1 "reg_or_const_operand" "hH")))]
|
(match_operand:HF 1 "reg_or_const_operand" "hH")))]
|
""
|
""
|
"cmpf\\t%1,%0"
|
"cmpf\\t%1,%0"
|
[(set_attr "type" "compare")])
|
[(set_attr "type" "compare")])
|
|
|
(define_insn "*cmphf_noov"
|
(define_insn "*cmphf_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:HF 0 "reg_operand" "h")
|
(compare:CC_NOOV (match_operand:HF 0 "reg_operand" "h")
|
(match_operand:HF 1 "reg_or_const_operand" "hH")))]
|
(match_operand:HF 1 "reg_or_const_operand" "hH")))]
|
""
|
""
|
"cmpf\\t%1,%0"
|
"cmpf\\t%1,%0"
|
[(set_attr "type" "compare")])
|
[(set_attr "type" "compare")])
|
|
|
; Inlined float divide for C4x
|
; Inlined float divide for C4x
|
(define_expand "divhf3_inline"
|
(define_expand "divhf3_inline"
|
[(parallel [(set (match_dup 3)
|
[(parallel [(set (match_dup 3)
|
(unspec:HF [(match_operand:HF 2 "reg_operand" "")] UNSPEC_RCPF))
|
(unspec:HF [(match_operand:HF 2 "reg_operand" "")] UNSPEC_RCPF))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
|
(parallel [(set (match_dup 4) (minus:HF (match_dup 5) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
|
(parallel [(set (match_dup 3) (mult:HF (match_dup 3) (match_dup 4)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(mult:HF (match_operand:HF 1 "reg_operand" "")
|
(mult:HF (match_operand:HF 1 "reg_operand" "")
|
(match_dup 3)))
|
(match_dup 3)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"
|
"
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[3] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[4] = gen_reg_rtx (HFmode);
|
operands[5] = CONST2_RTX (HFmode);
|
operands[5] = CONST2_RTX (HFmode);
|
")
|
")
|
|
|
(define_expand "divhf3"
|
(define_expand "divhf3"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(div:HF (match_operand:HF 1 "reg_operand" "")
|
(div:HF (match_operand:HF 1 "reg_operand" "")
|
(match_operand:HF 2 "reg_operand" "")))
|
(match_operand:HF 2 "reg_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"! TARGET_C3X && TARGET_INLINE"
|
"! TARGET_C3X && TARGET_INLINE"
|
"emit_insn (gen_divhf3_inline (operands[0], operands[1], operands[2]));
|
"emit_insn (gen_divhf3_inline (operands[0], operands[1], operands[2]));
|
DONE;")
|
DONE;")
|
|
|
|
|
;
|
;
|
; TWO OPERAND LONG LONG INSTRUCTIONS
|
; TWO OPERAND LONG LONG INSTRUCTIONS
|
;
|
;
|
|
|
(define_insn "*movhi_stik"
|
(define_insn "*movhi_stik"
|
[(set (match_operand:HI 0 "memory_operand" "=m")
|
[(set (match_operand:HI 0 "memory_operand" "=m")
|
(match_operand:HI 1 "stik_const_operand" "K"))]
|
(match_operand:HI 1 "stik_const_operand" "K"))]
|
"! TARGET_C3X"
|
"! TARGET_C3X"
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; We could load some constants using define_splits for the C30
|
; We could load some constants using define_splits for the C30
|
; in the large memory model---these would emit shift and or insns.
|
; in the large memory model---these would emit shift and or insns.
|
(define_expand "movhi"
|
(define_expand "movhi"
|
[(set (match_operand:HI 0 "src_operand" "")
|
[(set (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" ""))]
|
(match_operand:HI 1 "src_operand" ""))]
|
""
|
""
|
"if (c4x_emit_move_sequence (operands, HImode))
|
"if (c4x_emit_move_sequence (operands, HImode))
|
DONE;")
|
DONE;")
|
|
|
; The constraints for movhi must include 'r' if we don't
|
; The constraints for movhi must include 'r' if we don't
|
; restrict HImode regnos to start on an even number, since
|
; restrict HImode regnos to start on an even number, since
|
; we can get RC, R8 allocated as a pair. We want more
|
; we can get RC, R8 allocated as a pair. We want more
|
; votes for FP_REGS so we use dr as the constraints.
|
; votes for FP_REGS so we use dr as the constraints.
|
(define_insn "*movhi_noclobber"
|
(define_insn "*movhi_noclobber"
|
[(set (match_operand:HI 0 "dst_operand" "=dr,m")
|
[(set (match_operand:HI 0 "dst_operand" "=dr,m")
|
(match_operand:HI 1 "src_operand" "drIm,r"))]
|
(match_operand:HI 1 "src_operand" "drIm,r"))]
|
"reg_operand (operands[0], HImode)
|
"reg_operand (operands[0], HImode)
|
|| reg_operand (operands[1], HImode)"
|
|| reg_operand (operands[1], HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi")])
|
[(set_attr "type" "multi,multi")])
|
|
|
; This will fail miserably if the destination register is used in the
|
; This will fail miserably if the destination register is used in the
|
; source memory address.
|
; source memory address.
|
; The usual strategy in this case is to swap the order of insns we emit,
|
; The usual strategy in this case is to swap the order of insns we emit,
|
; however, this will fail if we have an autoincrement memory address.
|
; however, this will fail if we have an autoincrement memory address.
|
; For example:
|
; For example:
|
; ldi *ar0++, ar0
|
; ldi *ar0++, ar0
|
; ldi *ar0++, ar1
|
; ldi *ar0++, ar1
|
;
|
;
|
; We could convert this to
|
; We could convert this to
|
; ldi *ar0(1), ar1
|
; ldi *ar0(1), ar1
|
; ldi *ar0, ar0
|
; ldi *ar0, ar0
|
;
|
;
|
; However, things are likely to be very screwed up if we get this.
|
; However, things are likely to be very screwed up if we get this.
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "dst_operand" "")
|
[(set (match_operand:HI 0 "dst_operand" "")
|
(match_operand:HI 1 "src_operand" ""))]
|
(match_operand:HI 1 "src_operand" ""))]
|
"reload_completed
|
"reload_completed
|
&& (reg_operand (operands[0], HImode)
|
&& (reg_operand (operands[0], HImode)
|
|| reg_operand (operands[1], HImode)
|
|| reg_operand (operands[1], HImode)
|
|| stik_const_operand (operands[1], HImode))"
|
|| stik_const_operand (operands[1], HImode))"
|
[(set (match_dup 2) (match_dup 4))
|
[(set (match_dup 2) (match_dup 4))
|
(set (match_dup 3) (match_dup 5))]
|
(set (match_dup 3) (match_dup 5))]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
if (reg_overlap_mentioned_p (operands[2], operands[5]))
|
if (reg_overlap_mentioned_p (operands[2], operands[5]))
|
{
|
{
|
/* Swap order of move insns. */
|
/* Swap order of move insns. */
|
rtx tmp;
|
rtx tmp;
|
tmp = operands[2];
|
tmp = operands[2];
|
operands[2] =operands[3];
|
operands[2] =operands[3];
|
operands[3] = tmp;
|
operands[3] = tmp;
|
tmp = operands[4];
|
tmp = operands[4];
|
operands[4] =operands[5];
|
operands[4] =operands[5];
|
operands[5] = tmp;
|
operands[5] = tmp;
|
}")
|
}")
|
|
|
|
|
(define_insn "extendqihi2"
|
(define_insn "extendqihi2"
|
[(set (match_operand:HI 0 "reg_operand" "=dc")
|
[(set (match_operand:HI 0 "reg_operand" "=dc")
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "")))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed && TARGET_C3X"
|
"reload_completed && TARGET_C3X"
|
[(set (match_dup 2) (match_dup 1))
|
[(set (match_dup 2) (match_dup 1))
|
(set (match_dup 3) (match_dup 2))
|
(set (match_dup 3) (match_dup 2))
|
(parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 3) (const_int 31)))
|
(parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 3) (const_int 31)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "")))
|
(sign_extend:HI (match_operand:QI 1 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed && ! TARGET_C3X"
|
"reload_completed && ! TARGET_C3X"
|
[(set (match_dup 2) (match_dup 1))
|
[(set (match_dup 2) (match_dup 1))
|
(parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 2) (const_int 31)))
|
(parallel [(set (match_dup 3) (ashiftrt:QI (match_dup 2) (const_int 31)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
|
|
(define_insn "zero_extendqihi2"
|
(define_insn "zero_extendqihi2"
|
[(set (match_operand:HI 0 "reg_operand" "=?dc")
|
[(set (match_operand:HI 0 "reg_operand" "=?dc")
|
(zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "rm")))
|
(zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "rm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; If operand0 and operand1 are the same register we don't need
|
; If operand0 and operand1 are the same register we don't need
|
; the first set.
|
; the first set.
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "")))
|
(zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 2) (match_dup 1))
|
[(set (match_dup 2) (match_dup 1))
|
(set (match_dup 3) (const_int 0))]
|
(set (match_dup 3) (const_int 0))]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
|
|
;
|
;
|
; PUSH/POP
|
; PUSH/POP
|
;
|
;
|
(define_insn "*pushhi"
|
(define_insn "*pushhi"
|
[(set (mem:HI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:HI (pre_inc:QI (reg:QI 20)))
|
(match_operand:HI 0 "reg_operand" "r"))]
|
(match_operand:HI 0 "reg_operand" "r"))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (mem:HI (pre_inc:QI (reg:QI 20)))
|
[(set (mem:HI (pre_inc:QI (reg:QI 20)))
|
(match_operand:HI 0 "reg_operand" ""))]
|
(match_operand:HI 0 "reg_operand" ""))]
|
"reload_completed"
|
"reload_completed"
|
[(set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 2))
|
[(set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 2))
|
(set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 3))]
|
(set (mem:QI (pre_inc:QI (reg:QI 20))) (match_dup 3))]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
|
|
(define_insn "*pophi"
|
(define_insn "*pophi"
|
[(set (match_operand:HI 0 "reg_operand" "=r")
|
[(set (match_operand:HI 0 "reg_operand" "=r")
|
(mem:HI (post_dec:QI (reg:QI 20))))
|
(mem:HI (post_dec:QI (reg:QI 20))))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(mem:HI (pre_inc:QI (reg:QI 20))))]
|
(mem:HI (pre_inc:QI (reg:QI 20))))]
|
"reload_completed"
|
"reload_completed"
|
[(set (match_dup 2) (mem:QI (pre_inc:QI (reg:QI 20))))
|
[(set (match_dup 2) (mem:QI (pre_inc:QI (reg:QI 20))))
|
(set (match_dup 3) (mem:QI (pre_inc:QI (reg:QI 20))))]
|
(set (match_dup 3) (mem:QI (pre_inc:QI (reg:QI 20))))]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 0, HImode);
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
|
|
|
;
|
;
|
; NEG
|
; NEG
|
;
|
;
|
(define_insn "neghi2"
|
(define_insn "neghi2"
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d")
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d")
|
(neg:HI (match_operand:HI 1 "src_operand" "rm")))
|
(neg:HI (match_operand:HI 1 "src_operand" "rm")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
(neg:HI (match_operand:HI 1 "src_operand" "")))
|
(neg:HI (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (reg:CC_NOOV 21)
|
[(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (neg:QI (match_dup 3))
|
(compare:CC_NOOV (neg:QI (match_dup 3))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_dup 2) (neg:QI (match_dup 3)))])
|
(set (match_dup 2) (neg:QI (match_dup 3)))])
|
(parallel [(set (match_dup 4) (neg:QI (match_dup 5)))
|
(parallel [(set (match_dup 4) (neg:QI (match_dup 5)))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
|
|
|
(define_insn "one_cmplhi2"
|
(define_insn "one_cmplhi2"
|
[(set (match_operand:HI 0 "reg_operand" "=r")
|
[(set (match_operand:HI 0 "reg_operand" "=r")
|
(not:HI (match_operand:HI 1 "src_operand" "rm")))
|
(not:HI (match_operand:HI 1 "src_operand" "rm")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
""
|
""
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(not:HI (match_operand:HI 1 "src_operand" "")))
|
(not:HI (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (match_dup 2) (not:QI (match_dup 3)))
|
[(parallel [(set (match_dup 2) (not:QI (match_dup 3)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 4) (not:QI (match_dup 5)))
|
(parallel [(set (match_dup 4) (not:QI (match_dup 5)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[2] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[3] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
|
operands[5] = c4x_operand_subword (operands[1], 1, 1, HImode);")
|
|
|
(define_expand "floathiqf2"
|
(define_expand "floathiqf2"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(float:QF (match_operand:HI 1 "src_operand" "")))
|
(float:QF (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (floathiqf2_libfunc, FLOAT, QFmode, HImode, 2, operands);
|
"c4x_emit_libcall (floathiqf2_libfunc, FLOAT, QFmode, HImode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
(define_expand "floatunshiqf2"
|
(define_expand "floatunshiqf2"
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "reg_operand" "")
|
(unsigned_float:QF (match_operand:HI 1 "src_operand" "")))
|
(unsigned_float:QF (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (floatunshiqf2_libfunc, UNSIGNED_FLOAT,
|
"c4x_emit_libcall (floatunshiqf2_libfunc, UNSIGNED_FLOAT,
|
QFmode, HImode, 2, operands);
|
QFmode, HImode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
(define_expand "floathihf2"
|
(define_expand "floathihf2"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(float:HF (match_operand:HI 1 "src_operand" "")))
|
(float:HF (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (floathihf2_libfunc, FLOAT, HFmode, HImode, 2, operands);
|
"c4x_emit_libcall (floathihf2_libfunc, FLOAT, HFmode, HImode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
(define_expand "floatunshihf2"
|
(define_expand "floatunshihf2"
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HF 0 "reg_operand" "")
|
(unsigned_float:HF (match_operand:HI 1 "src_operand" "")))
|
(unsigned_float:HF (match_operand:HI 1 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall (floatunshihf2_libfunc, UNSIGNED_FLOAT,
|
"c4x_emit_libcall (floatunshihf2_libfunc, UNSIGNED_FLOAT,
|
HFmode, HImode, 2, operands);
|
HFmode, HImode, 2, operands);
|
DONE;")
|
DONE;")
|
|
|
|
|
;
|
;
|
; THREE OPERAND LONG LONG INSTRUCTIONS
|
; THREE OPERAND LONG LONG INSTRUCTIONS
|
;
|
;
|
|
|
(define_expand "addhi3"
|
(define_expand "addhi3"
|
[(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
|
(plus:HI (match_operand:HI 1 "src_operand" "")
|
(plus:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (PLUS, operands, HImode);")
|
"legitimize_operands (PLUS, operands, HImode);")
|
|
|
(define_insn "*addhi3_clobber"
|
(define_insn "*addhi3_clobber"
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
|
(plus:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(plus:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (PLUS, operands, HImode)"
|
"valid_operands (PLUS, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi,multi")])
|
[(set_attr "type" "multi,multi,multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
(plus:HI (match_operand:HI 1 "src_operand" "")
|
(plus:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (reg:CC_NOOV 21)
|
[(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (plus:QI (match_dup 4) (match_dup 5))
|
(compare:CC_NOOV (plus:QI (match_dup 4) (match_dup 5))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_dup 3) (plus:QI (match_dup 4) (match_dup 5)))])
|
(set (match_dup 3) (plus:QI (match_dup 4) (match_dup 5)))])
|
(parallel [(set (match_dup 6) (plus:QI (match_dup 7) (match_dup 8)))
|
(parallel [(set (match_dup 6) (plus:QI (match_dup 7) (match_dup 8)))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
|
|
(define_expand "subhi3"
|
(define_expand "subhi3"
|
[(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "ext_reg_operand" "")
|
(minus:HI (match_operand:HI 1 "src_operand" "")
|
(minus:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"legitimize_operands (MINUS, operands, HImode);")
|
"legitimize_operands (MINUS, operands, HImode);")
|
|
|
|
|
(define_insn "*subhi3_clobber"
|
(define_insn "*subhi3_clobber"
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
|
[(set (match_operand:HI 0 "ext_reg_operand" "=d,d,?d")
|
(minus:HI (match_operand:HI 1 "src_operand" "0,rR,rS<>")
|
(minus:HI (match_operand:HI 1 "src_operand" "0,rR,rS<>")
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"valid_operands (MINUS, operands, HImode)"
|
"valid_operands (MINUS, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi,multi")])
|
[(set_attr "type" "multi,multi,multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
[(set (match_operand:HI 0 "ext_reg_operand" "")
|
(minus:HI (match_operand:HI 1 "src_operand" "")
|
(minus:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC_NOOV 21))]
|
(clobber (reg:CC_NOOV 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (reg:CC_NOOV 21)
|
[(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (minus:QI (match_dup 4) (match_dup 5))
|
(compare:CC_NOOV (minus:QI (match_dup 4) (match_dup 5))
|
(const_int 0)))
|
(const_int 0)))
|
(set (match_dup 3) (minus:QI (match_dup 4) (match_dup 5)))])
|
(set (match_dup 3) (minus:QI (match_dup 4) (match_dup 5)))])
|
(parallel [(set (match_dup 6) (minus:QI (match_dup 7) (match_dup 8)))
|
(parallel [(set (match_dup 6) (minus:QI (match_dup 7) (match_dup 8)))
|
(use (reg:CC_NOOV 21))
|
(use (reg:CC_NOOV 21))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
|
|
(define_expand "iorhi3"
|
(define_expand "iorhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(ior:HI (match_operand:HI 1 "src_operand" "")
|
(ior:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (IOR, operands, HImode);")
|
"legitimize_operands (IOR, operands, HImode);")
|
|
|
(define_insn "*iorhi3_clobber"
|
(define_insn "*iorhi3_clobber"
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
(ior:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(ior:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (IOR, operands, HImode)"
|
"valid_operands (IOR, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi,multi")])
|
[(set_attr "type" "multi,multi,multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(ior:HI (match_operand:HI 1 "src_operand" "")
|
(ior:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (match_dup 3) (ior:QI (match_dup 4) (match_dup 5)))
|
[(parallel [(set (match_dup 3) (ior:QI (match_dup 4) (match_dup 5)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 6) (ior:QI (match_dup 7) (match_dup 8)))
|
(parallel [(set (match_dup 6) (ior:QI (match_dup 7) (match_dup 8)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
|
|
(define_expand "andhi3"
|
(define_expand "andhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(and:HI (match_operand:HI 1 "src_operand" "")
|
(and:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (AND, operands, HImode);")
|
"legitimize_operands (AND, operands, HImode);")
|
|
|
(define_insn "*andhi3_clobber"
|
(define_insn "*andhi3_clobber"
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
(and:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(and:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (AND, operands, HImode)"
|
"valid_operands (AND, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi,multi")])
|
[(set_attr "type" "multi,multi,multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(and:HI (match_operand:HI 1 "src_operand" "")
|
(and:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (match_dup 3) (and:QI (match_dup 4) (match_dup 5)))
|
[(parallel [(set (match_dup 3) (and:QI (match_dup 4) (match_dup 5)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 6) (and:QI (match_dup 7) (match_dup 8)))
|
(parallel [(set (match_dup 6) (and:QI (match_dup 7) (match_dup 8)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
|
|
(define_expand "xorhi3"
|
(define_expand "xorhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(xor:HI (match_operand:HI 1 "src_operand" "")
|
(xor:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"legitimize_operands (XOR, operands, HImode);")
|
"legitimize_operands (XOR, operands, HImode);")
|
|
|
|
|
(define_insn "*xorhi3_clobber"
|
(define_insn "*xorhi3_clobber"
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
[(set (match_operand:HI 0 "reg_operand" "=d,d,?d")
|
(xor:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(xor:HI (match_operand:HI 1 "src_operand" "%0,rR,rS<>")
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(match_operand:HI 2 "src_operand" "rm,R,rS<>")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"valid_operands (XOR, operands, HImode)"
|
"valid_operands (XOR, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi,multi,multi")])
|
[(set_attr "type" "multi,multi,multi")])
|
|
|
(define_split
|
(define_split
|
[(set (match_operand:HI 0 "reg_operand" "")
|
[(set (match_operand:HI 0 "reg_operand" "")
|
(xor:HI (match_operand:HI 1 "src_operand" "")
|
(xor:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))]
|
(clobber (reg:CC 21))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (match_dup 3) (xor:QI (match_dup 4) (match_dup 5)))
|
[(parallel [(set (match_dup 3) (xor:QI (match_dup 4) (match_dup 5)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 6) (xor:QI (match_dup 7) (match_dup 8)))
|
(parallel [(set (match_dup 6) (xor:QI (match_dup 7) (match_dup 8)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
"operands[3] = c4x_operand_subword (operands[0], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[4] = c4x_operand_subword (operands[1], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[5] = c4x_operand_subword (operands[2], 0, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[6] = c4x_operand_subword (operands[0], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[7] = c4x_operand_subword (operands[1], 1, 1, HImode);
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
operands[8] = c4x_operand_subword (operands[2], 1, 1, HImode);")
|
|
|
(define_expand "ashlhi3"
|
(define_expand "ashlhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(ashift:HI (match_operand:HI 1 "src_operand" "")
|
(ashift:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
{
|
{
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op1lo = operand_subword (operands[1], 0, 0, HImode);
|
rtx op1lo = operand_subword (operands[1], 0, 0, HImode);
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
|
|
if (INTVAL (count))
|
if (INTVAL (count))
|
emit_insn (gen_ashlqi3 (op0hi, op1lo, count));
|
emit_insn (gen_ashlqi3 (op0hi, op1lo, count));
|
else
|
else
|
emit_insn (gen_movqi (op0hi, op1lo));
|
emit_insn (gen_movqi (op0hi, op1lo));
|
emit_insn (gen_movqi (op0lo, const0_rtx));
|
emit_insn (gen_movqi (op0lo, const0_rtx));
|
DONE;
|
DONE;
|
}
|
}
|
if (! REG_P (operands[1]))
|
if (! REG_P (operands[1]))
|
operands[1] = force_reg (HImode, operands[1]);
|
operands[1] = force_reg (HImode, operands[1]);
|
emit_insn (gen_ashlhi3_reg (operands[0], operands[1], operands[2]));
|
emit_insn (gen_ashlhi3_reg (operands[0], operands[1], operands[2]));
|
DONE;
|
DONE;
|
")
|
")
|
|
|
; %0.lo = %1.lo << %2
|
; %0.lo = %1.lo << %2
|
; %0.hi = (%1.hi << %2 ) | (%1.lo >> (32 - %2))
|
; %0.hi = (%1.hi << %2 ) | (%1.lo >> (32 - %2))
|
; This algorithm should work for shift counts greater than 32
|
; This algorithm should work for shift counts greater than 32
|
(define_expand "ashlhi3_reg"
|
(define_expand "ashlhi3_reg"
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 7)
|
(parallel [(set (match_dup 7)
|
(ashift:QI (match_dup 3)
|
(ashift:QI (match_dup 3)
|
(match_operand:QI 2 "reg_operand" "")))
|
(match_operand:QI 2 "reg_operand" "")))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 8)
|
(parallel [(set (match_dup 8)
|
(ashift:QI (match_dup 4) (match_dup 2)))
|
(ashift:QI (match_dup 4) (match_dup 2)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 10)
|
(parallel [(set (match_dup 10)
|
(plus:QI (match_dup 2) (const_int -32)))
|
(plus:QI (match_dup 2) (const_int -32)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
/* If the shift count is greater than 32 this will do a left shift. */
|
/* If the shift count is greater than 32 this will do a left shift. */
|
(parallel [(set (match_dup 9)
|
(parallel [(set (match_dup 9)
|
(lshiftrt:QI (match_dup 3) (neg:QI (match_dup 10))))
|
(lshiftrt:QI (match_dup 3) (neg:QI (match_dup 10))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (match_dup 5) (match_dup 7))
|
(set (match_dup 5) (match_dup 7))
|
(parallel [(set (match_dup 6)
|
(parallel [(set (match_dup 6)
|
(ior:QI (match_dup 8) (match_dup 9)))
|
(ior:QI (match_dup 8) (match_dup 9)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"
|
"
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[7] = gen_reg_rtx (QImode); /* lo << count */
|
operands[7] = gen_reg_rtx (QImode); /* lo << count */
|
operands[8] = gen_reg_rtx (QImode); /* hi << count */
|
operands[8] = gen_reg_rtx (QImode); /* hi << count */
|
operands[9] = gen_reg_rtx (QImode); /* lo >> (32 - count) */
|
operands[9] = gen_reg_rtx (QImode); /* lo >> (32 - count) */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
")
|
")
|
|
|
; This should do all the dirty work with define_split
|
; This should do all the dirty work with define_split
|
(define_expand "lshrhi3"
|
(define_expand "lshrhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(lshiftrt:HI (match_operand:HI 1 "src_operand" "")
|
(lshiftrt:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
{
|
{
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
|
rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
|
|
if (INTVAL (count))
|
if (INTVAL (count))
|
emit_insn (gen_lshrqi3 (op0lo, op1hi, count));
|
emit_insn (gen_lshrqi3 (op0lo, op1hi, count));
|
else
|
else
|
emit_insn (gen_movqi (op0lo, op1hi));
|
emit_insn (gen_movqi (op0lo, op1hi));
|
emit_insn (gen_movqi (op0hi, const0_rtx));
|
emit_insn (gen_movqi (op0hi, const0_rtx));
|
DONE;
|
DONE;
|
}
|
}
|
if (! REG_P (operands[1]))
|
if (! REG_P (operands[1]))
|
operands[1] = force_reg (HImode, operands[1]);
|
operands[1] = force_reg (HImode, operands[1]);
|
emit_insn (gen_lshrhi3_reg (operands[0], operands[1], operands[2]));
|
emit_insn (gen_lshrhi3_reg (operands[0], operands[1], operands[2]));
|
DONE;")
|
DONE;")
|
|
|
; %0.hi = %1.hi >> %2
|
; %0.hi = %1.hi >> %2
|
; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
|
; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
|
; This algorithm should work for shift counts greater than 32
|
; This algorithm should work for shift counts greater than 32
|
(define_expand "lshrhi3_reg"
|
(define_expand "lshrhi3_reg"
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
(parallel [(set (match_dup 11)
|
(parallel [(set (match_dup 11)
|
(neg:QI (match_operand:QI 2 "reg_operand" "")))
|
(neg:QI (match_operand:QI 2 "reg_operand" "")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 7)
|
(parallel [(set (match_dup 7)
|
(lshiftrt:QI (match_dup 3)
|
(lshiftrt:QI (match_dup 3)
|
(neg:QI (match_dup 11))))
|
(neg:QI (match_dup 11))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 8)
|
(parallel [(set (match_dup 8)
|
(lshiftrt:QI (match_dup 4)
|
(lshiftrt:QI (match_dup 4)
|
(neg:QI (match_dup 11))))
|
(neg:QI (match_dup 11))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 10)
|
(parallel [(set (match_dup 10)
|
(plus:QI (match_dup 11) (const_int 32)))
|
(plus:QI (match_dup 11) (const_int 32)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
/* If the shift count is greater than 32 this will do an arithmetic
|
/* If the shift count is greater than 32 this will do an arithmetic
|
right shift. However, we need a logical right shift. */
|
right shift. However, we need a logical right shift. */
|
(parallel [(set (match_dup 9)
|
(parallel [(set (match_dup 9)
|
(ashift:QI (match_dup 4) (unspec:QI [(match_dup 10)] UNSPEC_LSH)))
|
(ashift:QI (match_dup 4) (unspec:QI [(match_dup 10)] UNSPEC_LSH)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (match_dup 6) (match_dup 8))
|
(set (match_dup 6) (match_dup 8))
|
(parallel [(set (match_dup 5)
|
(parallel [(set (match_dup 5)
|
(ior:QI (match_dup 7) (match_dup 9)))
|
(ior:QI (match_dup 7) (match_dup 9)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"
|
"
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[7] = gen_reg_rtx (QImode); /* lo >> count */
|
operands[7] = gen_reg_rtx (QImode); /* lo >> count */
|
operands[8] = gen_reg_rtx (QImode); /* hi >> count */
|
operands[8] = gen_reg_rtx (QImode); /* hi >> count */
|
operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
|
operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
operands[11] = gen_reg_rtx (QImode); /* -count */
|
operands[11] = gen_reg_rtx (QImode); /* -count */
|
")
|
")
|
|
|
; This should do all the dirty work with define_split
|
; This should do all the dirty work with define_split
|
(define_expand "ashrhi3"
|
(define_expand "ashrhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(ashiftrt:HI (match_operand:HI 1 "src_operand" "")
|
(ashiftrt:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:QI 2 "src_operand" "")))
|
(match_operand:QI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
"if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32)
|
{
|
{
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0hi = operand_subword (operands[0], 1, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op0lo = operand_subword (operands[0], 0, 0, HImode);
|
rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
|
rtx op1hi = operand_subword (operands[1], 1, 0, HImode);
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
rtx count = GEN_INT ((INTVAL (operands[2]) - 32));
|
|
|
if (INTVAL (count))
|
if (INTVAL (count))
|
emit_insn (gen_ashrqi3 (op0lo, op1hi, count));
|
emit_insn (gen_ashrqi3 (op0lo, op1hi, count));
|
else
|
else
|
emit_insn (gen_movqi (op0lo, op1hi));
|
emit_insn (gen_movqi (op0lo, op1hi));
|
emit_insn (gen_ashrqi3 (op0hi, op1hi, GEN_INT (31)));
|
emit_insn (gen_ashrqi3 (op0hi, op1hi, GEN_INT (31)));
|
DONE;
|
DONE;
|
}
|
}
|
if (! REG_P (operands[1]))
|
if (! REG_P (operands[1]))
|
operands[1] = force_reg (HImode, operands[1]);
|
operands[1] = force_reg (HImode, operands[1]);
|
emit_insn (gen_ashrhi3_reg (operands[0], operands[1], operands[2]));
|
emit_insn (gen_ashrhi3_reg (operands[0], operands[1], operands[2]));
|
DONE;")
|
DONE;")
|
|
|
; %0.hi = %1.hi >> %2
|
; %0.hi = %1.hi >> %2
|
; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
|
; %0.lo = (%1.lo >> %2 ) | (%1.hi << (32 - %2))
|
; This algorithm should work for shift counts greater than 32
|
; This algorithm should work for shift counts greater than 32
|
(define_expand "ashrhi3_reg"
|
(define_expand "ashrhi3_reg"
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
[(use (match_operand:HI 1 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
(use (match_operand:HI 0 "reg_operand" ""))
|
(parallel [(set (match_dup 11)
|
(parallel [(set (match_dup 11)
|
(neg:QI (match_operand:QI 2 "reg_operand" "")))
|
(neg:QI (match_operand:QI 2 "reg_operand" "")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 7)
|
(parallel [(set (match_dup 7)
|
(lshiftrt:QI (match_dup 3)
|
(lshiftrt:QI (match_dup 3)
|
(neg:QI (match_dup 11))))
|
(neg:QI (match_dup 11))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
/* If the shift count is greater than 32 this will give zero. */
|
/* If the shift count is greater than 32 this will give zero. */
|
(parallel [(set (match_dup 8)
|
(parallel [(set (match_dup 8)
|
(ashiftrt:QI (match_dup 4)
|
(ashiftrt:QI (match_dup 4)
|
(neg:QI (match_dup 11))))
|
(neg:QI (match_dup 11))))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(parallel [(set (match_dup 10)
|
(parallel [(set (match_dup 10)
|
(plus:QI (match_dup 11) (const_int 32)))
|
(plus:QI (match_dup 11) (const_int 32)))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
/* If the shift count is greater than 32 this will do an arithmetic
|
/* If the shift count is greater than 32 this will do an arithmetic
|
right shift. */
|
right shift. */
|
(parallel [(set (match_dup 9)
|
(parallel [(set (match_dup 9)
|
(ashift:QI (match_dup 4) (match_dup 10)))
|
(ashift:QI (match_dup 4) (match_dup 10)))
|
(clobber (reg:CC 21))])
|
(clobber (reg:CC 21))])
|
(set (match_dup 6) (match_dup 8))
|
(set (match_dup 6) (match_dup 8))
|
(parallel [(set (match_dup 5)
|
(parallel [(set (match_dup 5)
|
(ior:QI (match_dup 7) (match_dup 9)))
|
(ior:QI (match_dup 7) (match_dup 9)))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"
|
"
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[3] = operand_subword (operands[1], 0, 1, HImode); /* lo */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[4] = operand_subword (operands[1], 1, 1, HImode); /* hi */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[5] = operand_subword (operands[0], 0, 1, HImode); /* lo */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[6] = operand_subword (operands[0], 1, 1, HImode); /* hi */
|
operands[7] = gen_reg_rtx (QImode); /* lo >> count */
|
operands[7] = gen_reg_rtx (QImode); /* lo >> count */
|
operands[8] = gen_reg_rtx (QImode); /* hi >> count */
|
operands[8] = gen_reg_rtx (QImode); /* hi >> count */
|
operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
|
operands[9] = gen_reg_rtx (QImode); /* hi << (32 - count) */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
operands[10] = gen_reg_rtx (QImode); /* 32 - count */
|
operands[11] = gen_reg_rtx (QImode); /* -count */
|
operands[11] = gen_reg_rtx (QImode); /* -count */
|
")
|
")
|
|
|
(define_expand "cmphi"
|
(define_expand "cmphi"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" "")))]
|
(match_operand:HI 1 "src_operand" "")))]
|
""
|
""
|
"legitimize_operands (COMPARE, operands, HImode);
|
"legitimize_operands (COMPARE, operands, HImode);
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op0 = operands[0];
|
c4x_compare_op1 = operands[1];
|
c4x_compare_op1 = operands[1];
|
DONE;")
|
DONE;")
|
|
|
(define_insn "*cmphi_cc"
|
(define_insn "*cmphi_cc"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>")))]
|
(match_operand:HI 1 "src_operand" "R,rS<>")))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_insn "*cmphi_cc_noov"
|
(define_insn "*cmphi_cc_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>")))]
|
(match_operand:HI 1 "src_operand" "R,rS<>")))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"#"
|
"#"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
; This works only before reload because we need 2 extra registers.
|
; This works only before reload because we need 2 extra registers.
|
; Use unspec to avoid recursive split.
|
; Use unspec to avoid recursive split.
|
(define_split
|
(define_split
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" "")))]
|
(match_operand:HI 1 "src_operand" "")))]
|
"! reload_completed"
|
"! reload_completed"
|
[(parallel [(set (reg:CC 21)
|
[(parallel [(set (reg:CC 21)
|
(unspec:CC [(compare:CC (match_dup 0)
|
(unspec:CC [(compare:CC (match_dup 0)
|
(match_dup 1))] UNSPEC_CMPHI))
|
(match_dup 1))] UNSPEC_CMPHI))
|
(clobber (match_scratch:QI 2 ""))
|
(clobber (match_scratch:QI 2 ""))
|
(clobber (match_scratch:QI 3 ""))])]
|
(clobber (match_scratch:QI 3 ""))])]
|
"")
|
"")
|
|
|
(define_split
|
(define_split
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" "")))]
|
(match_operand:HI 1 "src_operand" "")))]
|
"! reload_completed"
|
"! reload_completed"
|
[(parallel [(set (reg:CC_NOOV 21)
|
[(parallel [(set (reg:CC_NOOV 21)
|
(unspec:CC_NOOV [(compare:CC_NOOV (match_dup 0)
|
(unspec:CC_NOOV [(compare:CC_NOOV (match_dup 0)
|
(match_dup 1))] UNSPEC_CMPHI))
|
(match_dup 1))] UNSPEC_CMPHI))
|
(clobber (match_scratch:QI 2 ""))
|
(clobber (match_scratch:QI 2 ""))
|
(clobber (match_scratch:QI 3 ""))])]
|
(clobber (match_scratch:QI 3 ""))])]
|
"")
|
"")
|
|
|
; This is normally not used. The define splits above are used first.
|
; This is normally not used. The define splits above are used first.
|
(define_split
|
(define_split
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(compare:CC (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" "")))]
|
(match_operand:HI 1 "src_operand" "")))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (reg:CC 21)
|
[(parallel [(set (reg:CC 21)
|
(compare:CC (match_dup 0) (match_dup 1)))
|
(compare:CC (match_dup 0) (match_dup 1)))
|
(use (reg:QI 20))])]
|
(use (reg:QI 20))])]
|
"")
|
"")
|
|
|
(define_split
|
(define_split
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "")
|
(match_operand:HI 1 "src_operand" "")))]
|
(match_operand:HI 1 "src_operand" "")))]
|
"reload_completed"
|
"reload_completed"
|
[(parallel [(set (reg:CC_NOOV 21)
|
[(parallel [(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_dup 0) (match_dup 1)))
|
(compare:CC_NOOV (match_dup 0) (match_dup 1)))
|
(use (reg:QI 20))])]
|
(use (reg:QI 20))])]
|
"")
|
"")
|
|
|
(define_insn "*cmphi"
|
(define_insn "*cmphi"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>")))
|
(match_operand:HI 1 "src_operand" "R,rS<>")))
|
(use (reg:QI 20))]
|
(use (reg:QI 20))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"*
|
"*
|
{
|
{
|
int use_ir1 = (reg_operand (operands[0], HImode)
|
int use_ir1 = (reg_operand (operands[0], HImode)
|
&& REG_P (operands[0])
|
&& REG_P (operands[0])
|
&& REGNO (operands[0]) == IR1_REGNO)
|
&& REGNO (operands[0]) == IR1_REGNO)
|
|| (reg_operand (operands[1], HImode)
|
|| (reg_operand (operands[1], HImode)
|
&& REG_P (operands[1])
|
&& REG_P (operands[1])
|
&& REGNO (operands[1]) == IR1_REGNO);
|
&& REGNO (operands[1]) == IR1_REGNO);
|
|
|
if (use_ir1)
|
if (use_ir1)
|
output_asm_insn (\"push\\tir1\", operands);
|
output_asm_insn (\"push\\tir1\", operands);
|
else
|
else
|
output_asm_insn (\"push\\tbk\", operands);
|
output_asm_insn (\"push\\tbk\", operands);
|
output_asm_insn (\"push\\tr0\", operands);
|
output_asm_insn (\"push\\tr0\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
{
|
{
|
output_asm_insn (\"ldiu\\tst,ir1\", operands);
|
output_asm_insn (\"ldiu\\tst,ir1\", operands);
|
output_asm_insn (\"or\\t07bh,ir1\", operands);
|
output_asm_insn (\"or\\t07bh,ir1\", operands);
|
}
|
}
|
else
|
else
|
{
|
{
|
output_asm_insn (\"ldiu\\tst,bk\", operands);
|
output_asm_insn (\"ldiu\\tst,bk\", operands);
|
output_asm_insn (\"or\\t07bh,bk\", operands);
|
output_asm_insn (\"or\\t07bh,bk\", operands);
|
}
|
}
|
output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
output_asm_insn (\"and3\\tir1,st,ir1\", operands);
|
output_asm_insn (\"and3\\tir1,st,ir1\", operands);
|
else
|
else
|
output_asm_insn (\"and3\\tbk,st,bk\", operands);
|
output_asm_insn (\"and3\\tbk,st,bk\", operands);
|
output_asm_insn (\"pop\\tr0\", operands);
|
output_asm_insn (\"pop\\tr0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
{
|
{
|
output_asm_insn (\"ldiu\\tir1,st\", operands);
|
output_asm_insn (\"ldiu\\tir1,st\", operands);
|
output_asm_insn (\"pop\\tir1\", operands);
|
output_asm_insn (\"pop\\tir1\", operands);
|
}
|
}
|
else
|
else
|
{
|
{
|
output_asm_insn (\"ldiu\\tbk,st\", operands);
|
output_asm_insn (\"ldiu\\tbk,st\", operands);
|
output_asm_insn (\"pop\\tbk\", operands);
|
output_asm_insn (\"pop\\tbk\", operands);
|
}
|
}
|
return \"\";
|
return \"\";
|
}"
|
}"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_insn "*cmphi_noov"
|
(define_insn "*cmphi_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>")))
|
(match_operand:HI 1 "src_operand" "R,rS<>")))
|
(use (reg:QI 20))]
|
(use (reg:QI 20))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"*
|
"*
|
{
|
{
|
int use_ir1 = (reg_operand (operands[0], HImode)
|
int use_ir1 = (reg_operand (operands[0], HImode)
|
&& REG_P (operands[0])
|
&& REG_P (operands[0])
|
&& REGNO (operands[0]) == IR1_REGNO)
|
&& REGNO (operands[0]) == IR1_REGNO)
|
|| (reg_operand (operands[1], HImode)
|
|| (reg_operand (operands[1], HImode)
|
&& REG_P (operands[1])
|
&& REG_P (operands[1])
|
&& REGNO (operands[1]) == IR1_REGNO);
|
&& REGNO (operands[1]) == IR1_REGNO);
|
|
|
if (use_ir1)
|
if (use_ir1)
|
output_asm_insn (\"push\\tir1\", operands);
|
output_asm_insn (\"push\\tir1\", operands);
|
else
|
else
|
output_asm_insn (\"push\\tbk\", operands);
|
output_asm_insn (\"push\\tbk\", operands);
|
output_asm_insn (\"push\\tr0\", operands);
|
output_asm_insn (\"push\\tr0\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,r0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
{
|
{
|
output_asm_insn (\"ldiu\\tst,ir1\", operands);
|
output_asm_insn (\"ldiu\\tst,ir1\", operands);
|
output_asm_insn (\"or\\t07bh,ir1\", operands);
|
output_asm_insn (\"or\\t07bh,ir1\", operands);
|
}
|
}
|
else
|
else
|
{
|
{
|
output_asm_insn (\"ldiu\\tst,bk\", operands);
|
output_asm_insn (\"ldiu\\tst,bk\", operands);
|
output_asm_insn (\"or\\t07bh,bk\", operands);
|
output_asm_insn (\"or\\t07bh,bk\", operands);
|
}
|
}
|
output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,r0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
output_asm_insn (\"and3\\tir1,st,ir1\", operands);
|
output_asm_insn (\"and3\\tir1,st,ir1\", operands);
|
else
|
else
|
output_asm_insn (\"and3\\tbk,st,bk\", operands);
|
output_asm_insn (\"and3\\tbk,st,bk\", operands);
|
output_asm_insn (\"pop\\tr0\", operands);
|
output_asm_insn (\"pop\\tr0\", operands);
|
if (use_ir1)
|
if (use_ir1)
|
{
|
{
|
output_asm_insn (\"ldiu\\tir1,st\", operands);
|
output_asm_insn (\"ldiu\\tir1,st\", operands);
|
output_asm_insn (\"pop\\tir1\", operands);
|
output_asm_insn (\"pop\\tir1\", operands);
|
}
|
}
|
else
|
else
|
{
|
{
|
output_asm_insn (\"ldiu\\tbk,st\", operands);
|
output_asm_insn (\"ldiu\\tbk,st\", operands);
|
output_asm_insn (\"pop\\tbk\", operands);
|
output_asm_insn (\"pop\\tbk\", operands);
|
}
|
}
|
return \"\";
|
return \"\";
|
}"
|
}"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
|
|
(define_insn "cmphi_cc"
|
(define_insn "cmphi_cc"
|
[(set (reg:CC 21)
|
[(set (reg:CC 21)
|
(unspec:CC [(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(unspec:CC [(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
|
(match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
|
(clobber (match_scratch:QI 2 "=&d,&d"))
|
(clobber (match_scratch:QI 2 "=&d,&d"))
|
(clobber (match_scratch:QI 3 "=&c,&c"))]
|
(clobber (match_scratch:QI 3 "=&c,&c"))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"*
|
"*
|
output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
|
output_asm_insn (\"ldiu\\tst,%3\", operands);
|
output_asm_insn (\"ldiu\\tst,%3\", operands);
|
output_asm_insn (\"or\\t07bh,%3\", operands);
|
output_asm_insn (\"or\\t07bh,%3\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
|
output_asm_insn (\"and\\t%3,st\", operands);
|
output_asm_insn (\"and\\t%3,st\", operands);
|
return \"\";"
|
return \"\";"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_insn "cmphi_cc_noov"
|
(define_insn "cmphi_cc_noov"
|
[(set (reg:CC_NOOV 21)
|
[(set (reg:CC_NOOV 21)
|
(unspec:CC_NOOV [(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(unspec:CC_NOOV [(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
|
(match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
|
(match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
|
(clobber (match_scratch:QI 2 "=&d,&d"))
|
(clobber (match_scratch:QI 2 "=&d,&d"))
|
(clobber (match_scratch:QI 3 "=&c,&c"))]
|
(clobber (match_scratch:QI 3 "=&c,&c"))]
|
"valid_operands (COMPARE, operands, HImode)"
|
"valid_operands (COMPARE, operands, HImode)"
|
"*
|
"*
|
output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
|
output_asm_insn (\"subi3\\t%1,%0,%2\", operands);
|
output_asm_insn (\"ldiu\\tst,%3\", operands);
|
output_asm_insn (\"ldiu\\tst,%3\", operands);
|
output_asm_insn (\"or\\t07bh,%3\", operands);
|
output_asm_insn (\"or\\t07bh,%3\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
|
output_asm_insn (\"subb3\\t%O1,%O0,%2\", operands);
|
output_asm_insn (\"and\\t%3,st\", operands);
|
output_asm_insn (\"and\\t%3,st\", operands);
|
return \"\";"
|
return \"\";"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_expand "mulhi3"
|
(define_expand "mulhi3"
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:HI 0 "reg_operand" "")
|
(mult:HI (match_operand:HI 1 "src_operand" "")
|
(mult:HI (match_operand:HI 1 "src_operand" "")
|
(match_operand:HI 2 "src_operand" "")))
|
(match_operand:HI 2 "src_operand" "")))
|
(clobber (reg:CC 21))])]
|
(clobber (reg:CC 21))])]
|
""
|
""
|
"c4x_emit_libcall3 (smul_optab->handlers[(int) HImode].libfunc,
|
"c4x_emit_libcall3 (smul_optab->handlers[(int) HImode].libfunc,
|
MULT, HImode, operands);
|
MULT, HImode, operands);
|
DONE;")
|
DONE;")
|
|
|
|
|
;
|
;
|
; PEEPHOLES
|
; PEEPHOLES
|
;
|
;
|
|
|
; dbCC peepholes
|
; dbCC peepholes
|
;
|
;
|
; Turns
|
; Turns
|
; loop:
|
; loop:
|
; [ ... ]
|
; [ ... ]
|
; bCC label ; abnormal loop termination
|
; bCC label ; abnormal loop termination
|
; dbu aN, loop ; normal loop termination
|
; dbu aN, loop ; normal loop termination
|
;
|
;
|
; Into
|
; Into
|
; loop:
|
; loop:
|
; [ ... ]
|
; [ ... ]
|
; dbCC aN, loop
|
; dbCC aN, loop
|
; bCC label
|
; bCC label
|
;
|
;
|
; Which moves the bCC condition outside the inner loop for free.
|
; Which moves the bCC condition outside the inner loop for free.
|
;
|
;
|
(define_peephole
|
(define_peephole
|
[(set (pc) (if_then_else (match_operator 3 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 3 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(label_ref (match_operand 2 "" ""))
|
(label_ref (match_operand 2 "" ""))
|
(pc)))
|
(pc)))
|
(parallel
|
(parallel
|
[(set (pc)
|
[(set (pc)
|
(if_then_else
|
(if_then_else
|
(ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
|
(ge (plus:QI (match_operand:QI 0 "addr_reg_operand" "+a")
|
(const_int -1))
|
(const_int -1))
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))
|
(const_int -1)))
|
(use (reg:QI 20))
|
(use (reg:QI 20))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
"! c4x_label_conflict (insn, operands[2], operands[1])"
|
"! c4x_label_conflict (insn, operands[2], operands[1])"
|
"db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
|
"db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
(define_peephole
|
(define_peephole
|
[(set (pc) (if_then_else (match_operator 3 "comparison_operator"
|
[(set (pc) (if_then_else (match_operator 3 "comparison_operator"
|
[(reg:CC 21) (const_int 0)])
|
[(reg:CC 21) (const_int 0)])
|
(label_ref (match_operand 2 "" ""))
|
(label_ref (match_operand 2 "" ""))
|
(pc)))
|
(pc)))
|
(parallel
|
(parallel
|
[(set (pc)
|
[(set (pc)
|
(if_then_else
|
(if_then_else
|
(ne (match_operand:QI 0 "addr_reg_operand" "+a")
|
(ne (match_operand:QI 0 "addr_reg_operand" "+a")
|
(const_int 0))
|
(const_int 0))
|
(label_ref (match_operand 1 "" ""))
|
(label_ref (match_operand 1 "" ""))
|
(pc)))
|
(pc)))
|
(set (match_dup 0)
|
(set (match_dup 0)
|
(plus:QI (match_dup 0)
|
(plus:QI (match_dup 0)
|
(const_int -1)))])]
|
(const_int -1)))])]
|
"! c4x_label_conflict (insn, operands[2], operands[1])"
|
"! c4x_label_conflict (insn, operands[2], operands[1])"
|
"db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
|
"db%I3\\t%0,%l1\\n\\tb%3\\t%l2"
|
[(set_attr "type" "multi")])
|
[(set_attr "type" "multi")])
|
|
|
;
|
;
|
; Peepholes to convert 'call label; rets' into jump label
|
; Peepholes to convert 'call label; rets' into jump label
|
;
|
;
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(call (mem:QI (match_operand:QI 0 "call_address_operand" ""))
|
[(parallel [(call (mem:QI (match_operand:QI 0 "call_address_operand" ""))
|
(match_operand:QI 1 "general_operand" ""))
|
(match_operand:QI 1 "general_operand" ""))
|
(clobber (reg:QI 31))])
|
(clobber (reg:QI 31))])
|
(return)]
|
(return)]
|
"! c4x_null_epilogue_p ()"
|
"! c4x_null_epilogue_p ()"
|
"*
|
"*
|
if (REG_P (operands[0]))
|
if (REG_P (operands[0]))
|
return \"bu%#\\t%C0\";
|
return \"bu%#\\t%C0\";
|
else
|
else
|
return \"br%#\\t%C0\";"
|
return \"br%#\\t%C0\";"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand 0 "" "")
|
[(parallel [(set (match_operand 0 "" "")
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" ""))
|
(call (mem:QI (match_operand:QI 1 "call_address_operand" ""))
|
(match_operand:QI 2 "general_operand" "")))
|
(match_operand:QI 2 "general_operand" "")))
|
(clobber (reg:QI 31))])
|
(clobber (reg:QI 31))])
|
(return)]
|
(return)]
|
"! c4x_null_epilogue_p ()"
|
"! c4x_null_epilogue_p ()"
|
"*
|
"*
|
if (REG_P (operands[1]))
|
if (REG_P (operands[1]))
|
return \"bu%#\\t%C1\";
|
return \"bu%#\\t%C1\";
|
else
|
else
|
return \"br%#\\t%C1\";"
|
return \"br%#\\t%C1\";"
|
[(set_attr "type" "jump")])
|
[(set_attr "type" "jump")])
|
|
|
|
|
; This peephole should be unnecessary with my patches to flow.c
|
; This peephole should be unnecessary with my patches to flow.c
|
; for better autoincrement detection
|
; for better autoincrement detection
|
(define_peephole
|
(define_peephole
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "")
|
[(set (match_operand:QF 0 "ext_low_reg_operand" "")
|
(mem:QF (match_operand:QI 1 "addr_reg_operand" "")))
|
(mem:QF (match_operand:QI 1 "addr_reg_operand" "")))
|
(set (match_operand:QF 2 "ext_low_reg_operand" "")
|
(set (match_operand:QF 2 "ext_low_reg_operand" "")
|
(mem:QF (plus:QI (match_dup 1) (const_int 1))))
|
(mem:QF (plus:QI (match_dup 1) (const_int 1))))
|
(parallel [(set (match_dup 1) (plus:QI (match_dup 1) (const_int 2)))
|
(parallel [(set (match_dup 1) (plus:QI (match_dup 1) (const_int 2)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"ldf\\t*%1++,%0\\n\\tldf\\t*%1++,%2")
|
"ldf\\t*%1++,%0\\n\\tldf\\t*%1++,%2")
|
|
|
|
|
; This peephole should be unnecessary with my patches to flow.c
|
; This peephole should be unnecessary with my patches to flow.c
|
; for better autoincrement detection
|
; for better autoincrement detection
|
(define_peephole
|
(define_peephole
|
[(set (mem:QF (match_operand:QI 0 "addr_reg_operand" ""))
|
[(set (mem:QF (match_operand:QI 0 "addr_reg_operand" ""))
|
(match_operand:QF 1 "ext_low_reg_operand" ""))
|
(match_operand:QF 1 "ext_low_reg_operand" ""))
|
(set (mem:QF (plus:QI (match_dup 0) (const_int 1)))
|
(set (mem:QF (plus:QI (match_dup 0) (const_int 1)))
|
(match_operand:QF 2 "ext_low_reg_operand" ""))
|
(match_operand:QF 2 "ext_low_reg_operand" ""))
|
(parallel [(set (match_dup 0) (plus:QI (match_dup 0) (const_int 2)))
|
(parallel [(set (match_dup 0) (plus:QI (match_dup 0) (const_int 2)))
|
(clobber (reg:CC_NOOV 21))])]
|
(clobber (reg:CC_NOOV 21))])]
|
""
|
""
|
"stf\\t%1,*%0++\\n\\tstf\\t%2,*%0++")
|
"stf\\t%1,*%0++\\n\\tstf\\t%2,*%0++")
|
|
|
|
|
; The following two peepholes remove an unnecessary load
|
; The following two peepholes remove an unnecessary load
|
; often found at the end of a function. These peepholes
|
; often found at the end of a function. These peepholes
|
; could be generalized to other binary operators. They shouldn't
|
; could be generalized to other binary operators. They shouldn't
|
; be required if we run a post reload mop-up pass.
|
; be required if we run a post reload mop-up pass.
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QF 0 "ext_reg_operand" "")
|
[(parallel [(set (match_operand:QF 0 "ext_reg_operand" "")
|
(plus:QF (match_operand:QF 1 "ext_reg_operand" "")
|
(plus:QF (match_operand:QF 1 "ext_reg_operand" "")
|
(match_operand:QF 2 "ext_reg_operand" "")))
|
(match_operand:QF 2 "ext_reg_operand" "")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (match_operand:QF 3 "ext_reg_operand" "")
|
(set (match_operand:QF 3 "ext_reg_operand" "")
|
(match_dup 0))]
|
(match_dup 0))]
|
"dead_or_set_p (insn, operands[0])"
|
"dead_or_set_p (insn, operands[0])"
|
"addf3\\t%2,%1,%3")
|
"addf3\\t%2,%1,%3")
|
|
|
(define_peephole
|
(define_peephole
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
[(parallel [(set (match_operand:QI 0 "reg_operand" "")
|
(plus:QI (match_operand:QI 1 "reg_operand" "")
|
(plus:QI (match_operand:QI 1 "reg_operand" "")
|
(match_operand:QI 2 "reg_operand" "")))
|
(match_operand:QI 2 "reg_operand" "")))
|
(clobber (reg:CC_NOOV 21))])
|
(clobber (reg:CC_NOOV 21))])
|
(set (match_operand:QI 3 "reg_operand" "")
|
(set (match_operand:QI 3 "reg_operand" "")
|
(match_dup 0))]
|
(match_dup 0))]
|
"dead_or_set_p (insn, operands[0])"
|
"dead_or_set_p (insn, operands[0])"
|
"addi3\\t%2,%1,%3")
|
"addi3\\t%2,%1,%3")
|
|
|