MSP430InstrInfo.td revision 198892
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 218// Any instruction that defines a 8-bit result leaves the high half of the 219// register. Truncate can be lowered to EXTRACT_SUBREG, and CopyFromReg may 220// be copying from a truncate, but any other 8-bit operation will zero-extend 221// up to 16 bits. 222def def8 : PatLeaf<(i8 GR8:$src), [{ 223 return N->getOpcode() != ISD::TRUNCATE && 224 N->getOpcode() != TargetInstrInfo::EXTRACT_SUBREG && 225 N->getOpcode() != ISD::CopyFromReg; 226}]>; 227 228// In the case of a 8-bit def that is known to implicitly zero-extend, 229// we can use a SUBREG_TO_REG. 230def : Pat<(i16 (zext def8:$src)), 231 (SUBREG_TO_REG (i16 0), GR8:$src, subreg_8bit)>; 232 233 234def MOV8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 235 "mov.b\t{$src, $dst}", 236 [(store (i8 imm:$src), addr:$dst)]>; 237def MOV16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 238 "mov.w\t{$src, $dst}", 239 [(store (i16 imm:$src), addr:$dst)]>; 240 241def MOV8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 242 "mov.b\t{$src, $dst}", 243 [(store GR8:$src, addr:$dst)]>; 244def MOV16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 245 "mov.w\t{$src, $dst}", 246 [(store GR16:$src, addr:$dst)]>; 247 248def MOV8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 249 "mov.b\t{$src, $dst}", 250 [(store (i8 (load addr:$src)), addr:$dst)]>; 251def MOV16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 252 "mov.w\t{$src, $dst}", 253 [(store (i16 (load addr:$src)), addr:$dst)]>; 254 255//===----------------------------------------------------------------------===// 256// Arithmetic Instructions 257 258let isTwoAddress = 1 in { 259 260let Defs = [SRW] in { 261 262let isCommutable = 1 in { // X = ADD Y, Z == X = ADD Z, Y 263// FIXME: Provide proper encoding! 264def ADD8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 265 "add.b\t{$src2, $dst}", 266 [(set GR8:$dst, (add GR8:$src1, GR8:$src2)), 267 (implicit SRW)]>; 268def ADD16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 269 "add.w\t{$src2, $dst}", 270 [(set GR16:$dst, (add GR16:$src1, GR16:$src2)), 271 (implicit SRW)]>; 272} 273 274def ADD8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 275 "add.b\t{$src2, $dst}", 276 [(set GR8:$dst, (add GR8:$src1, (load addr:$src2))), 277 (implicit SRW)]>; 278def ADD16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 279 "add.w\t{$src2, $dst}", 280 [(set GR16:$dst, (add GR16:$src1, (load addr:$src2))), 281 (implicit SRW)]>; 282 283def ADD8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 284 "add.b\t{$src2, $dst}", 285 [(set GR8:$dst, (add GR8:$src1, imm:$src2)), 286 (implicit SRW)]>; 287def ADD16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 288 "add.w\t{$src2, $dst}", 289 [(set GR16:$dst, (add GR16:$src1, imm:$src2)), 290 (implicit SRW)]>; 291 292let isTwoAddress = 0 in { 293def ADD8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 294 "add.b\t{$src, $dst}", 295 [(store (add (load addr:$dst), GR8:$src), addr:$dst), 296 (implicit SRW)]>; 297def ADD16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 298 "add.w\t{$src, $dst}", 299 [(store (add (load addr:$dst), GR16:$src), addr:$dst), 300 (implicit SRW)]>; 301 302def ADD8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 303 "add.b\t{$src, $dst}", 304 [(store (add (load addr:$dst), (i8 imm:$src)), addr:$dst), 305 (implicit SRW)]>; 306def ADD16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 307 "add.w\t{$src, $dst}", 308 [(store (add (load addr:$dst), (i16 imm:$src)), addr:$dst), 309 (implicit SRW)]>; 310 311def ADD8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 312 "add.b\t{$src, $dst}", 313 [(store (add (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 314 (implicit SRW)]>; 315def ADD16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 316 "add.w\t{$src, $dst}", 317 [(store (add (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 318 (implicit SRW)]>; 319} 320 321let Uses = [SRW] in { 322 323let isCommutable = 1 in { // X = ADDC Y, Z == X = ADDC Z, Y 324def ADC8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 325 "addc.b\t{$src2, $dst}", 326 [(set GR8:$dst, (adde GR8:$src1, GR8:$src2)), 327 (implicit SRW)]>; 328def ADC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 329 "addc.w\t{$src2, $dst}", 330 [(set GR16:$dst, (adde GR16:$src1, GR16:$src2)), 331 (implicit SRW)]>; 332} // isCommutable 333 334def ADC8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 335 "addc.b\t{$src2, $dst}", 336 [(set GR8:$dst, (adde GR8:$src1, imm:$src2)), 337 (implicit SRW)]>; 338def ADC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 339 "addc.w\t{$src2, $dst}", 340 [(set GR16:$dst, (adde GR16:$src1, imm:$src2)), 341 (implicit SRW)]>; 342 343def ADC8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 344 "addc.b\t{$src2, $dst}", 345 [(set GR8:$dst, (adde GR8:$src1, (load addr:$src2))), 346 (implicit SRW)]>; 347def ADC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 348 "addc.w\t{$src2, $dst}", 349 [(set GR16:$dst, (adde GR16:$src1, (load addr:$src2))), 350 (implicit SRW)]>; 351 352let isTwoAddress = 0 in { 353def ADC8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 354 "addc.b\t{$src, $dst}", 355 [(store (adde (load addr:$dst), GR8:$src), addr:$dst), 356 (implicit SRW)]>; 357def ADC16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 358 "addc.w\t{$src, $dst}", 359 [(store (adde (load addr:$dst), GR16:$src), addr:$dst), 360 (implicit SRW)]>; 361 362def ADC8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 363 "addc.b\t{$src, $dst}", 364 [(store (adde (load addr:$dst), (i8 imm:$src)), addr:$dst), 365 (implicit SRW)]>; 366def ADC16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 367 "addc.w\t{$src, $dst}", 368 [(store (adde (load addr:$dst), (i16 imm:$src)), addr:$dst), 369 (implicit SRW)]>; 370 371def ADC8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 372 "addc.b\t{$src, $dst}", 373 [(store (adde (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 374 (implicit SRW)]>; 375def ADC16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 376 "addc.w\t{$src, $dst}", 377 [(store (adde (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 378 (implicit SRW)]>; 379} 380 381} // Uses = [SRW] 382 383let isCommutable = 1 in { // X = AND Y, Z == X = AND Z, Y 384def AND8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 385 "and.b\t{$src2, $dst}", 386 [(set GR8:$dst, (and GR8:$src1, GR8:$src2)), 387 (implicit SRW)]>; 388def AND16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 389 "and.w\t{$src2, $dst}", 390 [(set GR16:$dst, (and GR16:$src1, GR16:$src2)), 391 (implicit SRW)]>; 392} 393 394def AND8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 395 "and.b\t{$src2, $dst}", 396 [(set GR8:$dst, (and GR8:$src1, imm:$src2)), 397 (implicit SRW)]>; 398def AND16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 399 "and.w\t{$src2, $dst}", 400 [(set GR16:$dst, (and GR16:$src1, imm:$src2)), 401 (implicit SRW)]>; 402 403def AND8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 404 "and.b\t{$src2, $dst}", 405 [(set GR8:$dst, (and GR8:$src1, (load addr:$src2))), 406 (implicit SRW)]>; 407def AND16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 408 "and.w\t{$src2, $dst}", 409 [(set GR16:$dst, (and GR16:$src1, (load addr:$src2))), 410 (implicit SRW)]>; 411 412let isTwoAddress = 0 in { 413def AND8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 414 "and.b\t{$src, $dst}", 415 [(store (and (load addr:$dst), GR8:$src), addr:$dst), 416 (implicit SRW)]>; 417def AND16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 418 "and.w\t{$src, $dst}", 419 [(store (and (load addr:$dst), GR16:$src), addr:$dst), 420 (implicit SRW)]>; 421 422def AND8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 423 "and.b\t{$src, $dst}", 424 [(store (and (load addr:$dst), (i8 imm:$src)), addr:$dst), 425 (implicit SRW)]>; 426def AND16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 427 "and.w\t{$src, $dst}", 428 [(store (and (load addr:$dst), (i16 imm:$src)), addr:$dst), 429 (implicit SRW)]>; 430 431def AND8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 432 "and.b\t{$src, $dst}", 433 [(store (and (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 434 (implicit SRW)]>; 435def AND16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 436 "and.w\t{$src, $dst}", 437 [(store (and (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 438 (implicit SRW)]>; 439} 440 441 442let isCommutable = 1 in { // X = XOR Y, Z == X = XOR Z, Y 443def XOR8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 444 "xor.b\t{$src2, $dst}", 445 [(set GR8:$dst, (xor GR8:$src1, GR8:$src2)), 446 (implicit SRW)]>; 447def XOR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 448 "xor.w\t{$src2, $dst}", 449 [(set GR16:$dst, (xor GR16:$src1, GR16:$src2)), 450 (implicit SRW)]>; 451} 452 453def XOR8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 454 "xor.b\t{$src2, $dst}", 455 [(set GR8:$dst, (xor GR8:$src1, imm:$src2)), 456 (implicit SRW)]>; 457def XOR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 458 "xor.w\t{$src2, $dst}", 459 [(set GR16:$dst, (xor GR16:$src1, imm:$src2)), 460 (implicit SRW)]>; 461 462def XOR8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 463 "xor.b\t{$src2, $dst}", 464 [(set GR8:$dst, (xor GR8:$src1, (load addr:$src2))), 465 (implicit SRW)]>; 466def XOR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 467 "xor.w\t{$src2, $dst}", 468 [(set GR16:$dst, (xor GR16:$src1, (load addr:$src2))), 469 (implicit SRW)]>; 470 471let isTwoAddress = 0 in { 472def XOR8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 473 "xor.b\t{$src, $dst}", 474 [(store (xor (load addr:$dst), GR8:$src), addr:$dst), 475 (implicit SRW)]>; 476def XOR16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 477 "xor.w\t{$src, $dst}", 478 [(store (xor (load addr:$dst), GR16:$src), addr:$dst), 479 (implicit SRW)]>; 480 481def XOR8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 482 "xor.b\t{$src, $dst}", 483 [(store (xor (load addr:$dst), (i8 imm:$src)), addr:$dst), 484 (implicit SRW)]>; 485def XOR16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 486 "xor.w\t{$src, $dst}", 487 [(store (xor (load addr:$dst), (i16 imm:$src)), addr:$dst), 488 (implicit SRW)]>; 489 490def XOR8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 491 "xor.b\t{$src, $dst}", 492 [(store (xor (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 493 (implicit SRW)]>; 494def XOR16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 495 "xor.w\t{$src, $dst}", 496 [(store (xor (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 497 (implicit SRW)]>; 498} 499 500 501def SUB8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 502 "sub.b\t{$src2, $dst}", 503 [(set GR8:$dst, (sub GR8:$src1, GR8:$src2)), 504 (implicit SRW)]>; 505def SUB16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 506 "sub.w\t{$src2, $dst}", 507 [(set GR16:$dst, (sub GR16:$src1, GR16:$src2)), 508 (implicit SRW)]>; 509 510def SUB8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 511 "sub.b\t{$src2, $dst}", 512 [(set GR8:$dst, (sub GR8:$src1, imm:$src2)), 513 (implicit SRW)]>; 514def SUB16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 515 "sub.w\t{$src2, $dst}", 516 [(set GR16:$dst, (sub GR16:$src1, imm:$src2)), 517 (implicit SRW)]>; 518 519def SUB8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 520 "sub.b\t{$src2, $dst}", 521 [(set GR8:$dst, (sub GR8:$src1, (load addr:$src2))), 522 (implicit SRW)]>; 523def SUB16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 524 "sub.w\t{$src2, $dst}", 525 [(set GR16:$dst, (sub GR16:$src1, (load addr:$src2))), 526 (implicit SRW)]>; 527 528let isTwoAddress = 0 in { 529def SUB8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 530 "sub.b\t{$src, $dst}", 531 [(store (sub (load addr:$dst), GR8:$src), addr:$dst), 532 (implicit SRW)]>; 533def SUB16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 534 "sub.w\t{$src, $dst}", 535 [(store (sub (load addr:$dst), GR16:$src), addr:$dst), 536 (implicit SRW)]>; 537 538def SUB8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 539 "sub.b\t{$src, $dst}", 540 [(store (sub (load addr:$dst), (i8 imm:$src)), addr:$dst), 541 (implicit SRW)]>; 542def SUB16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 543 "sub.w\t{$src, $dst}", 544 [(store (sub (load addr:$dst), (i16 imm:$src)), addr:$dst), 545 (implicit SRW)]>; 546 547def SUB8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 548 "sub.b\t{$src, $dst}", 549 [(store (sub (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 550 (implicit SRW)]>; 551def SUB16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 552 "sub.w\t{$src, $dst}", 553 [(store (sub (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 554 (implicit SRW)]>; 555} 556 557let Uses = [SRW] in { 558def SBC8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 559 "subc.b\t{$src2, $dst}", 560 [(set GR8:$dst, (sube GR8:$src1, GR8:$src2)), 561 (implicit SRW)]>; 562def SBC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 563 "subc.w\t{$src2, $dst}", 564 [(set GR16:$dst, (sube GR16:$src1, GR16:$src2)), 565 (implicit SRW)]>; 566 567def SBC8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 568 "subc.b\t{$src2, $dst}", 569 [(set GR8:$dst, (sube GR8:$src1, imm:$src2)), 570 (implicit SRW)]>; 571def SBC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 572 "subc.w\t{$src2, $dst}", 573 [(set GR16:$dst, (sube GR16:$src1, imm:$src2)), 574 (implicit SRW)]>; 575 576def SBC8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 577 "subc.b\t{$src2, $dst}", 578 [(set GR8:$dst, (sube GR8:$src1, (load addr:$src2))), 579 (implicit SRW)]>; 580def SBC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 581 "subc.w\t{$src2, $dst}", 582 [(set GR16:$dst, (sube GR16:$src1, (load addr:$src2))), 583 (implicit SRW)]>; 584 585let isTwoAddress = 0 in { 586def SBC8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 587 "subc.b\t{$src, $dst}", 588 [(store (sube (load addr:$dst), GR8:$src), addr:$dst), 589 (implicit SRW)]>; 590def SBC16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 591 "subc.w\t{$src, $dst}", 592 [(store (sube (load addr:$dst), GR16:$src), addr:$dst), 593 (implicit SRW)]>; 594 595def SBC8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 596 "subc.b\t{$src, $dst}", 597 [(store (sube (load addr:$dst), (i8 imm:$src)), addr:$dst), 598 (implicit SRW)]>; 599def SBC16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 600 "subc.w\t{$src, $dst}", 601 [(store (sube (load addr:$dst), (i16 imm:$src)), addr:$dst), 602 (implicit SRW)]>; 603 604def SBC8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 605 "subc.b\t{$src, $dst}", 606 [(store (sube (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 607 (implicit SRW)]>; 608def SBC16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 609 "subc.w\t{$src, $dst}", 610 [(store (sube (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 611 (implicit SRW)]>; 612} 613 614} // Uses = [SRW] 615 616// FIXME: Provide proper encoding! 617def SAR8r1 : Pseudo<(outs GR8:$dst), (ins GR8:$src), 618 "rra.b\t$dst", 619 [(set GR8:$dst, (MSP430rra GR8:$src)), 620 (implicit SRW)]>; 621def SAR16r1 : Pseudo<(outs GR16:$dst), (ins GR16:$src), 622 "rra.w\t$dst", 623 [(set GR16:$dst, (MSP430rra GR16:$src)), 624 (implicit SRW)]>; 625 626def SHL8r1 : Pseudo<(outs GR8:$dst), (ins GR8:$src), 627 "rla.b\t$dst", 628 [(set GR8:$dst, (MSP430rla GR8:$src)), 629 (implicit SRW)]>; 630def SHL16r1 : Pseudo<(outs GR16:$dst), (ins GR16:$src), 631 "rla.w\t$dst", 632 [(set GR16:$dst, (MSP430rla GR16:$src)), 633 (implicit SRW)]>; 634 635def SAR8r1c : Pseudo<(outs GR8:$dst), (ins GR8:$src), 636 "clrc\n\t" 637 "rrc.b\t$dst", 638 [(set GR8:$dst, (MSP430rrc GR8:$src)), 639 (implicit SRW)]>; 640def SAR16r1c : Pseudo<(outs GR16:$dst), (ins GR16:$src), 641 "clrc\n\t" 642 "rrc.w\t$dst", 643 [(set GR16:$dst, (MSP430rrc GR16:$src)), 644 (implicit SRW)]>; 645 646def SEXT16r : Pseudo<(outs GR16:$dst), (ins GR16:$src), 647 "sxt\t$dst", 648 [(set GR16:$dst, (sext_inreg GR16:$src, i8)), 649 (implicit SRW)]>; 650 651} // Defs = [SRW] 652 653def SWPB16r : Pseudo<(outs GR16:$dst), (ins GR16:$src), 654 "swpb\t$dst", 655 [(set GR16:$dst, (bswap GR16:$src))]>; 656 657let isCommutable = 1 in { // X = OR Y, Z == X = OR Z, Y 658def OR8rr : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2), 659 "bis.b\t{$src2, $dst}", 660 [(set GR8:$dst, (or GR8:$src1, GR8:$src2))]>; 661def OR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2), 662 "bis.w\t{$src2, $dst}", 663 [(set GR16:$dst, (or GR16:$src1, GR16:$src2))]>; 664} 665 666def OR8ri : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2), 667 "bis.b\t{$src2, $dst}", 668 [(set GR8:$dst, (or GR8:$src1, imm:$src2))]>; 669def OR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2), 670 "bis.w\t{$src2, $dst}", 671 [(set GR16:$dst, (or GR16:$src1, imm:$src2))]>; 672 673def OR8rm : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2), 674 "bis.b\t{$src2, $dst}", 675 [(set GR8:$dst, (or GR8:$src1, (load addr:$src2)))]>; 676def OR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2), 677 "bis.w\t{$src2, $dst}", 678 [(set GR16:$dst, (or GR16:$src1, (load addr:$src2)))]>; 679 680let isTwoAddress = 0 in { 681def OR8mr : Pseudo<(outs), (ins memdst:$dst, GR8:$src), 682 "bis.b\t{$src, $dst}", 683 [(store (or (load addr:$dst), GR8:$src), addr:$dst)]>; 684def OR16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src), 685 "bis.w\t{$src, $dst}", 686 [(store (or (load addr:$dst), GR16:$src), addr:$dst)]>; 687 688def OR8mi : Pseudo<(outs), (ins memdst:$dst, i8imm:$src), 689 "bis.b\t{$src, $dst}", 690 [(store (or (load addr:$dst), (i8 imm:$src)), addr:$dst)]>; 691def OR16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src), 692 "bis.w\t{$src, $dst}", 693 [(store (or (load addr:$dst), (i16 imm:$src)), addr:$dst)]>; 694 695def OR8mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 696 "bis.b\t{$src, $dst}", 697 [(store (or (i8 (load addr:$dst)), 698 (i8 (load addr:$src))), addr:$dst)]>; 699def OR16mm : Pseudo<(outs), (ins memdst:$dst, memsrc:$src), 700 "bis.w\t{$src, $dst}", 701 [(store (or (i16 (load addr:$dst)), 702 (i16 (load addr:$src))), addr:$dst)]>; 703} 704 705} // isTwoAddress = 1 706 707// Integer comparisons 708let Defs = [SRW] in { 709def CMP8rr : Pseudo<(outs), (ins GR8:$src1, GR8:$src2), 710 "cmp.b\t{$src1, $src2}", 711 [(MSP430cmp GR8:$src1, GR8:$src2), (implicit SRW)]>; 712def CMP16rr : Pseudo<(outs), (ins GR16:$src1, GR16:$src2), 713 "cmp.w\t{$src1, $src2}", 714 [(MSP430cmp GR16:$src1, GR16:$src2), (implicit SRW)]>; 715 716def CMP8ir : Pseudo<(outs), (ins i8imm:$src1, GR8:$src2), 717 "cmp.b\t{$src1, $src2}", 718 [(MSP430cmp imm:$src1, GR8:$src2), (implicit SRW)]>; 719def CMP16ir : Pseudo<(outs), (ins i16imm:$src1, GR16:$src2), 720 "cmp.w\t{$src1, $src2}", 721 [(MSP430cmp imm:$src1, GR16:$src2), (implicit SRW)]>; 722 723def CMP8im : Pseudo<(outs), (ins i8imm:$src1, memsrc:$src2), 724 "cmp.b\t{$src1, $src2}", 725 [(MSP430cmp (i8 imm:$src1), (load addr:$src2)), (implicit SRW)]>; 726def CMP16im : Pseudo<(outs), (ins i16imm:$src1, memsrc:$src2), 727 "cmp.w\t{$src1, $src2}", 728 [(MSP430cmp (i16 imm:$src1), (load addr:$src2)), (implicit SRW)]>; 729 730def CMP8rm : Pseudo<(outs), (ins GR8:$src1, memsrc:$src2), 731 "cmp.b\t{$src1, $src2}", 732 [(MSP430cmp GR8:$src1, (load addr:$src2)), (implicit SRW)]>; 733def CMP16rm : Pseudo<(outs), (ins GR16:$src1, memsrc:$src2), 734 "cmp.w\t{$src1, $src2}", 735 [(MSP430cmp GR16:$src1, (load addr:$src2)), (implicit SRW)]>; 736 737def CMP8mr : Pseudo<(outs), (ins memsrc:$src1, GR8:$src2), 738 "cmp.b\t{$src1, $src2}", 739 [(MSP430cmp (load addr:$src1), GR8:$src2), (implicit SRW)]>; 740def CMP16mr : Pseudo<(outs), (ins memsrc:$src1, GR16:$src2), 741 "cmp.w\t{$src1, $src2}", 742 [(MSP430cmp (load addr:$src1), GR16:$src2), (implicit SRW)]>; 743 744def CMP8mi0 : Pseudo<(outs), (ins memsrc:$src1), 745 "cmp.b\t{$src1, #0}", 746 [(MSP430cmp (load addr:$src1), (i8 0)), (implicit SRW)]>; 747def CMP16mi0: Pseudo<(outs), (ins memsrc:$src1), 748 "cmp.w\t{$src1, #0}", 749 [(MSP430cmp (load addr:$src1), (i16 0)), (implicit SRW)]>; 750def CMP8mi1 : Pseudo<(outs), (ins memsrc:$src1), 751 "cmp.b\t{$src1, #1}", 752 [(MSP430cmp (load addr:$src1), (i8 1)), (implicit SRW)]>; 753def CMP16mi1: Pseudo<(outs), (ins memsrc:$src1), 754 "cmp.w\t{$src1, #1}", 755 [(MSP430cmp (load addr:$src1), (i16 1)), (implicit SRW)]>; 756def CMP8mi2 : Pseudo<(outs), (ins memsrc:$src1), 757 "cmp.b\t{$src1, #2}", 758 [(MSP430cmp (load addr:$src1), (i8 2)), (implicit SRW)]>; 759def CMP16mi2: Pseudo<(outs), (ins memsrc:$src1), 760 "cmp.w\t{$src1, #2}", 761 [(MSP430cmp (load addr:$src1), (i16 2)), (implicit SRW)]>; 762def CMP8mi4 : Pseudo<(outs), (ins memsrc:$src1), 763 "cmp.b\t{$src1, #4}", 764 [(MSP430cmp (load addr:$src1), (i8 4)), (implicit SRW)]>; 765def CMP16mi4: Pseudo<(outs), (ins memsrc:$src1), 766 "cmp.w\t{$src1, #4}", 767 [(MSP430cmp (load addr:$src1), (i16 4)), (implicit SRW)]>; 768def CMP8mi8 : Pseudo<(outs), (ins memsrc:$src1), 769 "cmp.b\t{$src1, #8}", 770 [(MSP430cmp (load addr:$src1), (i8 8)), (implicit SRW)]>; 771def CMP16mi8: Pseudo<(outs), (ins memsrc:$src1), 772 "cmp.w\t{$src1, #8}", 773 [(MSP430cmp (load addr:$src1), (i16 8)), (implicit SRW)]>; 774 775} // Defs = [SRW] 776 777//===----------------------------------------------------------------------===// 778// Non-Instruction Patterns 779 780// extload 781def : Pat<(extloadi16i8 addr:$src), (MOVZX16rm8 addr:$src)>; 782 783// anyext 784def : Pat<(anyext addr:$src), (MOVZX16rr8 GR8:$src)>; 785 786// truncs 787def : Pat<(i8 (trunc GR16:$src)), 788 (EXTRACT_SUBREG GR16:$src, subreg_8bit)>; 789 790// GlobalAddress, ExternalSymbol 791def : Pat<(i16 (MSP430Wrapper tglobaladdr:$dst)), (MOV16ri tglobaladdr:$dst)>; 792def : Pat<(i16 (MSP430Wrapper texternalsym:$dst)), (MOV16ri texternalsym:$dst)>; 793 794def : Pat<(add GR16:$src1, (MSP430Wrapper tglobaladdr :$src2)), 795 (ADD16ri GR16:$src1, tglobaladdr:$src2)>; 796def : Pat<(add GR16:$src1, (MSP430Wrapper texternalsym:$src2)), 797 (ADD16ri GR16:$src1, texternalsym:$src2)>; 798 799def : Pat<(store (i16 (MSP430Wrapper tglobaladdr:$src)), addr:$dst), 800 (MOV16mi addr:$dst, tglobaladdr:$src)>; 801def : Pat<(store (i16 (MSP430Wrapper texternalsym:$src)), addr:$dst), 802 (MOV16mi addr:$dst, texternalsym:$src)>; 803 804// calls 805def : Pat<(MSP430call (i16 tglobaladdr:$dst)), 806 (CALLi tglobaladdr:$dst)>; 807def : Pat<(MSP430call (i16 texternalsym:$dst)), 808 (CALLi texternalsym:$dst)>; 809 810// add and sub always produce carry 811def : Pat<(addc GR16:$src1, GR16:$src2), 812 (ADD16rr GR16:$src1, GR16:$src2)>; 813def : Pat<(addc GR16:$src1, (load addr:$src2)), 814 (ADD16rm GR16:$src1, addr:$src2)>; 815def : Pat<(addc GR16:$src1, imm:$src2), 816 (ADD16ri GR16:$src1, imm:$src2)>; 817def : Pat<(store (addc (load addr:$dst), GR16:$src), addr:$dst), 818 (ADD16mr addr:$dst, GR16:$src)>; 819def : Pat<(store (addc (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 820 (ADD16mm addr:$dst, addr:$src)>; 821 822def : Pat<(addc GR8:$src1, GR8:$src2), 823 (ADD8rr GR8:$src1, GR8:$src2)>; 824def : Pat<(addc GR8:$src1, (load addr:$src2)), 825 (ADD8rm GR8:$src1, addr:$src2)>; 826def : Pat<(addc GR8:$src1, imm:$src2), 827 (ADD8ri GR8:$src1, imm:$src2)>; 828def : Pat<(store (addc (load addr:$dst), GR8:$src), addr:$dst), 829 (ADD8mr addr:$dst, GR8:$src)>; 830def : Pat<(store (addc (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 831 (ADD8mm addr:$dst, addr:$src)>; 832 833def : Pat<(subc GR16:$src1, GR16:$src2), 834 (SUB16rr GR16:$src1, GR16:$src2)>; 835def : Pat<(subc GR16:$src1, (load addr:$src2)), 836 (SUB16rm GR16:$src1, addr:$src2)>; 837def : Pat<(subc GR16:$src1, imm:$src2), 838 (SUB16ri GR16:$src1, imm:$src2)>; 839def : Pat<(store (subc (load addr:$dst), GR16:$src), addr:$dst), 840 (SUB16mr addr:$dst, GR16:$src)>; 841def : Pat<(store (subc (load addr:$dst), (i16 (load addr:$src))), addr:$dst), 842 (SUB16mm addr:$dst, addr:$src)>; 843 844def : Pat<(subc GR8:$src1, GR8:$src2), 845 (SUB8rr GR8:$src1, GR8:$src2)>; 846def : Pat<(subc GR8:$src1, (load addr:$src2)), 847 (SUB8rm GR8:$src1, addr:$src2)>; 848def : Pat<(subc GR8:$src1, imm:$src2), 849 (SUB8ri GR8:$src1, imm:$src2)>; 850def : Pat<(store (subc (load addr:$dst), GR8:$src), addr:$dst), 851 (SUB8mr addr:$dst, GR8:$src)>; 852def : Pat<(store (subc (load addr:$dst), (i8 (load addr:$src))), addr:$dst), 853 (SUB8mm addr:$dst, addr:$src)>; 854