|
|
1.1 ! root 1: ;; Mips.md Machine Description for MIPS based processors ! 2: ;; Contributed by A. Lichnewsky, [email protected] ! 3: ;; Changes by Michael Meissner, [email protected] ! 4: ;; Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc. ! 5: ! 6: ;; This file is part of GNU CC. ! 7: ! 8: ;; GNU CC is free software; you can redistribute it and/or modify ! 9: ;; it under the terms of the GNU General Public License as published by ! 10: ;; the Free Software Foundation; either version 2, or (at your option) ! 11: ;; any later version. ! 12: ! 13: ;; GNU CC is distributed in the hope that it will be useful, ! 14: ;; but WITHOUT ANY WARRANTY; without even the implied warranty of ! 15: ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ! 16: ;; GNU General Public License for more details. ! 17: ! 18: ;; You should have received a copy of the GNU General Public License ! 19: ;; along with GNU CC; see the file COPYING. If not, write to ! 20: ;; the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. ! 21: ! 22: ! 23: ! 24: ;; .................... ! 25: ;; ! 26: ;; Attributes ! 27: ;; ! 28: ;; .................... ! 29: ! 30: ;; Classification of each insn. ! 31: ;; branch conditional branch ! 32: ;; jump unconditional jump ! 33: ;; call unconditional call ! 34: ;; load load instruction(s) ! 35: ;; store store instruction(s) ! 36: ;; move data movement within same register set ! 37: ;; xfer transfer to/from coprocessor ! 38: ;; hilo transfer of hi/lo registers ! 39: ;; arith integer arithmetic instruction ! 40: ;; darith double precision integer arithmetic instructions ! 41: ;; imul integer multiply ! 42: ;; idiv integer divide ! 43: ;; icmp integer compare ! 44: ;; fadd floating point add/subtract ! 45: ;; fmul floating point multiply ! 46: ;; fdiv floating point divide ! 47: ;; fabs floating point absolute value ! 48: ;; fneg floating point negation ! 49: ;; fcmp floating point compare ! 50: ;; fcvt floating point convert ! 51: ;; fsqrt floating point square root ! 52: ;; multi multiword sequence (or user asm statements) ! 53: ;; nop no operation ! 54: ;; pic OSF/rose half pic load ! 55: ! 56: (define_attr "type" ! 57: "unknown,branch,jump,call,load,store,move,xfer,hilo,arith,darith,imul,idiv,icmp,fadd,fmul,fdiv,fabs,fneg,fcmp,fcvt,fsqrt,multi,nop,pic" ! 58: (const_string "unknown")) ! 59: ! 60: ;; Main data type used by the insn ! 61: (define_attr "mode" "unknown,none,QI,HI,SI,DI,SF,DF" (const_string "unknown")) ! 62: ! 63: ;; # instructions (4 bytes each) ! 64: (define_attr "length" "" (const_int 1)) ! 65: ! 66: ;; whether or not an instruction has a mandiatory delay slot ! 67: (define_attr "dslot" "no,yes" ! 68: (if_then_else (eq_attr "type" "branch,jump,call,load,xfer,hilo,fcmp") ! 69: (const_string "yes") ! 70: (const_string "no"))) ! 71: ! 72: ;; Attribute describing the processor ! 73: (define_attr "cpu" "default,r3000,r4000,r6000" ! 74: ; (const ! 75: (cond [(eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_DEFAULT")) (const_string "default") ! 76: (eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R3000")) (const_string "r3000") ! 77: (eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R4000")) (const_string "r4000") ! 78: (eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R6000")) (const_string "r6000")] ! 79: (const_string "default"))) ! 80: ! 81: ;; Attribute defining whether or not we can use the branch-likely instructions ! 82: ;; (MIPS ISA level 2) ! 83: ! 84: (define_attr "branch_likely" "no,yes" ! 85: ; (const ! 86: (if_then_else (ge (symbol_ref "mips_isa") (const_int 2)) ! 87: (const_string "yes") ! 88: (const_string "no"))) ! 89: ! 90: ! 91: ;; Describe a user's asm statement. ! 92: (define_asm_attributes ! 93: [(set_attr "type" "multi")]) ! 94: ! 95: ! 96: ! 97: ;; ......................... ! 98: ;; ! 99: ;; Delay slots, can't describe load/fcmp/xfer delay slots here ! 100: ;; ! 101: ;; ......................... ! 102: ! 103: (define_delay (eq_attr "type" "branch") ! 104: [(and (eq_attr "dslot" "no") (eq_attr "length" "1")) ! 105: (nil) ! 106: (eq_attr "branch_likely" "yes")]) ! 107: ! 108: (define_delay (eq_attr "type" "call,jump") ! 109: [(and (eq_attr "dslot" "no") (eq_attr "length" "1")) ! 110: (nil) ! 111: (nil)]) ! 112: ! 113: ! 114: ! 115: ;; ......................... ! 116: ;; ! 117: ;; Functional units ! 118: ;; ! 119: ;; ......................... ! 120: ! 121: ; (define_function_unit NAME MULTIPLICITY SIMULTANEITY ! 122: ; TEST READY-DELAY BUSY-DELAY [CONFLICT-LIST]) ! 123: ! 124: ;; Make the default case (PROCESSOR_DEFAULT) handle the worst case ! 125: ;; At present, the functional units with cpu attributes fully ! 126: ;; specified cause genattrtab to use more than 32 megabytes of ! 127: ;; data, which is too much for some systems, so simplify things ! 128: ;; to use only the default case. ! 129: ! 130: (define_function_unit "memory" 1 0 (eq_attr "type" "load,pic") 3 0) ! 131: (define_function_unit "memory" 1 0 (eq_attr "type" "store") 1 0) ! 132: ! 133: (define_function_unit "transfer" 1 0 (eq_attr "type" "xfer") 2 0) ! 134: (define_function_unit "transfer" 1 0 (eq_attr "type" "hilo") 3 0) ! 135: ! 136: (define_function_unit "imuldiv" 1 1 (eq_attr "type" "imul") 17 34) ! 137: (define_function_unit "imuldiv" 1 1 (eq_attr "type" "idiv") 38 76) ! 138: ! 139: (define_function_unit "adder" 1 1 (eq_attr "type" "fadd") 4 8) ! 140: (define_function_unit "fast" 1 1 (eq_attr "type" "fabs,fneg") 2 4) ! 141: ! 142: (define_function_unit "mult" 1 1 (and (eq_attr "type" "fmul") (eq_attr "mode" "SF")) 7 14) ! 143: (define_function_unit "mult" 1 1 (and (eq_attr "type" "fmul") (eq_attr "mode" "DF")) 8 16) ! 144: ! 145: (define_function_unit "divide" 1 1 (and (eq_attr "type" "fdiv") (eq_attr "mode" "SF")) 23 46) ! 146: (define_function_unit "divide" 1 1 (and (eq_attr "type" "fdiv") (eq_attr "mode" "DF")) 36 72) ! 147: ! 148: (define_function_unit "sqrt" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "SF")) 54 108) ! 149: (define_function_unit "sqrt" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "DF")) 112 224) ! 150: ! 151: ;; (define_function_unit "memory" 1 0 ! 152: ;; (and (eq_attr "type" "load,pic") (eq_attr "cpu" "!r3000")) ! 153: ;; 3 0) ! 154: ;; ! 155: ;; (define_function_unit "memory" 1 0 ! 156: ;; (and (eq_attr "type" "load,pic") (eq_attr "cpu" "r3000")) ! 157: ;; 2 0) ! 158: ;; ! 159: ;; (define_function_unit "memory" 1 0 (eq_attr "type" "store") 1 0) ! 160: ;; ! 161: ;; (define_function_unit "transfer" 1 0 (eq_attr "type" "xfer") 2 0) ! 162: ;; (define_function_unit "transfer" 1 0 (eq_attr "type" "hilo") 3 0) ! 163: ;; ! 164: ;; (define_function_unit "imuldiv" 1 1 ! 165: ;; (and (eq_attr "type" "imul") (eq_attr "cpu" "!r3000,r4000")) ! 166: ;; 17 34) ! 167: ;; ! 168: ;; (define_function_unit "imuldiv" 1 1 ! 169: ;; (and (eq_attr "type" "imul") (eq_attr "cpu" "r3000")) ! 170: ;; 12 24) ! 171: ;; ! 172: ;; (define_function_unit "imuldiv" 1 1 ! 173: ;; (and (eq_attr "type" "imul") (eq_attr "cpu" "r4000")) ! 174: ;; 10 20) ! 175: ;; ! 176: ;; (define_function_unit "imuldiv" 1 1 ! 177: ;; (and (eq_attr "type" "idiv") (eq_attr "cpu" "!r3000,r4000")) ! 178: ;; 38 76) ! 179: ;; ! 180: ;; (define_function_unit "imuldiv" 1 1 ! 181: ;; (and (eq_attr "type" "idiv") (eq_attr "cpu" "r3000")) ! 182: ;; 35 70) ! 183: ;; ! 184: ;; (define_function_unit "imuldiv" 1 1 ! 185: ;; (and (eq_attr "type" "idiv") (eq_attr "cpu" "r4000")) ! 186: ;; 69 138) ! 187: ;; ! 188: ;; (define_function_unit "adder" 1 1 ! 189: ;; (and (eq_attr "type" "fadd") (eq_attr "cpu" "!r3000,r6000")) ! 190: ;; 4 8) ! 191: ;; ! 192: ;; (define_function_unit "adder" 1 1 ! 193: ;; (and (eq_attr "type" "fadd") (eq_attr "cpu" "r3000")) ! 194: ;; 2 4) ! 195: ;; ! 196: ;; (define_function_unit "adder" 1 1 ! 197: ;; (and (eq_attr "type" "fadd") (eq_attr "cpu" "r6000")) ! 198: ;; 3 6) ! 199: ;; ! 200: ;; (define_function_unit "fast" 1 1 ! 201: ;; (and (eq_attr "type" "fabs,fneg") (eq_attr "cpu" "!r3000")) ! 202: ;; 2 4) ! 203: ;; ! 204: ;; (define_function_unit "fast" 1 1 ! 205: ;; (and (eq_attr "type" "fabs,fneg") (eq_attr "cpu" "r3000")) ! 206: ;; 1 2) ! 207: ;; ! 208: ;; (define_function_unit "mult" 1 1 ! 209: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "!r3000,r6000"))) ! 210: ;; 7 14) ! 211: ;; ! 212: ;; (define_function_unit "mult" 1 1 ! 213: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000"))) ! 214: ;; 4 8) ! 215: ;; ! 216: ;; (define_function_unit "mult" 1 1 ! 217: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000"))) ! 218: ;; 5 10) ! 219: ;; ! 220: ;; (define_function_unit "mult" 1 1 ! 221: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r3000,r6000"))) ! 222: ;; 8 16) ! 223: ;; ! 224: ;; (define_function_unit "mult" 1 1 ! 225: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000"))) ! 226: ;; 5 10) ! 227: ;; ! 228: ;; (define_function_unit "mult" 1 1 ! 229: ;; (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000"))) ! 230: ;; 6 12) ! 231: ;; ! 232: ;; (define_function_unit "divide" 1 1 ! 233: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "!r3000,r6000"))) ! 234: ;; 23 46) ! 235: ;; ! 236: ;; (define_function_unit "divide" 1 1 ! 237: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000"))) ! 238: ;; 12 24) ! 239: ;; ! 240: ;; (define_function_unit "divide" 1 1 ! 241: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000"))) ! 242: ;; 15 30) ! 243: ;; ! 244: ;; (define_function_unit "divide" 1 1 ! 245: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r3000,r6000"))) ! 246: ;; 36 72) ! 247: ;; ! 248: ;; (define_function_unit "divide" 1 1 ! 249: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000"))) ! 250: ;; 19 34) ! 251: ;; ! 252: ;; (define_function_unit "divide" 1 1 ! 253: ;; (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000"))) ! 254: ;; 16 32) ! 255: ;; ! 256: ;; (define_function_unit "sqrt" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "SF")) 54 108) ! 257: ;; (define_function_unit "sqrt" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "DF")) 112 224) ! 258: ! 259: ! 260: ;; ! 261: ;; .................... ! 262: ;; ! 263: ;; ADDITION ! 264: ;; ! 265: ;; .................... ! 266: ;; ! 267: ! 268: (define_insn "adddf3" ! 269: [(set (match_operand:DF 0 "register_operand" "=f") ! 270: (plus:DF (match_operand:DF 1 "register_operand" "f") ! 271: (match_operand:DF 2 "register_operand" "f")))] ! 272: "TARGET_HARD_FLOAT" ! 273: "add.d\\t%0,%1,%2" ! 274: [(set_attr "type" "fadd") ! 275: (set_attr "mode" "DF") ! 276: (set_attr "length" "1")]) ! 277: ! 278: (define_insn "addsf3" ! 279: [(set (match_operand:SF 0 "register_operand" "=f") ! 280: (plus:SF (match_operand:SF 1 "register_operand" "f") ! 281: (match_operand:SF 2 "register_operand" "f")))] ! 282: "TARGET_HARD_FLOAT" ! 283: "add.s\\t%0,%1,%2" ! 284: [(set_attr "type" "fadd") ! 285: (set_attr "mode" "SF") ! 286: (set_attr "length" "1")]) ! 287: ! 288: (define_insn "addsi3" ! 289: [(set (match_operand:SI 0 "register_operand" "=d") ! 290: (plus:SI (match_operand:SI 1 "arith_operand" "%d") ! 291: (match_operand:SI 2 "arith_operand" "dI")))] ! 292: "" ! 293: "* ! 294: { ! 295: return (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0) ! 296: ? \"subu\\t%0,%1,%n2\" ! 297: : \"addu\\t%0,%1,%2\"; ! 298: }" ! 299: [(set_attr "type" "arith") ! 300: (set_attr "mode" "SI") ! 301: (set_attr "length" "1")]) ! 302: ! 303: (define_expand "adddi3" ! 304: [(parallel [(set (match_operand:DI 0 "register_operand" "") ! 305: (plus:DI (match_operand:DI 1 "register_operand" "") ! 306: (match_operand:DI 2 "arith_operand" ""))) ! 307: (clobber (match_dup 3))])] ! 308: "!TARGET_DEBUG_G_MODE" ! 309: "operands[3] = gen_reg_rtx (SImode);") ! 310: ! 311: (define_insn "adddi3_internal_1" ! 312: [(set (match_operand:DI 0 "register_operand" "=d,&d") ! 313: (plus:DI (match_operand:DI 1 "register_operand" "0,d") ! 314: (match_operand:DI 2 "register_operand" "d,d"))) ! 315: (clobber (match_operand:SI 3 "register_operand" "=d,d"))] ! 316: "!TARGET_DEBUG_G_MODE" ! 317: "* ! 318: { ! 319: return (REGNO (operands[0]) == REGNO (operands[1]) ! 320: && REGNO (operands[0]) == REGNO (operands[2])) ! 321: ? \"srl\\t%3,%L0,31\;sll\\t%M0,%M0,1\;sll\\t%L0,%L1,1\;addu\\t%M0,%M0,%3\" ! 322: : \"addu\\t%L0,%L1,%L2\;sltu\\t%3,%L0,%L2\;addu\\t%M0,%M1,%M2\;addu\\t%M0,%M0,%3\"; ! 323: }" ! 324: [(set_attr "type" "darith,darith") ! 325: (set_attr "mode" "DI,DI") ! 326: (set_attr "length" "4,4")]) ! 327: ! 328: (define_split ! 329: [(set (match_operand:DI 0 "register_operand" "") ! 330: (plus:DI (match_operand:DI 1 "register_operand" "") ! 331: (match_operand:DI 2 "register_operand" ""))) ! 332: (clobber (match_operand:SI 3 "register_operand" ""))] ! 333: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 334: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 335: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 336: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2])) ! 337: && (REGNO (operands[0]) != REGNO (operands[1]) ! 338: || REGNO (operands[0]) != REGNO (operands[2]))" ! 339: ! 340: [(set (subreg:SI (match_dup 0) 0) ! 341: (plus:SI (subreg:SI (match_dup 1) 0) ! 342: (subreg:SI (match_dup 2) 0))) ! 343: ! 344: (set (match_dup 3) ! 345: (ltu:CC (subreg:SI (match_dup 0) 0) ! 346: (subreg:SI (match_dup 2) 0))) ! 347: ! 348: (set (subreg:SI (match_dup 0) 1) ! 349: (plus:SI (subreg:SI (match_dup 1) 1) ! 350: (subreg:SI (match_dup 2) 1))) ! 351: ! 352: (set (subreg:SI (match_dup 0) 1) ! 353: (plus:SI (subreg:SI (match_dup 0) 1) ! 354: (match_dup 3)))] ! 355: "") ! 356: ! 357: (define_split ! 358: [(set (match_operand:DI 0 "register_operand" "") ! 359: (plus:DI (match_operand:DI 1 "register_operand" "") ! 360: (match_operand:DI 2 "register_operand" ""))) ! 361: (clobber (match_operand:SI 3 "register_operand" ""))] ! 362: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 363: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 364: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 365: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2])) ! 366: && (REGNO (operands[0]) != REGNO (operands[1]) ! 367: || REGNO (operands[0]) != REGNO (operands[2]))" ! 368: ! 369: [(set (subreg:SI (match_dup 0) 1) ! 370: (plus:SI (subreg:SI (match_dup 1) 1) ! 371: (subreg:SI (match_dup 2) 1))) ! 372: ! 373: (set (match_dup 3) ! 374: (ltu:CC (subreg:SI (match_dup 0) 1) ! 375: (subreg:SI (match_dup 2) 1))) ! 376: ! 377: (set (subreg:SI (match_dup 0) 0) ! 378: (plus:SI (subreg:SI (match_dup 1) 0) ! 379: (subreg:SI (match_dup 2) 0))) ! 380: ! 381: (set (subreg:SI (match_dup 0) 0) ! 382: (plus:SI (subreg:SI (match_dup 0) 0) ! 383: (match_dup 3)))] ! 384: "") ! 385: ! 386: (define_insn "adddi3_internal_2" ! 387: [(set (match_operand:DI 0 "register_operand" "=d,d,d") ! 388: (plus:DI (match_operand:DI 1 "register_operand" "%d,%d,%d") ! 389: (match_operand:DI 2 "small_int" "P,J,N"))) ! 390: (clobber (match_operand:SI 3 "register_operand" "=d,d,d"))] ! 391: "!TARGET_DEBUG_G_MODE && INTVAL (operands[2]) != -32768" ! 392: "@ ! 393: addu\\t%L0,%L1,%2\;sltu\\t%3,%L0,%2\;addu\\t%M0,%M1,%3 ! 394: move\\t%L0,%L1\;move\\t%M0,%M1 ! 395: subu\\t%L0,%L1,%n2\;sltu\\t%3,%L0,%2\;subu\\t%M0,%M1,1\;addu\\t%M0,%M0,%3" ! 396: [(set_attr "type" "darith,darith,darith") ! 397: (set_attr "mode" "DI,DI,DI") ! 398: (set_attr "length" "3,2,4")]) ! 399: ! 400: (define_split ! 401: [(set (match_operand:DI 0 "register_operand" "") ! 402: (plus:DI (match_operand:DI 1 "register_operand" "") ! 403: (match_operand:DI 2 "small_int" ""))) ! 404: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 405: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 406: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 407: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 408: && INTVAL (operands[2]) > 0" ! 409: ! 410: [(set (subreg:SI (match_dup 0) 0) ! 411: (plus:SI (subreg:SI (match_dup 1) 0) ! 412: (match_dup 2))) ! 413: ! 414: (set (match_dup 3) ! 415: (ltu:CC (subreg:SI (match_dup 0) 0) ! 416: (match_dup 2))) ! 417: ! 418: (set (subreg:SI (match_dup 0) 1) ! 419: (plus:SI (subreg:SI (match_dup 1) 1) ! 420: (match_dup 3)))] ! 421: "") ! 422: ! 423: (define_split ! 424: [(set (match_operand:DI 0 "register_operand" "") ! 425: (plus:DI (match_operand:DI 1 "register_operand" "") ! 426: (match_operand:DI 2 "small_int" ""))) ! 427: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 428: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 429: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 430: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 431: && INTVAL (operands[2]) > 0" ! 432: ! 433: [(set (subreg:SI (match_dup 0) 1) ! 434: (plus:SI (subreg:SI (match_dup 1) 1) ! 435: (match_dup 2))) ! 436: ! 437: (set (match_dup 3) ! 438: (ltu:CC (subreg:SI (match_dup 0) 1) ! 439: (match_dup 2))) ! 440: ! 441: (set (subreg:SI (match_dup 0) 0) ! 442: (plus:SI (subreg:SI (match_dup 1) 0) ! 443: (match_dup 3)))] ! 444: "") ! 445: ! 446: ;; ! 447: ;; .................... ! 448: ;; ! 449: ;; SUBTRACTION ! 450: ;; ! 451: ;; .................... ! 452: ;; ! 453: ! 454: (define_insn "subdf3" ! 455: [(set (match_operand:DF 0 "register_operand" "=f") ! 456: (minus:DF (match_operand:DF 1 "register_operand" "f") ! 457: (match_operand:DF 2 "register_operand" "f")))] ! 458: "TARGET_HARD_FLOAT" ! 459: "sub.d\\t%0,%1,%2" ! 460: [(set_attr "type" "fadd") ! 461: (set_attr "mode" "DF") ! 462: (set_attr "length" "1")]) ! 463: ! 464: (define_insn "subsf3" ! 465: [(set (match_operand:SF 0 "register_operand" "=f") ! 466: (minus:SF (match_operand:SF 1 "register_operand" "f") ! 467: (match_operand:SF 2 "register_operand" "f")))] ! 468: "TARGET_HARD_FLOAT" ! 469: "sub.s\\t%0,%1,%2" ! 470: [(set_attr "type" "fadd") ! 471: (set_attr "mode" "SF") ! 472: (set_attr "length" "1")]) ! 473: ! 474: (define_insn "subsi3" ! 475: [(set (match_operand:SI 0 "register_operand" "=d") ! 476: (minus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ") ! 477: (match_operand:SI 2 "arith_operand" "dI")))] ! 478: "" ! 479: "* ! 480: { ! 481: return (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0) ! 482: ? \"addu\\t%0,%z1,%n2\" ! 483: : \"subu\\t%0,%z1,%2\"; ! 484: }" ! 485: [(set_attr "type" "arith") ! 486: (set_attr "mode" "SI") ! 487: (set_attr "length" "1")]) ! 488: ! 489: (define_expand "subdi3" ! 490: [(parallel [(set (match_operand:DI 0 "register_operand" "=d") ! 491: (minus:DI (match_operand:DI 1 "register_operand" "d") ! 492: (match_operand:DI 2 "register_operand" "d"))) ! 493: (clobber (match_dup 3))])] ! 494: "!TARGET_DEBUG_G_MODE" ! 495: "operands[3] = gen_reg_rtx (SImode);") ! 496: ! 497: (define_insn "subdi3_internal" ! 498: [(set (match_operand:DI 0 "register_operand" "=d") ! 499: (minus:DI (match_operand:DI 1 "register_operand" "d") ! 500: (match_operand:DI 2 "register_operand" "d"))) ! 501: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 502: "!TARGET_DEBUG_G_MODE" ! 503: "sltu\\t%3,%L1,%L2\;subu\\t%L0,%L1,%L2\;subu\\t%M0,%M1,%M2\;subu\\t%M0,%M0,%3" ! 504: [(set_attr "type" "darith") ! 505: (set_attr "mode" "DI") ! 506: (set_attr "length" "4")]) ! 507: ! 508: (define_split ! 509: [(set (match_operand:DI 0 "register_operand" "") ! 510: (minus:DI (match_operand:DI 1 "register_operand" "") ! 511: (match_operand:DI 2 "register_operand" ""))) ! 512: (clobber (match_operand:SI 3 "register_operand" ""))] ! 513: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 514: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 515: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 516: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 517: ! 518: [(set (match_dup 3) ! 519: (lt:CC (subreg:SI (match_dup 1) 0) ! 520: (subreg:SI (match_dup 2) 0))) ! 521: ! 522: (set (subreg:SI (match_dup 0) 0) ! 523: (minus:SI (subreg:SI (match_dup 1) 0) ! 524: (subreg:SI (match_dup 2) 0))) ! 525: ! 526: (set (subreg:SI (match_dup 0) 1) ! 527: (minus:SI (subreg:SI (match_dup 1) 1) ! 528: (subreg:SI (match_dup 2) 1))) ! 529: ! 530: (set (subreg:SI (match_dup 0) 1) ! 531: (minus:SI (subreg:SI (match_dup 0) 1) ! 532: (match_dup 3)))] ! 533: "") ! 534: ! 535: (define_split ! 536: [(set (match_operand:DI 0 "register_operand" "") ! 537: (minus:DI (match_operand:DI 1 "register_operand" "") ! 538: (match_operand:DI 2 "register_operand" ""))) ! 539: (clobber (match_operand:SI 3 "register_operand" ""))] ! 540: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 541: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 542: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 543: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 544: ! 545: [(set (match_dup 3) ! 546: (lt:CC (subreg:SI (match_dup 1) 1) ! 547: (subreg:SI (match_dup 2) 1))) ! 548: ! 549: (set (subreg:SI (match_dup 0) 1) ! 550: (minus:SI (subreg:SI (match_dup 1) 1) ! 551: (subreg:SI (match_dup 2) 1))) ! 552: ! 553: (set (subreg:SI (match_dup 0) 0) ! 554: (minus:SI (subreg:SI (match_dup 1) 0) ! 555: (subreg:SI (match_dup 2) 0))) ! 556: ! 557: (set (subreg:SI (match_dup 0) 0) ! 558: (minus:SI (subreg:SI (match_dup 0) 0) ! 559: (match_dup 3)))] ! 560: "") ! 561: ! 562: (define_insn "subdi3_internal_2" ! 563: [(set (match_operand:DI 0 "register_operand" "=d,d,d") ! 564: (minus:DI (match_operand:DI 1 "register_operand" "d,d,d") ! 565: (match_operand:DI 2 "small_int" "P,J,N"))) ! 566: (clobber (match_operand:SI 3 "register_operand" "=d,d,d"))] ! 567: "!TARGET_DEBUG_G_MODE && INTVAL (operands[2]) != -32768" ! 568: "@ ! 569: sltu\\t%3,%L1,%2\;subu\\t%L0,%L1,%2\;subu\\t%M0,%M1,%3 ! 570: move\\t%L0,%L1\;move\\t%M0,%M1 ! 571: sltu\\t%3,%L1,%2\;subu\\t%L0,%L1,%2\;subu\\t%M0,%M1,1\;subu\\t%M0,%M0,%3" ! 572: [(set_attr "type" "darith,darith,darith") ! 573: (set_attr "mode" "DI,DI,DI") ! 574: (set_attr "length" "3,2,4")]) ! 575: ! 576: (define_split ! 577: [(set (match_operand:DI 0 "register_operand" "") ! 578: (minus:DI (match_operand:DI 1 "register_operand" "") ! 579: (match_operand:DI 2 "small_int" ""))) ! 580: (clobber (match_operand:SI 3 "register_operand" ""))] ! 581: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 582: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 583: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 584: && INTVAL (operands[2]) > 0" ! 585: ! 586: [(set (match_dup 3) ! 587: (ltu:CC (subreg:SI (match_dup 1) 0) ! 588: (match_dup 2))) ! 589: ! 590: (set (subreg:SI (match_dup 0) 0) ! 591: (minus:SI (subreg:SI (match_dup 1) 0) ! 592: (match_dup 2))) ! 593: ! 594: (set (subreg:SI (match_dup 0) 1) ! 595: (minus:SI (subreg:SI (match_dup 1) 1) ! 596: (match_dup 3)))] ! 597: "") ! 598: ! 599: (define_split ! 600: [(set (match_operand:DI 0 "register_operand" "") ! 601: (minus:DI (match_operand:DI 1 "register_operand" "") ! 602: (match_operand:DI 2 "small_int" ""))) ! 603: (clobber (match_operand:SI 3 "register_operand" ""))] ! 604: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 605: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 606: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 607: && INTVAL (operands[2]) > 0" ! 608: ! 609: [(set (match_dup 3) ! 610: (ltu:CC (subreg:SI (match_dup 1) 1) ! 611: (match_dup 2))) ! 612: ! 613: (set (subreg:SI (match_dup 0) 1) ! 614: (minus:SI (subreg:SI (match_dup 1) 1) ! 615: (match_dup 2))) ! 616: ! 617: (set (subreg:SI (match_dup 0) 0) ! 618: (minus:SI (subreg:SI (match_dup 1) 0) ! 619: (match_dup 3)))] ! 620: "") ! 621: ! 622: ! 623: ;; ! 624: ;; .................... ! 625: ;; ! 626: ;; MULTIPLICATION ! 627: ;; ! 628: ;; .................... ! 629: ;; ! 630: ! 631: (define_insn "muldf3" ! 632: [(set (match_operand:DF 0 "register_operand" "=f") ! 633: (mult:DF (match_operand:DF 1 "register_operand" "f") ! 634: (match_operand:DF 2 "register_operand" "f")))] ! 635: "TARGET_HARD_FLOAT" ! 636: "mul.d\\t%0,%1,%2" ! 637: [(set_attr "type" "fmul") ! 638: (set_attr "mode" "DF") ! 639: (set_attr "length" "1")]) ! 640: ! 641: (define_insn "mulsf3" ! 642: [(set (match_operand:SF 0 "register_operand" "=f") ! 643: (mult:SF (match_operand:SF 1 "register_operand" "f") ! 644: (match_operand:SF 2 "register_operand" "f")))] ! 645: "TARGET_HARD_FLOAT" ! 646: "mul.s\\t%0,%1,%2" ! 647: [(set_attr "type" "fmul") ! 648: (set_attr "mode" "SF") ! 649: (set_attr "length" "1")]) ! 650: ! 651: (define_insn "mulsi3" ! 652: [(set (match_operand:SI 0 "register_operand" "=d") ! 653: (mult:SI (match_operand:SI 1 "register_operand" "d") ! 654: (match_operand:SI 2 "register_operand" "d"))) ! 655: (clobber (reg:SI 64)) ! 656: (clobber (reg:SI 65))] ! 657: "" ! 658: "* ! 659: { ! 660: rtx xoperands[10]; ! 661: ! 662: xoperands[0] = operands[0]; ! 663: xoperands[1] = gen_rtx (REG, SImode, LO_REGNUM); ! 664: ! 665: output_asm_insn (\"mult\\t%1,%2\", operands); ! 666: output_asm_insn (mips_move_1word (xoperands, insn), xoperands); ! 667: return \"\"; ! 668: }" ! 669: [(set_attr "type" "imul") ! 670: (set_attr "mode" "SI") ! 671: (set_attr "length" "3")]) ;; mult + mflo + delay ! 672: ! 673: (define_split ! 674: [(set (match_operand:SI 0 "register_operand" "") ! 675: (mult:SI (match_operand:SI 1 "register_operand" "") ! 676: (match_operand:SI 2 "register_operand" ""))) ! 677: (clobber (reg:SI 64)) ! 678: (clobber (reg:SI 65))] ! 679: "" ! 680: [(parallel [(set (reg:SI 65) ;; low register ! 681: (mult:SI (match_dup 1) ! 682: (match_dup 2))) ! 683: (clobber (reg:SI 64))]) ! 684: (set (match_dup 0) ! 685: (reg:SI 65))] ! 686: "") ! 687: ! 688: (define_insn "mulsi3_internal" ! 689: [(set (reg:SI 65) ;; low register ! 690: (mult:SI (match_operand:SI 0 "register_operand" "d") ! 691: (match_operand:SI 1 "register_operand" "d"))) ! 692: (clobber (reg:SI 64))] ! 693: "" ! 694: "mult\\t%0,%1" ! 695: [(set_attr "type" "imul") ! 696: (set_attr "mode" "SI") ! 697: (set_attr "length" "1")]) ! 698: ! 699: (define_insn "mulsidi3" ! 700: [(set (match_operand:DI 0 "register_operand" "=d") ! 701: (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d")) ! 702: (sign_extend:DI (match_operand:SI 2 "register_operand" "d")))) ! 703: (clobber (reg:DI 64))] ! 704: "" ! 705: "* ! 706: { ! 707: rtx xoperands[10]; ! 708: ! 709: xoperands[0] = operands[0]; ! 710: xoperands[1] = gen_rtx (REG, DImode, MD_REG_FIRST); ! 711: ! 712: output_asm_insn (\"mult\\t%1,%2\", operands); ! 713: output_asm_insn (mips_move_2words (xoperands, insn), xoperands); ! 714: return \"\"; ! 715: }" ! 716: [(set_attr "type" "imul") ! 717: (set_attr "mode" "SI") ! 718: (set_attr "length" "4")]) ;; mult + mflo + mfhi + delay ! 719: ! 720: (define_insn "umulsidi3" ! 721: [(set (match_operand:DI 0 "register_operand" "=d") ! 722: (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d")) ! 723: (zero_extend:DI (match_operand:SI 2 "register_operand" "d")))) ! 724: (clobber (reg:DI 64))] ! 725: "" ! 726: "* ! 727: { ! 728: rtx xoperands[10]; ! 729: ! 730: xoperands[0] = operands[0]; ! 731: xoperands[1] = gen_rtx (REG, DImode, MD_REG_FIRST); ! 732: ! 733: output_asm_insn (\"multu\\t%1,%2\", operands); ! 734: output_asm_insn (mips_move_2words (xoperands, insn), xoperands); ! 735: return \"\"; ! 736: }" ! 737: [(set_attr "type" "imul") ! 738: (set_attr "mode" "SI") ! 739: (set_attr "length" "4")]) ;; mult + mflo + mfhi + delay ! 740: ! 741: ! 742: ;; ! 743: ;; .................... ! 744: ;; ! 745: ;; DIVISION and REMAINDER ! 746: ;; ! 747: ;; .................... ! 748: ;; ! 749: ! 750: (define_insn "divdf3" ! 751: [(set (match_operand:DF 0 "register_operand" "=f") ! 752: (div:DF (match_operand:DF 1 "register_operand" "f") ! 753: (match_operand:DF 2 "register_operand" "f")))] ! 754: "TARGET_HARD_FLOAT" ! 755: "div.d\\t%0,%1,%2" ! 756: [(set_attr "type" "fdiv") ! 757: (set_attr "mode" "DF") ! 758: (set_attr "length" "1")]) ! 759: ! 760: (define_insn "divsf3" ! 761: [(set (match_operand:SF 0 "register_operand" "=f") ! 762: (div:SF (match_operand:SF 1 "register_operand" "f") ! 763: (match_operand:SF 2 "register_operand" "f")))] ! 764: "TARGET_HARD_FLOAT" ! 765: "div.s\\t%0,%1,%2" ! 766: [(set_attr "type" "fdiv") ! 767: (set_attr "mode" "SF") ! 768: (set_attr "length" "1")]) ! 769: ! 770: ;; If optimizing, prefer the divmod functions over separate div and ! 771: ;; mod functions, since this will allow using one instruction for both ! 772: ;; the quotient and remainder. At present, the divmod is not moved out ! 773: ;; of loops if it is constant within the loop, so allow -mdebugc to ! 774: ;; use the old method of doing things. ! 775: ! 776: ;; 64 is the multiply/divide hi register ! 777: ;; 65 is the multiply/divide lo register ! 778: ! 779: (define_insn "divmodsi4" ! 780: [(parallel [(set (match_operand:SI 0 "register_operand" "=d") ! 781: (div:SI (match_operand:SI 1 "register_operand" "d") ! 782: (match_operand:SI 2 "register_operand" "d"))) ! 783: (set (match_operand:SI 3 "register_operand" "=d") ! 784: (mod:SI (match_dup 1) ! 785: (match_dup 2))) ! 786: (clobber (reg:SI 64)) ! 787: (clobber (reg:SI 65))])] ! 788: "optimize && !TARGET_DEBUG_C_MODE" ! 789: "* ! 790: { ! 791: if (find_reg_note (insn, REG_UNUSED, operands[3])) ! 792: return \"div\\t%0,%1,%2\"; ! 793: ! 794: if (find_reg_note (insn, REG_UNUSED, operands[0])) ! 795: return \"rem\\t%3,%1,%2\"; ! 796: ! 797: return \"div\\t%0,%1,%2\;mfhi\\t%3\"; ! 798: }" ! 799: [(set_attr "type" "idiv") ! 800: (set_attr "mode" "SI") ! 801: (set_attr "length" "13")]) ;; various tests for dividing by 0 and such ! 802: ! 803: (define_insn "udivmodsi4" ! 804: [(parallel [(set (match_operand:SI 0 "register_operand" "=d") ! 805: (udiv:SI (match_operand:SI 1 "register_operand" "d") ! 806: (match_operand:SI 2 "register_operand" "d"))) ! 807: (set (match_operand:SI 3 "register_operand" "=d") ! 808: (umod:SI (match_dup 1) ! 809: (match_dup 2))) ! 810: (clobber (reg:SI 64)) ! 811: (clobber (reg:SI 65))])] ! 812: "optimize && !TARGET_DEBUG_C_MODE" ! 813: "* ! 814: { ! 815: if (find_reg_note (insn, REG_UNUSED, operands[3])) ! 816: return \"divu\\t%0,%1,%2\"; ! 817: ! 818: if (find_reg_note (insn, REG_UNUSED, operands[0])) ! 819: return \"remu\\t%3,%1,%2\"; ! 820: ! 821: return \"divu\\t%0,%1,%2\;mfhi\\t%3\"; ! 822: }" ! 823: [(set_attr "type" "idiv") ! 824: (set_attr "mode" "SI") ! 825: (set_attr "length" "13")]) ;; various tests for dividing by 0 and such ! 826: ! 827: (define_insn "divsi3" ! 828: [(set (match_operand:SI 0 "register_operand" "=d") ! 829: (div:SI (match_operand:SI 1 "register_operand" "d") ! 830: (match_operand:SI 2 "register_operand" "d"))) ! 831: (clobber (reg:SI 64)) ! 832: (clobber (reg:SI 65))] ! 833: "!optimize || TARGET_DEBUG_C_MODE" ! 834: "div\\t%0,%1,%2" ! 835: [(set_attr "type" "idiv") ! 836: (set_attr "mode" "SI") ! 837: (set_attr "length" "13")]) ;; various tests for dividing by 0 and such ! 838: ! 839: (define_insn "modsi3" ! 840: [(set (match_operand:SI 0 "register_operand" "=d") ! 841: (mod:SI (match_operand:SI 1 "register_operand" "d") ! 842: (match_operand:SI 2 "register_operand" "d"))) ! 843: (clobber (reg:SI 64)) ! 844: (clobber (reg:SI 65))] ! 845: "!optimize || TARGET_DEBUG_C_MODE" ! 846: "rem\\t%0,%1,%2" ! 847: [(set_attr "type" "idiv") ! 848: (set_attr "mode" "SI") ! 849: (set_attr "length" "14")]) ;; various tests for dividing by 0 and such ! 850: ! 851: (define_insn "udivsi3" ! 852: [(set (match_operand:SI 0 "register_operand" "=d") ! 853: (udiv:SI (match_operand:SI 1 "register_operand" "d") ! 854: (match_operand:SI 2 "register_operand" "d"))) ! 855: (clobber (reg:SI 64)) ! 856: (clobber (reg:SI 65))] ! 857: "!optimize || TARGET_DEBUG_C_MODE" ! 858: "divu\\t%0,%1,%2" ! 859: [(set_attr "type" "idiv") ! 860: (set_attr "mode" "SI") ! 861: (set_attr "length" "14")]) ;; various tests for dividing by 0 and such ! 862: ! 863: (define_insn "umodsi3" ! 864: [(set (match_operand:SI 0 "register_operand" "=d") ! 865: (umod:SI (match_operand:SI 1 "register_operand" "d") ! 866: (match_operand:SI 2 "register_operand" "d"))) ! 867: (clobber (reg:SI 64)) ! 868: (clobber (reg:SI 65))] ! 869: "!optimize || TARGET_DEBUG_C_MODE" ! 870: "remu\\t%0,%1,%2" ! 871: [(set_attr "type" "idiv") ! 872: (set_attr "mode" "SI") ! 873: (set_attr "length" "14")]) ;; various tests for dividing by 0 and such ! 874: ! 875: ! 876: ;; ! 877: ;; .................... ! 878: ;; ! 879: ;; SQUARE ROOT ! 880: ;; ! 881: ;; .................... ! 882: ! 883: (define_insn "sqrtdf2" ! 884: [(set (match_operand:DF 0 "register_operand" "=f") ! 885: (sqrt:DF (match_operand:DF 1 "register_operand" "f")))] ! 886: "TARGET_HARD_FLOAT && HAVE_SQRT_P()" ! 887: "sqrt.d\\t%0,%1" ! 888: [(set_attr "type" "fabs") ! 889: (set_attr "mode" "DF") ! 890: (set_attr "length" "1")]) ! 891: ! 892: (define_insn "sqrtsf2" ! 893: [(set (match_operand:SF 0 "register_operand" "=f") ! 894: (sqrt:SF (match_operand:SF 1 "register_operand" "f")))] ! 895: "TARGET_HARD_FLOAT && HAVE_SQRT_P()" ! 896: "sqrt.s\\t%0,%1" ! 897: [(set_attr "type" "fabs") ! 898: (set_attr "mode" "SF") ! 899: (set_attr "length" "1")]) ! 900: ! 901: ! 902: ;; ! 903: ;; .................... ! 904: ;; ! 905: ;; ABSOLUTE VALUE ! 906: ;; ! 907: ;; .................... ! 908: ! 909: ;; Do not use the integer abs macro instruction, since that signals an ! 910: ;; exception on -2147483648 (sigh). ! 911: ! 912: (define_insn "abssi2" ! 913: [(set (match_operand:SI 0 "register_operand" "=d") ! 914: (abs:SI (match_operand:SI 1 "register_operand" "d")))] ! 915: "" ! 916: "* ! 917: { ! 918: dslots_jump_total++; ! 919: dslots_jump_filled++; ! 920: operands[2] = const0_rtx; ! 921: ! 922: return (REGNO (operands[0]) == REGNO (operands[1])) ! 923: ? \"bgez\\t%1,1f%#\\n\\tsubu\\t%0,%z2,%0\\n1:\" ! 924: : \"%(bgez\\t%1,1f\\n\\tmove\\t%0,%1\\n\\tsubu\\t%0,%z2,%0\\n1:%)\"; ! 925: }" ! 926: [(set_attr "type" "multi") ! 927: (set_attr "mode" "SI") ! 928: (set_attr "length" "3")]) ! 929: ! 930: (define_insn "absdf2" ! 931: [(set (match_operand:DF 0 "register_operand" "=f") ! 932: (abs:DF (match_operand:DF 1 "register_operand" "f")))] ! 933: "TARGET_HARD_FLOAT" ! 934: "abs.d\\t%0,%1" ! 935: [(set_attr "type" "fabs") ! 936: (set_attr "mode" "DF") ! 937: (set_attr "length" "1")]) ! 938: ! 939: (define_insn "abssf2" ! 940: [(set (match_operand:SF 0 "register_operand" "=f") ! 941: (abs:SF (match_operand:SF 1 "register_operand" "f")))] ! 942: "TARGET_HARD_FLOAT" ! 943: "abs.s\\t%0,%1" ! 944: [(set_attr "type" "fabs") ! 945: (set_attr "mode" "SF") ! 946: (set_attr "length" "1")]) ! 947: ! 948: ! 949: ;; ! 950: ;; .................... ! 951: ;; ! 952: ;; FIND FIRST BIT INSTRUCTION ! 953: ;; ! 954: ;; .................... ! 955: ;; ! 956: ! 957: (define_insn "ffssi2" ! 958: [(set (match_operand:SI 0 "register_operand" "=&d") ! 959: (ffs:SI (match_operand:SI 1 "register_operand" "d"))) ! 960: (clobber (match_scratch:SI 2 "d")) ! 961: (clobber (match_scratch:SI 3 "d"))] ! 962: "" ! 963: "* ! 964: { ! 965: dslots_jump_total += 2; ! 966: dslots_jump_filled += 2; ! 967: operands[4] = const0_rtx; ! 968: ! 969: if (optimize && find_reg_note (insn, REG_DEAD, operands[1])) ! 970: return \"%(\\ ! 971: move\\t%0,%z4\\n\\ ! 972: \\tbeq\\t%1,%z4,2f\\n\\ ! 973: 1:\\tand\\t%2,%1,0x0001\\n\\ ! 974: \\taddu\\t%0,%0,1\\n\\ ! 975: \\tbeq\\t%2,%z4,1b\\n\\ ! 976: \\tsrl\\t%1,%1,1\\n\\ ! 977: 2:%)\"; ! 978: ! 979: return \"%(\\ ! 980: move\\t%0,%z4\\n\\ ! 981: \\tmove\\t%3,%1\\n\\ ! 982: \\tbeq\\t%3,%z4,2f\\n\\ ! 983: 1:\\tand\\t%2,%3,0x0001\\n\\ ! 984: \\taddu\\t%0,%0,1\\n\\ ! 985: \\tbeq\\t%2,%z4,1b\\n\\ ! 986: \\tsrl\\t%3,%3,1\\n\\ ! 987: 2:%)\"; ! 988: }" ! 989: [(set_attr "type" "multi") ! 990: (set_attr "mode" "SI") ! 991: (set_attr "length" "6")]) ! 992: ! 993: ! 994: ;; ! 995: ;; .................... ! 996: ;; ! 997: ;; NEGATION and ONE'S COMPLEMENT ! 998: ;; ! 999: ;; .................... ! 1000: ! 1001: (define_insn "negsi2" ! 1002: [(set (match_operand:SI 0 "register_operand" "=d") ! 1003: (neg:SI (match_operand:SI 1 "register_operand" "d")))] ! 1004: "" ! 1005: "* ! 1006: { ! 1007: operands[2] = const0_rtx; ! 1008: return \"subu\\t%0,%z2,%1\"; ! 1009: }" ! 1010: [(set_attr "type" "arith") ! 1011: (set_attr "mode" "SI") ! 1012: (set_attr "length" "1")]) ! 1013: ! 1014: (define_expand "negdi3" ! 1015: [(parallel [(set (match_operand:DI 0 "register_operand" "=d") ! 1016: (neg:DI (match_operand:DI 1 "register_operand" "d"))) ! 1017: (clobber (match_dup 2))])] ! 1018: "!TARGET_DEBUG_G_MODE" ! 1019: "operands[2] = gen_reg_rtx (SImode);") ! 1020: ! 1021: (define_insn "negdi3_internal" ! 1022: [(set (match_operand:DI 0 "register_operand" "=d") ! 1023: (neg:DI (match_operand:DI 1 "register_operand" "d"))) ! 1024: (clobber (match_operand:SI 2 "register_operand" "=d"))] ! 1025: "!TARGET_DEBUG_G_MODE" ! 1026: "* ! 1027: { ! 1028: operands[3] = const0_rtx; ! 1029: return \"subu\\t%L0,%z3,%L1\;subu\\t%M0,%z3,%M1\;sltu\\t%2,%z3,%L0\;subu\\t%M0,%M0,%2\"; ! 1030: }" ! 1031: [(set_attr "type" "darith") ! 1032: (set_attr "mode" "DI") ! 1033: (set_attr "length" "4")]) ! 1034: ! 1035: (define_insn "negdf2" ! 1036: [(set (match_operand:DF 0 "register_operand" "=f") ! 1037: (neg:DF (match_operand:DF 1 "register_operand" "f")))] ! 1038: "TARGET_HARD_FLOAT" ! 1039: "neg.d\\t%0,%1" ! 1040: [(set_attr "type" "fneg") ! 1041: (set_attr "mode" "DF") ! 1042: (set_attr "length" "1")]) ! 1043: ! 1044: (define_insn "negsf2" ! 1045: [(set (match_operand:SF 0 "register_operand" "=f") ! 1046: (neg:SF (match_operand:SF 1 "register_operand" "f")))] ! 1047: "TARGET_HARD_FLOAT" ! 1048: "neg.s\\t%0,%1" ! 1049: [(set_attr "type" "fneg") ! 1050: (set_attr "mode" "SF") ! 1051: (set_attr "length" "1")]) ! 1052: ! 1053: (define_insn "one_cmplsi2" ! 1054: [(set (match_operand:SI 0 "register_operand" "=d") ! 1055: (not:SI (match_operand:SI 1 "register_operand" "d")))] ! 1056: "" ! 1057: "* ! 1058: { ! 1059: operands[2] = const0_rtx; ! 1060: return \"nor\\t%0,%z2,%1\"; ! 1061: }" ! 1062: [(set_attr "type" "arith") ! 1063: (set_attr "mode" "SI") ! 1064: (set_attr "length" "1")]) ! 1065: ! 1066: (define_insn "one_cmpldi2" ! 1067: [(set (match_operand:DI 0 "register_operand" "=d") ! 1068: (not:SI (match_operand:DI 1 "register_operand" "d")))] ! 1069: "" ! 1070: "* ! 1071: { ! 1072: operands[2] = const0_rtx; ! 1073: return \"nor\\t%M0,%z2,%M1\;nor\\t%L0,%z2,%L1\"; ! 1074: }" ! 1075: [(set_attr "type" "darith") ! 1076: (set_attr "mode" "DI") ! 1077: (set_attr "length" "2")]) ! 1078: ! 1079: (define_split ! 1080: [(set (match_operand:DI 0 "register_operand" "") ! 1081: (not:DI (match_operand:DI 1 "register_operand" "")))] ! 1082: "reload_completed && !TARGET_DEBUG_G_MODE ! 1083: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1084: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))" ! 1085: ! 1086: [(set (subreg:SI (match_dup 0) 0) (not:SI (subreg:SI (match_dup 1) 0))) ! 1087: (set (subreg:SI (match_dup 0) 1) (not:SI (subreg:SI (match_dup 1) 1)))] ! 1088: "") ! 1089: ! 1090: ;; Simple hack to recognize the "nor" instruction on the MIPS ! 1091: ;; This must appear before the normal or patterns, so that the ! 1092: ;; combiner will correctly fold things. ! 1093: ! 1094: (define_insn "norsi3" ! 1095: [(set (match_operand:SI 0 "register_operand" "=d") ! 1096: (not:SI (ior:SI (match_operand:SI 1 "reg_or_0_operand" "dJ") ! 1097: (match_operand:SI 2 "reg_or_0_operand" "dJ"))))] ! 1098: "" ! 1099: "nor\\t%0,%z1,%z2" ! 1100: [(set_attr "type" "arith") ! 1101: (set_attr "mode" "SI") ! 1102: (set_attr "length" "1")]) ! 1103: ! 1104: (define_insn "nordi3" ! 1105: [(set (match_operand:DI 0 "register_operand" "=d") ! 1106: (not:DI (ior:DI (match_operand:DI 1 "register_operand" "d") ! 1107: (match_operand:DI 2 "register_operand" "d"))))] ! 1108: "" ! 1109: "nor\\t%M0,%M1,%M2\;nor\\t%L0,%L1,%L2" ! 1110: [(set_attr "type" "darith") ! 1111: (set_attr "mode" "DI") ! 1112: (set_attr "length" "2")]) ! 1113: ! 1114: (define_split ! 1115: [(set (match_operand:DI 0 "register_operand" "") ! 1116: (not:DI (ior:DI (match_operand:DI 1 "register_operand" "") ! 1117: (match_operand:DI 2 "register_operand" ""))))] ! 1118: "reload_completed && !TARGET_DEBUG_G_MODE ! 1119: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1120: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 1121: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 1122: ! 1123: [(set (subreg:SI (match_dup 0) 0) (not:SI (ior:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0)))) ! 1124: (set (subreg:SI (match_dup 0) 1) (not:SI (ior:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1))))] ! 1125: "") ! 1126: ! 1127: ! 1128: ;; ! 1129: ;; .................... ! 1130: ;; ! 1131: ;; LOGICAL ! 1132: ;; ! 1133: ;; .................... ! 1134: ;; ! 1135: ! 1136: ;; Be more liberal in allowing logical operations than the machine actually ! 1137: ;; supports. This causes better code to be generated for bitfields, since ! 1138: ;; the optimizer can fold things together, at the expense of not moving the ! 1139: ;; constant out of loops. ! 1140: ! 1141: (define_insn "andsi3" ! 1142: [(set (match_operand:SI 0 "register_operand" "=d,d,?d,?d") ! 1143: (and:SI (match_operand:SI 1 "arith32_operand" "%d,d,d,d") ! 1144: (match_operand:SI 2 "arith32_operand" "d,K,I,M")))] ! 1145: "" ! 1146: "@ ! 1147: and\\t%0,%1,%2 ! 1148: andi\\t%0,%1,%x2 ! 1149: %[li\\t%@,%X2\;and\\t%0,%1,%@%] ! 1150: %[li\\t%@,%X2\;and\\t%0,%1,%@%]" ! 1151: [(set_attr "type" "arith,arith,multi,multi") ! 1152: (set_attr "mode" "SI,SI,SI,SI") ! 1153: (set_attr "length" "1,1,2,3")]) ! 1154: ! 1155: (define_insn "anddi3" ! 1156: [(set (match_operand:DI 0 "register_operand" "=d") ! 1157: (and:DI (match_operand:DI 1 "register_operand" "d") ! 1158: (match_operand:DI 2 "register_operand" "d")))] ! 1159: "!TARGET_DEBUG_G_MODE" ! 1160: "and\\t%M0,%M1,%M2\;and\\t%L0,%L1,%L2" ! 1161: [(set_attr "type" "darith") ! 1162: (set_attr "mode" "DI") ! 1163: (set_attr "length" "2")]) ! 1164: ! 1165: (define_split ! 1166: [(set (match_operand:DI 0 "register_operand" "") ! 1167: (and:DI (match_operand:DI 1 "register_operand" "") ! 1168: (match_operand:DI 2 "register_operand" "")))] ! 1169: "reload_completed && !TARGET_DEBUG_G_MODE ! 1170: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1171: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 1172: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 1173: ! 1174: [(set (subreg:SI (match_dup 0) 0) (and:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0))) ! 1175: (set (subreg:SI (match_dup 0) 1) (and:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))] ! 1176: "") ! 1177: ! 1178: (define_insn "iorsi3" ! 1179: [(set (match_operand:SI 0 "register_operand" "=d,d,?d,?d") ! 1180: (ior:SI (match_operand:SI 1 "arith32_operand" "%d,d,d,d") ! 1181: (match_operand:SI 2 "arith32_operand" "d,K,I,M")))] ! 1182: "" ! 1183: "@ ! 1184: or\\t%0,%1,%2 ! 1185: ori\\t%0,%1,%x2 ! 1186: %[li\\t%@,%X2\;or\\t%0,%1,%@%] ! 1187: %[li\\t%@,%X2\;or\\t%0,%1,%@%]" ! 1188: [(set_attr "type" "arith,arith,multi,multi") ! 1189: (set_attr "mode" "SI,SI,SI,SI") ! 1190: (set_attr "length" "1,1,2,3")]) ! 1191: ! 1192: (define_insn "iordi3" ! 1193: [(set (match_operand:DI 0 "register_operand" "=d") ! 1194: (ior:DI (match_operand:DI 1 "register_operand" "d") ! 1195: (match_operand:DI 2 "register_operand" "d")))] ! 1196: "!TARGET_DEBUG_G_MODE" ! 1197: "or\\t%M0,%M1,%M2\;or\\t%L0,%L1,%L2" ! 1198: [(set_attr "type" "darith") ! 1199: (set_attr "mode" "DI") ! 1200: (set_attr "length" "2")]) ! 1201: ! 1202: (define_split ! 1203: [(set (match_operand:DI 0 "register_operand" "") ! 1204: (ior:DI (match_operand:DI 1 "register_operand" "") ! 1205: (match_operand:DI 2 "register_operand" "")))] ! 1206: "reload_completed && !TARGET_DEBUG_G_MODE ! 1207: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1208: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 1209: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 1210: ! 1211: [(set (subreg:SI (match_dup 0) 0) (ior:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0))) ! 1212: (set (subreg:SI (match_dup 0) 1) (ior:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))] ! 1213: "") ! 1214: ! 1215: (define_insn "xorsi3" ! 1216: [(set (match_operand:SI 0 "register_operand" "=d,d,?d,?d") ! 1217: (xor:SI (match_operand:SI 1 "arith32_operand" "%d,d,d,d") ! 1218: (match_operand:SI 2 "arith32_operand" "d,K,I,M")))] ! 1219: "" ! 1220: "@ ! 1221: xor\\t%0,%1,%2 ! 1222: xori\\t%0,%1,%x2 ! 1223: %[li\\t%@,%X2\;xor\\t%0,%1,%@%] ! 1224: %[li\\t%@,%X2\;xor\\t%0,%1,%@%]" ! 1225: [(set_attr "type" "arith,arith,multi,multi") ! 1226: (set_attr "mode" "SI,SI,SI,SI") ! 1227: (set_attr "length" "1,1,2,3")]) ! 1228: ! 1229: (define_insn "xordi3" ! 1230: [(set (match_operand:DI 0 "register_operand" "=d") ! 1231: (xor:DI (match_operand:DI 1 "register_operand" "d") ! 1232: (match_operand:DI 2 "register_operand" "d")))] ! 1233: "!TARGET_DEBUG_G_MODE" ! 1234: "xor\\t%M0,%M1,%M2\;xor\\t%L0,%L1,%L2" ! 1235: [(set_attr "type" "darith") ! 1236: (set_attr "mode" "DI") ! 1237: (set_attr "length" "2")]) ! 1238: ! 1239: (define_split ! 1240: [(set (match_operand:DI 0 "register_operand" "") ! 1241: (xor:DI (match_operand:DI 1 "register_operand" "") ! 1242: (match_operand:DI 2 "register_operand" "")))] ! 1243: "reload_completed && !TARGET_DEBUG_G_MODE ! 1244: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1245: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1])) ! 1246: && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))" ! 1247: ! 1248: [(set (subreg:SI (match_dup 0) 0) (xor:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0))) ! 1249: (set (subreg:SI (match_dup 0) 1) (xor:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))] ! 1250: "") ! 1251: ! 1252: ! 1253: ;; ! 1254: ;; .................... ! 1255: ;; ! 1256: ;; TRUNCATION ! 1257: ;; ! 1258: ;; .................... ! 1259: ! 1260: (define_insn "truncdfsf2" ! 1261: [(set (match_operand:SF 0 "register_operand" "=f") ! 1262: (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))] ! 1263: "TARGET_HARD_FLOAT" ! 1264: "cvt.s.d\\t%0,%1" ! 1265: [(set_attr "type" "fcvt") ! 1266: (set_attr "mode" "SF") ! 1267: (set_attr "length" "1")]) ! 1268: ! 1269: ! 1270: ;; ! 1271: ;; .................... ! 1272: ;; ! 1273: ;; ZERO EXTENSION ! 1274: ;; ! 1275: ;; .................... ! 1276: ! 1277: ;; Extension insns. ! 1278: ;; Those for integer source operand ! 1279: ;; are ordered widest source type first. ! 1280: ! 1281: (define_insn "zero_extendhisi2" ! 1282: [(set (match_operand:SI 0 "register_operand" "=d,d,d") ! 1283: (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "d,R,m")))] ! 1284: "" ! 1285: "* ! 1286: { ! 1287: if (which_alternative == 0) ! 1288: return \"andi\\t%0,%1,0xffff\"; ! 1289: else ! 1290: return mips_move_1word (operands, insn, TRUE); ! 1291: }" ! 1292: [(set_attr "type" "arith,load,load") ! 1293: (set_attr "mode" "SI,SI,SI") ! 1294: (set_attr "length" "1,1,2")]) ! 1295: ! 1296: (define_insn "zero_extendqihi2" ! 1297: [(set (match_operand:HI 0 "register_operand" "=d,d,d") ! 1298: (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,R,m")))] ! 1299: "" ! 1300: "* ! 1301: { ! 1302: if (which_alternative == 0) ! 1303: return \"andi\\t%0,%1,0x00ff\"; ! 1304: else ! 1305: return mips_move_1word (operands, insn, TRUE); ! 1306: }" ! 1307: [(set_attr "type" "arith,load,load") ! 1308: (set_attr "mode" "HI,HI,HI") ! 1309: (set_attr "length" "1,1,2")]) ! 1310: ! 1311: (define_insn "zero_extendqisi2" ! 1312: [(set (match_operand:SI 0 "register_operand" "=d,d,d") ! 1313: (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "d,R,m")))] ! 1314: "" ! 1315: "* ! 1316: { ! 1317: if (which_alternative == 0) ! 1318: return \"andi\\t%0,%1,0x00ff\"; ! 1319: else ! 1320: return mips_move_1word (operands, insn, TRUE); ! 1321: }" ! 1322: [(set_attr "type" "arith,load,load") ! 1323: (set_attr "mode" "SI,SI,SI") ! 1324: (set_attr "length" "1,1,2")]) ! 1325: ! 1326: ! 1327: ;; ! 1328: ;; .................... ! 1329: ;; ! 1330: ;; SIGN EXTENSION ! 1331: ;; ! 1332: ;; .................... ! 1333: ! 1334: ;; Extension insns. ! 1335: ;; Those for integer source operand ! 1336: ;; are ordered widest source type first. ! 1337: ! 1338: ;; These patterns originally accepted general_operands, however, slightly ! 1339: ;; better code is generated by only accepting register_operands, and then ! 1340: ;; letting combine generate the lh and lb insns. ! 1341: ! 1342: (define_expand "extendhisi2" ! 1343: [(set (match_operand:SI 0 "register_operand" "") ! 1344: (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))] ! 1345: "" ! 1346: " ! 1347: { ! 1348: if (optimize && GET_CODE (operands[1]) == MEM) ! 1349: operands[1] = force_not_mem (operands[1]); ! 1350: ! 1351: if (GET_CODE (operands[1]) != MEM) ! 1352: { ! 1353: rtx op1 = gen_lowpart (SImode, operands[1]); ! 1354: rtx temp = gen_reg_rtx (SImode); ! 1355: rtx shift = gen_rtx (CONST_INT, VOIDmode, 16); ! 1356: ! 1357: emit_insn (gen_ashlsi3 (temp, op1, shift)); ! 1358: emit_insn (gen_ashrsi3 (operands[0], temp, shift)); ! 1359: DONE; ! 1360: } ! 1361: }") ! 1362: ! 1363: (define_insn "extendhisi2_internal" ! 1364: [(set (match_operand:SI 0 "register_operand" "=d,d") ! 1365: (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,m")))] ! 1366: "" ! 1367: "* return mips_move_1word (operands, insn, FALSE);" ! 1368: [(set_attr "type" "load,load") ! 1369: (set_attr "mode" "SI,SI") ! 1370: (set_attr "length" "1,2")]) ! 1371: ! 1372: (define_expand "extendqihi2" ! 1373: [(set (match_operand:HI 0 "register_operand" "") ! 1374: (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))] ! 1375: "" ! 1376: " ! 1377: { ! 1378: if (optimize && GET_CODE (operands[1]) == MEM) ! 1379: operands[1] = force_not_mem (operands[1]); ! 1380: ! 1381: if (GET_CODE (operands[1]) != MEM) ! 1382: { ! 1383: rtx op0 = gen_lowpart (SImode, operands[0]); ! 1384: rtx op1 = gen_lowpart (SImode, operands[1]); ! 1385: rtx temp = gen_reg_rtx (SImode); ! 1386: rtx shift = gen_rtx (CONST_INT, VOIDmode, 24); ! 1387: ! 1388: emit_insn (gen_ashlsi3 (temp, op1, shift)); ! 1389: emit_insn (gen_ashrsi3 (op0, temp, shift)); ! 1390: DONE; ! 1391: } ! 1392: }") ! 1393: ! 1394: (define_insn "extendqihi2_internal" ! 1395: [(set (match_operand:HI 0 "register_operand" "=d,d") ! 1396: (sign_extend:HI (match_operand:QI 1 "memory_operand" "R,m")))] ! 1397: "" ! 1398: "* return mips_move_1word (operands, insn, FALSE);" ! 1399: [(set_attr "type" "load,load") ! 1400: (set_attr "mode" "SI,SI") ! 1401: (set_attr "length" "1,2")]) ! 1402: ! 1403: ! 1404: (define_expand "extendqisi2" ! 1405: [(set (match_operand:SI 0 "register_operand" "") ! 1406: (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))] ! 1407: "" ! 1408: " ! 1409: { ! 1410: if (optimize && GET_CODE (operands[1]) == MEM) ! 1411: operands[1] = force_not_mem (operands[1]); ! 1412: ! 1413: if (GET_CODE (operands[1]) != MEM) ! 1414: { ! 1415: rtx op1 = gen_lowpart (SImode, operands[1]); ! 1416: rtx temp = gen_reg_rtx (SImode); ! 1417: rtx shift = gen_rtx (CONST_INT, VOIDmode, 24); ! 1418: ! 1419: emit_insn (gen_ashlsi3 (temp, op1, shift)); ! 1420: emit_insn (gen_ashrsi3 (operands[0], temp, shift)); ! 1421: DONE; ! 1422: } ! 1423: }") ! 1424: ! 1425: (define_insn "extendqisi2_insn" ! 1426: [(set (match_operand:SI 0 "register_operand" "=d,d") ! 1427: (sign_extend:SI (match_operand:QI 1 "memory_operand" "R,m")))] ! 1428: "" ! 1429: "* return mips_move_1word (operands, insn, FALSE);" ! 1430: [(set_attr "type" "load,load") ! 1431: (set_attr "mode" "SI,SI") ! 1432: (set_attr "length" "1,2")]) ! 1433: ! 1434: ! 1435: (define_insn "extendsfdf2" ! 1436: [(set (match_operand:DF 0 "register_operand" "=f") ! 1437: (float_extend:DF (match_operand:SF 1 "register_operand" "f")))] ! 1438: "TARGET_HARD_FLOAT" ! 1439: "cvt.d.s\\t%0,%1" ! 1440: [(set_attr "type" "fcvt") ! 1441: (set_attr "mode" "DF") ! 1442: (set_attr "length" "1")]) ! 1443: ! 1444: ! 1445: ! 1446: ;; ! 1447: ;; .................... ! 1448: ;; ! 1449: ;; CONVERSIONS ! 1450: ;; ! 1451: ;; .................... ! 1452: ! 1453: (define_insn "fix_truncdfsi2_internal" ! 1454: [(set (match_operand:SI 0 "general_operand" "=d,*f,R,o") ! 1455: (fix:SI (match_operand:DF 1 "register_operand" "f,*f,f,f"))) ! 1456: (clobber (match_operand:SI 2 "register_operand" "d,*d,d,d")) ! 1457: (clobber (match_operand:DF 3 "register_operand" "f,*f,f,f"))] ! 1458: "TARGET_HARD_FLOAT" ! 1459: "* ! 1460: { ! 1461: rtx xoperands[10]; ! 1462: ! 1463: if (which_alternative == 1) ! 1464: return \"trunc.w.d %0,%1,%2\"; ! 1465: ! 1466: output_asm_insn (\"trunc.w.d %3,%1,%2\", operands); ! 1467: ! 1468: xoperands[0] = operands[0]; ! 1469: xoperands[1] = operands[3]; ! 1470: output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands); ! 1471: return \"\"; ! 1472: }" ! 1473: [(set_attr "type" "fcvt,fcvt,fcvt,fcvt") ! 1474: (set_attr "mode" "DF,DF,DF,DF") ! 1475: (set_attr "length" "14,12,13,14")]) ! 1476: ! 1477: ! 1478: (define_expand "fix_truncdfsi2" ! 1479: [(parallel [(set (match_operand:SI 0 "register_operand" "=d") ! 1480: (fix:SI (match_operand:DF 1 "register_operand" "f"))) ! 1481: (clobber (match_dup 2)) ! 1482: (clobber (match_dup 3))])] ! 1483: "TARGET_HARD_FLOAT" ! 1484: " ! 1485: { ! 1486: operands[2] = gen_reg_rtx (SImode); /* gp reg that saves FP status bits */ ! 1487: operands[3] = gen_reg_rtx (DFmode); /* fp reg that gets the conversion */ ! 1488: ! 1489: /* Fall through and generate default code */ ! 1490: }") ! 1491: ! 1492: (define_insn "fix_truncsfsi2_internal" ! 1493: [(set (match_operand:SI 0 "general_operand" "=d,*f,R,o") ! 1494: (fix:SI (match_operand:SF 1 "register_operand" "f,*f,f,f"))) ! 1495: (clobber (match_operand:SI 2 "register_operand" "d,*d,d,d")) ! 1496: (clobber (match_operand:SF 3 "register_operand" "f,*f,f,f"))] ! 1497: "TARGET_HARD_FLOAT" ! 1498: "* ! 1499: { ! 1500: rtx xoperands[10]; ! 1501: ! 1502: if (which_alternative == 1) ! 1503: return \"trunc.w.s %0,%1,%2\"; ! 1504: ! 1505: output_asm_insn (\"trunc.w.s %3,%1,%2\", operands); ! 1506: ! 1507: xoperands[0] = operands[0]; ! 1508: xoperands[1] = operands[3]; ! 1509: output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands); ! 1510: return \"\"; ! 1511: }" ! 1512: [(set_attr "type" "fcvt,fcvt,fcvt,fcvt") ! 1513: (set_attr "mode" "SF,SF,SF,SF") ! 1514: (set_attr "length" "14,12,13,14")]) ! 1515: ! 1516: ! 1517: (define_expand "fix_truncsfsi2" ! 1518: [(parallel [(set (match_operand:SI 0 "register_operand" "=f") ! 1519: (fix:SI (match_operand:SF 1 "register_operand" "f"))) ! 1520: (clobber (match_dup 2)) ! 1521: (clobber (match_dup 3))])] ! 1522: "TARGET_HARD_FLOAT" ! 1523: " ! 1524: { ! 1525: operands[2] = gen_reg_rtx (SImode); /* gp reg that saves FP status bits */ ! 1526: operands[3] = gen_reg_rtx (SFmode); /* fp reg that gets the conversion */ ! 1527: ! 1528: /* Fall through and generate default code */ ! 1529: }") ! 1530: ! 1531: ! 1532: (define_insn "floatsidf2" ! 1533: [(set (match_operand:DF 0 "register_operand" "=f") ! 1534: (float:DF (match_operand:SI 1 "register_operand" "d")))] ! 1535: "TARGET_HARD_FLOAT" ! 1536: "mtc1\\t%1,%0\;cvt.d.w\\t%0,%0" ! 1537: [(set_attr "type" "fcvt") ! 1538: (set_attr "mode" "DF") ! 1539: (set_attr "length" "13")]) ! 1540: ! 1541: (define_insn "floatsisf2" ! 1542: [(set (match_operand:SF 0 "register_operand" "=f") ! 1543: (float:SF (match_operand:SI 1 "register_operand" "d")))] ! 1544: "TARGET_HARD_FLOAT" ! 1545: "mtc1\\t%1,%0\;cvt.s.w\\t%0,%0" ! 1546: [(set_attr "type" "fcvt") ! 1547: (set_attr "mode" "SF") ! 1548: (set_attr "length" "13")]) ! 1549: ! 1550: (define_expand "fixuns_truncdfsi2" ! 1551: [(set (match_operand:SI 0 "register_operand" "") ! 1552: (unsigned_fix:SI (match_operand:DF 1 "register_operand" "")))] ! 1553: "TARGET_HARD_FLOAT" ! 1554: " ! 1555: { ! 1556: rtx reg1 = gen_reg_rtx (DFmode); ! 1557: rtx reg2 = gen_reg_rtx (DFmode); ! 1558: rtx reg3 = gen_reg_rtx (SImode); ! 1559: rtx label1 = gen_label_rtx (); ! 1560: rtx label2 = gen_label_rtx (); ! 1561: REAL_VALUE_TYPE offset = REAL_VALUE_LDEXP (1.0, 31); ! 1562: ! 1563: if (reg1) /* turn off complaints about unreached code */ ! 1564: { ! 1565: extern rtx gen_cmpdf (); ! 1566: emit_move_insn (reg1, immed_real_const_1 (offset, DFmode)); ! 1567: do_pending_stack_adjust (); ! 1568: ! 1569: emit_insn (gen_cmpdf (operands[1], reg1)); ! 1570: emit_jump_insn (gen_bge (label1)); ! 1571: ! 1572: emit_insn (gen_fix_truncdfsi2 (operands[0], operands[1])); ! 1573: emit_jump_insn (gen_rtx (SET, VOIDmode, pc_rtx, ! 1574: gen_rtx (LABEL_REF, VOIDmode, label2))); ! 1575: emit_barrier (); ! 1576: ! 1577: emit_label (label1); ! 1578: emit_move_insn (reg2, gen_rtx (MINUS, DFmode, operands[1], reg1)); ! 1579: emit_move_insn (reg3, gen_rtx (CONST_INT, VOIDmode, 0x80000000)); ! 1580: ! 1581: emit_insn (gen_fix_truncdfsi2 (operands[0], reg2)); ! 1582: emit_insn (gen_iorsi3 (operands[0], operands[0], reg3)); ! 1583: ! 1584: emit_label (label2); ! 1585: ! 1586: /* allow REG_NOTES to be set on last insn (labels don't have enough ! 1587: fields, and can't be used for REG_NOTES anyway). */ ! 1588: emit_insn (gen_rtx (USE, VOIDmode, stack_pointer_rtx)); ! 1589: DONE; ! 1590: } ! 1591: }") ! 1592: ! 1593: (define_expand "fixuns_truncsfsi2" ! 1594: [(set (match_operand:SI 0 "register_operand" "") ! 1595: (unsigned_fix:SI (match_operand:SF 1 "register_operand" "")))] ! 1596: "TARGET_HARD_FLOAT" ! 1597: " ! 1598: { ! 1599: rtx reg1 = gen_reg_rtx (SFmode); ! 1600: rtx reg2 = gen_reg_rtx (SFmode); ! 1601: rtx reg3 = gen_reg_rtx (SImode); ! 1602: rtx label1 = gen_label_rtx (); ! 1603: rtx label2 = gen_label_rtx (); ! 1604: REAL_VALUE_TYPE offset = REAL_VALUE_LDEXP (1.0, 31); ! 1605: ! 1606: if (reg1) /* turn off complaints about unreached code */ ! 1607: { ! 1608: extern rtx gen_cmpsf (); ! 1609: emit_move_insn (reg1, immed_real_const_1 (offset, SFmode)); ! 1610: do_pending_stack_adjust (); ! 1611: ! 1612: emit_insn (gen_cmpsf (operands[1], reg1)); ! 1613: emit_jump_insn (gen_bge (label1)); ! 1614: ! 1615: emit_insn (gen_fix_truncsfsi2 (operands[0], operands[1])); ! 1616: emit_jump_insn (gen_rtx (SET, VOIDmode, pc_rtx, ! 1617: gen_rtx (LABEL_REF, VOIDmode, label2))); ! 1618: emit_barrier (); ! 1619: ! 1620: emit_label (label1); ! 1621: emit_move_insn (reg2, gen_rtx (MINUS, SFmode, operands[1], reg1)); ! 1622: emit_move_insn (reg3, gen_rtx (CONST_INT, VOIDmode, 0x80000000)); ! 1623: ! 1624: emit_insn (gen_fix_truncsfsi2 (operands[0], reg2)); ! 1625: emit_insn (gen_iorsi3 (operands[0], operands[0], reg3)); ! 1626: ! 1627: emit_label (label2); ! 1628: ! 1629: /* allow REG_NOTES to be set on last insn (labels don't have enough ! 1630: fields, and can't be used for REG_NOTES anyway). */ ! 1631: emit_insn (gen_rtx (USE, VOIDmode, stack_pointer_rtx)); ! 1632: DONE; ! 1633: } ! 1634: }") ! 1635: ! 1636: ! 1637: ;; ! 1638: ;; .................... ! 1639: ;; ! 1640: ;; DATA MOVEMENT ! 1641: ;; ! 1642: ;; .................... ! 1643: ! 1644: ;; unaligned word moves generated by the block moves. ! 1645: ;; We use (use (reg:SI 0)) to select this pattern rather than the ! 1646: ;; normal movsi. Make these before the normal move patterns so they ! 1647: ;; match first. ! 1648: ! 1649: (define_expand "movsi_unaligned" ! 1650: [(parallel [(set (match_operand:SI 0 "general_operand" "") ! 1651: (match_operand:SI 1 "general_operand" "")) ! 1652: (use (reg:SI 0))])] ! 1653: "" ! 1654: " ! 1655: { ! 1656: extern rtx force_reg (); ! 1657: extern rtx gen_movsi_ulw (); ! 1658: extern rtx gen_movsi (); ! 1659: ! 1660: if (GET_CODE (operands[0]) == MEM && !reg_or_0_operand (operands[1], SImode)) ! 1661: { ! 1662: rtx reg = gen_reg_rtx (SImode); ! 1663: ! 1664: emit_insn (gen_movsi_ulw (reg, operands[1])); ! 1665: operands[1] = reg; ! 1666: } ! 1667: ! 1668: /* Generate appropriate load, store. If not a load or store, ! 1669: do a normal movsi. */ ! 1670: if (GET_CODE (operands[0]) != MEM && GET_CODE (operands[1]) != MEM) ! 1671: { ! 1672: emit_insn (gen_movsi (operands[0], operands[1])); ! 1673: DONE; ! 1674: } ! 1675: ! 1676: /* Fall through and generate normal code. */ ! 1677: }") ! 1678: ! 1679: (define_insn "movsi_ulw" ! 1680: [(set (match_operand:SI 0 "register_operand" "=&d,&d,d,d") ! 1681: (match_operand:SI 1 "general_operand" "R,o,dIKL,M")) ! 1682: (use (reg:SI 0))] ! 1683: "" ! 1684: "* ! 1685: { ! 1686: extern rtx eliminate_constant_term (); ! 1687: enum rtx_code code; ! 1688: char *ret; ! 1689: int offset; ! 1690: rtx addr; ! 1691: rtx mem_addr; ! 1692: ! 1693: if (which_alternative != 0) ! 1694: return mips_move_1word (operands, insn, FALSE); ! 1695: ! 1696: if (TARGET_STATS) ! 1697: mips_count_memory_refs (operands[1], 2); ! 1698: ! 1699: /* The stack/frame pointers are always aligned, so we can convert ! 1700: to the faster lw if we are referencing an aligned stack location. */ ! 1701: ! 1702: offset = 0; ! 1703: addr = XEXP (operands[1], 0); ! 1704: mem_addr = eliminate_constant_term (addr, &offset); ! 1705: ! 1706: if ((offset & (UNITS_PER_WORD-1)) == 0 ! 1707: && (mem_addr == stack_pointer_rtx || mem_addr == frame_pointer_rtx)) ! 1708: ret = \"lw\\t%0,%1\"; ! 1709: ! 1710: else ! 1711: { ! 1712: ret = \"ulw\\t%0,%1\"; ! 1713: if (TARGET_GAS) ! 1714: { ! 1715: enum rtx_code code = GET_CODE (addr); ! 1716: ! 1717: if (code == CONST || code == SYMBOL_REF || code == LABEL_REF) ! 1718: { ! 1719: operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 1); ! 1720: ret = \"%[la\\t%2,%1\;ulw\\t%0,0(%2)%]\"; ! 1721: } ! 1722: } ! 1723: } ! 1724: ! 1725: return mips_fill_delay_slot (ret, DELAY_LOAD, operands, insn); ! 1726: }" ! 1727: [(set_attr "type" "load,load,move,arith") ! 1728: (set_attr "mode" "SI,SI,SI,SI") ! 1729: (set_attr "length" "2,4,1,2")]) ! 1730: ! 1731: (define_insn "movsi_usw" ! 1732: [(set (match_operand:SI 0 "memory_operand" "=R,o") ! 1733: (match_operand:SI 1 "reg_or_0_operand" "dJ,dJ")) ! 1734: (use (reg:SI 0))] ! 1735: "" ! 1736: "* ! 1737: { ! 1738: extern rtx eliminate_constant_term (); ! 1739: int offset = 0; ! 1740: rtx addr = XEXP (operands[0], 0); ! 1741: rtx mem_addr = eliminate_constant_term (addr, &offset); ! 1742: ! 1743: if (TARGET_STATS) ! 1744: mips_count_memory_refs (operands[0], 2); ! 1745: ! 1746: /* The stack/frame pointers are always aligned, so we can convert ! 1747: to the faster sw if we are referencing an aligned stack location. */ ! 1748: ! 1749: if ((offset & (UNITS_PER_WORD-1)) == 0 ! 1750: && (mem_addr == stack_pointer_rtx || mem_addr == frame_pointer_rtx)) ! 1751: return \"sw\\t%1,%0\"; ! 1752: ! 1753: ! 1754: if (TARGET_GAS) ! 1755: { ! 1756: enum rtx_code code = GET_CODE (XEXP (operands[0], 0)); ! 1757: ! 1758: if (code == CONST || code == SYMBOL_REF || code == LABEL_REF) ! 1759: { ! 1760: operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 1); ! 1761: return \"%[la\\t%2,%0\;usw\\t%z1,0(%2)%]\"; ! 1762: } ! 1763: } ! 1764: ! 1765: return \"usw\\t%z1,%0\"; ! 1766: }" ! 1767: [(set_attr "type" "load,load") ! 1768: (set_attr "mode" "SI,SI") ! 1769: (set_attr "length" "2,4")]) ! 1770: ! 1771: ;; 64-bit integer moves ! 1772: ! 1773: ;; Unlike most other insns, the move insns can't be split with ! 1774: ;; different predicates, because register spilling and other parts of ! 1775: ;; the compiler, have memoized the insn number already. ! 1776: ! 1777: (define_insn "movdi" ! 1778: [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,d,R,o,*d,*f,*f,*f,*f,*R,*o,*d,*x") ! 1779: (match_operand:DI 1 "general_operand" "d,iF,R,o,d,d,*f,*d,*f,*R,*o,*f,*f,*x,*d"))] ! 1780: "" ! 1781: "* return mips_move_2words (operands, insn); " ! 1782: [(set_attr "type" "move,arith,load,load,store,store,xfer,xfer,move,load,load,store,store,hilo,hilo") ! 1783: (set_attr "mode" "DI,DI,DI,DI,DI,DI,DI,DI,DI,DI,DI,DI,DI,DI,DI") ! 1784: (set_attr "length" "2,4,2,4,2,4,2,2,1,2,4,2,4,2,2")]) ! 1785: ! 1786: (define_split ! 1787: [(set (match_operand:DI 0 "register_operand" "") ! 1788: (match_operand:DI 1 "register_operand" ""))] ! 1789: "reload_completed && !TARGET_DEBUG_G_MODE ! 1790: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1791: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))" ! 1792: ! 1793: [(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0)) ! 1794: (set (subreg:SI (match_dup 0) 1) (subreg:SI (match_dup 1) 1))] ! 1795: "") ! 1796: ! 1797: ! 1798: ;; 32-bit Integer moves ! 1799: ! 1800: (define_split ! 1801: [(set (match_operand:SI 0 "register_operand" "") ! 1802: (match_operand:SI 1 "large_int" ""))] ! 1803: "" ! 1804: [(set (match_dup 0) ! 1805: (match_dup 2)) ! 1806: (set (match_dup 0) ! 1807: (ior:SI (match_dup 0) ! 1808: (match_dup 3)))] ! 1809: " ! 1810: { ! 1811: operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff0000); ! 1812: operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0x0000ffff); ! 1813: }") ! 1814: ! 1815: ;; Unlike most other insns, the move insns can't be split with ! 1816: ;; different predicates, because register spilling and other parts of ! 1817: ;; the compiler, have memoized the insn number already. ! 1818: ! 1819: (define_insn "movsi" ! 1820: [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d,d,R,m,*d,*fs,*f,*f,*f,*R,*m,*x,*d") ! 1821: (match_operand:SI 1 "general_operand" "d,S,IKL,Mnis,R,m,dJ,dJ,*fs,*d,*f,*R,*m,*f,*f,*d,*x"))] ! 1822: "" ! 1823: "* return mips_move_1word (operands, insn, TRUE);" ! 1824: [(set_attr "type" "move,pic,arith,arith,load,load,store,store,xfer,xfer,move,load,load,store,store,hilo,hilo") ! 1825: (set_attr "mode" "SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI,SI") ! 1826: (set_attr "length" "1,4,1,2,1,2,1,2,1,1,1,1,2,1,2,1,1")]) ! 1827: ! 1828: ;; 16-bit Integer moves ! 1829: ! 1830: ;; Unlike most other insns, the move insns can't be split with ! 1831: ;; different predicates, because register spilling and other parts of ! 1832: ;; the compiler, have memoized the insn number already. ! 1833: ;; Unsigned loads are used because BYTE_LOADS_ZERO_EXTEND is defined ! 1834: ! 1835: (define_insn "movhi" ! 1836: [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*f,*f,*x,*d") ! 1837: (match_operand:HI 1 "general_operand" "d,IK,R,m,dJ,dJ,*fs,*d,*f,*d,*x"))] ! 1838: "" ! 1839: "* return mips_move_1word (operands, insn, TRUE);" ! 1840: [(set_attr "type" "move,arith,load,load,store,store,xfer,xfer,move,hilo,hilo") ! 1841: (set_attr "mode" "HI,HI,HI,HI,HI,HI,HI,HI,HI,HI,HI") ! 1842: (set_attr "length" "1,1,1,2,1,2,1,1,1,1,1")]) ! 1843: ! 1844: ;; 8-bit Integer moves ! 1845: ! 1846: ;; Unlike most other insns, the move insns can't be split with ! 1847: ;; different predicates, because register spilling and other parts of ! 1848: ;; the compiler, have memoized the insn number already. ! 1849: ;; Unsigned loads are used because BYTE_LOADS_ZERO_EXTEND is defined ! 1850: ! 1851: (define_insn "movqi" ! 1852: [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*f,*f,*x,*d") ! 1853: (match_operand:QI 1 "general_operand" "d,IK,R,m,dJ,dJ,*fs,*d,*f,*d,*x"))] ! 1854: "" ! 1855: "* return mips_move_1word (operands, insn, TRUE);" ! 1856: [(set_attr "type" "move,arith,load,load,store,store,xfer,xfer,move,hilo,hilo") ! 1857: (set_attr "mode" "QI,QI,QI,QI,QI,QI,QI,QI,QI,QI,QI") ! 1858: (set_attr "length" "1,1,1,2,1,2,1,1,1,1,1")]) ! 1859: ! 1860: ! 1861: ;; 32-bit floating point moves ! 1862: ! 1863: (define_insn "movsf" ! 1864: [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,f,f,R,m,*f,*d,*d,*d,*d,*R,*m") ! 1865: (match_operand:SF 1 "general_operand" "f,G,R,Em,fG,fG,*d,*f,*Gd,*R,*Em,*d,*d"))] ! 1866: "" ! 1867: "* return mips_move_1word (operands, insn, FALSE);" ! 1868: [(set_attr "type" "move,xfer,load,load,store,store,xfer,xfer,move,load,load,store,store") ! 1869: (set_attr "mode" "SF,SF,SF,SF,SF,SF,SF,SF,SF,SF,SF,SF,SF") ! 1870: (set_attr "length" "1,1,1,2,1,2,1,1,1,1,2,1,2")]) ! 1871: ! 1872: ;; 64-bit floating point moves ! 1873: ! 1874: (define_insn "movdf" ! 1875: [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,R,o,f,*f,*d,*d,*d,*d,*R,*o") ! 1876: (match_operand:DF 1 "general_operand" "f,R,o,fG,fG,E,*d,*f,*dG,*R,*oE,*d,*d"))] ! 1877: "" ! 1878: "* return mips_move_2words (operands, insn); " ! 1879: [(set_attr "type" "move,load,load,store,store,load,xfer,xfer,move,load,load,store,store") ! 1880: (set_attr "mode" "DF,DF,DF,DF,DF,DF,DF,DF,DF,DF,DF,DF,DF") ! 1881: (set_attr "length" "1,2,4,2,4,4,2,2,2,2,4,2,4")]) ! 1882: ! 1883: (define_split ! 1884: [(set (match_operand:DF 0 "register_operand" "") ! 1885: (match_operand:DF 1 "register_operand" ""))] ! 1886: "reload_completed && !TARGET_DEBUG_G_MODE ! 1887: && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0])) ! 1888: && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))" ! 1889: ! 1890: [(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0)) ! 1891: (set (subreg:SI (match_dup 0) 1) (subreg:SI (match_dup 1) 1))] ! 1892: "") ! 1893: ! 1894: ;; Block moves, see mips.c for more details. ! 1895: ;; Argument 0 is the destination ! 1896: ;; Argument 1 is the source ! 1897: ;; Argument 2 is the length ! 1898: ;; Argument 3 is the alignment ! 1899: ! 1900: (define_expand "movstrsi" ! 1901: [(parallel [(set (mem:BLK (match_operand:BLK 0 "general_operand" "")) ! 1902: (mem:BLK (match_operand:BLK 1 "general_operand" ""))) ! 1903: (use (match_operand:SI 2 "arith32_operand" "")) ! 1904: (use (match_operand:SI 3 "immediate_operand" ""))])] ! 1905: "" ! 1906: " ! 1907: { ! 1908: if (operands[0]) /* avoid unused code messages */ ! 1909: { ! 1910: expand_block_move (operands); ! 1911: DONE; ! 1912: } ! 1913: }") ! 1914: ! 1915: ! 1916: ;; ! 1917: ;; .................... ! 1918: ;; ! 1919: ;; SHIFTS ! 1920: ;; ! 1921: ;; .................... ! 1922: ! 1923: (define_insn "ashlsi3" ! 1924: [(set (match_operand:SI 0 "register_operand" "=d") ! 1925: (ashift:SI (match_operand:SI 1 "register_operand" "d") ! 1926: (match_operand:SI 2 "arith_operand" "dI")))] ! 1927: "" ! 1928: "* ! 1929: { ! 1930: if (GET_CODE (operands[2]) == CONST_INT) ! 1931: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 1932: ! 1933: return \"sll\\t%0,%1,%2\"; ! 1934: }" ! 1935: [(set_attr "type" "arith") ! 1936: (set_attr "mode" "SI") ! 1937: (set_attr "length" "1")]) ! 1938: ! 1939: ! 1940: (define_expand "ashldi3" ! 1941: [(parallel [(set (match_operand:DI 0 "register_operand" "") ! 1942: (ashift:DI (match_operand:DI 1 "register_operand" "") ! 1943: (match_operand:SI 2 "arith_operand" ""))) ! 1944: (clobber (match_dup 3))])] ! 1945: "!TARGET_DEBUG_G_MODE" ! 1946: "operands[3] = gen_reg_rtx (SImode);") ! 1947: ! 1948: ! 1949: (define_insn "ashldi3_internal" ! 1950: [(set (match_operand:DI 0 "register_operand" "=d") ! 1951: (ashift:DI (match_operand:DI 1 "register_operand" "d") ! 1952: (match_operand:SI 2 "register_operand" "d"))) ! 1953: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 1954: "!TARGET_DEBUG_G_MODE" ! 1955: "* ! 1956: { ! 1957: operands[4] = const0_rtx; ! 1958: dslots_jump_total += 3; ! 1959: dslots_jump_filled += 2; ! 1960: ! 1961: return \"sll\\t%3,%2,26\\n\\ ! 1962: \\tbgez\\t%3,1f\\n\\ ! 1963: \\tsll\\t%M0,%L1,%2\\n\\ ! 1964: \\t%(b\\t3f\\n\\ ! 1965: \\tmove\\t%L0,%z4%)\\n\\ ! 1966: \\n\\ ! 1967: 1:\\n\\ ! 1968: \\t%(beq\\t%3,%z4,2f\\n\\ ! 1969: \\tsll\\t%M0,%M1,%2%)\\n\\ ! 1970: \\n\\ ! 1971: \\tsubu\\t%3,%z4,%2\\n\\ ! 1972: \\tsrl\\t%3,%L1,%3\\n\\ ! 1973: \\tor\\t%M0,%M0,%3\\n\\ ! 1974: 2:\\n\\ ! 1975: \\tsll\\t%L0,%L1,%2\\n\\ ! 1976: 3:\"; ! 1977: }" ! 1978: [(set_attr "type" "darith") ! 1979: (set_attr "mode" "SI") ! 1980: (set_attr "length" "12")]) ! 1981: ! 1982: ! 1983: (define_insn "ashldi3_internal2" ! 1984: [(set (match_operand:DI 0 "register_operand" "=d") ! 1985: (ashift:DI (match_operand:DI 1 "register_operand" "d") ! 1986: (match_operand:SI 2 "small_int" "IJK"))) ! 1987: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 1988: "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0" ! 1989: "* ! 1990: { ! 1991: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 1992: operands[4] = const0_rtx; ! 1993: return \"sll\\t%M0,%L1,%2\;move\\t%L0,%z4\"; ! 1994: }" ! 1995: [(set_attr "type" "darith") ! 1996: (set_attr "mode" "DI") ! 1997: (set_attr "length" "2")]) ! 1998: ! 1999: ! 2000: (define_split ! 2001: [(set (match_operand:DI 0 "register_operand" "") ! 2002: (ashift:DI (match_operand:DI 1 "register_operand" "") ! 2003: (match_operand:SI 2 "small_int" ""))) ! 2004: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2005: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2006: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2007: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2008: && (INTVAL (operands[2]) & 32) != 0" ! 2009: ! 2010: [(set (subreg:SI (match_dup 0) 1) (ashift:SI (subreg:SI (match_dup 1) 0) (match_dup 2))) ! 2011: (set (subreg:SI (match_dup 0) 0) (const_int 0))] ! 2012: ! 2013: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2014: ! 2015: ! 2016: (define_split ! 2017: [(set (match_operand:DI 0 "register_operand" "") ! 2018: (ashift:DI (match_operand:DI 1 "register_operand" "") ! 2019: (match_operand:SI 2 "small_int" ""))) ! 2020: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2021: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2022: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2023: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2024: && (INTVAL (operands[2]) & 32) != 0" ! 2025: ! 2026: [(set (subreg:SI (match_dup 0) 0) (ashift:SI (subreg:SI (match_dup 1) 1) (match_dup 2))) ! 2027: (set (subreg:SI (match_dup 0) 1) (const_int 0))] ! 2028: ! 2029: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2030: ! 2031: ! 2032: (define_insn "ashldi3_internal3" ! 2033: [(set (match_operand:DI 0 "register_operand" "=d") ! 2034: (ashift:DI (match_operand:DI 1 "register_operand" "d") ! 2035: (match_operand:SI 2 "small_int" "IJK"))) ! 2036: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2037: "!TARGET_DEBUG_G_MODE ! 2038: && (INTVAL (operands[2]) & 63) < 32 ! 2039: && (INTVAL (operands[2]) & 63) != 0" ! 2040: "* ! 2041: { ! 2042: int amount = INTVAL (operands[2]); ! 2043: ! 2044: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2045: operands[4] = const0_rtx; ! 2046: operands[5] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2047: ! 2048: return \"sll\\t%M0,%M1,%2\;srl\\t%3,%L1,%5\;or\\t%M0,%M0,%3\;sll\\t%L0,%L1,%2\"; ! 2049: }" ! 2050: [(set_attr "type" "darith") ! 2051: (set_attr "mode" "DI") ! 2052: (set_attr "length" "4")]) ! 2053: ! 2054: ! 2055: (define_split ! 2056: [(set (match_operand:DI 0 "register_operand" "") ! 2057: (ashift:DI (match_operand:DI 1 "register_operand" "") ! 2058: (match_operand:SI 2 "small_int" ""))) ! 2059: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2060: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2061: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2062: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2063: && (INTVAL (operands[2]) & 63) < 32 ! 2064: && (INTVAL (operands[2]) & 63) != 0" ! 2065: ! 2066: [(set (subreg:SI (match_dup 0) 1) ! 2067: (ashift:SI (subreg:SI (match_dup 1) 1) ! 2068: (match_dup 2))) ! 2069: ! 2070: (set (match_dup 3) ! 2071: (lshiftrt:SI (subreg:SI (match_dup 1) 0) ! 2072: (match_dup 4))) ! 2073: ! 2074: (set (subreg:SI (match_dup 0) 1) ! 2075: (ior:SI (subreg:SI (match_dup 0) 1) ! 2076: (match_dup 3))) ! 2077: ! 2078: (set (subreg:SI (match_dup 0) 0) ! 2079: (ashift:SI (subreg:SI (match_dup 1) 0) ! 2080: (match_dup 2)))] ! 2081: " ! 2082: { ! 2083: int amount = INTVAL (operands[2]); ! 2084: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2085: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2086: }") ! 2087: ! 2088: ! 2089: (define_split ! 2090: [(set (match_operand:DI 0 "register_operand" "") ! 2091: (ashift:DI (match_operand:DI 1 "register_operand" "") ! 2092: (match_operand:SI 2 "small_int" ""))) ! 2093: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2094: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2095: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2096: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2097: && (INTVAL (operands[2]) & 63) < 32 ! 2098: && (INTVAL (operands[2]) & 63) != 0" ! 2099: ! 2100: [(set (subreg:SI (match_dup 0) 0) ! 2101: (ashift:SI (subreg:SI (match_dup 1) 0) ! 2102: (match_dup 2))) ! 2103: ! 2104: (set (match_dup 3) ! 2105: (lshiftrt:SI (subreg:SI (match_dup 1) 1) ! 2106: (match_dup 4))) ! 2107: ! 2108: (set (subreg:SI (match_dup 0) 0) ! 2109: (ior:SI (subreg:SI (match_dup 0) 0) ! 2110: (match_dup 3))) ! 2111: ! 2112: (set (subreg:SI (match_dup 0) 1) ! 2113: (ashift:SI (subreg:SI (match_dup 1) 1) ! 2114: (match_dup 2)))] ! 2115: " ! 2116: { ! 2117: int amount = INTVAL (operands[2]); ! 2118: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2119: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2120: }") ! 2121: ! 2122: ! 2123: (define_insn "ashrsi3" ! 2124: [(set (match_operand:SI 0 "register_operand" "=d") ! 2125: (ashiftrt:SI (match_operand:SI 1 "register_operand" "d") ! 2126: (match_operand:SI 2 "arith_operand" "dI")))] ! 2127: "" ! 2128: "* ! 2129: { ! 2130: if (GET_CODE (operands[2]) == CONST_INT) ! 2131: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 2132: ! 2133: return \"sra\\t%0,%1,%2\"; ! 2134: }" ! 2135: [(set_attr "type" "arith") ! 2136: (set_attr "mode" "SI") ! 2137: (set_attr "length" "1")]) ! 2138: ! 2139: ! 2140: (define_expand "ashrdi3" ! 2141: [(parallel [(set (match_operand:DI 0 "register_operand" "") ! 2142: (ashiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2143: (match_operand:SI 2 "arith_operand" ""))) ! 2144: (clobber (match_dup 3))])] ! 2145: "!TARGET_DEBUG_G_MODE" ! 2146: "operands[3] = gen_reg_rtx (SImode);") ! 2147: ! 2148: ! 2149: (define_insn "ashrdi3_internal" ! 2150: [(set (match_operand:DI 0 "register_operand" "=d") ! 2151: (ashiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2152: (match_operand:SI 2 "register_operand" "d"))) ! 2153: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2154: "!TARGET_DEBUG_G_MODE" ! 2155: "* ! 2156: { ! 2157: operands[4] = const0_rtx; ! 2158: dslots_jump_total += 3; ! 2159: dslots_jump_filled += 2; ! 2160: ! 2161: return \"sll\\t%3,%2,26\\n\\ ! 2162: \\tbgez\\t%3,1f\\n\\ ! 2163: \\tsra\\t%L0,%M1,%2\\n\\ ! 2164: \\t%(b\\t3f\\n\\ ! 2165: \\tsra\\t%M0,%M1,31%)\\n\\ ! 2166: \\n\\ ! 2167: 1:\\n\\ ! 2168: \\t%(beq\\t%3,%z4,2f\\n\\ ! 2169: \\tsrl\\t%L0,%L1,%2%)\\n\\ ! 2170: \\n\\ ! 2171: \\tsubu\\t%3,%z4,%2\\n\\ ! 2172: \\tsll\\t%3,%M1,%3\\n\\ ! 2173: \\tor\\t%L0,%L0,%3\\n\\ ! 2174: 2:\\n\\ ! 2175: \\tsra\\t%M0,%M1,%2\\n\\ ! 2176: 3:\"; ! 2177: }" ! 2178: [(set_attr "type" "darith") ! 2179: (set_attr "mode" "DI") ! 2180: (set_attr "length" "12")]) ! 2181: ! 2182: ! 2183: (define_insn "ashrdi3_internal2" ! 2184: [(set (match_operand:DI 0 "register_operand" "=d") ! 2185: (ashiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2186: (match_operand:SI 2 "small_int" "IJK"))) ! 2187: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2188: "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0" ! 2189: "* ! 2190: { ! 2191: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 2192: return \"sra\\t%L0,%M1,%2\;sra\\t%M0,%M1,31\"; ! 2193: }" ! 2194: [(set_attr "type" "darith") ! 2195: (set_attr "mode" "DI") ! 2196: (set_attr "length" "2")]) ! 2197: ! 2198: ! 2199: (define_split ! 2200: [(set (match_operand:DI 0 "register_operand" "") ! 2201: (ashiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2202: (match_operand:SI 2 "small_int" ""))) ! 2203: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2204: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2205: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2206: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2207: && (INTVAL (operands[2]) & 32) != 0" ! 2208: ! 2209: [(set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 1) (match_dup 2))) ! 2210: (set (subreg:SI (match_dup 0) 1) (ashiftrt:SI (subreg:SI (match_dup 1) 1) (const_int 31)))] ! 2211: ! 2212: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2213: ! 2214: ! 2215: (define_split ! 2216: [(set (match_operand:DI 0 "register_operand" "") ! 2217: (ashiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2218: (match_operand:SI 2 "small_int" ""))) ! 2219: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2220: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2221: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2222: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2223: && (INTVAL (operands[2]) & 32) != 0" ! 2224: ! 2225: [(set (subreg:SI (match_dup 0) 1) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2))) ! 2226: (set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (const_int 31)))] ! 2227: ! 2228: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2229: ! 2230: ! 2231: (define_insn "ashrdi3_internal3" ! 2232: [(set (match_operand:DI 0 "register_operand" "=d") ! 2233: (ashiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2234: (match_operand:SI 2 "small_int" "IJK"))) ! 2235: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2236: "!TARGET_DEBUG_G_MODE ! 2237: && (INTVAL (operands[2]) & 63) < 32 ! 2238: && (INTVAL (operands[2]) & 63) != 0" ! 2239: "* ! 2240: { ! 2241: int amount = INTVAL (operands[2]); ! 2242: ! 2243: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2244: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2245: ! 2246: return \"srl\\t%L0,%L1,%2\;sll\\t%3,%M1,%4\;or\\t%L0,%L0,%3\;sra\\t%M0,%M1,%2\"; ! 2247: }" ! 2248: [(set_attr "type" "darith") ! 2249: (set_attr "mode" "DI") ! 2250: (set_attr "length" "4")]) ! 2251: ! 2252: ! 2253: (define_split ! 2254: [(set (match_operand:DI 0 "register_operand" "") ! 2255: (ashiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2256: (match_operand:SI 2 "small_int" ""))) ! 2257: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2258: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2259: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2260: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2261: && (INTVAL (operands[2]) & 63) < 32 ! 2262: && (INTVAL (operands[2]) & 63) != 0" ! 2263: ! 2264: [(set (subreg:SI (match_dup 0) 0) ! 2265: (lshiftrt:SI (subreg:SI (match_dup 1) 0) ! 2266: (match_dup 2))) ! 2267: ! 2268: (set (match_dup 3) ! 2269: (ashift:SI (subreg:SI (match_dup 1) 1) ! 2270: (match_dup 4))) ! 2271: ! 2272: (set (subreg:SI (match_dup 0) 0) ! 2273: (ior:SI (subreg:SI (match_dup 0) 0) ! 2274: (match_dup 3))) ! 2275: ! 2276: (set (subreg:SI (match_dup 0) 1) ! 2277: (ashiftrt:SI (subreg:SI (match_dup 1) 1) ! 2278: (match_dup 2)))] ! 2279: " ! 2280: { ! 2281: int amount = INTVAL (operands[2]); ! 2282: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2283: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2284: }") ! 2285: ! 2286: ! 2287: (define_split ! 2288: [(set (match_operand:DI 0 "register_operand" "") ! 2289: (ashiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2290: (match_operand:SI 2 "small_int" ""))) ! 2291: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2292: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2293: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2294: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2295: && (INTVAL (operands[2]) & 63) < 32 ! 2296: && (INTVAL (operands[2]) & 63) != 0" ! 2297: ! 2298: [(set (subreg:SI (match_dup 0) 1) ! 2299: (lshiftrt:SI (subreg:SI (match_dup 1) 1) ! 2300: (match_dup 2))) ! 2301: ! 2302: (set (match_dup 3) ! 2303: (ashift:SI (subreg:SI (match_dup 1) 0) ! 2304: (match_dup 4))) ! 2305: ! 2306: (set (subreg:SI (match_dup 0) 1) ! 2307: (ior:SI (subreg:SI (match_dup 0) 1) ! 2308: (match_dup 3))) ! 2309: ! 2310: (set (subreg:SI (match_dup 0) 0) ! 2311: (ashiftrt:SI (subreg:SI (match_dup 1) 0) ! 2312: (match_dup 2)))] ! 2313: " ! 2314: { ! 2315: int amount = INTVAL (operands[2]); ! 2316: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2317: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2318: }") ! 2319: ! 2320: ! 2321: (define_insn "lshrsi3" ! 2322: [(set (match_operand:SI 0 "register_operand" "=d") ! 2323: (lshiftrt:SI (match_operand:SI 1 "register_operand" "d") ! 2324: (match_operand:SI 2 "arith_operand" "dI")))] ! 2325: "" ! 2326: "* ! 2327: { ! 2328: if (GET_CODE (operands[2]) == CONST_INT) ! 2329: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 2330: ! 2331: return \"srl\\t%0,%1,%2\"; ! 2332: }" ! 2333: [(set_attr "type" "arith") ! 2334: (set_attr "mode" "SI") ! 2335: (set_attr "length" "1")]) ! 2336: ! 2337: ! 2338: (define_expand "lshrdi3" ! 2339: [(parallel [(set (match_operand:DI 0 "register_operand" "") ! 2340: (lshiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2341: (match_operand:SI 2 "arith_operand" ""))) ! 2342: (clobber (match_dup 3))])] ! 2343: "!TARGET_DEBUG_G_MODE" ! 2344: "operands[3] = gen_reg_rtx (SImode);") ! 2345: ! 2346: ! 2347: (define_insn "lshrdi3_internal" ! 2348: [(set (match_operand:DI 0 "register_operand" "=&d") ! 2349: (lshiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2350: (match_operand:SI 2 "register_operand" "d"))) ! 2351: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2352: "!TARGET_DEBUG_G_MODE" ! 2353: "* ! 2354: { ! 2355: operands[4] = const0_rtx; ! 2356: dslots_jump_total += 3; ! 2357: dslots_jump_filled += 2; ! 2358: ! 2359: return \"sll\\t%3,%2,26\\n\\ ! 2360: \\tbgez\\t%3,1f\\n\\ ! 2361: \\tsrl\\t%L0,%M1,%2\\n\\ ! 2362: \\t%(b\\t3f\\n\\ ! 2363: \\tmove\\t%M0,%z4%)\\n\\ ! 2364: \\n\\ ! 2365: 1:\\n\\ ! 2366: \\t%(beq\\t%3,%z4,2f\\n\\ ! 2367: \\tsrl\\t%L0,%L1,%2%)\\n\\ ! 2368: \\n\\ ! 2369: \\tsubu\\t%3,%z4,%2\\n\\ ! 2370: \\tsll\\t%3,%M1,%3\\n\\ ! 2371: \\tor\\t%L0,%L0,%3\\n\\ ! 2372: 2:\\n\\ ! 2373: \\tsrl\\t%M0,%M1,%2\\n\\ ! 2374: 3:\"; ! 2375: }" ! 2376: [(set_attr "type" "darith") ! 2377: (set_attr "mode" "DI") ! 2378: (set_attr "length" "12")]) ! 2379: ! 2380: ! 2381: (define_insn "lshrdi3_internal2" ! 2382: [(set (match_operand:DI 0 "register_operand" "=d") ! 2383: (lshiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2384: (match_operand:SI 2 "small_int" "IJK"))) ! 2385: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2386: "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0" ! 2387: "* ! 2388: { ! 2389: operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f); ! 2390: operands[4] = const0_rtx; ! 2391: return \"srl\\t%L0,%M1,%2\;move\\t%M0,%z4\"; ! 2392: }" ! 2393: [(set_attr "type" "darith") ! 2394: (set_attr "mode" "DI") ! 2395: (set_attr "length" "2")]) ! 2396: ! 2397: ! 2398: (define_split ! 2399: [(set (match_operand:DI 0 "register_operand" "") ! 2400: (lshiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2401: (match_operand:SI 2 "small_int" ""))) ! 2402: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2403: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2404: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2405: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2406: && (INTVAL (operands[2]) & 32) != 0" ! 2407: ! 2408: [(set (subreg:SI (match_dup 0) 0) (lshiftrt:SI (subreg:SI (match_dup 1) 1) (match_dup 2))) ! 2409: (set (subreg:SI (match_dup 0) 1) (const_int 0))] ! 2410: ! 2411: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2412: ! 2413: ! 2414: (define_split ! 2415: [(set (match_operand:DI 0 "register_operand" "") ! 2416: (lshiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2417: (match_operand:SI 2 "small_int" ""))) ! 2418: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2419: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2420: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2421: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2422: && (INTVAL (operands[2]) & 32) != 0" ! 2423: ! 2424: [(set (subreg:SI (match_dup 0) 1) (lshiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2))) ! 2425: (set (subreg:SI (match_dup 0) 0) (const_int 0))] ! 2426: ! 2427: "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);") ! 2428: ! 2429: ! 2430: (define_insn "lshrdi3_internal3" ! 2431: [(set (match_operand:DI 0 "register_operand" "=d") ! 2432: (lshiftrt:DI (match_operand:DI 1 "register_operand" "d") ! 2433: (match_operand:SI 2 "small_int" "IJK"))) ! 2434: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 2435: "!TARGET_DEBUG_G_MODE ! 2436: && (INTVAL (operands[2]) & 63) < 32 ! 2437: && (INTVAL (operands[2]) & 63) != 0" ! 2438: "* ! 2439: { ! 2440: int amount = INTVAL (operands[2]); ! 2441: ! 2442: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2443: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2444: ! 2445: return \"srl\\t%L0,%L1,%2\;sll\\t%3,%M1,%4\;or\\t%L0,%L0,%3\;srl\\t%M0,%M1,%2\"; ! 2446: }" ! 2447: [(set_attr "type" "darith") ! 2448: (set_attr "mode" "DI") ! 2449: (set_attr "length" "4")]) ! 2450: ! 2451: ! 2452: (define_split ! 2453: [(set (match_operand:DI 0 "register_operand" "") ! 2454: (lshiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2455: (match_operand:SI 2 "small_int" ""))) ! 2456: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2457: "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2458: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2459: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2460: && (INTVAL (operands[2]) & 63) < 32 ! 2461: && (INTVAL (operands[2]) & 63) != 0" ! 2462: ! 2463: [(set (subreg:SI (match_dup 0) 0) ! 2464: (lshiftrt:SI (subreg:SI (match_dup 1) 0) ! 2465: (match_dup 2))) ! 2466: ! 2467: (set (match_dup 3) ! 2468: (ashift:SI (subreg:SI (match_dup 1) 1) ! 2469: (match_dup 4))) ! 2470: ! 2471: (set (subreg:SI (match_dup 0) 0) ! 2472: (ior:SI (subreg:SI (match_dup 0) 0) ! 2473: (match_dup 3))) ! 2474: ! 2475: (set (subreg:SI (match_dup 0) 1) ! 2476: (lshiftrt:SI (subreg:SI (match_dup 1) 1) ! 2477: (match_dup 2)))] ! 2478: " ! 2479: { ! 2480: int amount = INTVAL (operands[2]); ! 2481: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2482: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2483: }") ! 2484: ! 2485: ! 2486: (define_split ! 2487: [(set (match_operand:DI 0 "register_operand" "") ! 2488: (lshiftrt:DI (match_operand:DI 1 "register_operand" "") ! 2489: (match_operand:SI 2 "small_int" ""))) ! 2490: (clobber (match_operand:SI 3 "register_operand" ""))] ! 2491: "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_G_MODE ! 2492: && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER ! 2493: && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER ! 2494: && (INTVAL (operands[2]) & 63) < 32 ! 2495: && (INTVAL (operands[2]) & 63) != 0" ! 2496: ! 2497: [(set (subreg:SI (match_dup 0) 1) ! 2498: (lshiftrt:SI (subreg:SI (match_dup 1) 1) ! 2499: (match_dup 2))) ! 2500: ! 2501: (set (match_dup 3) ! 2502: (ashift:SI (subreg:SI (match_dup 1) 0) ! 2503: (match_dup 4))) ! 2504: ! 2505: (set (subreg:SI (match_dup 0) 1) ! 2506: (ior:SI (subreg:SI (match_dup 0) 1) ! 2507: (match_dup 3))) ! 2508: ! 2509: (set (subreg:SI (match_dup 0) 0) ! 2510: (lshiftrt:SI (subreg:SI (match_dup 1) 0) ! 2511: (match_dup 2)))] ! 2512: " ! 2513: { ! 2514: int amount = INTVAL (operands[2]); ! 2515: operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31)); ! 2516: operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31)); ! 2517: }") ! 2518: ! 2519: ! 2520: ;; ! 2521: ;; .................... ! 2522: ;; ! 2523: ;; COMPARISONS ! 2524: ;; ! 2525: ;; .................... ! 2526: ! 2527: ;; Flow here is rather complex: ! 2528: ;; ! 2529: ;; 1) The cmp{si,sf,df} routine is called. It deposits the ! 2530: ;; arguments into the branch_cmp array, and the type into ! 2531: ;; branch_type. No RTL is generated. ! 2532: ;; ! 2533: ;; 2) The appropriate branch define_expand is called, which then ! 2534: ;; creates the appropriate RTL for the comparison and branch. ! 2535: ;; Different CC modes are used, based on what type of branch is ! 2536: ;; done, so that we can constrain things appropriately. There ! 2537: ;; are assumptions in the rest of GCC that break if we fold the ! 2538: ;; operands into the branchs for integer operations, and use cc0 ! 2539: ;; for floating point. ! 2540: ;; ! 2541: ;; 3) The compare define_insns then once again set branch_cmp and ! 2542: ;; branch_type, and the branch define_insns use them. ! 2543: ;; ! 2544: ;; 4) If a set condition code is done instead of a branch, then the ! 2545: ;; operands are folded into the RTL, and a separate set of cc0 is ! 2546: ;; not done. This allows slt's to be put into delay slots. ! 2547: ! 2548: (define_expand "cmpsi" ! 2549: [(set (cc0) ! 2550: (compare:CC (match_operand:SI 0 "register_operand" "") ! 2551: (match_operand:SI 1 "arith_operand" "")))] ! 2552: "" ! 2553: " ! 2554: { ! 2555: if (operands[0]) /* avoid unused code message */ ! 2556: { ! 2557: branch_cmp[0] = operands[0]; ! 2558: branch_cmp[1] = operands[1]; ! 2559: branch_type = CMP_SI; ! 2560: DONE; ! 2561: } ! 2562: }") ! 2563: ! 2564: (define_expand "tstsi" ! 2565: [(set (cc0) ! 2566: (match_operand:SI 0 "register_operand" ""))] ! 2567: "" ! 2568: " ! 2569: { ! 2570: if (operands[0]) /* avoid unused code message */ ! 2571: { ! 2572: branch_cmp[0] = operands[0]; ! 2573: branch_cmp[1] = const0_rtx; ! 2574: branch_type = CMP_SI; ! 2575: DONE; ! 2576: } ! 2577: }") ! 2578: ! 2579: (define_insn "cmpsi_eqne" ! 2580: [(set (cc0) ! 2581: (compare:CC_EQ (match_operand:SI 0 "register_operand" "dJ") ! 2582: (match_operand:SI 1 "reg_or_0_operand" "dJ")))] ! 2583: "" ! 2584: "* ! 2585: { ! 2586: branch_cmp[0] = operands[0]; ! 2587: branch_cmp[1] = operands[1]; ! 2588: branch_type = CMP_SI; ! 2589: return \"\"; ! 2590: }" ! 2591: [(set_attr "type" "icmp") ! 2592: (set_attr "mode" "none") ! 2593: (set_attr "length" "0")]) ! 2594: ! 2595: (define_insn "cmpsi_zero" ! 2596: [(set (cc0) ! 2597: (match_operand:SI 0 "reg_or_0_operand" "dJ"))] ! 2598: "" ! 2599: "* ! 2600: { ! 2601: branch_cmp[0] = operands[0]; ! 2602: branch_cmp[1] = const0_rtx; ! 2603: branch_type = CMP_SI; ! 2604: return \"\"; ! 2605: }" ! 2606: [(set_attr "type" "icmp") ! 2607: (set_attr "mode" "none") ! 2608: (set_attr "length" "0")]) ! 2609: ! 2610: (define_insn "cmpsi_relational" ! 2611: [(set (cc0) ! 2612: (compare:CC (match_operand:SI 0 "register_operand" "dJ") ! 2613: (match_operand:SI 1 "arith_operand" "dI")))] ! 2614: "" ! 2615: "* ! 2616: { ! 2617: branch_cmp[0] = operands[0]; ! 2618: branch_cmp[1] = operands[1]; ! 2619: branch_type = CMP_SI; ! 2620: return \"\"; ! 2621: }" ! 2622: [(set_attr "type" "icmp") ! 2623: (set_attr "mode" "none") ! 2624: (set_attr "length" "0")]) ! 2625: ! 2626: (define_expand "cmpdf" ! 2627: [(set (cc0) ! 2628: (compare:CC_FP (match_operand:DF 0 "register_operand" "") ! 2629: (match_operand:DF 1 "register_operand" "")))] ! 2630: "TARGET_HARD_FLOAT" ! 2631: " ! 2632: { ! 2633: if (operands[0]) /* avoid unused code message */ ! 2634: { ! 2635: branch_cmp[0] = operands[0]; ! 2636: branch_cmp[1] = operands[1]; ! 2637: branch_type = CMP_DF; ! 2638: DONE; ! 2639: } ! 2640: }") ! 2641: ! 2642: (define_insn "cmpdf_internal" ! 2643: [(set (cc0) ! 2644: (compare:CC_FP (match_operand:DF 0 "register_operand" "f") ! 2645: (match_operand:DF 1 "register_operand" "f")))] ! 2646: "TARGET_HARD_FLOAT" ! 2647: "* ! 2648: { ! 2649: branch_cmp[0] = operands[0]; ! 2650: branch_cmp[1] = operands[1]; ! 2651: branch_type = CMP_DF; ! 2652: return \"\"; ! 2653: }" ! 2654: [(set_attr "type" "fcmp") ! 2655: (set_attr "mode" "none") ! 2656: (set_attr "length" "0")]) ! 2657: ! 2658: ! 2659: (define_expand "cmpsf" ! 2660: [(set (cc0) ! 2661: (compare:CC_FP (match_operand:SF 0 "register_operand" "") ! 2662: (match_operand:SF 1 "register_operand" "")))] ! 2663: "TARGET_HARD_FLOAT" ! 2664: " ! 2665: { ! 2666: if (operands[0]) /* avoid unused code message */ ! 2667: { ! 2668: branch_cmp[0] = operands[0]; ! 2669: branch_cmp[1] = operands[1]; ! 2670: branch_type = CMP_SF; ! 2671: DONE; ! 2672: } ! 2673: }") ! 2674: ! 2675: (define_insn "cmpsf_internal" ! 2676: [(set (cc0) ! 2677: (compare:CC_FP (match_operand:SF 0 "register_operand" "f") ! 2678: (match_operand:SF 1 "register_operand" "f")))] ! 2679: "TARGET_HARD_FLOAT" ! 2680: "* ! 2681: { ! 2682: branch_cmp[0] = operands[0]; ! 2683: branch_cmp[1] = operands[1]; ! 2684: branch_type = CMP_SF; ! 2685: return \"\"; ! 2686: }" ! 2687: [(set_attr "type" "fcmp") ! 2688: (set_attr "mode" "none") ! 2689: (set_attr "length" "0")]) ! 2690: ! 2691: ! 2692: ;; ! 2693: ;; .................... ! 2694: ;; ! 2695: ;; CONDITIONAL BRANCHES ! 2696: ;; ! 2697: ;; .................... ! 2698: ! 2699: ;; We really can't note that integer branches clobber $at, and FP ! 2700: ;; branches clobber $fcr31 because if we use a parallel operation, a ! 2701: ;; normal insn is used to hold the value instead of jump_insn. See ! 2702: ;; above for cmpxx saving the operands in branch_cmp and branch_type. ! 2703: ! 2704: (define_insn "branch_fp_true" ! 2705: [(set (pc) ! 2706: (if_then_else (match_operator:CC_FP 0 "fcmp_op" [(cc0) (const_int 0)]) ! 2707: (label_ref (match_operand 1 "" "")) ! 2708: (pc)))] ! 2709: "" ! 2710: "* ! 2711: { ! 2712: operands[2] = branch_cmp[0]; ! 2713: operands[3] = branch_cmp[1]; ! 2714: ! 2715: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2716: if (branch_type == CMP_DF) ! 2717: { ! 2718: switch (GET_CODE (operands[0])) ! 2719: { ! 2720: case EQ: return \"c.eq.d\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2721: case NE: return \"c.eq.d\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2722: case LT: return \"c.lt.d\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2723: case LE: return \"c.le.d\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2724: case GT: return \"c.lt.d\\t%3,%2%#\;%*bc1t%?\\t%l1\"; ! 2725: case GE: return \"c.le.d\\t%3,%2%#\;%*bc1t%?\\t%l1\"; ! 2726: } ! 2727: } ! 2728: ! 2729: else if (branch_type == CMP_SF) ! 2730: { ! 2731: switch (GET_CODE (operands[0])) ! 2732: { ! 2733: case EQ: return \"c.eq.s\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2734: case NE: return \"c.eq.s\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2735: case LT: return \"c.lt.s\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2736: case LE: return \"c.le.s\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2737: case GT: return \"c.lt.s\\t%3,%2%#\;%*bc1t%?\\t%l1\"; ! 2738: case GE: return \"c.le.s\\t%3,%2%#\;%*bc1t%?\\t%l1\"; ! 2739: } ! 2740: } ! 2741: ! 2742: abort_with_insn (insn, \"Bad floating compare/branch\"); ! 2743: return (char *)0; ! 2744: }" ! 2745: [(set_attr "type" "branch") ! 2746: (set_attr "mode" "none") ! 2747: (set_attr "length" "3")]) ! 2748: ! 2749: (define_insn "branch_fp_false" ! 2750: [(set (pc) ! 2751: (if_then_else (match_operator:CC_FP 0 "fcmp_op" [(cc0) (const_int 0)]) ! 2752: (pc) ! 2753: (label_ref (match_operand 1 "" ""))))] ! 2754: "" ! 2755: "* ! 2756: { ! 2757: operands[2] = branch_cmp[0]; ! 2758: operands[3] = branch_cmp[1]; ! 2759: ! 2760: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2761: if (branch_type == CMP_DF) ! 2762: { ! 2763: switch (GET_CODE (operands[0])) ! 2764: { ! 2765: case EQ: return \"c.eq.d\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2766: case NE: return \"c.eq.d\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2767: case LT: return \"c.lt.d\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2768: case LE: return \"c.le.d\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2769: case GT: return \"c.lt.d\\t%3,%2%#\;%*bc1f%?\\t%l1\"; ! 2770: case GE: return \"c.le.d\\t%3,%2%#\;%*bc1f%?\\t%l1\"; ! 2771: } ! 2772: } ! 2773: ! 2774: else if (branch_type == CMP_SF) ! 2775: { ! 2776: switch (GET_CODE (operands[0])) ! 2777: { ! 2778: case EQ: return \"c.eq.s\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2779: case NE: return \"c.eq.s\\t%2,%3%#\;%*bc1t%?\\t%l1\"; ! 2780: case LT: return \"c.lt.s\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2781: case LE: return \"c.le.s\\t%2,%3%#\;%*bc1f%?\\t%l1\"; ! 2782: case GT: return \"c.lt.s\\t%3,%2%#\;%*bc1f%?\\t%l1\"; ! 2783: case GE: return \"c.le.s\\t%3,%2%#\;%*bc1f%?\\t%l1\"; ! 2784: } ! 2785: } ! 2786: ! 2787: abort_with_insn (insn, \"Bad floating compare/branch\"); ! 2788: return (char *)0; ! 2789: }" ! 2790: [(set_attr "type" "branch") ! 2791: (set_attr "mode" "none") ! 2792: (set_attr "length" "3")]) ! 2793: ! 2794: ! 2795: (define_insn "branch_eqne_true" ! 2796: [(set (pc) ! 2797: (if_then_else (match_operator:CC_EQ 0 "equality_op" [(cc0) (const_int 0)]) ! 2798: (label_ref (match_operand 1 "" "")) ! 2799: (pc)))] ! 2800: "" ! 2801: "* ! 2802: { ! 2803: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2804: operands[2] = branch_cmp[0]; ! 2805: operands[3] = branch_cmp[1]; ! 2806: return \"%*b%C0%?\\t%z2,%z3,%1\"; ! 2807: }" ! 2808: [(set_attr "type" "branch") ! 2809: (set_attr "mode" "none") ! 2810: (set_attr "length" "1")]) ! 2811: ! 2812: (define_insn "branch_eqne_false" ! 2813: [(set (pc) ! 2814: (if_then_else (match_operator:CC_EQ 0 "equality_op" [(cc0) (const_int 0)]) ! 2815: (pc) ! 2816: (label_ref (match_operand 1 "" ""))))] ! 2817: "" ! 2818: "* ! 2819: { ! 2820: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2821: operands[2] = branch_cmp[0]; ! 2822: operands[3] = branch_cmp[1]; ! 2823: return \"%*b%N0%?\\t%z2,%z3,%1\"; ! 2824: }" ! 2825: [(set_attr "type" "branch") ! 2826: (set_attr "mode" "none") ! 2827: (set_attr "length" "1")]) ! 2828: ! 2829: (define_insn "branch_zero_true" ! 2830: [(set (pc) ! 2831: (if_then_else (match_operator:CC_0 0 "cmp_op" [(cc0) (const_int 0)]) ! 2832: (label_ref (match_operand 1 "" "")) ! 2833: (pc)))] ! 2834: "" ! 2835: "* ! 2836: { ! 2837: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2838: operands[2] = branch_cmp[0]; ! 2839: ! 2840: switch (GET_CODE (operands[0])) ! 2841: { ! 2842: case EQ: return \"%*beq%?\\t%z2,%.,%1\"; ! 2843: case NE: return \"%*bne%?\\t%z2,%.,%1\"; ! 2844: case GTU: return \"%*bne%?\\t%z2,%.,%1\"; ! 2845: case LEU: return \"%*beq%?\\t%z2,%.,%1\"; ! 2846: } ! 2847: ! 2848: return \"%*b%C0z%?\\t%z2,%1\"; ! 2849: }" ! 2850: [(set_attr "type" "branch") ! 2851: (set_attr "mode" "none") ! 2852: (set_attr "length" "1")]) ! 2853: ! 2854: (define_insn "branch_zero_false" ! 2855: [(set (pc) ! 2856: (if_then_else (match_operator:CC_0 0 "cmp_op" [(cc0) (const_int 0)]) ! 2857: (pc) ! 2858: (label_ref (match_operand 1 "" ""))))] ! 2859: "" ! 2860: "* ! 2861: { ! 2862: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2863: operands[2] = branch_cmp[0]; ! 2864: switch (GET_CODE (operands[0])) ! 2865: { ! 2866: case EQ: return \"%*bne%?\\t%z2,%.,%1\"; ! 2867: case NE: return \"%*beq%?\\t%z2,%.,%1\"; ! 2868: case GTU: return \"%*beq%?\\t%z2,%.,%1\"; ! 2869: case LEU: return \"%*bne\\t%z2,%.,%1\"; ! 2870: } ! 2871: ! 2872: return \"%*b%N0z%?\\t%z2,%1\"; ! 2873: }" ! 2874: [(set_attr "type" "branch") ! 2875: (set_attr "mode" "none") ! 2876: (set_attr "length" "1")]) ! 2877: ! 2878: (define_insn "branch_relop_true" ! 2879: [(set (pc) ! 2880: (if_then_else (match_operator:CC 0 "cmp2_op" [(cc0) (const_int 0)]) ! 2881: (label_ref (match_operand 1 "" "")) ! 2882: (pc)))] ! 2883: "" ! 2884: "* ! 2885: { ! 2886: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2887: operands[2] = branch_cmp[0]; ! 2888: operands[3] = branch_cmp[1]; ! 2889: ! 2890: return \"%&b%C0%?\\t%z2,%z3,%1%!\"; ! 2891: }" ! 2892: [(set_attr "type" "branch") ! 2893: (set_attr "mode" "none") ! 2894: (set_attr "length" "2")]) ! 2895: ! 2896: (define_insn "branch_relop_false" ! 2897: [(set (pc) ! 2898: (if_then_else (match_operator:CC 0 "cmp2_op" [(cc0) (const_int 0)]) ! 2899: (pc) ! 2900: (label_ref (match_operand 1 "" ""))))] ! 2901: "" ! 2902: "* ! 2903: { ! 2904: mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn)); ! 2905: operands[2] = branch_cmp[0]; ! 2906: operands[3] = branch_cmp[1]; ! 2907: ! 2908: return \"%&b%N0%?\\t%z2,%z3,%1%!\"; ! 2909: }" ! 2910: [(set_attr "type" "branch") ! 2911: (set_attr "mode" "none") ! 2912: (set_attr "length" "2")]) ! 2913: ! 2914: (define_expand "beq" ! 2915: [(set (pc) ! 2916: (if_then_else (eq:CC_EQ (cc0) ! 2917: (const_int 0)) ! 2918: (label_ref (match_operand 0 "" "")) ! 2919: (pc)))] ! 2920: "" ! 2921: " ! 2922: { ! 2923: if (operands[0]) /* avoid unused code warning */ ! 2924: { ! 2925: gen_conditional_branch (operands, EQ); ! 2926: DONE; ! 2927: } ! 2928: }") ! 2929: ! 2930: (define_expand "bne" ! 2931: [(set (pc) ! 2932: (if_then_else (ne:CC_EQ (cc0) ! 2933: (const_int 0)) ! 2934: (label_ref (match_operand 0 "" "")) ! 2935: (pc)))] ! 2936: "" ! 2937: " ! 2938: { ! 2939: if (operands[0]) /* avoid unused code warning */ ! 2940: { ! 2941: gen_conditional_branch (operands, NE); ! 2942: DONE; ! 2943: } ! 2944: }") ! 2945: ! 2946: (define_expand "bgt" ! 2947: [(set (pc) ! 2948: (if_then_else (gt:CC (cc0) ! 2949: (const_int 0)) ! 2950: (label_ref (match_operand 0 "" "")) ! 2951: (pc)))] ! 2952: "" ! 2953: " ! 2954: { ! 2955: if (operands[0]) /* avoid unused code warning */ ! 2956: { ! 2957: gen_conditional_branch (operands, GT); ! 2958: DONE; ! 2959: } ! 2960: }") ! 2961: ! 2962: (define_expand "bge" ! 2963: [(set (pc) ! 2964: (if_then_else (ge:CC (cc0) ! 2965: (const_int 0)) ! 2966: (label_ref (match_operand 0 "" "")) ! 2967: (pc)))] ! 2968: "" ! 2969: " ! 2970: { ! 2971: if (operands[0]) /* avoid unused code warning */ ! 2972: { ! 2973: gen_conditional_branch (operands, GE); ! 2974: DONE; ! 2975: } ! 2976: }") ! 2977: ! 2978: (define_expand "blt" ! 2979: [(set (pc) ! 2980: (if_then_else (lt:CC (cc0) ! 2981: (const_int 0)) ! 2982: (label_ref (match_operand 0 "" "")) ! 2983: (pc)))] ! 2984: "" ! 2985: " ! 2986: { ! 2987: if (operands[0]) /* avoid unused code warning */ ! 2988: { ! 2989: gen_conditional_branch (operands, LT); ! 2990: DONE; ! 2991: } ! 2992: }") ! 2993: ! 2994: (define_expand "ble" ! 2995: [(set (pc) ! 2996: (if_then_else (le:CC (cc0) ! 2997: (const_int 0)) ! 2998: (label_ref (match_operand 0 "" "")) ! 2999: (pc)))] ! 3000: "" ! 3001: " ! 3002: { ! 3003: if (operands[0]) /* avoid unused code warning */ ! 3004: { ! 3005: gen_conditional_branch (operands, LE); ! 3006: DONE; ! 3007: } ! 3008: }") ! 3009: ! 3010: (define_expand "bgtu" ! 3011: [(set (pc) ! 3012: (if_then_else (gtu:CC (cc0) ! 3013: (const_int 0)) ! 3014: (label_ref (match_operand 0 "" "")) ! 3015: (pc)))] ! 3016: "" ! 3017: " ! 3018: { ! 3019: if (operands[0]) /* avoid unused code warning */ ! 3020: { ! 3021: gen_conditional_branch (operands, GTU); ! 3022: DONE; ! 3023: } ! 3024: }") ! 3025: ! 3026: (define_expand "bgeu" ! 3027: [(set (pc) ! 3028: (if_then_else (geu:CC (cc0) ! 3029: (const_int 0)) ! 3030: (label_ref (match_operand 0 "" "")) ! 3031: (pc)))] ! 3032: "" ! 3033: " ! 3034: { ! 3035: if (operands[0]) /* avoid unused code warning */ ! 3036: { ! 3037: gen_conditional_branch (operands, GEU); ! 3038: DONE; ! 3039: } ! 3040: }") ! 3041: ! 3042: ! 3043: (define_expand "bltu" ! 3044: [(set (pc) ! 3045: (if_then_else (ltu:CC (cc0) ! 3046: (const_int 0)) ! 3047: (label_ref (match_operand 0 "" "")) ! 3048: (pc)))] ! 3049: "" ! 3050: " ! 3051: { ! 3052: if (operands[0]) /* avoid unused code warning */ ! 3053: { ! 3054: gen_conditional_branch (operands, LTU); ! 3055: DONE; ! 3056: } ! 3057: }") ! 3058: ! 3059: (define_expand "bleu" ! 3060: [(set (pc) ! 3061: (if_then_else (leu:CC (cc0) ! 3062: (const_int 0)) ! 3063: (label_ref (match_operand 0 "" "")) ! 3064: (pc)))] ! 3065: "" ! 3066: " ! 3067: { ! 3068: if (operands[0]) /* avoid unused code warning */ ! 3069: { ! 3070: gen_conditional_branch (operands, LEU); ! 3071: DONE; ! 3072: } ! 3073: }") ! 3074: ! 3075: ! 3076: ;; ! 3077: ;; .................... ! 3078: ;; ! 3079: ;; SETTING A REGISTER FROM A COMPARISON ! 3080: ;; ! 3081: ;; .................... ! 3082: ! 3083: (define_expand "seq" ! 3084: [(set (match_operand:SI 0 "register_operand" "=d") ! 3085: (eq:CC_EQ (match_dup 1) ! 3086: (match_dup 2)))] ! 3087: "" ! 3088: " ! 3089: { ! 3090: extern rtx force_reg (); ! 3091: ! 3092: if (branch_type != CMP_SI) ! 3093: FAIL; ! 3094: ! 3095: /* set up operands from compare. */ ! 3096: operands[1] = branch_cmp[0]; ! 3097: operands[2] = branch_cmp[1]; ! 3098: ! 3099: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0) ! 3100: operands[2] = force_reg (SImode, operands[2]); ! 3101: ! 3102: /* fall through and generate default code */ ! 3103: }") ! 3104: ! 3105: (define_insn "seq_si" ! 3106: [(set (match_operand:SI 0 "register_operand" "=d,d,d") ! 3107: (eq:CC_EQ (match_operand:SI 1 "register_operand" "%d,d,d") ! 3108: (match_operand:SI 2 "uns_arith_operand" "J,d,K")))] ! 3109: "" ! 3110: "@ ! 3111: sltu\\t%0,%1,1 ! 3112: xor\\t%0,%1,%2\;sltu\\t%0,%0,1 ! 3113: xori\\t%0,%1,%x2\;sltu\\t%0,%0,1" ! 3114: [(set_attr "type" "arith,arith,arith") ! 3115: (set_attr "mode" "SI,SI,SI") ! 3116: (set_attr "length" "1,2,2")]) ! 3117: ! 3118: (define_split ! 3119: [(set (match_operand:SI 0 "register_operand" "") ! 3120: (eq:CC_EQ (match_operand:SI 1 "register_operand" "") ! 3121: (match_operand:SI 2 "uns_arith_operand" "")))] ! 3122: "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0" ! 3123: [(set (match_dup 0) ! 3124: (xor:SI (match_dup 1) ! 3125: (match_dup 2))) ! 3126: (set (match_dup 0) ! 3127: (ltu:CC (match_dup 0) ! 3128: (const_int 1)))] ! 3129: "") ! 3130: ! 3131: (define_expand "sne" ! 3132: [(set (match_operand:SI 0 "register_operand" "=d") ! 3133: (ne:CC_EQ (match_dup 1) ! 3134: (match_dup 2)))] ! 3135: "" ! 3136: " ! 3137: { ! 3138: extern rtx force_reg (); ! 3139: ! 3140: if (branch_type != CMP_SI) ! 3141: FAIL; ! 3142: ! 3143: /* set up operands from compare. */ ! 3144: operands[1] = branch_cmp[0]; ! 3145: operands[2] = branch_cmp[1]; ! 3146: ! 3147: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0) ! 3148: operands[2] = force_reg (SImode, operands[2]); ! 3149: ! 3150: /* fall through and generate default code */ ! 3151: }") ! 3152: ! 3153: (define_insn "sne_si" ! 3154: [(set (match_operand:SI 0 "register_operand" "=d,d,d") ! 3155: (ne:CC_EQ (match_operand:SI 1 "register_operand" "%d,d,d") ! 3156: (match_operand:SI 2 "uns_arith_operand" "J,d,K")))] ! 3157: "" ! 3158: "* ! 3159: { ! 3160: if (GET_CODE (operands[2]) != CONST_INT) ! 3161: return \"xor\\t%0,%1,%2\;sltu\\t%0,%.,%0\"; ! 3162: ! 3163: if (INTVAL (operands[2]) == 0) ! 3164: return \"sltu\\t%0,%.,%1\"; ! 3165: ! 3166: return \"xori\\t%0,%1,%x2\;sltu\\t%0,%.,%0\"; ! 3167: }" ! 3168: [(set_attr "type" "arith,arith,arith") ! 3169: (set_attr "mode" "SI,SI,SI") ! 3170: (set_attr "length" "1,2,2")]) ! 3171: ! 3172: (define_split ! 3173: [(set (match_operand:SI 0 "register_operand" "") ! 3174: (ne:CC_EQ (match_operand:SI 1 "register_operand" "") ! 3175: (match_operand:SI 2 "uns_arith_operand" "")))] ! 3176: "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0" ! 3177: [(set (match_dup 0) ! 3178: (xor:SI (match_dup 1) ! 3179: (match_dup 2))) ! 3180: (set (match_dup 0) ! 3181: (gtu:CC (match_dup 0) ! 3182: (const_int 0)))] ! 3183: "") ! 3184: ! 3185: (define_expand "sgt" ! 3186: [(set (match_operand:SI 0 "register_operand" "=d") ! 3187: (gt:CC (match_dup 1) ! 3188: (match_dup 2)))] ! 3189: "" ! 3190: " ! 3191: { ! 3192: extern rtx force_reg (); ! 3193: ! 3194: if (branch_type != CMP_SI) ! 3195: FAIL; ! 3196: ! 3197: /* set up operands from compare. */ ! 3198: operands[1] = branch_cmp[0]; ! 3199: operands[2] = branch_cmp[1]; ! 3200: ! 3201: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0) ! 3202: operands[2] = force_reg (SImode, operands[2]); ! 3203: ! 3204: /* fall through and generate default code */ ! 3205: }") ! 3206: ! 3207: (define_insn "sgt_si" ! 3208: [(set (match_operand:SI 0 "register_operand" "=d") ! 3209: (gt:CC (match_operand:SI 1 "register_operand" "d") ! 3210: (match_operand:SI 2 "reg_or_0_operand" "dJ")))] ! 3211: "" ! 3212: "slt\\t%0,%z2,%1" ! 3213: [(set_attr "type" "arith") ! 3214: (set_attr "mode" "SI") ! 3215: (set_attr "length" "1")]) ! 3216: ! 3217: (define_expand "sge" ! 3218: [(set (match_operand:SI 0 "register_operand" "=d") ! 3219: (ge:CC (match_dup 1) ! 3220: (match_dup 2)))] ! 3221: "" ! 3222: " ! 3223: { ! 3224: if (branch_type != CMP_SI) ! 3225: FAIL; ! 3226: ! 3227: /* set up operands from compare. */ ! 3228: operands[1] = branch_cmp[0]; ! 3229: operands[2] = branch_cmp[1]; ! 3230: ! 3231: /* fall through and generate default code */ ! 3232: }") ! 3233: ! 3234: (define_insn "sge_si" ! 3235: [(set (match_operand:SI 0 "register_operand" "=d") ! 3236: (ge:CC (match_operand:SI 1 "register_operand" "d") ! 3237: (match_operand:SI 2 "arith_operand" "dI")))] ! 3238: "" ! 3239: "slt\\t%0,%1,%2\;xori\\t%0,%0,0x0001" ! 3240: [(set_attr "type" "arith") ! 3241: (set_attr "mode" "SI") ! 3242: (set_attr "length" "2")]) ! 3243: ! 3244: (define_split ! 3245: [(set (match_operand:SI 0 "register_operand" "") ! 3246: (ge:CC (match_operand:SI 1 "register_operand" "") ! 3247: (match_operand:SI 2 "arith_operand" "")))] ! 3248: "" ! 3249: [(set (match_dup 0) ! 3250: (lt:CC (match_dup 1) ! 3251: (match_dup 2))) ! 3252: (set (match_dup 0) ! 3253: (xor:SI (match_dup 0) ! 3254: (const_int 1)))] ! 3255: "") ! 3256: ! 3257: (define_expand "slt" ! 3258: [(set (match_operand:SI 0 "register_operand" "=d") ! 3259: (lt:CC (match_dup 1) ! 3260: (match_dup 2)))] ! 3261: "" ! 3262: " ! 3263: { ! 3264: if (branch_type != CMP_SI) ! 3265: FAIL; ! 3266: ! 3267: /* set up operands from compare. */ ! 3268: operands[1] = branch_cmp[0]; ! 3269: operands[2] = branch_cmp[1]; ! 3270: ! 3271: /* fall through and generate default code */ ! 3272: }") ! 3273: ! 3274: (define_insn "slt_si" ! 3275: [(set (match_operand:SI 0 "register_operand" "=d") ! 3276: (lt:CC (match_operand:SI 1 "register_operand" "d") ! 3277: (match_operand:SI 2 "arith_operand" "dI")))] ! 3278: "" ! 3279: "slt\\t%0,%1,%2" ! 3280: [(set_attr "type" "arith") ! 3281: (set_attr "mode" "SI") ! 3282: (set_attr "length" "1")]) ! 3283: ! 3284: (define_expand "sle" ! 3285: [(set (match_operand:SI 0 "register_operand" "=d") ! 3286: (le:CC (match_dup 1) ! 3287: (match_dup 2)))] ! 3288: "" ! 3289: " ! 3290: { ! 3291: extern rtx force_reg (); ! 3292: ! 3293: if (branch_type != CMP_SI) ! 3294: FAIL; ! 3295: ! 3296: /* set up operands from compare. */ ! 3297: operands[1] = branch_cmp[0]; ! 3298: operands[2] = branch_cmp[1]; ! 3299: ! 3300: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767) ! 3301: operands[2] = force_reg (SImode, operands[2]); ! 3302: ! 3303: /* fall through and generate default code */ ! 3304: }") ! 3305: ! 3306: (define_insn "sle_si" ! 3307: [(set (match_operand:SI 0 "register_operand" "=d,d") ! 3308: (le:CC (match_operand:SI 1 "register_operand" "d,d") ! 3309: (match_operand:SI 2 "arith_operand" "d,I")))] ! 3310: "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) < 32767" ! 3311: "@ ! 3312: slt\\t%0,%z2,%1\;xori\\t%0,%0,0x0001 ! 3313: slt\\t%0,%1,(%2+1)" ! 3314: [(set_attr "type" "arith,arith") ! 3315: (set_attr "mode" "SI,SI") ! 3316: (set_attr "length" "2,1")]) ! 3317: ! 3318: (define_split ! 3319: [(set (match_operand:SI 0 "register_operand" "") ! 3320: (le:CC (match_operand:SI 1 "register_operand" "") ! 3321: (match_operand:SI 2 "register_operand" "")))] ! 3322: "" ! 3323: [(set (match_dup 0) ! 3324: (lt:CC (match_dup 2) ! 3325: (match_dup 1))) ! 3326: (set (match_dup 0) ! 3327: (xor:SI (match_dup 0) ! 3328: (const_int 1)))] ! 3329: "") ! 3330: ! 3331: (define_expand "sgtu" ! 3332: [(set (match_operand:SI 0 "register_operand" "=d") ! 3333: (gtu:CC (match_dup 1) ! 3334: (match_dup 2)))] ! 3335: "" ! 3336: " ! 3337: { ! 3338: extern rtx force_reg (); ! 3339: ! 3340: if (branch_type != CMP_SI) ! 3341: FAIL; ! 3342: ! 3343: /* set up operands from compare. */ ! 3344: operands[1] = branch_cmp[0]; ! 3345: operands[2] = branch_cmp[1]; ! 3346: ! 3347: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0) ! 3348: operands[2] = force_reg (SImode, operands[2]); ! 3349: ! 3350: /* fall through and generate default code */ ! 3351: }") ! 3352: ! 3353: (define_insn "sgtu_si" ! 3354: [(set (match_operand:SI 0 "register_operand" "=d") ! 3355: (gtu:CC (match_operand:SI 1 "register_operand" "d") ! 3356: (match_operand:SI 2 "reg_or_0_operand" "dJ")))] ! 3357: "" ! 3358: "sltu\\t%0,%z2,%1" ! 3359: [(set_attr "type" "arith") ! 3360: (set_attr "mode" "SI") ! 3361: (set_attr "length" "1")]) ! 3362: ! 3363: (define_expand "sgeu" ! 3364: [(set (match_operand:SI 0 "register_operand" "=d") ! 3365: (geu:CC (match_dup 1) ! 3366: (match_dup 2)))] ! 3367: "" ! 3368: " ! 3369: { ! 3370: if (branch_type != CMP_SI) ! 3371: FAIL; ! 3372: ! 3373: /* set up operands from compare. */ ! 3374: operands[1] = branch_cmp[0]; ! 3375: operands[2] = branch_cmp[1]; ! 3376: ! 3377: /* fall through and generate default code */ ! 3378: }") ! 3379: ! 3380: (define_insn "sgeu_si" ! 3381: [(set (match_operand:SI 0 "register_operand" "=d") ! 3382: (geu:CC (match_operand:SI 1 "register_operand" "d") ! 3383: (match_operand:SI 2 "arith_operand" "dI")))] ! 3384: "" ! 3385: "sltu\\t%0,%1,%2\;xori\\t%0,%0,0x0001" ! 3386: [(set_attr "type" "arith") ! 3387: (set_attr "mode" "SI") ! 3388: (set_attr "length" "2")]) ! 3389: ! 3390: (define_split ! 3391: [(set (match_operand:SI 0 "register_operand" "") ! 3392: (geu:CC (match_operand:SI 1 "register_operand" "") ! 3393: (match_operand:SI 2 "arith_operand" "")))] ! 3394: "" ! 3395: [(set (match_dup 0) ! 3396: (ltu:CC (match_dup 1) ! 3397: (match_dup 2))) ! 3398: (set (match_dup 0) ! 3399: (xor:SI (match_dup 0) ! 3400: (const_int 1)))] ! 3401: "") ! 3402: ! 3403: (define_expand "sltu" ! 3404: [(set (match_operand:SI 0 "register_operand" "=d") ! 3405: (ltu:CC (match_dup 1) ! 3406: (match_dup 2)))] ! 3407: "" ! 3408: " ! 3409: { ! 3410: if (branch_type != CMP_SI) ! 3411: FAIL; ! 3412: ! 3413: /* set up operands from compare. */ ! 3414: operands[1] = branch_cmp[0]; ! 3415: operands[2] = branch_cmp[1]; ! 3416: ! 3417: /* fall through and generate default code */ ! 3418: }") ! 3419: ! 3420: (define_insn "sltu_si" ! 3421: [(set (match_operand:SI 0 "register_operand" "=d") ! 3422: (ltu:CC (match_operand:SI 1 "register_operand" "d") ! 3423: (match_operand:SI 2 "arith_operand" "dI")))] ! 3424: "" ! 3425: "sltu\\t%0,%1,%2" ! 3426: [(set_attr "type" "arith") ! 3427: (set_attr "mode" "SI") ! 3428: (set_attr "length" "1")]) ! 3429: ! 3430: (define_expand "sleu" ! 3431: [(set (match_operand:SI 0 "register_operand" "=d") ! 3432: (leu:CC (match_dup 1) ! 3433: (match_dup 2)))] ! 3434: "" ! 3435: " ! 3436: { ! 3437: extern rtx force_reg (); ! 3438: ! 3439: if (branch_type != CMP_SI) ! 3440: FAIL; ! 3441: ! 3442: /* set up operands from compare. */ ! 3443: operands[1] = branch_cmp[0]; ! 3444: operands[2] = branch_cmp[1]; ! 3445: ! 3446: if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767) ! 3447: operands[2] = force_reg (SImode, operands[2]); ! 3448: ! 3449: /* fall through and generate default code */ ! 3450: }") ! 3451: ! 3452: (define_insn "sleu_si" ! 3453: [(set (match_operand:SI 0 "register_operand" "=d,d") ! 3454: (leu:CC (match_operand:SI 1 "register_operand" "d,d") ! 3455: (match_operand:SI 2 "arith_operand" "d,I")))] ! 3456: "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) < 32767" ! 3457: "@ ! 3458: sltu\\t%0,%z2,%1\;xori\\t%0,%0,0x0001 ! 3459: sltu\\t%0,%1,(%2+1)" ! 3460: [(set_attr "type" "arith,arith") ! 3461: (set_attr "mode" "SI,SI") ! 3462: (set_attr "length" "2,1")]) ! 3463: ! 3464: (define_split ! 3465: [(set (match_operand:SI 0 "register_operand" "") ! 3466: (leu:CC (match_operand:SI 1 "register_operand" "") ! 3467: (match_operand:SI 2 "register_operand" "")))] ! 3468: "" ! 3469: [(set (match_dup 0) ! 3470: (ltu:CC (match_dup 2) ! 3471: (match_dup 1))) ! 3472: (set (match_dup 0) ! 3473: (xor:SI (match_dup 0) ! 3474: (const_int 1)))] ! 3475: "") ! 3476: ! 3477: ! 3478: ;; ! 3479: ;; .................... ! 3480: ;; ! 3481: ;; UNCONDITIONAL BRANCHES ! 3482: ;; ! 3483: ;; .................... ! 3484: ! 3485: ;; Unconditional branches. ! 3486: ! 3487: (define_insn "jump" ! 3488: [(set (pc) ! 3489: (label_ref (match_operand 0 "" "")))] ! 3490: "" ! 3491: "* ! 3492: { ! 3493: if (GET_CODE (operands[0]) == REG) ! 3494: return \"%*j\\t%0\"; ! 3495: else ! 3496: return \"%*j\\t%l0\"; ! 3497: }" ! 3498: [(set_attr "type" "jump") ! 3499: (set_attr "mode" "none") ! 3500: (set_attr "length" "1")]) ! 3501: ! 3502: (define_insn "indirect_jump" ! 3503: [(set (pc) (match_operand:SI 0 "register_operand" "d"))] ! 3504: "" ! 3505: "%*j\\t%0" ! 3506: [(set_attr "type" "jump") ! 3507: (set_attr "mode" "none") ! 3508: (set_attr "length" "1")]) ! 3509: ! 3510: (define_insn "tablejump" ! 3511: [(set (pc) ! 3512: (match_operand:SI 0 "register_operand" "d")) ! 3513: (use (label_ref (match_operand 1 "" "")))] ! 3514: "" ! 3515: "%*j\\t%0" ! 3516: [(set_attr "type" "jump") ! 3517: (set_attr "mode" "none") ! 3518: (set_attr "length" "1")]) ! 3519: ! 3520: ;; Function return, only allow after optimization, so that we can ! 3521: ;; eliminate jumps to jumps if no stack space is used. ! 3522: ! 3523: (define_insn "return" ! 3524: [(return)] ! 3525: "null_epilogue ()" ! 3526: "* ! 3527: { ! 3528: operands[0] = gen_rtx (REG, SImode, GP_REG_FIRST + 31); ! 3529: return \"%*j\\t%0\"; ! 3530: }" ! 3531: [(set_attr "type" "jump") ! 3532: (set_attr "mode" "none") ! 3533: (set_attr "length" "1")]) ! 3534: ! 3535: ! 3536: ;; ! 3537: ;; .................... ! 3538: ;; ! 3539: ;; FUNCTION CALLS ! 3540: ;; ! 3541: ;; .................... ! 3542: ! 3543: ;; calls.c now passes a third argument, make saber happy ! 3544: ! 3545: (define_expand "call" ! 3546: [(parallel [(call (match_operand 0 "call_memory_operand" "m") ! 3547: (match_operand 1 "" "i")) ! 3548: (clobber (match_operand 2 "" ""))])] ;; overwrite op2 with $31 ! 3549: "" ! 3550: " ! 3551: { ! 3552: rtx addr; ! 3553: ! 3554: operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 31); ! 3555: ! 3556: addr = XEXP (operands[0], 0); ! 3557: if (! call_memory_operand (addr, VOIDmode)) ! 3558: XEXP (operands[0], 0) = force_reg (FUNCTION_MODE, addr); ! 3559: }") ! 3560: ! 3561: (define_insn "call_internal" ! 3562: [(call (match_operand 0 "call_memory_operand" "m") ! 3563: (match_operand 1 "" "i")) ! 3564: (clobber (match_operand:SI 2 "register_operand" "=d"))] ! 3565: "" ! 3566: "* ! 3567: { ! 3568: register rtx target = XEXP (operands[0], 0); ! 3569: ! 3570: if (GET_CODE (target) == SYMBOL_REF) ! 3571: return \"%*jal\\t%0\"; ! 3572: ! 3573: else ! 3574: { ! 3575: operands[0] = target; ! 3576: operands[1] = gen_rtx (REG, SImode, GP_REG_FIRST + 31); ! 3577: return \"%*jal\\t%1,%0\"; ! 3578: } ! 3579: }" ! 3580: [(set_attr "type" "call") ! 3581: (set_attr "mode" "none") ! 3582: (set_attr "length" "1")]) ! 3583: ! 3584: ;; calls.c now passes a fourth argument, make saber happy ! 3585: ! 3586: (define_expand "call_value" ! 3587: [(parallel [(set (match_operand 0 "register_operand" "=df") ! 3588: (call (match_operand 1 "call_memory_operand" "m") ! 3589: (match_operand 2 "" "i"))) ! 3590: (clobber (match_operand 3 "" ""))])] ;; overwrite op3 with $31 ! 3591: "" ! 3592: " ! 3593: { ! 3594: rtx addr; ! 3595: ! 3596: operands[3] = gen_rtx (REG, SImode, GP_REG_FIRST + 31); ! 3597: ! 3598: addr = XEXP (operands[1], 0); ! 3599: if (! call_memory_operand (addr, VOIDmode)) ! 3600: XEXP (operands[1], 0) = force_reg (FUNCTION_MODE, addr); ! 3601: }") ! 3602: ! 3603: (define_insn "call_value_internal" ! 3604: [(set (match_operand 0 "register_operand" "=df") ! 3605: (call (match_operand 1 "call_memory_operand" "m") ! 3606: (match_operand 2 "" "i"))) ! 3607: (clobber (match_operand:SI 3 "register_operand" "=d"))] ! 3608: "" ! 3609: "* ! 3610: { ! 3611: register rtx target = XEXP (operands[1], 0); ! 3612: ! 3613: if (GET_CODE (target) == SYMBOL_REF) ! 3614: return \"%*jal\\t%1\"; ! 3615: ! 3616: else ! 3617: { ! 3618: operands[1] = target; ! 3619: operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 31); ! 3620: return \"%*jal\\t%2,%1\"; ! 3621: } ! 3622: }" ! 3623: [(set_attr "type" "call") ! 3624: (set_attr "mode" "none") ! 3625: (set_attr "length" "1")]) ! 3626: ! 3627: ! 3628: ;; ! 3629: ;; .................... ! 3630: ;; ! 3631: ;; MISC. ! 3632: ;; ! 3633: ;; .................... ! 3634: ;; ! 3635: ! 3636: (define_insn "nop" ! 3637: [(const_int 0)] ! 3638: "" ! 3639: "%(nop%)" ! 3640: [(set_attr "type" "nop") ! 3641: (set_attr "mode" "none") ! 3642: (set_attr "length" "1")]) ! 3643: ! 3644: (define_expand "probe" ! 3645: [(set (match_dup 0) ! 3646: (match_dup 1))] ! 3647: "" ! 3648: " ! 3649: { ! 3650: operands[0] = gen_reg_rtx (SImode); ! 3651: operands[1] = gen_rtx (MEM, SImode, stack_pointer_rtx); ! 3652: MEM_VOLATILE_P (operands[1]) = TRUE; ! 3653: ! 3654: /* fall through and generate default code */ ! 3655: }") ! 3656: ! 3657: ! 3658: ;; ! 3659: ;; Local variables: ! 3660: ;; mode:emacs-lisp ! 3661: ;; comment-start: ";; " ! 3662: ;; eval: (set-syntax-table (copy-sequence (syntax-table))) ! 3663: ;; eval: (modify-syntax-entry ?[ "(]") ! 3664: ;; eval: (modify-syntax-entry ?] ")[") ! 3665: ;; eval: (modify-syntax-entry ?{ "(}") ! 3666: ;; eval: (modify-syntax-entry ?} "){") ! 3667: ;; End:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.