OSDN Git Service

* decl2.c (is_late_template_attribute): Don't defer attribute
[pf3gnuchains/gcc-fork.git] / gcc / config / c4x / c4x.md
index 022c92c..364457d 100644 (file)
@@ -1,26 +1,25 @@
-;; Machine description for the TMS320C[34]x for GNU C compiler
+;; Machine description for the TMS320C[34]x for GCC
 ;; Copyright (C) 1994, 1995, 1996, 1997, 1998,
-;; 1999, 2000 Free Software Foundation, Inc.
+;; 1999, 2000, 2002, 2004, 2005, 2007 Free Software Foundation, Inc.
 
 ;; Contributed by Michael Hayes (m.hayes@elec.canterbury.ac.nz)
 ;;            and Herman Ten Brugge (Haj.Ten.Brugge@net.HCC.nl)
 
-;; This file is part of GNU CC.
+;; This file is part of GCC.
 
-;; GNU CC 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
-;; the Free Software Foundation; either version 2, or (at your option)
+;; the Free Software Foundation; either version 3, or (at your option)
 ;; any later version.
 
-;; GNU CC 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
 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 ;; GNU General Public License for more details.
 
 ;; You should have received a copy of the GNU General Public License
-;; along with GNU CC; see the file COPYING.  If not, write to
-;; the Free Software Foundation, 59 Temple Place - Suite 330,
-;; Boston, MA 02111-1307, USA.
+;; along with GCC; see the file COPYING3.  If not see
+;; <http://www.gnu.org/licenses/>.
 
 ;
 ; TODO :
@@ -29,7 +28,7 @@
 ;        for QImode and Pmode, whether Pmode was QImode or PQImode.
 ;        For addresses we wouldn't have to have a clobber of the CC
 ;        associated with each insn and we could use MPYI in address
-;        calculations without having to synthesise a proper 32 bit multiply.
+;        calculations without having to synthesize a proper 32-bit multiply.
 
 ; Additional C30/C40 instructions not coded:
 ; CALLcond, IACK, IDLE, LDE, LDFI, LDII, LDM, NORM, RETIcond
 ; L   unsigned 16-bit
 ; M   unsigned 8-bit  (C4x only)
 ; N   ones complement of unsigned 16-bit
-; O   16 bit high constant
+; O   16-bit high constant
 ; Q   ARx + 9-bit signed disp
 ; R   ARx + 5-bit unsigned disp  (C4x only)
 ; S   ARx + 0, 1, IRx disp
 ;  not for 'c'.
 
 ;  The 'f' constraint is only for float register operands---when 
-;  a register satisying 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 ! in front of the 'b' constaint 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.
 
 ;  Note that we deal with the condition code CC like some of the RISC
 ;  delayed branch slots.
 
 ;  Since the C[34]x has many instructions that set the CC, we pay the
-;  price of having to explicity 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). 
 
 ;  Note that many patterns say that the CC is clobbered when in fact
 ;  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
 ;  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
 ;  didn't allow it to move the CC around.
 
 ;  Note that fundamental operations, such as moves, must not clobber the
-;  CC.  Thus movqi choses 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
 ;  chose the move instruction that sets the CC.
 
 ;  a new spill register.
 
 ;  Note that the floating point representation of 0.0 on the C4x
-;  is 0x80000000 (-2147483648).  This value produces an warning
+;  is 0x80000000 (-2147483648).  This value produces a warning
 ;  message on 32-bit machines about the decimal constant being so large
 ;  that it is unsigned.
 
 ;        op3             fetch executed
 ; This means that we can allow any instruction in the last delay slot
 ; and only instructions which modify registers in the first two. 
-; lda can not be executed in the first delay slot 
-; and ldpk can not be executed in the first two delay slots.
+; lda cannot be executed in the first delay slot 
+; and ldpk cannot be executed in the first two delay slots.
 
 (define_attr "onlyreg" "false,true"
        (cond [(eq_attr "type" "unary,unarycc")
                (const_string "false")))
 
 /* 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.  */
 (define_attr "in_annul_slot_3" "false,true"
-  (if_then_else (and (eq_attr "cpu" "c4x")
-                    (eq_attr "type" "!jump,call,rets,jmpc,db,dbc,repeat,repeat_top,laj,push,pop,ldp,multi"))
+  (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 "onlyreg_nomod" "true"))
                (const_string "true")
                (const_string "false")))
 
 ;
 ; C4x UNSPEC NUMBERS
 ;
-;  1 BU/BUD
-;  2 RPTS
-;  3 LSH
-;  4 cmphi
-;  5 RCPF
-;  6 RND
-;  7 repeat block filler
-;  8 loadhf_int
-;  9 storehf_int
-; 10 RSQRF
-; 11 loadqf_int
-; 12 storeqf_int
-; 13 Conditional load on overflow
-; 14 push_st
-; 15 pop_st
-; 16 push_dp
-; 17 pop_dp
-; 18 popqi_unspec
-; 19 popqf_unspec
-; 20 andn_st
-; 22 rptb_init
-; 23 toieee
-; 24 frieee
-
-;
-; C4x FUNCTIONAL UNITS
-;
-; Define functional units for instruction scheduling to minimise
-; pipeline conflicts.
+(define_constants
+  [
+   (UNSPEC_BU                  1)
+   (UNSPEC_RPTS                        2)
+   (UNSPEC_LSH                 3)
+   (UNSPEC_CMPHI               4)
+   (UNSPEC_RCPF                        5)
+   (UNSPEC_RND                 6)
+   (UNSPEC_RPTB_FILL           7)
+   (UNSPEC_LOADHF_INT          8)
+   (UNSPEC_STOREHF_INT         9)
+   (UNSPEC_RSQRF               10)
+   (UNSPEC_LOADQF_INT          11)
+   (UNSPEC_STOREQF_INT         12)
+   (UNSPEC_LDIV                        13)
+   (UNSPEC_PUSH_ST             14)
+   (UNSPEC_POP_ST              15)
+   (UNSPEC_PUSH_DP             16)
+   (UNSPEC_POP_DP              17)
+   (UNSPEC_POPQI               18)
+   (UNSPEC_POPQF               19)
+   (UNSPEC_ANDN_ST             20)
+   (UNSPEC_RPTB_INIT           22)
+   (UNSPEC_TOIEEE              23)
+   (UNSPEC_FRIEEE              24)
+  ])
+
+;
+; C4x PIPELINE MODEL
 ;
 ; With the C3x, an external memory write (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
 ; takes two cycles.  With internal memory, reads and writes take
 ; half a cycle.
-;
 ; When a C4x address register is loaded it will not be available for
 ; an extra machine cycle.  Calculating with a C4x address register
-; makes it unavailable for 2 machine cycles.  To notify GCC of these
-; pipeline delays, each of the auxiliary and index registers are declared
-; as separate functional units.
-;
-; (define_function_unit NAME MULTIPLICITY SIMULTANEITY
-;                      TEST READY-DELAY ISSUE-DELAY [CONFLICT-LIST])
+; makes it unavailable for 2 machine cycles.
 ;
-; MULTIPLICITY 1 (C4x has no independent identical function units)
-; SIMULTANEITY 0 (C4x is pipelined)
-; READY_DELAY  1 (Results usually ready after every cyle)
-; ISSUE_DELAY  1 (Can issue insns every cycle)
-
 ; Just some dummy definitions. The real work is done in c4x_adjust_cost.
 ; These are needed so the min/max READY_DELAY is known.
 
-(define_function_unit "dummy" 1 0 (const_int 0) 1 1)
-(define_function_unit "dummy" 1 0 (const_int 0) 2 1)
-(define_function_unit "dummy" 1 0 (const_int 0) 3 1)
+(define_insn_reservation "any_insn" 1 (const_int 1) "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.
 ; Note that the attributes unarycc and binarycc do not apply
                                      (const_int 1) (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:
 ; (1) AR0-AR7, IR0-IR1, BK
 ; (2) DP
                             (const_int 1) (const_int 0))]
              (const_int 0)))
 
+(include "predicates.md")
 
 ;
 ; C4x INSN PATTERNS:
 (define_split
   [(set (match_operand:QI 0 "std_reg_operand" "")
         (match_operand:QI 1 "symbolic_address_operand" ""))]
-  "! TARGET_C3X && ! TARGET_TI"
+  "reload_completed && ! TARGET_C3X && ! TARGET_TI"
   [(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) (ior:QI (match_dup 0) (match_dup 3)))]
   "
 {
-   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & ~0xffff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff);
+   operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
+   operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
 }")
 
 (define_split
    (set (match_dup 0) (ior:QI (match_dup 0) (match_dup 3)))]
   "
 {
-   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & ~0xffff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff);
+   operands[2] = GEN_INT (INTVAL (operands[1]) & ~0xffff);
+   operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
 }")
 
 (define_split
   "
 {
    /* Generate two's complement value of 16 MSBs.  */
-   operands[2] = gen_rtx (CONST_INT, VOIDmode,
-                         (((INTVAL (operands[1]) >> 16) & 0xffff)
+   operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
                           - 0x8000) ^ ~0x7fff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff);
-   operands[4] = gen_rtx (CONST_INT, VOIDmode, 16);
+   operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
+   operands[4] = GEN_INT (16);
 }")
 
 (define_split
   "
 {
    /* Generate two's complement value of 16 MSBs.  */
-   operands[2] = gen_rtx (CONST_INT, VOIDmode,
-                         (((INTVAL (operands[1]) >> 16) & 0xffff)
+   operands[2] = GEN_INT ((((INTVAL (operands[1]) >> 16) & 0xffff)
                           - 0x8000) ^ ~0x7fff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff);
-   operands[4] = gen_rtx (CONST_INT, VOIDmode, 16);
+   operands[3] = GEN_INT (INTVAL (operands[1]) & 0xffff);
+   operands[4] = GEN_INT (16);
 }")
 
 (define_split
    /* Generate two's complement value of MSBs.  */
    int shift = c4x_shiftable_constant (operands[1]);
 
-   operands[2] = gen_rtx (CONST_INT, VOIDmode,
-                         (((INTVAL (operands[1]) >> shift) & 0xffff)
+   operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
                           - 0x8000) ^ ~0x7fff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, shift);
+   operands[3] = GEN_INT (shift);
 }")
 
 (define_split
    /* Generate two's complement value of MSBs.  */
    int shift = c4x_shiftable_constant (operands[1]);
 
-   operands[2] = gen_rtx (CONST_INT, VOIDmode,
-                         (((INTVAL (operands[1]) >> shift) & 0xffff)
-                          - 0x8000) ^ ~0x7fff);
-   operands[3] = gen_rtx (CONST_INT, VOIDmode, shift);
+   operands[2] = GEN_INT ((((INTVAL (operands[1]) >> shift) & 0xffff)
+                           - 0x8000) ^ ~0x7fff);
+   operands[3] = GEN_INT (shift);
 }")
 
 (define_split
   [(set (match_operand:QI 0 "std_reg_operand" "")
         (match_operand:QI 1 "symbolic_address_operand" ""))
    (clobber (reg:QI 16))]
-  "! TARGET_C3X && ! TARGET_TI"
+  "reload_completed && ! TARGET_C3X && ! TARGET_TI"
   [(set (match_dup 0) (high:QI (match_dup 1)))
    (set (match_dup 0) (lo_sum:QI (match_dup 0) (match_dup 1)))]
   "")
   [(set (match_operand:QI 0 "reg_operand" "")
         (match_operand:QI 1 "symbolic_address_operand" ""))
    (clobber (reg:QI 16))]
-  "! TARGET_SMALL 
-   && (TARGET_C3X || TARGET_TI
-       || (reload_completed
-           && ! std_reg_operand (operands[0], QImode)))"
+  "reload_completed
+   && ! TARGET_SMALL 
+   && (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
   [(set (match_dup 2) (high:QI (match_dup 3)))
    (set (match_dup 0) (match_dup 4))
    (use (match_dup 1))]
   [(set (match_operand:QI 0 "reg_operand" "")
         (match_operand:QI 1 "symbolic_address_operand" ""))
    (clobber (reg:QI 16))]
-  "TARGET_SMALL
-   && (TARGET_C3X || TARGET_TI
-       || (reload_completed
-           && ! std_reg_operand (operands[0], QImode)))"
+  "reload_completed
+   && TARGET_SMALL
+   && (TARGET_C3X || TARGET_TI || ! std_reg_operand (operands[0], QImode))"
   [(set (match_dup 0) (match_dup 2))
    (use (match_dup 1))]
   "
    (set (reg:CC 21)
         (compare:CC (match_dup 0) (const_int 0)))]
   ""
-  "@
-  ldi\\t%1,%0"
+  "ldi\\t%1,%0"
   [(set_attr "type" "unarycc")
    (set_attr "data" "int16")])
 
    (set (match_operand:QI 0 "ext_reg_operand" "=d")
         (match_dup 1))]
   ""
-  "@
-  ldi\\t%1,%0"
+  "ldi\\t%1,%0"
   [(set_attr "type" "unarycc")
    (set_attr "data" "int16")])
 
 ;  If one of the operands is not a register, then we should
 ;  emit two insns, using a scratch register.  This will produce
 ;  better code in loops if the source operand is invariant, since
-;  the source reload can be optimised 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.
 
 ;  Unlike most other insns, the move insns can't be split with
   [(set_attr "type" "push")])
 
 (define_insn "push_st"
-  [(set (mem:QI (pre_inc:QI (reg:QI 20))) (unspec:QI [(reg:QI 21)] 14))
+  [(set (mem:QI (pre_inc:QI (reg:QI 20)))
+        (unspec:QI [(reg:QI 21)] UNSPEC_PUSH_ST))
    (use (reg:QI 21))]
   ""
   "push\\tst"
   [(set_attr "type" "push")])
 
 (define_insn "push_dp"
-  [(set (mem:QI (pre_inc:QI (reg:QI 20))) (unspec:QI [(reg:QI 16)] 16))
+  [(set (mem:QI (pre_inc:QI (reg:QI 20))) 
+        (unspec:QI [(reg:QI 16)] UNSPEC_PUSH_DP))
    (use (reg:QI 16))]
   ""
   "push\\tdp"
   [(set_attr "type" "pop")])
 
 (define_insn "pop_st"
-  [(set (unspec:QI [(reg:QI 21)] 15) (mem:QI (post_dec:QI (reg:QI 20))))
+  [(set (unspec:QI [(reg:QI 21)] UNSPEC_POP_ST) 
+        (mem:QI (post_dec:QI (reg:QI 20))))
    (clobber (reg:CC 21))]
   ""
   "pop\\tst"
   [(set_attr "type" "pop")])
 
 (define_insn "pop_dp"
-  [(set (unspec:QI [(reg:QI 16)] 17) (mem:QI (post_dec:QI (reg:QI 20))))
+  [(set (unspec:QI [(reg:QI 16)] UNSPEC_POP_DP)
+        (mem:QI (post_dec:QI (reg:QI 20))))
    (clobber (reg:CC 16))]
   ""
   "pop\\tdp"
   [(set_attr "type" "pop")])
 
 (define_insn "popqi_unspec"
-  [(set (unspec:QI [(match_operand:QI 0 "reg_operand" "=r")] 18)
+  [(set (unspec:QI [(match_operand:QI 0 "reg_operand" "=r")] UNSPEC_POPQI)
         (mem:QI (post_dec:QI (reg:QI 20))))
    (clobber (match_dup 0))
    (clobber (reg:CC 21))]
       DONE;
    }")
 
+; This pattern is required primarily for manipulating the stack pointer
+; where GCC doesn't expect CC to be clobbered or for calculating
+; addresses during reload.  Since this is a more specific pattern
+; it needs to go first (otherwise we get into problems trying to decide
+; to add clobbers).
+(define_insn "addqi3_noclobber"
+  [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
+        (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
+                 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
+  "valid_operands (PLUS, operands, QImode)"
+  "@
+   addi\\t%2,%0
+   addi3\\t%2,%1,%0
+   addi3\\t%2,%1,%0"
+  [(set_attr "type" "binary,binary,binary")])
+; Default to int16 data attr.
+
 (define_insn "*addqi3_clobber"
   [(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<>")
   [(set_attr "type" "binarycc,binarycc,binarycc")])
 ; Default to int16 data attr.
 
-; This pattern is required primarily for manipulating the stack pointer
-; where GCC doesn't expect CC to be clobbered or for calculating
-; addresses during reload.
-(define_insn "addqi3_noclobber"
-  [(set (match_operand:QI 0 "std_reg_operand" "=c,c,c")
-        (plus:QI (match_operand:QI 1 "src_operand" "%0,rR,rS<>")
-                 (match_operand:QI 2 "src_operand" "rIm,JR,rS<>")))]
-  "valid_operands (PLUS, operands, QImode)"
-  "@
-   addi\\t%2,%0
-   addi3\\t%2,%1,%0
-   addi3\\t%2,%1,%0"
-  [(set_attr "type" "binary,binary,binary")])
-; Default to int16 data attr.
-
 
 ; This pattern is required during reload when eliminate_regs_in_insn
 ; effectively converts a move insn into an add insn when the src
      {        
        if (GET_CODE (operands[2]) == CONST_INT)
          {
-          /* Let GCC try to synthesise the multiplication using shifts
+          /* Let GCC try to synthesize the multiplication using shifts
              and adds.  In most cases this will be more profitable than
              using the C3x MPYI.  */
             FAIL;
                                           operands[2]));
             DONE;
          }
-       c4x_emit_libcall3 (smul_optab->handlers[(int) QImode].libfunc,
+       c4x_emit_libcall3 (optab_libfunc (smul_optab, QImode),
                          MULT, QImode, operands);
        DONE;
      }
                (truncate:QI
                 (lshiftrt:HI
                  (mult:HI
-                  (zero_extend:HI (match_operand:QI 1 "src_operand" ""))
-                  (zero_extend:HI (match_operand:QI 2 "lsrc_operand" "")))
+                  (zero_extend:HI (match_operand:QI 1
+                                  "nonimmediate_src_operand" ""))
+                  (zero_extend:HI (match_operand:QI 2
+                                  "nonimmediate_lsrc_operand" "")))
                  (const_int 32))))
               (clobber (reg:CC_NOOV 21))])]
  ""
         (truncate:QI
          (lshiftrt:HI
           (mult:HI 
-           (zero_extend:HI (match_operand:QI 1 "src_operand" "%0,rR,rS<>,0,rR,rS<>"))
-           (zero_extend:HI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>,rLm,JR,rS<>")))
+           (zero_extend:HI (match_operand:QI 1
+                           "nonimmediate_src_operand" "%0,rR,rS<>,0,rR,rS<>"))
+           (zero_extend:HI (match_operand:QI 2
+                           "nonimmediate_lsrc_operand" "rm,R,rS<>,rm,R,rS<>")))
           (const_int 32))))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
         (truncate:QI
          (lshiftrt:HI
           (mult:HI 
-           (zero_extend:HI (match_operand:QI 1 "src_operand" "0,rR,rS<>"))
-           (zero_extend:HI (match_operand:QI 2 "lsrc_operand" "rLm,JR,rS<>")))
+           (zero_extend:HI (match_operand:QI 1
+                           "nonimmediate_src_operand" "0,rR,rS<>"))
+           (zero_extend:HI (match_operand:QI 2
+                           "nonimmediate_lsrc_operand" "rm,R,rS<>")))
           (const_int 32))))]
   "! TARGET_C3X && valid_operands (MULT, operands, QImode)"
   "@
 
 (define_insn "andn_st"
   [(set (unspec:QI [(reg:QI 21)] 20)
-        (and:QI (unspec:QI [(reg:QI 21)] 20)
+        (and:QI (unspec:QI [(reg:QI 21)] UNSPEC_ANDN_ST)
                 (match_operand:QI 0 "" "N")))
    (use (match_dup 0))
    (use (reg:CC 21))
    (clobber (reg:CC 21))]
   ""
-  "@
-   andn\\t%N0,st"
+  "andn\\t%N0,st"
   [(set_attr "type" "misc")
    (set_attr "data" "not_uint16")])
 
 (define_insn "*lshlqi3_clobber"
   [(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<>")
-                   (unspec:QI [(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")] 3)))
+                   (unspec:QI [(match_operand:QI 2 "src_operand" "rIm,JR,rS<>,rIm,JR,rS<>")] UNSPEC_LSH)))
    (clobber (reg:CC 21))]
   "valid_operands (ASHIFT, operands, QImode)"
   "@
 ; 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)
 ; so that it could be hoisted out of the loop so that we only
-; would need to do cmpi3 *ar0++, r0.  Now the loop optimisation 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.
-; Ideally, GCC requires another loop optimisation pass (preferably after
+; Ideally, GCC requires another loop optimization pass (preferably after
 ; reload) so that it can hoist invariants out of loops.
 ; The current solution modifies legitimize_operands () so that small
 ; constants are forced into a pseudo register.
 ;  If one of the operands is not a register, then we should
 ;  emit two insns, using a scratch register.  This will produce
 ;  better code in loops if the source operand is invariant, since
-;  the source reload can be optimised out.  During reload we cannot
+;  the source reload can be optimized out.  During reload we cannot
 ;  use change_address or force_reg.
 (define_expand "movqf"
   [(set (match_operand:QF 0 "src_operand" "")
 
 ; This can generate invalid stack slot displacements
 (define_split
- [(set (match_operand:QI 0 "reg_operand" "=r")
-       (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] 12))]
+ [(set (match_operand:QI 0 "reg_operand" "")
+       (unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))]
   "reload_completed"
   [(set (match_dup 3) (match_dup 1))
    (set (match_dup 0) (match_dup 2))]
 
 (define_insn "storeqf_int"
  [(set (match_operand:QI 0 "reg_operand" "=r")
-       (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] 12))]
+       (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))]
  ""
  "#"
   [(set_attr "type" "multi")])
 
 (define_split
- [(parallel [(set (match_operand:QI 0 "reg_operand" "=r")
-                  (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] 12))
+ [(parallel [(set (match_operand:QI 0 "reg_operand" "")
+                  (unspec:QI [(match_operand:QF 1 "reg_operand" "")] UNSPEC_STOREQF_INT))
              (clobber (reg:CC 21))])]
   "reload_completed"
   [(set (mem:QF (pre_inc:QI (reg:QI 20)))
 
 (define_insn "storeqf_int_clobber"
  [(parallel [(set (match_operand:QI 0 "reg_operand" "=r")
-                  (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] 12))
+                  (unspec:QI [(match_operand:QF 1 "reg_operand" "f")] UNSPEC_STOREQF_INT))
              (clobber (reg:CC 21))])]
  ""
  "#"
 
 ; This can generate invalid stack slot displacements
 (define_split
- [(set (match_operand:QF 0 "reg_operand" "=f")
-       (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] 11))]
+ [(set (match_operand:QF 0 "reg_operand" "")
+       (unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))]
   "reload_completed"
   [(set (match_dup 2) (match_dup 1))
    (set (match_dup 0) (match_dup 3))]
 
 (define_insn "loadqf_int"
  [(set (match_operand:QF 0 "reg_operand" "=f")
-       (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] 11))]
+       (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))]
  ""
  "#"
   [(set_attr "type" "multi")])
 
 (define_split
- [(parallel [(set (match_operand:QF 0 "reg_operand" "=f")
-                  (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] 11))
+ [(parallel [(set (match_operand:QF 0 "reg_operand" "")
+                  (unspec:QF [(match_operand:QI 1 "reg_operand" "")] UNSPEC_LOADQF_INT))
              (clobber (reg:CC 21))])]
   "reload_completed"
   [(set (mem:QI (pre_inc:QI (reg:QI 20)))
 
 (define_insn "loadqf_int_clobber"
  [(parallel [(set (match_operand:QF 0 "reg_operand" "=f")
-                  (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] 11))
+                  (unspec:QF [(match_operand:QI 1 "reg_operand" "r")] UNSPEC_LOADQF_INT))
              (clobber (reg:CC 21))])]
  ""
  "#"
  [(set_attr "type" "pop")])
 
 (define_insn "popqf_unspec"
-  [(set (unspec:QF [(match_operand:QF 0 "reg_operand" "=f")] 19)
+  [(set (unspec:QF [(match_operand:QF 0 "reg_operand" "=f")] UNSPEC_POPQF)
         (mem:QF (post_dec:QI (reg:QI 20))))
    (clobber (match_dup 0))
    (clobber (reg:CC 21))]
                               (match_dup 3)))
              (set (match_dup 4)
                   (float:QF (match_dup 1)))])
-  (set (match_dup 6)
+  (set (match_dup 2)
        (if_then_else:QF (lt (reg:CC 21) (const_int 0))
                         (match_dup 5)
                         (match_dup 2)))
   (parallel [(set (match_operand:QF 0 "reg_operand" "")
-                  (plus:QF (match_dup 6) (match_dup 4)))
+                  (plus:QF (match_dup 2) (match_dup 4)))
              (clobber (reg:CC_NOOV 21))])]
  ""
  "operands[2] = gen_reg_rtx (QFmode);
   operands[3] = CONST0_RTX (QFmode); 
   operands[4] = gen_reg_rtx (QFmode);
   operands[5] = gen_reg_rtx (QFmode);
-  operands[6] = gen_reg_rtx (QFmode);
-  emit_move_insn (operands[5], 
-   immed_real_const_1 (REAL_VALUE_ATOF (\"4294967296.0\", QFmode), QFmode));")
+  emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
 
 (define_expand "floatunsqihf2"
  [(set (match_dup 2) (match_dup 3))
                               (match_dup 3)))
              (set (match_dup 4)
                   (float:HF (match_dup 1)))])
-  (set (match_dup 6)
+  (set (match_dup 2)
        (if_then_else:HF (lt (reg:CC 21) (const_int 0))
                         (match_dup 5)
                         (match_dup 2)))
   (parallel [(set (match_operand:HF 0 "reg_operand" "")
-                  (plus:HF (match_dup 6) (match_dup 4)))
+                  (plus:HF (match_dup 2) (match_dup 4)))
              (clobber (reg:CC_NOOV 21))])]
  ""
  "operands[2] = gen_reg_rtx (HFmode);
   operands[3] = CONST0_RTX (HFmode); 
   operands[4] = gen_reg_rtx (HFmode);
   operands[5] = gen_reg_rtx (HFmode);
-  operands[6] = gen_reg_rtx (HFmode);
-  emit_move_insn (operands[5], 
-   immed_real_const_1 (REAL_VALUE_ATOF (\"4294967296.0\", HFmode), HFmode));")
+  emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
 
 (define_insn "floatqihf2"
   [(set (match_operand:HF 0 "reg_operand" "=h")
  "fix\\t%1,%0"
   [(set_attr "type" "unarycc")])
 
-(define_insn "*fixhfqi_set"
-  [(set (reg:CC 21)
-        (compare:CC (fix:QI (match_operand:HF 1 "src_operand" "fH"))
-                    (const_int 0)))
-   (set (match_operand:QI 0 "ext_reg_operand" "=d")
-        (fix:QI (match_dup 1)))]
- ""
- "fix\\t%1,%0"
-  [(set_attr "type" "unarycc")])
-
 ;
 ; 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
   operands[5] = gen_reg_rtx (QImode);
  ")
 
-(define_expand "fix_trunchfqi2"
-  [(parallel [(set (match_dup 2)
-                   (fix:QI (match_operand:HF 1 "src_operand" "")))
-              (clobber (reg:CC 21))])
-   (parallel [(set (match_dup 3) (neg:HF (match_dup 1)))
-              (clobber (reg:CC_NOOV 21))])
-   (parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
-              (clobber (reg:CC 21))])
-   (parallel [(set (reg:CC_NOOV 21)
-                   (compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
-              (set (match_dup 5) (neg:QI (match_dup 4)))])
-   (set (match_dup 2)
-        (if_then_else:QI (le (reg:CC 21) (const_int 0))
-                         (match_dup 5)
-                         (match_dup 2)))
-   (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
- ""
- "if (TARGET_FAST_FIX)
-    {
-       emit_insn (gen_fixhfqi_clobber (operands[0], operands[1]));
-       DONE;
-    }
-  operands[2] = gen_reg_rtx (QImode);
-  operands[3] = gen_reg_rtx (HFmode);
-  operands[4] = gen_reg_rtx (QImode);
-  operands[5] = gen_reg_rtx (QImode);
- ")
-
 (define_expand "fix_truncqfhi2"
   [(parallel [(set (match_operand:HI 0 "reg_operand" "")
                    (fix:HI (match_operand:QF 1 "src_operand" "")))
                              (const_int 0)))
             (set (match_dup 4)
                  (fix:QI (match_dup 3)))])
-  (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] 13))
+  (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
              (use (reg:CC 21))])
   (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
  ""
   operands[3] = gen_reg_rtx (QFmode);
   operands[4] = gen_reg_rtx (QImode);
   operands[5] = gen_reg_rtx (QFmode);
-  emit_move_insn (operands[5],
-   immed_real_const_1 (REAL_VALUE_ATOF (\"4294967296.0\", QFmode), QFmode));")
-
-(define_expand "fixuns_trunchfqi2"
- [(parallel [(set (match_dup 2)
-                 (fix:QI (match_operand:HF 1 "src_operand" "hH")))
-            (clobber (reg:CC 21))])
-  (parallel [(set (match_dup 3)
-                 (minus:HF (match_dup 1) (match_dup 5)))
-            (clobber (reg:CC_NOOV 21))])
-  (parallel [(set (reg:CC 21)
-                 (compare:CC (fix:QI (match_dup 3))
-                             (const_int 0)))
-            (set (match_dup 4)
-                 (fix:QI (match_dup 3)))])
-  (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] 13))
-             (use (reg:CC 21))])
-  (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
- ""
- "operands[2] = gen_reg_rtx (QImode);
-  operands[3] = gen_reg_rtx (HFmode);
-  operands[4] = gen_reg_rtx (QImode);
-  operands[5] = gen_reg_rtx (HFmode);
-  emit_move_insn (operands[5],
-   immed_real_const_1 (REAL_VALUE_ATOF (\"4294967296.0\", HFmode), HFmode));")
+  emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", QFmode));")
 
 (define_expand "fixuns_truncqfhi2"
   [(parallel [(set (match_operand:HI 0 "reg_operand" "")
 ;
 (define_insn "rcpfqf_clobber"
   [(set (match_operand:QF 0 "reg_operand" "=f")
-        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] 5))
+        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RCPF))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rcpf\\t%1,%0"
 ;
 (define_insn "*rsqrfqf_clobber"
   [(set (match_operand:QF 0 "reg_operand" "=f")
-        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] 10))
+        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RSQRF))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rsqrf\\t%1,%0"
 ;
 (define_insn "*rndqf_clobber"
   [(set (match_operand:QF 0 "reg_operand" "=f")
-        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] 6))
+        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_RND))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rnd\\t%1,%0"
 ; Inlined float square root for C4x
 (define_expand "sqrtqf2_inline"
   [(parallel [(set (match_dup 2)
-                  (unspec:QF [(match_operand:QF 1 "src_operand" "")] 10))
+                  (unspec:QF [(match_operand:QF 1 "src_operand" "")] UNSPEC_RSQRF))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_dup 3) (mult:QF (match_dup 5) (match_dup 1)))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 1)))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_operand:QF 0 "reg_operand" "")
-                  (unspec:QF [(match_dup 4)] 6))
+                  (unspec:QF [(match_dup 4)] UNSPEC_RND))
              (clobber (reg:CC_NOOV 21))])]
   "! TARGET_C3X"
   "if (! reload_in_progress
    operands[2] = gen_reg_rtx (QFmode);
    operands[3] = gen_reg_rtx (QFmode);
    operands[4] = gen_reg_rtx (QFmode);
-   operands[5] = immed_real_const_1 (REAL_VALUE_ATOF (\"0.5\", QFmode),
-                                     QFmode);
-   operands[6] = immed_real_const_1 (REAL_VALUE_ATOF (\"1.5\", QFmode),
-                                     QFmode);")
+   operands[5] = CONST_DOUBLE_ATOF (\"0.5\", QFmode);
+   operands[6] = CONST_DOUBLE_ATOF (\"1.5\", QFmode);")
 
 (define_expand "sqrtqf2"
   [(parallel [(set (match_operand:QF 0 "reg_operand" "")
 ;
 (define_insn "toieee"
   [(set (match_operand:QF 0 "reg_operand" "=f")
-        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] 23))
+        (unspec:QF [(match_operand:QF 1 "src_operand" "fHm")] UNSPEC_TOIEEE))
    (clobber (reg:CC 21))]
  ""
  "toieee\\t%1,%0")
 
 (define_insn "frieee"
   [(set (match_operand:QF 0 "reg_operand" "=f")
-        (unspec:QF [(match_operand:QF 1 "memory_operand" "m")] 24))
+        (unspec:QF [(match_operand:QF 1 "memory_operand" "m")] UNSPEC_FRIEEE))
    (clobber (reg:CC 21))]
  ""
  "frieee\\t%1,%0")
 ; Inlined float divide for C4x
 (define_expand "divqf3_inline"
   [(parallel [(set (match_dup 3)
-                  (unspec:QF [(match_operand:QF 2 "src_operand" "")] 5))
+                  (unspec:QF [(match_operand:QF 2 "src_operand" "")] UNSPEC_RCPF))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_dup 4) (mult:QF (match_dup 2) (match_dup 3)))
              (clobber (reg:CC_NOOV 21))])
                            (match_dup 3)))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_operand:QF 0 "reg_operand" "")
-                  (unspec:QF [(match_dup 3)] 6))
+                  (unspec:QF [(match_dup 3)] UNSPEC_RND))
              (clobber (reg:CC_NOOV 21))])]
   "! TARGET_C3X"
   "if (! reload_in_progress
                           [(reg:CC 21) (const_int 0)])
                          (match_operand:QI 2 "src_operand" "rIm,0")
                          (match_operand:QI 3 "src_operand" "0,rIm")))]
- ""
+ "valid_operands (IF_THEN_ELSE, operands, QImode)"
  "@
   ldi%1\\t%2,%0
   ldi%I1\\t%3,%0"
  "GET_CODE (operands[1]) != LE
   && GET_CODE (operands[1]) != GE
   && GET_CODE (operands[1]) != LT
-  && GET_CODE (operands[1]) != GT"
+  && GET_CODE (operands[1]) != GT
+  && valid_operands (IF_THEN_ELSE, operands, QImode)"
  "@
   ldi%1\\t%2,%0
   ldi%I1\\t%3,%0"
 
 (define_insn "*ldi_on_overflow"
   [(set (match_operand:QI 0 "reg_operand" "=r")
-       (unspec:QI [(match_operand:QI 1 "src_operand" "rIm")] 13))
+       (unspec:QI [(match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LDIV))
    (use (reg:CC 21))]
   ""
-  "@
-   ldiv\\t%1,%0"
+  "ldiv\\t%1,%0"
   [(set_attr "type" "unary")])
 
 ; Move operand 2 to operand 0 if condition (operand 1) is true
     if (ccreg == NULL_RTX) FAIL;
     emit_insn (gen_rtx_SET (QImode, operands[0],
                             gen_rtx_IF_THEN_ELSE (QImode,
-                                 gen_rtx (code, VOIDmode, ccreg, const0_rtx),
-                                          operands[2], operands[3])));
+                                 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
+                                                operands[2], operands[3])));
     DONE;}")
                       
 (define_insn "*ldf_conditional"
                           [(reg:CC 21) (const_int 0)])
                          (match_operand:QF 2 "src_operand" "fHm,0")
                          (match_operand:QF 3 "src_operand" "0,fHm")))]
- ""
+ "valid_operands (IF_THEN_ELSE, operands, QFmode)"
  "@
   ldf%1\\t%2,%0
   ldf%I1\\t%3,%0"
  "GET_CODE (operands[1]) != LE
   && GET_CODE (operands[1]) != GE
   && GET_CODE (operands[1]) != LT
-  && GET_CODE (operands[1]) != GT"
+  && GET_CODE (operands[1]) != GT
+  && valid_operands (IF_THEN_ELSE, operands, QFmode)"
  "@
   ldf%1\\t%2,%0
   ldf%I1\\t%3,%0"
     if (ccreg == NULL_RTX) FAIL;
     emit_insn (gen_rtx_SET (QFmode, operands[0],
                             gen_rtx_IF_THEN_ELSE (QFmode,
-                                 gen_rtx (code, VOIDmode, ccreg, const0_rtx),
-                                          operands[2], operands[3])));
+                                 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
+                                                operands[2], operands[3])));
     DONE;}")
 
 (define_insn "*ldhf_conditional"
     if (ccreg == NULL_RTX) FAIL;
     emit_insn (gen_rtx_SET (HFmode, operands[0],
                             gen_rtx_IF_THEN_ELSE (HFmode,
-                                 gen_rtx (code, VOIDmode, ccreg, const0_rtx),
-                                          operands[2], operands[3])));
+                                 gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx),
+                                                operands[2], operands[3])));
     DONE;}")
 
 (define_expand "seq"
 
 (define_insn "*bu"
   [(set (pc)
-        (unspec [(match_operand:QI 0 "reg_operand" "r")] 1))]
+        (unspec [(match_operand:QI 0 "reg_operand" "r")] UNSPEC_BU))]
   ""
   "bu%#\\t%0"
   [(set_attr "type" "jump")])
 
 (define_insn "*toieee_movqf_clobber"
   [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
-       (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] 23))
+       (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_TOIEEE))
    (set (match_operand:QF 2 "par_ind_operand" "=S<>")
         (match_operand:QF 3 "ext_low_reg_operand" "q"))
    (clobber (reg:CC 21))]
 
 (define_insn "*frieee_movqf_clobber"
   [(set (match_operand:QF 0 "ext_low_reg_operand" "=q")
-       (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] 24))
+       (unspec:QF [(match_operand:QF 1 "par_ind_operand" "S<>")] UNSPEC_FRIEEE))
    (set (match_operand:QF 2 "par_ind_operand" "=S<>")
         (match_operand:QF 3 "ext_low_reg_operand" "q"))
    (clobber (reg:CC 21))]
   "! TARGET_C3X"
   "*
    if (final_sequence)
-     return \"laj%U0\\t%C0\";
+     return c4x_check_laj_p (insn)
+        ? \"nop\\n\\tlaj%U0\\t%C0\" : \"laj%U0\\t%C0\";
    else
      return \"call%U0\\t%C0\";"
   [(set_attr "type" "laj")])
   "! TARGET_C3X"
   "*
    if (final_sequence)
-     return \"laj%U1\\t%C1\";
+     return c4x_check_laj_p (insn)
+        ? \"nop\\n\\tlaj%U1\\t%C1\" : \"laj%U1\\t%C1\";
    else
      return \"call%U1\\t%C1\";"
   [(set_attr "type" "laj")])
 
 (define_insn "return"
   [(return)]
-  "c4x_null_epilogue_p ()"
+  "c4x_null_epilogue_p ()"
   "rets"
   [(set_attr "type" "rets")])
 
                       [(reg:CC 21) (const_int 0)])
                       (return)
                        (pc)))]
-  "c4x_null_epilogue_p ()"
+  "c4x_null_epilogue_p ()"
   "rets%0"
   [(set_attr "type" "rets")])
 
    && GET_CODE (operands[0]) != GE
    && GET_CODE (operands[0]) != LT
    && GET_CODE (operands[0]) != GT
-   && c4x_null_epilogue_p ()"
+   && c4x_null_epilogue_p ()"
   "rets%0"
   [(set_attr "type" "rets")])
 
                       [(reg:CC 21) (const_int 0)])
                        (pc)
                       (return)))]
-  "c4x_null_epilogue_p ()"
+  "c4x_null_epilogue_p ()"
   "rets%I0"
   [(set_attr "type" "rets")])
 
    && GET_CODE (operands[0]) != GE
    && GET_CODE (operands[0]) != LT
    && GET_CODE (operands[0]) != GT
-   && c4x_null_epilogue_p ()"
+   && c4x_null_epilogue_p ()"
   "rets%I0"
   [(set_attr "type" "rets")])
 
 ; Note we have to emit a dbu instruction if there are no delay slots
 ; to fill.
 ; Also note that GCC will try to reverse a loop to see if it can
-; utilise 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
 ; the loop will work :(  (see check_dbra_loop() in loop.c)
 ; Note that the C3x only decrements the 24 LSBs of the address register
 
 (define_insn "rpts_top"
   [(unspec [(use (label_ref (match_operand 0 "" "")))
-            (use (label_ref (match_operand 1 "" "")))] 2)
+            (use (label_ref (match_operand 1 "" "")))] UNSPEC_RPTS)
    (clobber (reg:QI 25))
    (clobber (reg:QI 26))]
   ""
 ; This pattern needs to be emitted at the start of the loop to
 ; say that RS and RE are loaded.
 (define_insn "rptb_init"
-  [(unspec [(match_operand:QI 0 "register_operand" "va")] 22)
+  [(unspec [(match_operand:QI 0 "register_operand" "va")] UNSPEC_RPTB_INIT)
    (clobber (reg:QI 25))
    (clobber (reg:QI 26))]
   ""
    (use (label_ref (match_operand 4 "" "")))]
   ""
   "if (! TARGET_LOOP_UNSIGNED 
-       && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > (1U << 31))
+       && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > ((unsigned) 1 << 31))
      FAIL;
    if (INTVAL (operands[3]) > 1 || ! TARGET_RPTB)
      {
     DONE;
   ")
 
-; The current low overhead looping code is naff and is not failsafe
-; If you want RTPB instructions to be generated, apply the patches
-; from www.elec.canterbury.ac.nz/c4x.  This will utilise the
-; doloop_begin and doloop_end patterns in this MD.
 (define_expand "decrement_and_branch_on_count"
   [(parallel [(set (pc)
                    (if_then_else (ge (match_operand:QI 0 "register_operand" "")
   "0"
   "")
 
-(define_expand "movstrqi_small2"
+(define_expand "movmemqi_small"
   [(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
                    (mem:BLK (match_operand:BLK 1 "src_operand" "")))
               (use (match_operand:QI 2 "immediate_operand" ""))
 ; BLOCK MOVE
 ; We should probably get RC loaded when using RPTB automagically...
 ; There's probably no need to call _memcpy() if we don't get
-; a 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.
 ; operand 2 is the number of bytes
 ; operand 3 is the shared alignment
 ; operand 4 is a scratch register
 
-(define_insn "movstrqi_small"
-  [(set (mem:BLK (match_operand:QI 0 "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 3 "immediate_operand" ""))
-   (clobber (match_operand:QI 4 "ext_low_reg_operand" "=&q"))
-   (clobber (match_dup 0))
-   (clobber (match_dup 1))]
-  ""
-  "*
- {
-   int i;
-   int len = INTVAL (operands[2]);
-   int first = 1;
-
-   for (i = 0; i < len; i++)
-    {
-      if (first)
-        output_asm_insn (\"ldiu\\t*%1++,%4\", operands);
-      else
-        output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
-      output_asm_insn (\"sti\\t%4,*%0++\", operands);
-      first = 0;
-    } 
-  return \"\";
-  }
-  "
-  [(set_attr "type" "multi")])
-
-(define_insn "movstrqi_large"
-  [(set (mem:BLK (match_operand:QI 0 "addr_reg_operand" "+a"))
-        (mem:BLK (match_operand:QI 1 "addr_reg_operand" "+a")))
+(define_insn "movmemqi_large"
+  [(set (mem:BLK (match_operand:QI 0 "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 3 "immediate_operand" ""))
    (clobber (match_operand:QI 4 "ext_low_reg_operand" "=&q"))
-   (clobber (match_dup 0))
-   (clobber (match_dup 1))
+   (clobber (match_scratch:QI 5 "=0"))
+   (clobber (match_scratch:QI 6 "=1"))
    (clobber (reg:QI 25))
    (clobber (reg:QI 26))
    (clobber (reg:QI 27))]
   ""
   "*
  {
+   int i;
    int len = INTVAL (operands[2]);
 
    output_asm_insn (\"ldiu\\t*%1++,%4\", operands);
-   if (TARGET_RPTS_CYCLES (len))
+   if (len < 8)
      {
-        output_asm_insn (\"rpts\\t%2-2\", operands);  
-        output_asm_insn (\"sti\\t%4,*%0++\", operands);
-        output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
-        return \"sti\\t%4,*%0++\";
+       for (i = 1; i < len; i++)
+        {
+           output_asm_insn (\"sti\\t%4,*%0++\", operands);
+           output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
+         } 
      }
    else
      {
-        output_asm_insn (\"ldiu\\t%2-2,rc\", operands);
-        output_asm_insn (\"rptb\\t$+1\", operands);  
-        output_asm_insn (\"sti\\t%4,*%0++\", operands);
-        output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
-
-        return \"sti\\t%4,*%0++\";
+       if (TARGET_RPTS_CYCLES (len))
+         {
+           output_asm_insn (\"rpts\\t%2-2\", operands);  
+           output_asm_insn (\"sti\\t%4,*%0++\", operands);
+           output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
+         }
+       else
+         {
+           output_asm_insn (\"ldiu\\t%2-2,rc\", operands);
+           output_asm_insn (\"rptb\\t$+1\", operands);  
+           output_asm_insn (\"sti\\t%4,*%0++\", operands);
+           output_asm_insn (\"|| ldi\\t*%1++,%4\", operands);
+        }
      }
-  }
 "
 [(set_attr "type" "multi")])
+   return \"sti\\t%4,*%0++\";
}"
+ [(set_attr "type" "multi")])
 
 ; Operand 2 is the count, operand 3 is the alignment.
-(define_expand "movstrqi"
+(define_expand "movmemqi"
   [(parallel [(set (mem:BLK (match_operand:BLK 0 "src_operand" ""))
                    (mem:BLK (match_operand:BLK 1 "src_operand" "")))
               (use (match_operand:QI 2 "immediate_operand" ""))
    operands[0] = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
    operands[1] = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
    tmp = gen_reg_rtx (QImode);
-   if (INTVAL (operands[2]) < 8)
-     emit_insn (gen_movstrqi_small2 (operands[0], operands[1], operands[2],
+   /* Disabled because of reload problems.  */
+   if (0 && INTVAL (operands[2]) < 8)
+     emit_insn (gen_movmemqi_small (operands[0], operands[1], operands[2],
                                     operands[3], tmp));
    else
      {
-      emit_insn (gen_movstrqi_large (operands[0], operands[1], operands[2],
+      emit_insn (gen_movmemqi_large (operands[0], operands[1], operands[2],
                                      operands[3], tmp));
      }
    DONE;
  }")
 
 
-(define_insn "*cmpstrqi"
+(define_insn "*cmpstrnqi"
   [(set (match_operand:QI 0 "ext_reg_operand" "=d")
         (compare:QI (mem:BLK (match_operand:QI 1 "addr_reg_operand" "+a"))
                     (mem:BLK (match_operand:QI 2 "addr_reg_operand" "+a"))))
     return \"\";
  }")
 
-(define_expand "cmpstrqi"
+(define_expand "cmpstrnqi"
   [(parallel [(set (match_operand:QI 0 "reg_operand" "")
                    (compare:QI (match_operand:BLK 1 "general_operand" "")
                                (match_operand:BLK 2 "general_operand" "")))
  "reload_completed"
  [(set (match_dup 0) (float_extend:HF (match_dup 2)))
   (set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
-                                            (match_dup 3)] 8))]
+                                            (match_dup 3)] UNSPEC_LOADHF_INT))]
  "operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
   operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
   PUT_MODE (operands[2], QFmode);
  "reload_completed && 0"
  [(set (match_dup 0) (float_extend:HF (match_dup 2)))
   (set (match_dup 0) (unspec:HF [(subreg:QI (match_dup 0) 0)
-                                            (match_dup 3)] 8))]
+                                            (match_dup 3)] UNSPEC_LOADHF_INT))]
  "operands[2] = c4x_operand_subword (operands[1], 0, 1, HFmode);
   operands[3] = c4x_operand_subword (operands[1], 1, 1, HFmode);
   PUT_MODE (operands[2], QFmode);
        (match_operand:HF 1 "reg_operand" ""))]
   "reload_completed"
   [(set (match_dup 2) (float_truncate:QF (match_dup 1)))
-   (set (match_dup 3) (unspec:QI [(match_dup 1)] 9))]
+   (set (match_dup 3) (unspec:QI [(match_dup 1)] UNSPEC_STOREHF_INT))]
  "operands[2] = c4x_operand_subword (operands[0], 0, 1, HFmode);
   operands[3] = c4x_operand_subword (operands[0], 1, 1, HFmode);
   PUT_MODE (operands[2], QFmode);
  [(set (match_operand:HF 0 "reg_operand" "=h")
        (float_extend:HF (match_operand:QF 1 "src_operand" "fHm")))]
  ""
- "@
-  ldfu\\t%1,%0"
+ "ldfu\\t%1,%0"
   [(set_attr "type" "unary")])
 
 (define_insn "*loadhf_int"
  [(set (match_operand:HF 0 "reg_operand" "+h")
        (unspec:HF [(subreg:QI (match_dup 0) 0)
-                   (match_operand:QI 1 "src_operand" "rIm")] 8))]
+                   (match_operand:QI 1 "src_operand" "rIm")] UNSPEC_LOADHF_INT))]
  ""
- "@
-  ldiu\\t%1,%0"
+ "ldiu\\t%1,%0"
   [(set_attr "type" "unary")])
 
 (define_insn "*storehf_float"
 
 (define_insn "*storehf_int"
  [(set (match_operand:QI 0 "memory_operand" "=m")
-       (unspec:QI [(match_operand:HF 1 "reg_operand" "h")] 9))]
+       (unspec:QI [(match_operand:HF 1 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
  ""
- "@
-  sti\\t%1,%0"
+ "sti\\t%1,%0"
   [(set_attr "type" "store")])
 
 (define_insn "extendqfhf2"
   [(set (mem:QF (pre_inc:QI (reg:QI 20)))
         (float_truncate:QF (match_dup 0)))
    (set (mem:QI (pre_inc:QI (reg:QI 20)))
-        (unspec:QI [(match_dup 0)] 9))]
+        (unspec:QI [(match_dup 0)] UNSPEC_STOREHF_INT))]
  "")
 
 (define_insn "pushhf_trunc"
 
 (define_insn "pushhf_int"
   [(set (mem:QI (pre_inc:QI (reg:QI 20)))
-        (unspec:QI [(match_operand:HF 0 "reg_operand" "h")] 9))]
+        (unspec:QI [(match_operand:HF 0 "reg_operand" "h")] UNSPEC_STOREHF_INT))]
  ""
  "push\\t%0"
  [(set_attr "type" "push")])
 
-; we can not 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"
 ;  [(set (match_operand:HF 0 "reg_operand" "=h")
 ;        (mem:HF (post_dec:QI (reg:QI 20))))
               (clobber (reg:CC 21))])
    (parallel [(set (match_dup 0)
                    (unspec:HF [(subreg:QI (match_dup 0) 0)
-                   (mem:QI (post_dec:QI (reg:QI 20)))] 8))
+                   (mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
               (clobber (reg:CC 21))])]
  "")
 
 (define_insn "*pophf_int"
  [(set (match_operand:HF 0 "reg_operand" "+h")
        (unspec:HF [(subreg:QI (match_dup 0) 0)
-                   (mem:QI (post_dec:QI (reg:QI 20)))] 8))
+                   (mem:QI (post_dec:QI (reg:QI 20)))] UNSPEC_LOADHF_INT))
   (clobber (reg:CC 21))]
  ""
- "@
-  pop\\t%0"
+ "pop\\t%0"
   [(set_attr "type" "pop")])
 
 (define_insn "*pophf_float"
        (float_extend:HF (mem:QF (post_dec:QI (reg:QI 20)))))
   (clobber (reg:CC 21))]
  ""
- "@
-  popf\\t%0"
+ "popf\\t%0"
   [(set_attr "type" "pop")])
 
 ;
 ; FIX
 ;
+(define_expand "fixuns_trunchfqi2"
+ [(parallel [(set (match_dup 2)
+                 (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
+            (clobber (reg:CC 21))])
+  (parallel [(set (match_dup 3)
+                 (minus:HF (match_dup 1) (match_dup 5)))
+            (clobber (reg:CC_NOOV 21))])
+  (parallel [(set (reg:CC 21)
+                 (compare:CC (fix:QI (match_dup 3))
+                             (const_int 0)))
+            (set (match_dup 4)
+                 (fix:QI (match_dup 3)))])
+  (parallel [(set (match_dup 4) (unspec:QI [(match_dup 2)] UNSPEC_LDIV))
+             (use (reg:CC 21))])
+  (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 4))]
+ ""
+ "operands[2] = gen_reg_rtx (QImode);
+  operands[3] = gen_reg_rtx (HFmode);
+  operands[4] = gen_reg_rtx (QImode);
+  operands[5] = gen_reg_rtx (HFmode);
+  emit_move_insn (operands[5], CONST_DOUBLE_ATOF (\"4294967296.0\", HFmode));")
+
+(define_expand "fix_trunchfqi2"
+  [(parallel [(set (match_dup 2)
+                   (fix:QI (match_operand:HF 1 "reg_or_const_operand" "")))
+              (clobber (reg:CC 21))])
+   (parallel [(set (match_dup 3) (neg:HF (match_dup 1)))
+              (clobber (reg:CC_NOOV 21))])
+   (parallel [(set (match_dup 4) (fix:QI (match_dup 3)))
+              (clobber (reg:CC 21))])
+   (parallel [(set (reg:CC_NOOV 21)
+                   (compare:CC_NOOV (neg:QI (match_dup 4)) (const_int 0)))
+              (set (match_dup 5) (neg:QI (match_dup 4)))])
+   (set (match_dup 2)
+        (if_then_else:QI (le (reg:CC 21) (const_int 0))
+                         (match_dup 5)
+                         (match_dup 2)))
+   (set (match_operand:QI 0 "reg_operand" "=r") (match_dup 2))]
+ ""
+ "if (TARGET_FAST_FIX)
+    {
+       emit_insn (gen_fixhfqi_clobber (operands[0], operands[1]));
+       DONE;
+    }
+  operands[2] = gen_reg_rtx (QImode);
+  operands[3] = gen_reg_rtx (HFmode);
+  operands[4] = gen_reg_rtx (QImode);
+  operands[5] = gen_reg_rtx (QImode);
+ ")
+
+(define_insn "*fixhfqi_set"
+  [(set (reg:CC 21)
+        (compare:CC (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH"))
+                    (const_int 0)))
+   (set (match_operand:QI 0 "ext_reg_operand" "=d")
+        (fix:QI (match_dup 1)))]
+ ""
+ "fix\\t%1,%0"
+  [(set_attr "type" "unarycc")])
+
 (define_insn "fixhfqi_clobber"
   [(set (match_operand:QI 0 "reg_operand" "=dc")
         (fix:QI (match_operand:HF 1 "reg_or_const_operand" "hH")))
  "fix\\t%1,%0"
   [(set_attr "type" "unarycc")])
 
+(define_expand "fix_trunchfhi2"
+  [(parallel [(set (match_operand:HI 0 "reg_operand" "")
+                   (fix:HI (match_operand:HF 1 "reg_operand" "")))
+              (clobber (reg:CC 21))])]
+  ""
+  "c4x_emit_libcall (fix_trunchfhi2_libfunc, FIX, HImode, HFmode, 2, operands);
+   DONE;")
+
+(define_expand "fixuns_trunchfhi2"
+  [(parallel [(set (match_operand:HI 0 "reg_operand" "")
+                   (unsigned_fix:HI (match_operand:HF 1 "reg_operand" "")))
+              (clobber (reg:CC 21))])]
+  ""
+  "c4x_emit_libcall (fixuns_trunchfhi2_libfunc, UNSIGNED_FIX, 
+                     HImode, HFmode, 2, operands);
+   DONE;")
+
 ;
 ; ABSF
 ;
 ;
 (define_insn "*rcpfhf_clobber"
   [(set (match_operand:HF 0 "reg_operand" "=h")
-        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] 5))
+        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RCPF))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rcpf\\t%1,%0"
 ;
 (define_insn "*rsqrfhf_clobber"
   [(set (match_operand:HF 0 "reg_operand" "=h")
-        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] 10))
+        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RSQRF))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rsqrf\\t%1,%0"
 ;
 (define_insn "*rndhf_clobber"
   [(set (match_operand:HF 0 "reg_operand" "=h")
-        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] 6))
+        (unspec:HF [(match_operand:HF 1 "reg_or_const_operand" "hH")] UNSPEC_RND))
    (clobber (reg:CC_NOOV 21))]
   "! TARGET_C3X"
   "rnd\\t%1,%0"
 ; Inlined float square root for C4x
 (define_expand "sqrthf2_inline"
   [(parallel [(set (match_dup 2)
-                  (unspec:HF [(match_operand:HF 1 "reg_operand" "")] 10))
+                  (unspec:HF [(match_operand:HF 1 "reg_operand" "")] UNSPEC_RSQRF))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_dup 3) (mult:HF (match_dup 5) (match_dup 1)))
              (clobber (reg:CC_NOOV 21))])
   operands[2] = gen_reg_rtx (HFmode);
   operands[3] = gen_reg_rtx (HFmode);
   operands[4] = gen_reg_rtx (HFmode);
-  operands[5] = immed_real_const_1 (REAL_VALUE_ATOF (\"0.5\", HFmode), HFmode);
-  operands[6] = immed_real_const_1 (REAL_VALUE_ATOF (\"1.5\", HFmode), HFmode);
+  operands[5] = CONST_DOUBLE_ATOF (\"0.5\", HFmode);
+  operands[6] = CONST_DOUBLE_ATOF (\"1.5\", HFmode);
   ")
 
 
   "emit_insn (gen_sqrthf2_inline (operands[0], operands[1]));
    DONE;")
 
-
-(define_expand "fix_trunchfhi2"
-  [(parallel [(set (match_operand:HI 0 "reg_operand" "")
-                   (fix:HI (match_operand:HF 1 "reg_operand" "")))
-              (clobber (reg:CC 21))])]
-  ""
-  "c4x_emit_libcall (fix_trunchfhi2_libfunc, FIX, HImode, HFmode, 2, operands);
-   DONE;")
-
-(define_expand "fixuns_trunchfhi2"
-  [(parallel [(set (match_operand:HI 0 "reg_operand" "")
-                   (unsigned_fix:HI (match_operand:HF 1 "reg_operand" "")))
-              (clobber (reg:CC 21))])]
-  ""
-  "c4x_emit_libcall (fixuns_trunchfhi2_libfunc, UNSIGNED_FIX, 
-                     HImode, HFmode, 2, operands);
-   DONE;")
-
 ;
 ; THREE OPERAND LONG DOUBLE INSTRUCTIONS
 ;
 ;
 ; MULF
 ;
-; The C3x MPYF only uses 24 bit precision while the C4x uses 32 bit precison.
+; The C3x MPYF only uses 24-bit precision while the C4x uses 32-bit precision.
 ;
 (define_expand "mulhf3"
   [(parallel [(set (match_operand:HF 0 "reg_operand" "=h")
 ; Inlined float divide for C4x
 (define_expand "divhf3_inline"
   [(parallel [(set (match_dup 3)
-                  (unspec:HF [(match_operand:HF 2 "reg_operand" "")] 5))
+                  (unspec:HF [(match_operand:HF 2 "reg_operand" "")] UNSPEC_RCPF))
              (clobber (reg:CC_NOOV 21))])
    (parallel [(set (match_dup 4) (mult:HF (match_dup 2) (match_dup 3)))
              (clobber (reg:CC_NOOV 21))])
   [(set_attr "type" "multi")])
 
 (define_split
-  [(set (match_operand:HI 0 "reg_operand" "=?dc")
-        (sign_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
+  [(set (match_operand:HI 0 "reg_operand" "")
+        (sign_extend:HI (match_operand:QI 1 "src_operand" "")))
    (clobber (reg:CC 21))]
   "reload_completed && TARGET_C3X"
   [(set (match_dup 2) (match_dup 1))
    operands[3] = c4x_operand_subword (operands[0], 1, 0, HImode);")
 
 (define_split
-  [(set (match_operand:HI 0 "reg_operand" "=?dc")
-        (sign_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
+  [(set (match_operand:HI 0 "reg_operand" "")
+        (sign_extend:HI (match_operand:QI 1 "src_operand" "")))
    (clobber (reg:CC 21))]
   "reload_completed && ! TARGET_C3X"
   [(set (match_dup 2) (match_dup 1))
 
 (define_insn "zero_extendqihi2"
   [(set (match_operand:HI 0 "reg_operand" "=?dc")
-        (zero_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
+        (zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "rm")))
    (clobber (reg:CC 21))]
   ""
   "#"
 ; If operand0 and operand1 are the same register we don't need
 ; the first set.
 (define_split
-  [(set (match_operand:HI 0 "reg_operand" "=?dc")
-        (zero_extend:HI (match_operand:QI 1 "src_operand" "rIm")))
+  [(set (match_operand:HI 0 "reg_operand" "")
+        (zero_extend:HI (match_operand:QI 1 "nonimmediate_src_operand" "")))
    (clobber (reg:CC 21))]
   "reload_completed"
   [(set (match_dup 2) (match_dup 1))
   /* If the shift count is greater than 32 this will do an arithmetic
      right shift.  However, we need a logical right shift.  */
   (parallel [(set (match_dup 9)
-                  (ashift:QI (match_dup 4) (unspec:QI [(match_dup 10)] 3)))
+                  (ashift:QI (match_dup 4) (unspec:QI [(match_dup 10)] UNSPEC_LSH)))
              (clobber (reg:CC 21))])
   (set (match_dup 6) (match_dup 8))
   (parallel [(set (match_dup 5)
   "! reload_completed"
   [(parallel [(set (reg:CC 21)
                    (unspec:CC [(compare:CC (match_dup 0)
-                                           (match_dup 1))] 4))
+                                           (match_dup 1))] UNSPEC_CMPHI))
               (clobber (match_scratch:QI 2 ""))
              (clobber (match_scratch:QI 3 ""))])]
   "")
   "! reload_completed"
   [(parallel [(set (reg:CC_NOOV 21)
                    (unspec:CC_NOOV [(compare:CC_NOOV (match_dup 0)
-                                                     (match_dup 1))] 4))
+                                                     (match_dup 1))] UNSPEC_CMPHI))
               (clobber (match_scratch:QI 2 ""))
              (clobber (match_scratch:QI 3 ""))])]
   "")
 (define_insn "cmphi_cc"
   [(set (reg:CC 21)
         (unspec:CC [(compare:CC (match_operand:HI 0 "src_operand" "rR,rS<>")
-                                (match_operand:HI 1 "src_operand" "R,rS<>"))] 4))
+                                (match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
    (clobber (match_scratch:QI 2 "=&d,&d"))
    (clobber (match_scratch:QI 3 "=&c,&c"))]
   "valid_operands (COMPARE, operands, HImode)"
 (define_insn "cmphi_cc_noov"
   [(set (reg:CC_NOOV 21)
         (unspec:CC_NOOV [(compare:CC_NOOV (match_operand:HI 0 "src_operand" "rR,rS<>")
-                                     (match_operand:HI 1 "src_operand" "R,rS<>"))] 4))
+                                     (match_operand:HI 1 "src_operand" "R,rS<>"))] UNSPEC_CMPHI))
    (clobber (match_scratch:QI 2 "=&d,&d"))
    (clobber (match_scratch:QI 3 "=&c,&c"))]
   "valid_operands (COMPARE, operands, HImode)"
                             (match_operand:HI 2 "src_operand" "")))
               (clobber (reg:CC 21))])]
   ""
-  "c4x_emit_libcall3 (smul_optab->handlers[(int) HImode].libfunc,
+  "c4x_emit_libcall3 (optab_libfunc (smul_optab, HImode),
                      MULT, HImode, operands);
    DONE;")
 
                     (match_operand:QI 1 "general_operand" ""))
               (clobber (reg:QI 31))])
    (return)]
-  "c4x_null_epilogue_p ()"
+  "c4x_null_epilogue_p ()"
   "*
    if (REG_P (operands[0]))
      return \"bu%#\\t%C0\";
                          (match_operand:QI 2 "general_operand" "")))
               (clobber (reg:QI 31))])
    (return)]
-  "c4x_null_epilogue_p ()"
+  "c4x_null_epilogue_p ()"
   "*
    if (REG_P (operands[1]))
      return \"bu%#\\t%C1\";
  "stf\\t%1,*%0++\\n\\tstf\\t%2,*%0++")
 
 
-; The following two peepholes remove an unecessary load
+; The following two peepholes remove an unnecessary load
 ; often found at the end of a function.  These peepholes
-; could be generalised 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.
 (define_peephole
  [(parallel [(set (match_operand:QF 0 "ext_reg_operand" "")