MSP430InstrInfo.td revision 52f28e9b63b862fa3dafd9330eb76d5874c21574
1//===- MSP430InstrInfo.td - MSP430 Instruction defs -----------*- tblgen-*-===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file describes the MSP430 instructions in TableGen format. 11// 12//===----------------------------------------------------------------------===// 13 14include "MSP430InstrFormats.td" 15 16//===----------------------------------------------------------------------===// 17// Type Constraints. 18//===----------------------------------------------------------------------===// 19class SDTCisI8<int OpNum> : SDTCisVT<OpNum, i8>; 20class SDTCisI16<int OpNum> : SDTCisVT<OpNum, i16>; 21 22//===----------------------------------------------------------------------===// 23// Type Profiles. 24//===----------------------------------------------------------------------===// 25def SDT_MSP430Call : SDTypeProfile<0, -1, [SDTCisVT<0, iPTR>]>; 26def SDT_MSP430CallSeqStart : SDCallSeqStart<[SDTCisVT<0, i16>]>; 27def SDT_MSP430CallSeqEnd : SDCallSeqEnd<[SDTCisVT<0, i16>, SDTCisVT<1, i16>]>; 28def SDT_MSP430Wrapper : SDTypeProfile<1, 1, [SDTCisSameAs<0, 1>, SDTCisPtrTy<0>]>; 29def SDT_MSP430Cmp : SDTypeProfile<0, 2, [SDTCisSameAs<0, 1>]>; 30def SDT_MSP430BrCC : SDTypeProfile<0, 2, [SDTCisVT<0, OtherVT>, 31 SDTCisVT<1, i8>]>; 32def SDT_MSP430SelectCC : SDTypeProfile<1, 3, [SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>, 33 SDTCisVT<3, i8>]>; 34 35//===----------------------------------------------------------------------===// 36// MSP430 Specific Node Definitions. 37//===----------------------------------------------------------------------===// 38def MSP430retflag : SDNode<"MSP430ISD::RET_FLAG", SDTNone, 39 [SDNPHasChain, SDNPOptInFlag]>; 40 41def MSP430rra : SDNode<"MSP430ISD::RRA", SDTIntUnaryOp, []>; 42def MSP430rla : SDNode<"MSP430ISD::RLA", SDTIntUnaryOp, []>; 43def MSP430rrc : SDNode<"MSP430ISD::RRC", SDTIntUnaryOp, []>; 44 45def MSP430call : SDNode<"MSP430ISD::CALL", SDT_MSP430Call, 46 [SDNPHasChain, SDNPOutFlag, SDNPOptInFlag]>; 47def MSP430callseq_start : 48 SDNode<"ISD::CALLSEQ_START", SDT_MSP430CallSeqStart, 49 [SDNPHasChain, SDNPOutFlag]>; 50def MSP430callseq_end : 51 SDNode<"ISD::CALLSEQ_END", SDT_MSP430CallSeqEnd, 52 [SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>; 53def MSP430Wrapper : SDNode<"MSP430ISD::Wrapper", SDT_MSP430Wrapper>; 54def MSP430cmp : SDNode<"MSP430ISD::CMP", SDT_MSP430Cmp, [SDNPOutFlag]>; 55def MSP430brcc : SDNode<"MSP430ISD::BR_CC", SDT_MSP430BrCC, [SDNPHasChain, SDNPInFlag]>; 56def MSP430selectcc: SDNode<"MSP430ISD::SELECT_CC", SDT_MSP430SelectCC, [SDNPInFlag]>; 57 58//===----------------------------------------------------------------------===// 59// MSP430 Operand Definitions. 60//===----------------------------------------------------------------------===// 61 62// Address operands 63def memsrc : Operand<i16> { 64 let PrintMethod = "printSrcMemOperand"; 65 let MIOperandInfo = (ops GR16, i16imm); 66} 67 68def memdst : Operand<i16> { 69 let PrintMethod = "printSrcMemOperand"; 70 let MIOperandInfo = (ops GR16, i16imm); 71} 72 73// Branch targets have OtherVT type. 74def brtarget : Operand<OtherVT> { 75 let PrintMethod = "printPCRelImmOperand"; 76} 77 78// Operand for printing out a condition code. 79def cc : Operand<i8> { 80 let PrintMethod = "printCCOperand"; 81} 82 83//===----------------------------------------------------------------------===// 84// MSP430 Complex Pattern Definitions. 85//===----------------------------------------------------------------------===// 86 87def addr : ComplexPattern<iPTR, 2, "SelectAddr", [], []>; 88 89//===----------------------------------------------------------------------===// 90// Pattern Fragments 91def zextloadi16i8 : PatFrag<(ops node:$ptr), (i16 (zextloadi8 node:$ptr))>; 92def extloadi16i8 : PatFrag<(ops node:$ptr), (i16 ( extloadi8 node:$ptr))>; 93 94//===----------------------------------------------------------------------===// 95// Instruction list.. 96 97// ADJCALLSTACKDOWN/UP implicitly use/def SP because they may be expanded into 98// a stack adjustment and the codegen must know that they may modify the stack 99// pointer before prolog-epilog rewriting occurs. 100// Pessimistically assume ADJCALLSTACKDOWN / ADJCALLSTACKUP will become 101// sub / add which can clobber SRW. 102let Defs = [SPW, SRW], Uses = [SPW] in { 103def ADJCALLSTACKDOWN : Pseudo<(outs), (ins i16imm:$amt), 104 "#ADJCALLSTACKDOWN", 105 [(MSP430callseq_start timm:$amt)]>; 106def ADJCALLSTACKUP : Pseudo<(outs), (ins i16imm:$amt1, i16imm:$amt2), 107 "#ADJCALLSTACKUP", 108 [(MSP430callseq_end timm:$amt1, timm:$amt2)]>; 109} 110 111let usesCustomInserter = 1 in { 112 def Select8 : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2, i8imm:$cc), 113 "# Select8 PSEUDO", 114 [(set GR8:$dst, 115 (MSP430selectcc GR8:$src1, GR8:$src2, imm:$cc))]>; 116 def Select16 : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2, i8imm:$cc), 117 "# Select16 PSEUDO", 118 [(set GR16:$dst, 119 (MSP430selectcc GR16:$src1, GR16:$src2, imm:$cc))]>; 120} 121 122let neverHasSideEffects = 1 in 123def NOP : Pseudo<(outs), (ins), "nop", []>; 124 125//===----------------------------------------------------------------------===// 126// Control Flow Instructions... 127// 128 129// FIXME: Provide proper encoding! 130let isReturn = 1, isTerminator = 1 in { 131 def RET : Pseudo<(outs), (ins), "ret", [(MSP430retflag)]>; 132} 133 134let isBranch = 1, isTerminator = 1 in { 135 136// Direct branch 137let isBarrier = 1 in 138 def JMP : Pseudo<(outs), (ins brtarget:$dst), 139 "jmp\t$dst", 140 [(br bb:$dst)]>; 141 142// Conditional branches 143let Uses = [SRW] in 144 def JCC : Pseudo<(outs), (ins brtarget:$dst, cc:$cc), 145 "j$cc $dst", 146 [(MSP430brcc bb:$dst, imm:$cc)]>; 147} // isBranch, isTerminator 148 149//===----------------------------------------------------------------------===// 150// Call Instructions... 151// 152let isCall = 1 in 153 // All calls clobber the non-callee saved registers. SPW is marked as 154 // a use to prevent stack-pointer assignments that appear immediately 155 // before calls from potentially appearing dead. Uses for argument 156 // registers are added manually. 157 let Defs = [R12W, R13W, R14W, R15W, SRW], 158 Uses = [SPW] in { 159 def CALLi : Pseudo<(outs), (ins i16imm:$dst, variable_ops), 160 "call\t$dst", [(MSP430call imm:$dst)]>; 161 def CALLr : Pseudo<(outs), (ins GR16:$dst, variable_ops), 162 "call\t$dst", [(MSP430call GR16:$dst)]>; 163 def CALLm : Pseudo<(outs), (ins memsrc:$dst, variable_ops), 164 "call\t${dst:mem}", [(MSP430call (load addr:$dst))]>; 165 } 166 167 168//===----------------------------------------------------------------------===// 169// Miscellaneous Instructions... 170// 171let Defs = [SPW], Uses = [SPW], neverHasSideEffects=1 in { 172let mayLoad = 1 in 173def POP16r : Pseudo<(outs GR16:$reg), (ins), "pop.w\t$reg", []>; 174 175let mayStore = 1 in 176def PUSH16r : Pseudo<(outs), (ins GR16:$reg), "push.w\t$reg",[]>; 177} 178 179//===----------------------------------------------------------------------===// 180// Move Instructions 181 182// FIXME: Provide proper encoding! 183let neverHasSideEffects = 1 in { 184def MOV8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src), 185 "mov.b\t{$src, $dst}", 186 []>; 187def MOV16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src), 188 "mov.w\t{$src, $dst}", 189 []>; 190} 191 192// FIXME: Provide proper encoding! 193let isReMaterializable = 1, isAsCheapAsAMove = 1 in { 194def MOV8ri : Pseudo<(outs GR8:$dst), (ins i8imm:$src), 195 "mov.b\t{$src, $dst}", 196 [(set GR8:$dst, imm:$src)]>; 197def MOV16ri : Pseudo<(outs GR16:$dst), (ins i16imm:$src), 198 "mov.w\t{$src, $dst}", 199 [(set GR16:$dst, imm:$src)]>; 200} 201 202let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in { 203def MOV8rm : Pseudo<(outs GR8:$dst), (ins memsrc:$src), 204 "mov.b\t{$src, $dst}", 205 [(set GR8:$dst, (load addr:$src))]>; 206def MOV16rm : Pseudo<(outs GR16:$dst), (ins memsrc:$src), 207 "mov.w\t{$src, $dst}", 208 [(set GR16:$dst, (load addr:$src))]>; 209} 210 211def MOVZX16rr8 : Pseudo<(outs GR16:$dst), (ins GR8:$src), 212 "mov.b\t{$src, $dst}", 213 [(set GR16:$dst, (zext GR8:$src))]>; 214def MOVZX16rm8 : Pseudo<(outs GR16:$dst), (ins memsrc:$src), 215 "mov.b\t{$src, $dst}", 216 [(set GR16:$dst, (zextloadi16i8 addr:$src))]>; 217 218let mayLoad = 1, hasExtraDefRegAllocReq = 1, Constraints = "$base = $base_wb" in { 219def MOV8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR16:$base), 220 "mov.b\t{@$base+, $dst}", []>; 221def MOV16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$base), 222 "mov.w\t{@$base+, $dst}", []>; 223} 224 225// Any instruction that defines a 8-bit result leaves the high half of the 226// register. Truncate can be lowered to EXTRACT_SUBREG, and CopyFromReg may 227// be copying from a truncate, but any other 8-bit operation will zero-extend 228// up to 16 bits. 229def def8 : PatLeaf<(i8 GR8:$src), [{ 230 return N->getOpcode() != ISD::TRUNCATE && 231 N->getOpcode() != TargetInstrInfo::EXTRACT_SUBREG && 232 N->getOpcode() != ISD::CopyFromReg; 233}]>; 234 235// In the case of a 8-bit def that is known to implicitly zero-extend, 236// we can use a SUBREG_TO_REG. 237def : Pat<(i16 (zext def8:$src)), 238 (SUBREG_TO_REG (i16 0), GR8:$src, subreg_8bit)>; 239 240 241def MOV8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 242 "mov.b\t{$src, $dst}", 243 [(store (i8 imm:$src), addr:$dst)]>; 244def MOV16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 245 "mov.w\t{$src, $dst}", 246 [(store (i16 imm:$src), addr:$dst)]>; 247 248def MOV8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 249 "mov.b\t{$src, $dst}", 250 [(store GR8:$src, addr:$dst)]>; 251def MOV16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 252 "mov.w\t{$src, $dst}", 253 [(store GR16:$src, addr:$dst)]>; 254 255def MOV8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 256 "mov.b\t{$src, $dst}", 257 [(store (i8 (load addr:$src)), addr:$dst)]>; 258def MOV16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 259 "mov.w\t{$src, $dst}", 260 [(store (i16 (load addr:$src)), addr:$dst)]>; 261 262//===----------------------------------------------------------------------===// 263// Arithmetic Instructions 264 265let isTwoAddress = 1 in { 266 267let Defs = [SRW] in { 268 269let isCommutable = 1 in { // X = ADD Y, Z == X = ADD Z, Y 270// FIXME: Provide proper encoding! 271def ADD8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 272 "add.b\t{$src2, $dst}", 273 [(set GR8:$dst, (add GR8:$src1, GR8:$src2)), 274 (implicit SRW)]>; 275def ADD16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 276 "add.w\t{$src2, $dst}", 277 [(set GR16:$dst, (add GR16:$src1, GR16:$src2)), 278 (implicit SRW)]>; 279} 280 281def ADD8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 282 "add.b\t{$src2, $dst}", 283 [(set GR8:$dst, (add GR8:$src1, (load addr:$src2))), 284 (implicit SRW)]>; 285def ADD16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 286 "add.w\t{$src2, $dst}", 287 [(set GR16:$dst, (add GR16:$src1, (load addr:$src2))), 288 (implicit SRW)]>; 289 290let mayLoad = 1, hasExtraDefRegAllocReq = 1, 291Constraints = "$base = $base_wb, $src1 = $dst" in { 292def ADD8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR8:$src1, GR16:$base), 293 "add.b\t{@$base+, $dst}", []>; 294def ADD16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$src1, GR16:$base), 295 "add.w\t{@$base+, $dst}", []>; 296} 297 298 299def ADD8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 300 "add.b\t{$src2, $dst}", 301 [(set GR8:$dst, (add GR8:$src1, imm:$src2)), 302 (implicit SRW)]>; 303def ADD16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 304 "add.w\t{$src2, $dst}", 305 [(set GR16:$dst, (add GR16:$src1, imm:$src2)), 306 (implicit SRW)]>; 307 308let isTwoAddress = 0 in { 309def ADD8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 310 "add.b\t{$src, $dst}", 311 [(store (add (load addr:$dst), GR8:$src), addr:$dst), 312 (implicit SRW)]>; 313def ADD16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 314 "add.w\t{$src, $dst}", 315 [(store (add (load addr:$dst), GR16:$src), addr:$dst), 316 (implicit SRW)]>; 317 318def ADD8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 319 "add.b\t{$src, $dst}", 320 [(store (add (load addr:$dst), (i8 imm:$src)), addr:$dst), 321 (implicit SRW)]>; 322def ADD16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 323 "add.w\t{$src, $dst}", 324 [(store (add (load addr:$dst), (i16 imm:$src)), addr:$dst), 325 (implicit SRW)]>; 326 327def ADD8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 328 "add.b\t{$src, $dst}", 329 [(store (add (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 330 (implicit SRW)]>; 331def ADD16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 332 "add.w\t{$src, $dst}", 333 [(store (add (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 334 (implicit SRW)]>; 335} 336 337let Uses = [SRW] in { 338 339let isCommutable = 1 in { // X = ADDC Y, Z == X = ADDC Z, Y 340def ADC8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 341 "addc.b\t{$src2, $dst}", 342 [(set GR8:$dst, (adde GR8:$src1, GR8:$src2)), 343 (implicit SRW)]>; 344def ADC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 345 "addc.w\t{$src2, $dst}", 346 [(set GR16:$dst, (adde GR16:$src1, GR16:$src2)), 347 (implicit SRW)]>; 348} // isCommutable 349 350def ADC8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 351 "addc.b\t{$src2, $dst}", 352 [(set GR8:$dst, (adde GR8:$src1, imm:$src2)), 353 (implicit SRW)]>; 354def ADC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 355 "addc.w\t{$src2, $dst}", 356 [(set GR16:$dst, (adde GR16:$src1, imm:$src2)), 357 (implicit SRW)]>; 358 359def ADC8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 360 "addc.b\t{$src2, $dst}", 361 [(set GR8:$dst, (adde GR8:$src1, (load addr:$src2))), 362 (implicit SRW)]>; 363def ADC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 364 "addc.w\t{$src2, $dst}", 365 [(set GR16:$dst, (adde GR16:$src1, (load addr:$src2))), 366 (implicit SRW)]>; 367 368let isTwoAddress = 0 in { 369def ADC8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 370 "addc.b\t{$src, $dst}", 371 [(store (adde (load addr:$dst), GR8:$src), addr:$dst), 372 (implicit SRW)]>; 373def ADC16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 374 "addc.w\t{$src, $dst}", 375 [(store (adde (load addr:$dst), GR16:$src), addr:$dst), 376 (implicit SRW)]>; 377 378def ADC8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 379 "addc.b\t{$src, $dst}", 380 [(store (adde (load addr:$dst), (i8 imm:$src)), addr:$dst), 381 (implicit SRW)]>; 382def ADC16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 383 "addc.w\t{$src, $dst}", 384 [(store (adde (load addr:$dst), (i16 imm:$src)), addr:$dst), 385 (implicit SRW)]>; 386 387def ADC8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 388 "addc.b\t{$src, $dst}", 389 [(store (adde (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 390 (implicit SRW)]>; 391def ADC16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 392 "addc.w\t{$src, $dst}", 393 [(store (adde (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 394 (implicit SRW)]>; 395} 396 397} // Uses = [SRW] 398 399let isCommutable = 1 in { // X = AND Y, Z == X = AND Z, Y 400def AND8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 401 "and.b\t{$src2, $dst}", 402 [(set GR8:$dst, (and GR8:$src1, GR8:$src2)), 403 (implicit SRW)]>; 404def AND16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 405 "and.w\t{$src2, $dst}", 406 [(set GR16:$dst, (and GR16:$src1, GR16:$src2)), 407 (implicit SRW)]>; 408} 409 410def AND8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 411 "and.b\t{$src2, $dst}", 412 [(set GR8:$dst, (and GR8:$src1, imm:$src2)), 413 (implicit SRW)]>; 414def AND16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 415 "and.w\t{$src2, $dst}", 416 [(set GR16:$dst, (and GR16:$src1, imm:$src2)), 417 (implicit SRW)]>; 418 419def AND8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 420 "and.b\t{$src2, $dst}", 421 [(set GR8:$dst, (and GR8:$src1, (load addr:$src2))), 422 (implicit SRW)]>; 423def AND16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 424 "and.w\t{$src2, $dst}", 425 [(set GR16:$dst, (and GR16:$src1, (load addr:$src2))), 426 (implicit SRW)]>; 427 428let mayLoad = 1, hasExtraDefRegAllocReq = 1, 429Constraints = "$base = $base_wb, $src1 = $dst" in { 430def AND8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR8:$src1, GR16:$base), 431 "and.b\t{@$base+, $dst}", []>; 432def AND16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$src1, GR16:$base), 433 "and.w\t{@$base+, $dst}", []>; 434} 435 436let isTwoAddress = 0 in { 437def AND8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 438 "and.b\t{$src, $dst}", 439 [(store (and (load addr:$dst), GR8:$src), addr:$dst), 440 (implicit SRW)]>; 441def AND16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 442 "and.w\t{$src, $dst}", 443 [(store (and (load addr:$dst), GR16:$src), addr:$dst), 444 (implicit SRW)]>; 445 446def AND8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 447 "and.b\t{$src, $dst}", 448 [(store (and (load addr:$dst), (i8 imm:$src)), addr:$dst), 449 (implicit SRW)]>; 450def AND16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 451 "and.w\t{$src, $dst}", 452 [(store (and (load addr:$dst), (i16 imm:$src)), addr:$dst), 453 (implicit SRW)]>; 454 455def AND8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 456 "and.b\t{$src, $dst}", 457 [(store (and (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 458 (implicit SRW)]>; 459def AND16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 460 "and.w\t{$src, $dst}", 461 [(store (and (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 462 (implicit SRW)]>; 463} 464 465 466let isCommutable = 1 in { // X = XOR Y, Z == X = XOR Z, Y 467def XOR8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 468 "xor.b\t{$src2, $dst}", 469 [(set GR8:$dst, (xor GR8:$src1, GR8:$src2)), 470 (implicit SRW)]>; 471def XOR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 472 "xor.w\t{$src2, $dst}", 473 [(set GR16:$dst, (xor GR16:$src1, GR16:$src2)), 474 (implicit SRW)]>; 475} 476 477def XOR8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 478 "xor.b\t{$src2, $dst}", 479 [(set GR8:$dst, (xor GR8:$src1, imm:$src2)), 480 (implicit SRW)]>; 481def XOR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 482 "xor.w\t{$src2, $dst}", 483 [(set GR16:$dst, (xor GR16:$src1, imm:$src2)), 484 (implicit SRW)]>; 485 486def XOR8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 487 "xor.b\t{$src2, $dst}", 488 [(set GR8:$dst, (xor GR8:$src1, (load addr:$src2))), 489 (implicit SRW)]>; 490def XOR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 491 "xor.w\t{$src2, $dst}", 492 [(set GR16:$dst, (xor GR16:$src1, (load addr:$src2))), 493 (implicit SRW)]>; 494 495let mayLoad = 1, hasExtraDefRegAllocReq = 1, 496Constraints = "$base = $base_wb, $src1 = $dst" in { 497def XOR8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR8:$src1, GR16:$base), 498 "xor.b\t{@$base+, $dst}", []>; 499def XOR16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$src1, GR16:$base), 500 "xor.w\t{@$base+, $dst}", []>; 501} 502 503let isTwoAddress = 0 in { 504def XOR8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 505 "xor.b\t{$src, $dst}", 506 [(store (xor (load addr:$dst), GR8:$src), addr:$dst), 507 (implicit SRW)]>; 508def XOR16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 509 "xor.w\t{$src, $dst}", 510 [(store (xor (load addr:$dst), GR16:$src), addr:$dst), 511 (implicit SRW)]>; 512 513def XOR8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 514 "xor.b\t{$src, $dst}", 515 [(store (xor (load addr:$dst), (i8 imm:$src)), addr:$dst), 516 (implicit SRW)]>; 517def XOR16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 518 "xor.w\t{$src, $dst}", 519 [(store (xor (load addr:$dst), (i16 imm:$src)), addr:$dst), 520 (implicit SRW)]>; 521 522def XOR8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 523 "xor.b\t{$src, $dst}", 524 [(store (xor (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 525 (implicit SRW)]>; 526def XOR16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 527 "xor.w\t{$src, $dst}", 528 [(store (xor (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 529 (implicit SRW)]>; 530} 531 532 533def SUB8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 534 "sub.b\t{$src2, $dst}", 535 [(set GR8:$dst, (sub GR8:$src1, GR8:$src2)), 536 (implicit SRW)]>; 537def SUB16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 538 "sub.w\t{$src2, $dst}", 539 [(set GR16:$dst, (sub GR16:$src1, GR16:$src2)), 540 (implicit SRW)]>; 541 542def SUB8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 543 "sub.b\t{$src2, $dst}", 544 [(set GR8:$dst, (sub GR8:$src1, imm:$src2)), 545 (implicit SRW)]>; 546def SUB16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 547 "sub.w\t{$src2, $dst}", 548 [(set GR16:$dst, (sub GR16:$src1, imm:$src2)), 549 (implicit SRW)]>; 550 551def SUB8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 552 "sub.b\t{$src2, $dst}", 553 [(set GR8:$dst, (sub GR8:$src1, (load addr:$src2))), 554 (implicit SRW)]>; 555def SUB16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 556 "sub.w\t{$src2, $dst}", 557 [(set GR16:$dst, (sub GR16:$src1, (load addr:$src2))), 558 (implicit SRW)]>; 559 560let mayLoad = 1, hasExtraDefRegAllocReq = 1, 561Constraints = "$base = $base_wb, $src1 = $dst" in { 562def SUB8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR8:$src1, GR16:$base), 563 "sub.b\t{@$base+, $dst}", []>; 564def SUB16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$src1, GR16:$base), 565 "sub.w\t{@$base+, $dst}", []>; 566} 567 568let isTwoAddress = 0 in { 569def SUB8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 570 "sub.b\t{$src, $dst}", 571 [(store (sub (load addr:$dst), GR8:$src), addr:$dst), 572 (implicit SRW)]>; 573def SUB16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 574 "sub.w\t{$src, $dst}", 575 [(store (sub (load addr:$dst), GR16:$src), addr:$dst), 576 (implicit SRW)]>; 577 578def SUB8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 579 "sub.b\t{$src, $dst}", 580 [(store (sub (load addr:$dst), (i8 imm:$src)), addr:$dst), 581 (implicit SRW)]>; 582def SUB16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 583 "sub.w\t{$src, $dst}", 584 [(store (sub (load addr:$dst), (i16 imm:$src)), addr:$dst), 585 (implicit SRW)]>; 586 587def SUB8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 588 "sub.b\t{$src, $dst}", 589 [(store (sub (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 590 (implicit SRW)]>; 591def SUB16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 592 "sub.w\t{$src, $dst}", 593 [(store (sub (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 594 (implicit SRW)]>; 595} 596 597let Uses = [SRW] in { 598def SBC8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 599 "subc.b\t{$src2, $dst}", 600 [(set GR8:$dst, (sube GR8:$src1, GR8:$src2)), 601 (implicit SRW)]>; 602def SBC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 603 "subc.w\t{$src2, $dst}", 604 [(set GR16:$dst, (sube GR16:$src1, GR16:$src2)), 605 (implicit SRW)]>; 606 607def SBC8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 608 "subc.b\t{$src2, $dst}", 609 [(set GR8:$dst, (sube GR8:$src1, imm:$src2)), 610 (implicit SRW)]>; 611def SBC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 612 "subc.w\t{$src2, $dst}", 613 [(set GR16:$dst, (sube GR16:$src1, imm:$src2)), 614 (implicit SRW)]>; 615 616def SBC8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 617 "subc.b\t{$src2, $dst}", 618 [(set GR8:$dst, (sube GR8:$src1, (load addr:$src2))), 619 (implicit SRW)]>; 620def SBC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 621 "subc.w\t{$src2, $dst}", 622 [(set GR16:$dst, (sube GR16:$src1, (load addr:$src2))), 623 (implicit SRW)]>; 624 625let isTwoAddress = 0 in { 626def SBC8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 627 "subc.b\t{$src, $dst}", 628 [(store (sube (load addr:$dst), GR8:$src), addr:$dst), 629 (implicit SRW)]>; 630def SBC16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 631 "subc.w\t{$src, $dst}", 632 [(store (sube (load addr:$dst), GR16:$src), addr:$dst), 633 (implicit SRW)]>; 634 635def SBC8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 636 "subc.b\t{$src, $dst}", 637 [(store (sube (load addr:$dst), (i8 imm:$src)), addr:$dst), 638 (implicit SRW)]>; 639def SBC16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 640 "subc.w\t{$src, $dst}", 641 [(store (sube (load addr:$dst), (i16 imm:$src)), addr:$dst), 642 (implicit SRW)]>; 643 644def SBC8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 645 "subc.b\t{$src, $dst}", 646 [(store (sube (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 647 (implicit SRW)]>; 648def SBC16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 649 "subc.w\t{$src, $dst}", 650 [(store (sube (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 651 (implicit SRW)]>; 652} 653 654} // Uses = [SRW] 655 656// FIXME: Provide proper encoding! 657def SAR8r1 : Pseudo<(outs GR8:$dst), (ins GR8:$src), 658 "rra.b\t$dst", 659 [(set GR8:$dst, (MSP430rra GR8:$src)), 660 (implicit SRW)]>; 661def SAR16r1 : Pseudo<(outs GR16:$dst), (ins GR16:$src), 662 "rra.w\t$dst", 663 [(set GR16:$dst, (MSP430rra GR16:$src)), 664 (implicit SRW)]>; 665 666def SHL8r1 : Pseudo<(outs GR8:$dst), (ins GR8:$src), 667 "rla.b\t$dst", 668 [(set GR8:$dst, (MSP430rla GR8:$src)), 669 (implicit SRW)]>; 670def SHL16r1 : Pseudo<(outs GR16:$dst), (ins GR16:$src), 671 "rla.w\t$dst", 672 [(set GR16:$dst, (MSP430rla GR16:$src)), 673 (implicit SRW)]>; 674 675def SAR8r1c : Pseudo<(outs GR8:$dst), (ins GR8:$src), 676 "clrc\n\t" 677 "rrc.b\t$dst", 678 [(set GR8:$dst, (MSP430rrc GR8:$src)), 679 (implicit SRW)]>; 680def SAR16r1c : Pseudo<(outs GR16:$dst), (ins GR16:$src), 681 "clrc\n\t" 682 "rrc.w\t$dst", 683 [(set GR16:$dst, (MSP430rrc GR16:$src)), 684 (implicit SRW)]>; 685 686def SEXT16r : Pseudo<(outs GR16:$dst), (ins GR16:$src), 687 "sxt\t$dst", 688 [(set GR16:$dst, (sext_inreg GR16:$src, i8)), 689 (implicit SRW)]>; 690 691} // Defs = [SRW] 692 693def SWPB16r : Pseudo<(outs GR16:$dst), (ins GR16:$src), 694 "swpb\t$dst", 695 [(set GR16:$dst, (bswap GR16:$src))]>; 696 697let isCommutable = 1 in { // X = OR Y, Z == X = OR Z, Y 698def OR8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 699 "bis.b\t{$src2, $dst}", 700 [(set GR8:$dst, (or GR8:$src1, GR8:$src2))]>; 701def OR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 702 "bis.w\t{$src2, $dst}", 703 [(set GR16:$dst, (or GR16:$src1, GR16:$src2))]>; 704} 705 706def OR8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 707 "bis.b\t{$src2, $dst}", 708 [(set GR8:$dst, (or GR8:$src1, imm:$src2))]>; 709def OR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 710 "bis.w\t{$src2, $dst}", 711 [(set GR16:$dst, (or GR16:$src1, imm:$src2))]>; 712 713def OR8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 714 "bis.b\t{$src2, $dst}", 715 [(set GR8:$dst, (or GR8:$src1, (load addr:$src2)))]>; 716def OR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 717 "bis.w\t{$src2, $dst}", 718 [(set GR16:$dst, (or GR16:$src1, (load addr:$src2)))]>; 719 720let mayLoad = 1, hasExtraDefRegAllocReq = 1, 721Constraints = "$base = $base_wb, $src1 = $dst" in { 722def OR8rm_POST : Pseudo<(outs GR8:$dst, GR16:$base_wb), (ins GR8:$src1, GR16:$base), 723 "bis.b\t{@$base+, $dst}", []>; 724def OR16rm_POST : Pseudo<(outs GR16:$dst, GR16:$base_wb), (ins GR16:$src1, GR16:$base), 725 "bis.w\t{@$base+, $dst}", []>; 726} 727 728let isTwoAddress = 0 in { 729def OR8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 730 "bis.b\t{$src, $dst}", 731 [(store (or (load addr:$dst), GR8:$src), addr:$dst)]>; 732def OR16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 733 "bis.w\t{$src, $dst}", 734 [(store (or (load addr:$dst), GR16:$src), addr:$dst)]>; 735 736def OR8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 737 "bis.b\t{$src, $dst}", 738 [(store (or (load addr:$dst), (i8 imm:$src)), addr:$dst)]>; 739def OR16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 740 "bis.w\t{$src, $dst}", 741 [(store (or (load addr:$dst), (i16 imm:$src)), addr:$dst)]>; 742 743def OR8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 744 "bis.b\t{$src, $dst}", 745 [(store (or (i8 (load addr:$dst)), 746 (i8 (load addr:$src))), addr:$dst)]>; 747def OR16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 748 "bis.w\t{$src, $dst}", 749 [(store (or (i16 (load addr:$dst)), 750 (i16 (load addr:$src))), addr:$dst)]>; 751} 752 753} // isTwoAddress = 1 754 755// Integer comparisons 756let Defs = [SRW] in { 757def CMP8rr : Pseudo<(outs), (ins GR8:$src1, GR8:$src2), 758 "cmp.b\t{$src1, $src2}", 759 [(MSP430cmp GR8:$src1, GR8:$src2), (implicit SRW)]>; 760def CMP16rr : Pseudo<(outs), (ins GR16:$src1, GR16:$src2), 761 "cmp.w\t{$src1, $src2}", 762 [(MSP430cmp GR16:$src1, GR16:$src2), (implicit SRW)]>; 763 764def CMP8ir : Pseudo<(outs), (ins i8imm:$src1, GR8:$src2), 765 "cmp.b\t{$src1, $src2}", 766 [(MSP430cmp imm:$src1, GR8:$src2), (implicit SRW)]>; 767def CMP16ir : Pseudo<(outs), (ins i16imm:$src1, GR16:$src2), 768 "cmp.w\t{$src1, $src2}", 769 [(MSP430cmp imm:$src1, GR16:$src2), (implicit SRW)]>; 770 771def CMP8im : Pseudo<(outs), (ins i8imm:$src1, memsrc:$src2), 772 "cmp.b\t{$src1, $src2}", 773 [(MSP430cmp (i8 imm:$src1), (load addr:$src2)), (implicit SRW)]>; 774def CMP16im : Pseudo<(outs), (ins i16imm:$src1, memsrc:$src2), 775 "cmp.w\t{$src1, $src2}", 776 [(MSP430cmp (i16 imm:$src1), (load addr:$src2)), (implicit SRW)]>; 777 778def CMP8rm : Pseudo<(outs), (ins GR8:$src1, memsrc:$src2), 779 "cmp.b\t{$src1, $src2}", 780 [(MSP430cmp GR8:$src1, (load addr:$src2)), (implicit SRW)]>; 781def CMP16rm : Pseudo<(outs), (ins GR16:$src1, memsrc:$src2), 782 "cmp.w\t{$src1, $src2}", 783 [(MSP430cmp GR16:$src1, (load addr:$src2)), (implicit SRW)]>; 784 785def CMP8mr : Pseudo<(outs), (ins memsrc:$src1, GR8:$src2), 786 "cmp.b\t{$src1, $src2}", 787 [(MSP430cmp (load addr:$src1), GR8:$src2), (implicit SRW)]>; 788def CMP16mr : Pseudo<(outs), (ins memsrc:$src1, GR16:$src2), 789 "cmp.w\t{$src1, $src2}", 790 [(MSP430cmp (load addr:$src1), GR16:$src2), (implicit SRW)]>; 791 792def CMP8mi0 : Pseudo<(outs), (ins memsrc:$src1), 793 "cmp.b\t{$src1, #0}", 794 [(MSP430cmp (load addr:$src1), (i8 0)), (implicit SRW)]>; 795def CMP16mi0: Pseudo<(outs), (ins memsrc:$src1), 796 "cmp.w\t{$src1, #0}", 797 [(MSP430cmp (load addr:$src1), (i16 0)), (implicit SRW)]>; 798def CMP8mi1 : Pseudo<(outs), (ins memsrc:$src1), 799 "cmp.b\t{$src1, #1}", 800 [(MSP430cmp (load addr:$src1), (i8 1)), (implicit SRW)]>; 801def CMP16mi1: Pseudo<(outs), (ins memsrc:$src1), 802 "cmp.w\t{$src1, #1}", 803 [(MSP430cmp (load addr:$src1), (i16 1)), (implicit SRW)]>; 804def CMP8mi2 : Pseudo<(outs), (ins memsrc:$src1), 805 "cmp.b\t{$src1, #2}", 806 [(MSP430cmp (load addr:$src1), (i8 2)), (implicit SRW)]>; 807def CMP16mi2: Pseudo<(outs), (ins memsrc:$src1), 808 "cmp.w\t{$src1, #2}", 809 [(MSP430cmp (load addr:$src1), (i16 2)), (implicit SRW)]>; 810def CMP8mi4 : Pseudo<(outs), (ins memsrc:$src1), 811 "cmp.b\t{$src1, #4}", 812 [(MSP430cmp (load addr:$src1), (i8 4)), (implicit SRW)]>; 813def CMP16mi4: Pseudo<(outs), (ins memsrc:$src1), 814 "cmp.w\t{$src1, #4}", 815 [(MSP430cmp (load addr:$src1), (i16 4)), (implicit SRW)]>; 816def CMP8mi8 : Pseudo<(outs), (ins memsrc:$src1), 817 "cmp.b\t{$src1, #8}", 818 [(MSP430cmp (load addr:$src1), (i8 8)), (implicit SRW)]>; 819def CMP16mi8: Pseudo<(outs), (ins memsrc:$src1), 820 "cmp.w\t{$src1, #8}", 821 [(MSP430cmp (load addr:$src1), (i16 8)), (implicit SRW)]>; 822 823} // Defs = [SRW] 824 825//===----------------------------------------------------------------------===// 826// Non-Instruction Patterns 827 828// extload 829def : Pat<(extloadi16i8 addr:$src), (MOVZX16rm8 addr:$src)>; 830 831// anyext 832def : Pat<(anyext addr:$src), (MOVZX16rr8 GR8:$src)>; 833 834// truncs 835def : Pat<(i8 (trunc GR16:$src)), 836 (EXTRACT_SUBREG GR16:$src, subreg_8bit)>; 837 838// GlobalAddress, ExternalSymbol 839def : Pat<(i16 (MSP430Wrapper tglobaladdr:$dst)), (MOV16ri tglobaladdr:$dst)>; 840def : Pat<(i16 (MSP430Wrapper texternalsym:$dst)), (MOV16ri texternalsym:$dst)>; 841 842def : Pat<(add GR16:$src1, (MSP430Wrapper tglobaladdr :$src2)), 843 (ADD16ri GR16:$src1, tglobaladdr:$src2)>; 844def : Pat<(add GR16:$src1, (MSP430Wrapper texternalsym:$src2)), 845 (ADD16ri GR16:$src1, texternalsym:$src2)>; 846 847def : Pat<(store (i16 (MSP430Wrapper tglobaladdr:$src)), addr:$dst), 848 (MOV16mi addr:$dst, tglobaladdr:$src)>; 849def : Pat<(store (i16 (MSP430Wrapper texternalsym:$src)), addr:$dst), 850 (MOV16mi addr:$dst, texternalsym:$src)>; 851 852// calls 853def : Pat<(MSP430call (i16 tglobaladdr:$dst)), 854 (CALLi tglobaladdr:$dst)>; 855def : Pat<(MSP430call (i16 texternalsym:$dst)), 856 (CALLi texternalsym:$dst)>; 857 858// add and sub always produce carry 859def : Pat<(addc GR16:$src1, GR16:$src2), 860 (ADD16rr GR16:$src1, GR16:$src2)>; 861def : Pat<(addc GR16:$src1, (load addr:$src2)), 862 (ADD16rm GR16:$src1, addr:$src2)>; 863def : Pat<(addc GR16:$src1, imm:$src2), 864 (ADD16ri GR16:$src1, imm:$src2)>; 865def : Pat<(store (addc (load addr:$dst), GR16:$src), addr:$dst), 866 (ADD16mr addr:$dst, GR16:$src)>; 867def : Pat<(store (addc (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 868 (ADD16mm addr:$dst, addr:$src)>; 869 870def : Pat<(addc GR8:$src1, GR8:$src2), 871 (ADD8rr GR8:$src1, GR8:$src2)>; 872def : Pat<(addc GR8:$src1, (load addr:$src2)), 873 (ADD8rm GR8:$src1, addr:$src2)>; 874def : Pat<(addc GR8:$src1, imm:$src2), 875 (ADD8ri GR8:$src1, imm:$src2)>; 876def : Pat<(store (addc (load addr:$dst), GR8:$src), addr:$dst), 877 (ADD8mr addr:$dst, GR8:$src)>; 878def : Pat<(store (addc (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 879 (ADD8mm addr:$dst, addr:$src)>; 880 881def : Pat<(subc GR16:$src1, GR16:$src2), 882 (SUB16rr GR16:$src1, GR16:$src2)>; 883def : Pat<(subc GR16:$src1, (load addr:$src2)), 884 (SUB16rm GR16:$src1, addr:$src2)>; 885def : Pat<(subc GR16:$src1, imm:$src2), 886 (SUB16ri GR16:$src1, imm:$src2)>; 887def : Pat<(store (subc (load addr:$dst), GR16:$src), addr:$dst), 888 (SUB16mr addr:$dst, GR16:$src)>; 889def : Pat<(store (subc (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 890 (SUB16mm addr:$dst, addr:$src)>; 891 892def : Pat<(subc GR8:$src1, GR8:$src2), 893 (SUB8rr GR8:$src1, GR8:$src2)>; 894def : Pat<(subc GR8:$src1, (load addr:$src2)), 895 (SUB8rm GR8:$src1, addr:$src2)>; 896def : Pat<(subc GR8:$src1, imm:$src2), 897 (SUB8ri GR8:$src1, imm:$src2)>; 898def : Pat<(store (subc (load addr:$dst), GR8:$src), addr:$dst), 899 (SUB8mr addr:$dst, GR8:$src)>; 900def : Pat<(store (subc (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 901 (SUB8mm addr:$dst, addr:$src)>; 902