SparcISelDAGToDAG.cpp revision 7a4d2913ea04b708c191595ad6f1841abd36b077
1//===-- SparcV8ISelDAGToDAG.cpp - A dag to dag inst selector for SparcV8 --===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file was developed by Chris Lattner and is distributed under 6// the University of Illinois Open Source License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file defines an instruction selector for the V8 target 11// 12//===----------------------------------------------------------------------===// 13 14#include "SparcV8.h" 15#include "SparcV8TargetMachine.h" 16#include "llvm/DerivedTypes.h" 17#include "llvm/Function.h" 18#include "llvm/CodeGen/MachineFrameInfo.h" 19#include "llvm/CodeGen/MachineFunction.h" 20#include "llvm/CodeGen/MachineInstrBuilder.h" 21#include "llvm/CodeGen/SelectionDAG.h" 22#include "llvm/CodeGen/SelectionDAGISel.h" 23#include "llvm/CodeGen/SSARegMap.h" 24#include "llvm/Target/TargetLowering.h" 25#include "llvm/Support/Debug.h" 26#include <iostream> 27using namespace llvm; 28 29//===----------------------------------------------------------------------===// 30// TargetLowering Implementation 31//===----------------------------------------------------------------------===// 32 33namespace V8ISD { 34 enum { 35 FIRST_NUMBER = ISD::BUILTIN_OP_END+V8::INSTRUCTION_LIST_END, 36 CMPICC, // Compare two GPR operands, set icc. 37 CMPFCC, // Compare two FP operands, set fcc. 38 BRICC, // Branch to dest on icc condition 39 BRFCC, // Branch to dest on fcc condition 40 SELECT_ICC, // Select between two values using the current ICC flags. 41 SELECT_FCC, // Select between two values using the current FCC flags. 42 43 Hi, Lo, // Hi/Lo operations, typically on a global address. 44 45 FTOI, // FP to Int within a FP register. 46 ITOF, // Int to FP within a FP register. 47 48 CALL, // A V8 call instruction. 49 RET_FLAG, // Return with a flag operand. 50 }; 51} 52 53/// IntCondCCodeToICC - Convert a DAG integer condition code to a SPARC ICC 54/// condition. 55static V8CC::CondCodes IntCondCCodeToICC(ISD::CondCode CC) { 56 switch (CC) { 57 default: assert(0 && "Unknown integer condition code!"); 58 case ISD::SETEQ: return V8CC::ICC_E; 59 case ISD::SETNE: return V8CC::ICC_NE; 60 case ISD::SETLT: return V8CC::ICC_L; 61 case ISD::SETGT: return V8CC::ICC_G; 62 case ISD::SETLE: return V8CC::ICC_LE; 63 case ISD::SETGE: return V8CC::ICC_GE; 64 case ISD::SETULT: return V8CC::ICC_CS; 65 case ISD::SETULE: return V8CC::ICC_LEU; 66 case ISD::SETUGT: return V8CC::ICC_GU; 67 case ISD::SETUGE: return V8CC::ICC_CC; 68 } 69} 70 71/// FPCondCCodeToFCC - Convert a DAG floatingp oint condition code to a SPARC 72/// FCC condition. 73static V8CC::CondCodes FPCondCCodeToFCC(ISD::CondCode CC) { 74 switch (CC) { 75 default: assert(0 && "Unknown fp condition code!"); 76 case ISD::SETEQ: return V8CC::FCC_E; 77 case ISD::SETNE: return V8CC::FCC_NE; 78 case ISD::SETLT: return V8CC::FCC_L; 79 case ISD::SETGT: return V8CC::FCC_G; 80 case ISD::SETLE: return V8CC::FCC_LE; 81 case ISD::SETGE: return V8CC::FCC_GE; 82 case ISD::SETULT: return V8CC::FCC_UL; 83 case ISD::SETULE: return V8CC::FCC_ULE; 84 case ISD::SETUGT: return V8CC::FCC_UG; 85 case ISD::SETUGE: return V8CC::FCC_UGE; 86 case ISD::SETUO: return V8CC::FCC_U; 87 case ISD::SETO: return V8CC::FCC_O; 88 case ISD::SETONE: return V8CC::FCC_LG; 89 case ISD::SETUEQ: return V8CC::FCC_UE; 90 } 91} 92 93namespace { 94 class SparcV8TargetLowering : public TargetLowering { 95 int VarArgsFrameOffset; // Frame offset to start of varargs area. 96 public: 97 SparcV8TargetLowering(TargetMachine &TM); 98 virtual SDOperand LowerOperation(SDOperand Op, SelectionDAG &DAG); 99 100 /// isMaskedValueZeroForTargetNode - Return true if 'Op & Mask' is known to 101 /// be zero. Op is expected to be a target specific node. Used by DAG 102 /// combiner. 103 virtual bool isMaskedValueZeroForTargetNode(const SDOperand &Op, 104 uint64_t Mask) const; 105 106 virtual std::vector<SDOperand> 107 LowerArguments(Function &F, SelectionDAG &DAG); 108 virtual std::pair<SDOperand, SDOperand> 109 LowerCallTo(SDOperand Chain, const Type *RetTy, bool isVarArg, 110 unsigned CC, 111 bool isTailCall, SDOperand Callee, ArgListTy &Args, 112 SelectionDAG &DAG); 113 virtual std::pair<SDOperand, SDOperand> 114 LowerFrameReturnAddress(bool isFrameAddr, SDOperand Chain, unsigned Depth, 115 SelectionDAG &DAG); 116 virtual MachineBasicBlock *InsertAtEndOfBasicBlock(MachineInstr *MI, 117 MachineBasicBlock *MBB); 118 119 virtual const char *getTargetNodeName(unsigned Opcode) const; 120 }; 121} 122 123SparcV8TargetLowering::SparcV8TargetLowering(TargetMachine &TM) 124 : TargetLowering(TM) { 125 126 // Set up the register classes. 127 addRegisterClass(MVT::i32, V8::IntRegsRegisterClass); 128 addRegisterClass(MVT::f32, V8::FPRegsRegisterClass); 129 addRegisterClass(MVT::f64, V8::DFPRegsRegisterClass); 130 131 // Custom legalize GlobalAddress nodes into LO/HI parts. 132 setOperationAction(ISD::GlobalAddress, MVT::i32, Custom); 133 setOperationAction(ISD::ConstantPool , MVT::i32, Custom); 134 135 // Sparc doesn't have sext_inreg, replace them with shl/sra 136 setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i16, Expand); 137 setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i8 , Expand); 138 setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i1 , Expand); 139 140 // Sparc has no REM operation. 141 setOperationAction(ISD::UREM, MVT::i32, Expand); 142 setOperationAction(ISD::SREM, MVT::i32, Expand); 143 144 // Custom expand fp<->sint 145 setOperationAction(ISD::FP_TO_SINT, MVT::i32, Custom); 146 setOperationAction(ISD::SINT_TO_FP, MVT::i32, Custom); 147 148 // Expand fp<->uint 149 setOperationAction(ISD::FP_TO_UINT, MVT::i32, Expand); 150 setOperationAction(ISD::UINT_TO_FP, MVT::i32, Expand); 151 152 setOperationAction(ISD::BIT_CONVERT, MVT::f32, Expand); 153 setOperationAction(ISD::BIT_CONVERT, MVT::i32, Expand); 154 155 // Turn FP extload into load/fextend 156 setOperationAction(ISD::EXTLOAD, MVT::f32, Expand); 157 158 // Sparc has no select or setcc: expand to SELECT_CC. 159 setOperationAction(ISD::SELECT, MVT::i32, Expand); 160 setOperationAction(ISD::SELECT, MVT::f32, Expand); 161 setOperationAction(ISD::SELECT, MVT::f64, Expand); 162 setOperationAction(ISD::SETCC, MVT::i32, Expand); 163 setOperationAction(ISD::SETCC, MVT::f32, Expand); 164 setOperationAction(ISD::SETCC, MVT::f64, Expand); 165 166 // Sparc doesn't have BRCOND either, it has BR_CC. 167 setOperationAction(ISD::BRCOND, MVT::Other, Expand); 168 setOperationAction(ISD::BRCONDTWOWAY, MVT::Other, Expand); 169 setOperationAction(ISD::BRTWOWAY_CC, MVT::Other, Expand); 170 setOperationAction(ISD::BR_CC, MVT::i32, Custom); 171 setOperationAction(ISD::BR_CC, MVT::f32, Custom); 172 setOperationAction(ISD::BR_CC, MVT::f64, Custom); 173 174 setOperationAction(ISD::SELECT_CC, MVT::i32, Custom); 175 setOperationAction(ISD::SELECT_CC, MVT::f32, Custom); 176 setOperationAction(ISD::SELECT_CC, MVT::f64, Custom); 177 178 // V8 has no intrinsics for these particular operations. 179 setOperationAction(ISD::MEMMOVE, MVT::Other, Expand); 180 setOperationAction(ISD::MEMSET, MVT::Other, Expand); 181 setOperationAction(ISD::MEMCPY, MVT::Other, Expand); 182 183 setOperationAction(ISD::FSIN , MVT::f64, Expand); 184 setOperationAction(ISD::FCOS , MVT::f64, Expand); 185 setOperationAction(ISD::FSIN , MVT::f32, Expand); 186 setOperationAction(ISD::FCOS , MVT::f32, Expand); 187 setOperationAction(ISD::CTPOP, MVT::i32, Expand); 188 setOperationAction(ISD::CTTZ , MVT::i32, Expand); 189 setOperationAction(ISD::CTLZ , MVT::i32, Expand); 190 setOperationAction(ISD::ROTL , MVT::i32, Expand); 191 setOperationAction(ISD::ROTR , MVT::i32, Expand); 192 setOperationAction(ISD::BSWAP, MVT::i32, Expand); 193 194 setOperationAction(ISD::SHL_PARTS, MVT::i32, Expand); 195 setOperationAction(ISD::SRA_PARTS, MVT::i32, Expand); 196 setOperationAction(ISD::SRL_PARTS, MVT::i32, Expand); 197 198 // We don't have line number support yet. 199 setOperationAction(ISD::LOCATION, MVT::Other, Expand); 200 setOperationAction(ISD::DEBUG_LOC, MVT::Other, Expand); 201 setOperationAction(ISD::DEBUG_LABEL, MVT::Other, Expand); 202 203 // RET must be custom lowered, to meet ABI requirements 204 setOperationAction(ISD::RET , MVT::Other, Custom); 205 206 // VASTART needs to be custom lowered to use the VarArgsFrameIndex 207 setOperationAction(ISD::VASTART , MVT::Other, Custom); 208 209 // Use the default implementation. 210 setOperationAction(ISD::VAARG , MVT::Other, Expand); 211 setOperationAction(ISD::VACOPY , MVT::Other, Expand); 212 setOperationAction(ISD::VAEND , MVT::Other, Expand); 213 setOperationAction(ISD::STACKSAVE , MVT::Other, Expand); 214 setOperationAction(ISD::STACKRESTORE , MVT::Other, Expand); 215 setOperationAction(ISD::DYNAMIC_STACKALLOC, MVT::i32 , Expand); 216 217 setOperationAction(ISD::ConstantFP, MVT::f64, Expand); 218 setOperationAction(ISD::ConstantFP, MVT::f32, Expand); 219 220 setStackPointerRegisterToSaveRestore(V8::O6); 221 222 if (TM.getSubtarget<SparcV8Subtarget>().isV9()) { 223 setOperationAction(ISD::CTPOP, MVT::i32, Legal); 224 } 225 226 computeRegisterProperties(); 227} 228 229const char *SparcV8TargetLowering::getTargetNodeName(unsigned Opcode) const { 230 switch (Opcode) { 231 default: return 0; 232 case V8ISD::CMPICC: return "V8ISD::CMPICC"; 233 case V8ISD::CMPFCC: return "V8ISD::CMPFCC"; 234 case V8ISD::BRICC: return "V8ISD::BRICC"; 235 case V8ISD::BRFCC: return "V8ISD::BRFCC"; 236 case V8ISD::SELECT_ICC: return "V8ISD::SELECT_ICC"; 237 case V8ISD::SELECT_FCC: return "V8ISD::SELECT_FCC"; 238 case V8ISD::Hi: return "V8ISD::Hi"; 239 case V8ISD::Lo: return "V8ISD::Lo"; 240 case V8ISD::FTOI: return "V8ISD::FTOI"; 241 case V8ISD::ITOF: return "V8ISD::ITOF"; 242 case V8ISD::CALL: return "V8ISD::CALL"; 243 case V8ISD::RET_FLAG: return "V8ISD::RET_FLAG"; 244 } 245} 246 247/// isMaskedValueZeroForTargetNode - Return true if 'Op & Mask' is known to 248/// be zero. Op is expected to be a target specific node. Used by DAG 249/// combiner. 250bool SparcV8TargetLowering:: 251isMaskedValueZeroForTargetNode(const SDOperand &Op, uint64_t Mask) const { 252 switch (Op.getOpcode()) { 253 default: return false; 254 case V8ISD::SELECT_ICC: 255 case V8ISD::SELECT_FCC: 256 assert(MVT::isInteger(Op.getValueType()) && "Not an integer select!"); 257 // These operations are masked zero if both the left and the right are zero. 258 return MaskedValueIsZero(Op.getOperand(0), Mask) && 259 MaskedValueIsZero(Op.getOperand(1), Mask); 260 } 261} 262 263 264/// LowerArguments - V8 uses a very simple ABI, where all values are passed in 265/// either one or two GPRs, including FP values. TODO: we should pass FP values 266/// in FP registers for fastcc functions. 267std::vector<SDOperand> 268SparcV8TargetLowering::LowerArguments(Function &F, SelectionDAG &DAG) { 269 MachineFunction &MF = DAG.getMachineFunction(); 270 SSARegMap *RegMap = MF.getSSARegMap(); 271 std::vector<SDOperand> ArgValues; 272 273 static const unsigned ArgRegs[] = { 274 V8::I0, V8::I1, V8::I2, V8::I3, V8::I4, V8::I5 275 }; 276 277 const unsigned *CurArgReg = ArgRegs, *ArgRegEnd = ArgRegs+6; 278 unsigned ArgOffset = 68; 279 280 SDOperand Root = DAG.getRoot(); 281 std::vector<SDOperand> OutChains; 282 283 for (Function::arg_iterator I = F.arg_begin(), E = F.arg_end(); I != E; ++I) { 284 MVT::ValueType ObjectVT = getValueType(I->getType()); 285 286 switch (ObjectVT) { 287 default: assert(0 && "Unhandled argument type!"); 288 case MVT::i1: 289 case MVT::i8: 290 case MVT::i16: 291 case MVT::i32: 292 if (I->use_empty()) { // Argument is dead. 293 if (CurArgReg < ArgRegEnd) ++CurArgReg; 294 ArgValues.push_back(DAG.getNode(ISD::UNDEF, ObjectVT)); 295 } else if (CurArgReg < ArgRegEnd) { // Lives in an incoming GPR 296 unsigned VReg = RegMap->createVirtualRegister(&V8::IntRegsRegClass); 297 MF.addLiveIn(*CurArgReg++, VReg); 298 SDOperand Arg = DAG.getCopyFromReg(Root, VReg, MVT::i32); 299 if (ObjectVT != MVT::i32) { 300 unsigned AssertOp = I->getType()->isSigned() ? ISD::AssertSext 301 : ISD::AssertZext; 302 Arg = DAG.getNode(AssertOp, MVT::i32, Arg, 303 DAG.getValueType(ObjectVT)); 304 Arg = DAG.getNode(ISD::TRUNCATE, ObjectVT, Arg); 305 } 306 ArgValues.push_back(Arg); 307 } else { 308 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(4, ArgOffset); 309 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 310 SDOperand Load; 311 if (ObjectVT == MVT::i32) { 312 Load = DAG.getLoad(MVT::i32, Root, FIPtr, DAG.getSrcValue(0)); 313 } else { 314 unsigned LoadOp = 315 I->getType()->isSigned() ? ISD::SEXTLOAD : ISD::ZEXTLOAD; 316 317 // Sparc is big endian, so add an offset based on the ObjectVT. 318 unsigned Offset = 4-std::max(1U, MVT::getSizeInBits(ObjectVT)/8); 319 FIPtr = DAG.getNode(ISD::ADD, MVT::i32, FIPtr, 320 DAG.getConstant(Offset, MVT::i32)); 321 Load = DAG.getExtLoad(LoadOp, MVT::i32, Root, FIPtr, 322 DAG.getSrcValue(0), ObjectVT); 323 Load = DAG.getNode(ISD::TRUNCATE, ObjectVT, Load); 324 } 325 ArgValues.push_back(Load); 326 } 327 328 ArgOffset += 4; 329 break; 330 case MVT::f32: 331 if (I->use_empty()) { // Argument is dead. 332 if (CurArgReg < ArgRegEnd) ++CurArgReg; 333 ArgValues.push_back(DAG.getNode(ISD::UNDEF, ObjectVT)); 334 } else if (CurArgReg < ArgRegEnd) { // Lives in an incoming GPR 335 // FP value is passed in an integer register. 336 unsigned VReg = RegMap->createVirtualRegister(&V8::IntRegsRegClass); 337 MF.addLiveIn(*CurArgReg++, VReg); 338 SDOperand Arg = DAG.getCopyFromReg(Root, VReg, MVT::i32); 339 340 Arg = DAG.getNode(ISD::BIT_CONVERT, MVT::f32, Arg); 341 ArgValues.push_back(Arg); 342 } else { 343 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(4, ArgOffset); 344 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 345 SDOperand Load = DAG.getLoad(MVT::f32, Root, FIPtr, DAG.getSrcValue(0)); 346 ArgValues.push_back(Load); 347 } 348 ArgOffset += 4; 349 break; 350 351 case MVT::i64: 352 case MVT::f64: 353 if (I->use_empty()) { // Argument is dead. 354 if (CurArgReg < ArgRegEnd) ++CurArgReg; 355 if (CurArgReg < ArgRegEnd) ++CurArgReg; 356 ArgValues.push_back(DAG.getNode(ISD::UNDEF, ObjectVT)); 357 } else if (/* FIXME: Apparently this isn't safe?? */ 358 0 && CurArgReg == ArgRegEnd && ObjectVT == MVT::f64 && 359 ((CurArgReg-ArgRegs) & 1) == 0) { 360 // If this is a double argument and the whole thing lives on the stack, 361 // and the argument is aligned, load the double straight from the stack. 362 // We can't do a load in cases like void foo([6ints], int,double), 363 // because the double wouldn't be aligned! 364 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(8, ArgOffset); 365 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 366 ArgValues.push_back(DAG.getLoad(MVT::f64, Root, FIPtr, 367 DAG.getSrcValue(0))); 368 } else { 369 SDOperand HiVal; 370 if (CurArgReg < ArgRegEnd) { // Lives in an incoming GPR 371 unsigned VRegHi = RegMap->createVirtualRegister(&V8::IntRegsRegClass); 372 MF.addLiveIn(*CurArgReg++, VRegHi); 373 HiVal = DAG.getCopyFromReg(Root, VRegHi, MVT::i32); 374 } else { 375 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(4, ArgOffset); 376 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 377 HiVal = DAG.getLoad(MVT::i32, Root, FIPtr, DAG.getSrcValue(0)); 378 } 379 380 SDOperand LoVal; 381 if (CurArgReg < ArgRegEnd) { // Lives in an incoming GPR 382 unsigned VRegLo = RegMap->createVirtualRegister(&V8::IntRegsRegClass); 383 MF.addLiveIn(*CurArgReg++, VRegLo); 384 LoVal = DAG.getCopyFromReg(Root, VRegLo, MVT::i32); 385 } else { 386 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(4, ArgOffset+4); 387 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 388 LoVal = DAG.getLoad(MVT::i32, Root, FIPtr, DAG.getSrcValue(0)); 389 } 390 391 // Compose the two halves together into an i64 unit. 392 SDOperand WholeValue = 393 DAG.getNode(ISD::BUILD_PAIR, MVT::i64, LoVal, HiVal); 394 395 // If we want a double, do a bit convert. 396 if (ObjectVT == MVT::f64) 397 WholeValue = DAG.getNode(ISD::BIT_CONVERT, MVT::f64, WholeValue); 398 399 ArgValues.push_back(WholeValue); 400 } 401 ArgOffset += 8; 402 break; 403 } 404 } 405 406 // Store remaining ArgRegs to the stack if this is a varargs function. 407 if (F.getFunctionType()->isVarArg()) { 408 // Remember the vararg offset for the va_start implementation. 409 VarArgsFrameOffset = ArgOffset; 410 411 for (; CurArgReg != ArgRegEnd; ++CurArgReg) { 412 unsigned VReg = RegMap->createVirtualRegister(&V8::IntRegsRegClass); 413 MF.addLiveIn(*CurArgReg, VReg); 414 SDOperand Arg = DAG.getCopyFromReg(DAG.getRoot(), VReg, MVT::i32); 415 416 int FrameIdx = MF.getFrameInfo()->CreateFixedObject(4, ArgOffset); 417 SDOperand FIPtr = DAG.getFrameIndex(FrameIdx, MVT::i32); 418 419 OutChains.push_back(DAG.getNode(ISD::STORE, MVT::Other, DAG.getRoot(), 420 Arg, FIPtr, DAG.getSrcValue(0))); 421 ArgOffset += 4; 422 } 423 } 424 425 if (!OutChains.empty()) 426 DAG.setRoot(DAG.getNode(ISD::TokenFactor, MVT::Other, OutChains)); 427 428 // Finally, inform the code generator which regs we return values in. 429 switch (getValueType(F.getReturnType())) { 430 default: assert(0 && "Unknown type!"); 431 case MVT::isVoid: break; 432 case MVT::i1: 433 case MVT::i8: 434 case MVT::i16: 435 case MVT::i32: 436 MF.addLiveOut(V8::I0); 437 break; 438 case MVT::i64: 439 MF.addLiveOut(V8::I0); 440 MF.addLiveOut(V8::I1); 441 break; 442 case MVT::f32: 443 MF.addLiveOut(V8::F0); 444 break; 445 case MVT::f64: 446 MF.addLiveOut(V8::D0); 447 break; 448 } 449 450 return ArgValues; 451} 452 453std::pair<SDOperand, SDOperand> 454SparcV8TargetLowering::LowerCallTo(SDOperand Chain, const Type *RetTy, 455 bool isVarArg, unsigned CC, 456 bool isTailCall, SDOperand Callee, 457 ArgListTy &Args, SelectionDAG &DAG) { 458 MachineFunction &MF = DAG.getMachineFunction(); 459 // Count the size of the outgoing arguments. 460 unsigned ArgsSize = 0; 461 for (unsigned i = 0, e = Args.size(); i != e; ++i) { 462 switch (getValueType(Args[i].second)) { 463 default: assert(0 && "Unknown value type!"); 464 case MVT::i1: 465 case MVT::i8: 466 case MVT::i16: 467 case MVT::i32: 468 case MVT::f32: 469 ArgsSize += 4; 470 break; 471 case MVT::i64: 472 case MVT::f64: 473 ArgsSize += 8; 474 break; 475 } 476 } 477 if (ArgsSize > 4*6) 478 ArgsSize -= 4*6; // Space for first 6 arguments is prereserved. 479 else 480 ArgsSize = 0; 481 482 // Keep stack frames 8-byte aligned. 483 ArgsSize = (ArgsSize+7) & ~7; 484 485 Chain = DAG.getNode(ISD::CALLSEQ_START, MVT::Other, Chain, 486 DAG.getConstant(ArgsSize, getPointerTy())); 487 488 SDOperand StackPtr, NullSV; 489 std::vector<SDOperand> Stores; 490 std::vector<SDOperand> RegValuesToPass; 491 unsigned ArgOffset = 68; 492 for (unsigned i = 0, e = Args.size(); i != e; ++i) { 493 SDOperand Val = Args[i].first; 494 MVT::ValueType ObjectVT = Val.getValueType(); 495 SDOperand ValToStore(0, 0); 496 unsigned ObjSize; 497 switch (ObjectVT) { 498 default: assert(0 && "Unhandled argument type!"); 499 case MVT::i1: 500 case MVT::i8: 501 case MVT::i16: 502 // Promote the integer to 32-bits. If the input type is signed, use a 503 // sign extend, otherwise use a zero extend. 504 if (Args[i].second->isSigned()) 505 Val = DAG.getNode(ISD::SIGN_EXTEND, MVT::i32, Val); 506 else 507 Val = DAG.getNode(ISD::ZERO_EXTEND, MVT::i32, Val); 508 // FALL THROUGH 509 case MVT::i32: 510 ObjSize = 4; 511 512 if (RegValuesToPass.size() >= 6) { 513 ValToStore = Val; 514 } else { 515 RegValuesToPass.push_back(Val); 516 } 517 break; 518 case MVT::f32: 519 ObjSize = 4; 520 if (RegValuesToPass.size() >= 6) { 521 ValToStore = Val; 522 } else { 523 // Convert this to a FP value in an int reg. 524 Val = DAG.getNode(ISD::BIT_CONVERT, MVT::i32, Val); 525 RegValuesToPass.push_back(Val); 526 } 527 break; 528 case MVT::f64: 529 ObjSize = 8; 530 // If we can store this directly into the outgoing slot, do so. We can 531 // do this when all ArgRegs are used and if the outgoing slot is aligned. 532 // FIXME: McGill/misr fails with this. 533 if (0 && RegValuesToPass.size() >= 6 && ((ArgOffset-68) & 7) == 0) { 534 ValToStore = Val; 535 break; 536 } 537 538 // Otherwise, convert this to a FP value in int regs. 539 Val = DAG.getNode(ISD::BIT_CONVERT, MVT::i64, Val); 540 // FALL THROUGH 541 case MVT::i64: 542 ObjSize = 8; 543 if (RegValuesToPass.size() >= 6) { 544 ValToStore = Val; // Whole thing is passed in memory. 545 break; 546 } 547 548 // Split the value into top and bottom part. Top part goes in a reg. 549 SDOperand Hi = DAG.getNode(ISD::EXTRACT_ELEMENT, MVT::i32, Val, 550 DAG.getConstant(1, MVT::i32)); 551 SDOperand Lo = DAG.getNode(ISD::EXTRACT_ELEMENT, MVT::i32, Val, 552 DAG.getConstant(0, MVT::i32)); 553 RegValuesToPass.push_back(Hi); 554 555 if (RegValuesToPass.size() >= 6) { 556 ValToStore = Lo; 557 ArgOffset += 4; 558 ObjSize = 4; 559 } else { 560 RegValuesToPass.push_back(Lo); 561 } 562 break; 563 } 564 565 if (ValToStore.Val) { 566 if (!StackPtr.Val) { 567 StackPtr = DAG.getRegister(V8::O6, MVT::i32); 568 NullSV = DAG.getSrcValue(NULL); 569 } 570 SDOperand PtrOff = DAG.getConstant(ArgOffset, getPointerTy()); 571 PtrOff = DAG.getNode(ISD::ADD, MVT::i32, StackPtr, PtrOff); 572 Stores.push_back(DAG.getNode(ISD::STORE, MVT::Other, Chain, 573 ValToStore, PtrOff, NullSV)); 574 } 575 ArgOffset += ObjSize; 576 } 577 578 // Emit all stores, make sure the occur before any copies into physregs. 579 if (!Stores.empty()) 580 Chain = DAG.getNode(ISD::TokenFactor, MVT::Other, Stores); 581 582 static const unsigned ArgRegs[] = { 583 V8::O0, V8::O1, V8::O2, V8::O3, V8::O4, V8::O5 584 }; 585 586 // Build a sequence of copy-to-reg nodes chained together with token chain 587 // and flag operands which copy the outgoing args into O[0-5]. 588 SDOperand InFlag; 589 for (unsigned i = 0, e = RegValuesToPass.size(); i != e; ++i) { 590 Chain = DAG.getCopyToReg(Chain, ArgRegs[i], RegValuesToPass[i], InFlag); 591 InFlag = Chain.getValue(1); 592 } 593 594 // If the callee is a GlobalAddress node (quite common, every direct call is) 595 // turn it into a TargetGlobalAddress node so that legalize doesn't hack it. 596 if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) 597 Callee = DAG.getTargetGlobalAddress(G->getGlobal(), MVT::i32); 598 599 std::vector<MVT::ValueType> NodeTys; 600 NodeTys.push_back(MVT::Other); // Returns a chain 601 NodeTys.push_back(MVT::Flag); // Returns a flag for retval copy to use. 602 std::vector<SDOperand> Ops; 603 Ops.push_back(Chain); 604 Ops.push_back(Callee); 605 if (InFlag.Val) 606 Ops.push_back(InFlag); 607 Chain = DAG.getNode(V8ISD::CALL, NodeTys, Ops); 608 InFlag = Chain.getValue(1); 609 610 MVT::ValueType RetTyVT = getValueType(RetTy); 611 SDOperand RetVal; 612 if (RetTyVT != MVT::isVoid) { 613 switch (RetTyVT) { 614 default: assert(0 && "Unknown value type to return!"); 615 case MVT::i1: 616 case MVT::i8: 617 case MVT::i16: 618 RetVal = DAG.getCopyFromReg(Chain, V8::O0, MVT::i32, InFlag); 619 Chain = RetVal.getValue(1); 620 621 // Add a note to keep track of whether it is sign or zero extended. 622 RetVal = DAG.getNode(RetTy->isSigned() ? ISD::AssertSext :ISD::AssertZext, 623 MVT::i32, RetVal, DAG.getValueType(RetTyVT)); 624 RetVal = DAG.getNode(ISD::TRUNCATE, RetTyVT, RetVal); 625 break; 626 case MVT::i32: 627 RetVal = DAG.getCopyFromReg(Chain, V8::O0, MVT::i32, InFlag); 628 Chain = RetVal.getValue(1); 629 break; 630 case MVT::f32: 631 RetVal = DAG.getCopyFromReg(Chain, V8::F0, MVT::f32, InFlag); 632 Chain = RetVal.getValue(1); 633 break; 634 case MVT::f64: 635 RetVal = DAG.getCopyFromReg(Chain, V8::D0, MVT::f64, InFlag); 636 Chain = RetVal.getValue(1); 637 break; 638 case MVT::i64: 639 SDOperand Lo = DAG.getCopyFromReg(Chain, V8::O1, MVT::i32, InFlag); 640 SDOperand Hi = DAG.getCopyFromReg(Lo.getValue(1), V8::O0, MVT::i32, 641 Lo.getValue(2)); 642 RetVal = DAG.getNode(ISD::BUILD_PAIR, MVT::i64, Lo, Hi); 643 Chain = Hi.getValue(1); 644 break; 645 } 646 } 647 648 Chain = DAG.getNode(ISD::CALLSEQ_END, MVT::Other, Chain, 649 DAG.getConstant(ArgsSize, getPointerTy())); 650 651 return std::make_pair(RetVal, Chain); 652} 653 654std::pair<SDOperand, SDOperand> SparcV8TargetLowering:: 655LowerFrameReturnAddress(bool isFrameAddr, SDOperand Chain, unsigned Depth, 656 SelectionDAG &DAG) { 657 assert(0 && "Unimp"); 658 abort(); 659} 660 661// Look at LHS/RHS/CC and see if they are a lowered V8 setcc instruction. If so 662// set LHS/RHS and V8CC to the LHS/RHS of the setcc and V8CC to the condition. 663static void LookThroughSetCC(SDOperand &LHS, SDOperand &RHS, 664 ISD::CondCode CC, unsigned &V8CC) { 665 if (isa<ConstantSDNode>(RHS) && cast<ConstantSDNode>(RHS)->getValue() == 0 && 666 CC == ISD::SETNE && 667 ((LHS.getOpcode() == V8ISD::SELECT_ICC && 668 LHS.getOperand(3).getOpcode() == V8ISD::CMPICC) || 669 (LHS.getOpcode() == V8ISD::SELECT_FCC && 670 LHS.getOperand(3).getOpcode() == V8ISD::CMPFCC)) && 671 isa<ConstantSDNode>(LHS.getOperand(0)) && 672 isa<ConstantSDNode>(LHS.getOperand(1)) && 673 cast<ConstantSDNode>(LHS.getOperand(0))->getValue() == 1 && 674 cast<ConstantSDNode>(LHS.getOperand(1))->getValue() == 0) { 675 SDOperand CMPCC = LHS.getOperand(3); 676 V8CC = cast<ConstantSDNode>(LHS.getOperand(2))->getValue(); 677 LHS = CMPCC.getOperand(0); 678 RHS = CMPCC.getOperand(1); 679 } 680} 681 682 683SDOperand SparcV8TargetLowering:: 684LowerOperation(SDOperand Op, SelectionDAG &DAG) { 685 switch (Op.getOpcode()) { 686 default: assert(0 && "Should not custom lower this!"); 687 case ISD::GlobalAddress: { 688 GlobalValue *GV = cast<GlobalAddressSDNode>(Op)->getGlobal(); 689 SDOperand GA = DAG.getTargetGlobalAddress(GV, MVT::i32); 690 SDOperand Hi = DAG.getNode(V8ISD::Hi, MVT::i32, GA); 691 SDOperand Lo = DAG.getNode(V8ISD::Lo, MVT::i32, GA); 692 return DAG.getNode(ISD::ADD, MVT::i32, Lo, Hi); 693 } 694 case ISD::ConstantPool: { 695 Constant *C = cast<ConstantPoolSDNode>(Op)->get(); 696 SDOperand CP = DAG.getTargetConstantPool(C, MVT::i32); 697 SDOperand Hi = DAG.getNode(V8ISD::Hi, MVT::i32, CP); 698 SDOperand Lo = DAG.getNode(V8ISD::Lo, MVT::i32, CP); 699 return DAG.getNode(ISD::ADD, MVT::i32, Lo, Hi); 700 } 701 case ISD::FP_TO_SINT: 702 // Convert the fp value to integer in an FP register. 703 assert(Op.getValueType() == MVT::i32); 704 Op = DAG.getNode(V8ISD::FTOI, MVT::f32, Op.getOperand(0)); 705 return DAG.getNode(ISD::BIT_CONVERT, MVT::i32, Op); 706 case ISD::SINT_TO_FP: { 707 assert(Op.getOperand(0).getValueType() == MVT::i32); 708 SDOperand Tmp = DAG.getNode(ISD::BIT_CONVERT, MVT::f32, Op.getOperand(0)); 709 // Convert the int value to FP in an FP register. 710 return DAG.getNode(V8ISD::ITOF, Op.getValueType(), Tmp); 711 } 712 case ISD::BR_CC: { 713 SDOperand Chain = Op.getOperand(0); 714 ISD::CondCode CC = cast<CondCodeSDNode>(Op.getOperand(1))->get(); 715 SDOperand LHS = Op.getOperand(2); 716 SDOperand RHS = Op.getOperand(3); 717 SDOperand Dest = Op.getOperand(4); 718 unsigned Opc, V8CC = ~0U; 719 720 // If this is a br_cc of a "setcc", and if the setcc got lowered into 721 // an CMP[IF]CC/SELECT_[IF]CC pair, find the original compared values. 722 LookThroughSetCC(LHS, RHS, CC, V8CC); 723 724 // Get the condition flag. 725 SDOperand CompareFlag; 726 if (LHS.getValueType() == MVT::i32) { 727 std::vector<MVT::ValueType> VTs; 728 VTs.push_back(MVT::i32); 729 VTs.push_back(MVT::Flag); 730 std::vector<SDOperand> Ops; 731 Ops.push_back(LHS); 732 Ops.push_back(RHS); 733 CompareFlag = DAG.getNode(V8ISD::CMPICC, VTs, Ops).getValue(1); 734 if (V8CC == ~0U) V8CC = IntCondCCodeToICC(CC); 735 Opc = V8ISD::BRICC; 736 } else { 737 CompareFlag = DAG.getNode(V8ISD::CMPFCC, MVT::Flag, LHS, RHS); 738 if (V8CC == ~0U) V8CC = FPCondCCodeToFCC(CC); 739 Opc = V8ISD::BRFCC; 740 } 741 return DAG.getNode(Opc, MVT::Other, Chain, Dest, 742 DAG.getConstant(V8CC, MVT::i32), CompareFlag); 743 } 744 case ISD::SELECT_CC: { 745 SDOperand LHS = Op.getOperand(0); 746 SDOperand RHS = Op.getOperand(1); 747 ISD::CondCode CC = cast<CondCodeSDNode>(Op.getOperand(4))->get(); 748 SDOperand TrueVal = Op.getOperand(2); 749 SDOperand FalseVal = Op.getOperand(3); 750 unsigned Opc, V8CC = ~0U; 751 752 // If this is a select_cc of a "setcc", and if the setcc got lowered into 753 // an CMP[IF]CC/SELECT_[IF]CC pair, find the original compared values. 754 LookThroughSetCC(LHS, RHS, CC, V8CC); 755 756 SDOperand CompareFlag; 757 if (LHS.getValueType() == MVT::i32) { 758 std::vector<MVT::ValueType> VTs; 759 VTs.push_back(LHS.getValueType()); // subcc returns a value 760 VTs.push_back(MVT::Flag); 761 std::vector<SDOperand> Ops; 762 Ops.push_back(LHS); 763 Ops.push_back(RHS); 764 CompareFlag = DAG.getNode(V8ISD::CMPICC, VTs, Ops).getValue(1); 765 Opc = V8ISD::SELECT_ICC; 766 if (V8CC == ~0U) V8CC = IntCondCCodeToICC(CC); 767 } else { 768 CompareFlag = DAG.getNode(V8ISD::CMPFCC, MVT::Flag, LHS, RHS); 769 Opc = V8ISD::SELECT_FCC; 770 if (V8CC == ~0U) V8CC = FPCondCCodeToFCC(CC); 771 } 772 return DAG.getNode(Opc, TrueVal.getValueType(), TrueVal, FalseVal, 773 DAG.getConstant(V8CC, MVT::i32), CompareFlag); 774 } 775 case ISD::VASTART: { 776 // vastart just stores the address of the VarArgsFrameIndex slot into the 777 // memory location argument. 778 SDOperand Offset = DAG.getNode(ISD::ADD, MVT::i32, 779 DAG.getRegister(V8::I6, MVT::i32), 780 DAG.getConstant(VarArgsFrameOffset, MVT::i32)); 781 return DAG.getNode(ISD::STORE, MVT::Other, Op.getOperand(0), Offset, 782 Op.getOperand(1), Op.getOperand(2)); 783 } 784 case ISD::RET: { 785 SDOperand Copy; 786 787 switch(Op.getNumOperands()) { 788 default: 789 assert(0 && "Do not know how to return this many arguments!"); 790 abort(); 791 case 1: 792 return SDOperand(); // ret void is legal 793 case 2: { 794 unsigned ArgReg; 795 switch(Op.getOperand(1).getValueType()) { 796 default: assert(0 && "Unknown type to return!"); 797 case MVT::i32: ArgReg = V8::I0; break; 798 case MVT::f32: ArgReg = V8::F0; break; 799 case MVT::f64: ArgReg = V8::D0; break; 800 } 801 Copy = DAG.getCopyToReg(Op.getOperand(0), ArgReg, Op.getOperand(1), 802 SDOperand()); 803 break; 804 } 805 case 3: 806 Copy = DAG.getCopyToReg(Op.getOperand(0), V8::I0, Op.getOperand(2), 807 SDOperand()); 808 Copy = DAG.getCopyToReg(Copy, V8::I1, Op.getOperand(1), Copy.getValue(1)); 809 break; 810 } 811 return DAG.getNode(V8ISD::RET_FLAG, MVT::Other, Copy, Copy.getValue(1)); 812 } 813 } 814} 815 816MachineBasicBlock * 817SparcV8TargetLowering::InsertAtEndOfBasicBlock(MachineInstr *MI, 818 MachineBasicBlock *BB) { 819 unsigned BROpcode; 820 unsigned CC; 821 // Figure out the conditional branch opcode to use for this select_cc. 822 switch (MI->getOpcode()) { 823 default: assert(0 && "Unknown SELECT_CC!"); 824 case V8::SELECT_CC_Int_ICC: 825 case V8::SELECT_CC_FP_ICC: 826 case V8::SELECT_CC_DFP_ICC: 827 BROpcode = V8::BCOND; 828 case V8::SELECT_CC_Int_FCC: 829 case V8::SELECT_CC_FP_FCC: 830 case V8::SELECT_CC_DFP_FCC: 831 BROpcode = V8::FBCOND; 832 break; 833 } 834 835 CC = (V8CC::CondCodes)MI->getOperand(3).getImmedValue(); 836 837 // To "insert" a SELECT_CC instruction, we actually have to insert the diamond 838 // control-flow pattern. The incoming instruction knows the destination vreg 839 // to set, the condition code register to branch on, the true/false values to 840 // select between, and a branch opcode to use. 841 const BasicBlock *LLVM_BB = BB->getBasicBlock(); 842 ilist<MachineBasicBlock>::iterator It = BB; 843 ++It; 844 845 // thisMBB: 846 // ... 847 // TrueVal = ... 848 // [f]bCC copy1MBB 849 // fallthrough --> copy0MBB 850 MachineBasicBlock *thisMBB = BB; 851 MachineBasicBlock *copy0MBB = new MachineBasicBlock(LLVM_BB); 852 MachineBasicBlock *sinkMBB = new MachineBasicBlock(LLVM_BB); 853 BuildMI(BB, BROpcode, 2).addMBB(sinkMBB).addImm(CC); 854 MachineFunction *F = BB->getParent(); 855 F->getBasicBlockList().insert(It, copy0MBB); 856 F->getBasicBlockList().insert(It, sinkMBB); 857 // Update machine-CFG edges 858 BB->addSuccessor(copy0MBB); 859 BB->addSuccessor(sinkMBB); 860 861 // copy0MBB: 862 // %FalseValue = ... 863 // # fallthrough to sinkMBB 864 BB = copy0MBB; 865 866 // Update machine-CFG edges 867 BB->addSuccessor(sinkMBB); 868 869 // sinkMBB: 870 // %Result = phi [ %FalseValue, copy0MBB ], [ %TrueValue, thisMBB ] 871 // ... 872 BB = sinkMBB; 873 BuildMI(BB, V8::PHI, 4, MI->getOperand(0).getReg()) 874 .addReg(MI->getOperand(2).getReg()).addMBB(copy0MBB) 875 .addReg(MI->getOperand(1).getReg()).addMBB(thisMBB); 876 877 delete MI; // The pseudo instruction is gone now. 878 return BB; 879} 880 881//===----------------------------------------------------------------------===// 882// Instruction Selector Implementation 883//===----------------------------------------------------------------------===// 884 885//===--------------------------------------------------------------------===// 886/// SparcV8DAGToDAGISel - SPARC specific code to select Sparc V8 machine 887/// instructions for SelectionDAG operations. 888/// 889namespace { 890class SparcV8DAGToDAGISel : public SelectionDAGISel { 891 SparcV8TargetLowering V8Lowering; 892 893 /// Subtarget - Keep a pointer to the Sparc Subtarget around so that we can 894 /// make the right decision when generating code for different targets. 895 const SparcV8Subtarget &Subtarget; 896public: 897 SparcV8DAGToDAGISel(TargetMachine &TM) 898 : SelectionDAGISel(V8Lowering), V8Lowering(TM), 899 Subtarget(TM.getSubtarget<SparcV8Subtarget>()) { 900 } 901 902 SDOperand Select(SDOperand Op); 903 904 // Complex Pattern Selectors. 905 bool SelectADDRrr(SDOperand N, SDOperand &R1, SDOperand &R2); 906 bool SelectADDRri(SDOperand N, SDOperand &Base, SDOperand &Offset); 907 908 /// InstructionSelectBasicBlock - This callback is invoked by 909 /// SelectionDAGISel when it has created a SelectionDAG for us to codegen. 910 virtual void InstructionSelectBasicBlock(SelectionDAG &DAG); 911 912 virtual const char *getPassName() const { 913 return "SparcV8 DAG->DAG Pattern Instruction Selection"; 914 } 915 916 // Include the pieces autogenerated from the target description. 917#include "SparcV8GenDAGISel.inc" 918}; 919} // end anonymous namespace 920 921/// InstructionSelectBasicBlock - This callback is invoked by 922/// SelectionDAGISel when it has created a SelectionDAG for us to codegen. 923void SparcV8DAGToDAGISel::InstructionSelectBasicBlock(SelectionDAG &DAG) { 924 DEBUG(BB->dump()); 925 926 // Select target instructions for the DAG. 927 DAG.setRoot(Select(DAG.getRoot())); 928 CodeGenMap.clear(); 929 DAG.RemoveDeadNodes(); 930 931 // Emit machine code to BB. 932 ScheduleAndEmitDAG(DAG); 933} 934 935bool SparcV8DAGToDAGISel::SelectADDRri(SDOperand Addr, SDOperand &Base, 936 SDOperand &Offset) { 937 if (FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(Addr)) { 938 Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), MVT::i32); 939 Offset = CurDAG->getTargetConstant(0, MVT::i32); 940 return true; 941 } 942 943 if (Addr.getOpcode() == ISD::ADD) { 944 if (ConstantSDNode *CN = dyn_cast<ConstantSDNode>(Addr.getOperand(1))) { 945 if (Predicate_simm13(CN)) { 946 if (FrameIndexSDNode *FIN = 947 dyn_cast<FrameIndexSDNode>(Addr.getOperand(0))) { 948 // Constant offset from frame ref. 949 Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), MVT::i32); 950 } else { 951 Base = Select(Addr.getOperand(0)); 952 } 953 Offset = CurDAG->getTargetConstant(CN->getValue(), MVT::i32); 954 return true; 955 } 956 } 957 if (Addr.getOperand(0).getOpcode() == V8ISD::Lo) { 958 Base = Select(Addr.getOperand(1)); 959 Offset = Addr.getOperand(0).getOperand(0); 960 return true; 961 } 962 if (Addr.getOperand(1).getOpcode() == V8ISD::Lo) { 963 Base = Select(Addr.getOperand(0)); 964 Offset = Addr.getOperand(1).getOperand(0); 965 return true; 966 } 967 } 968 Base = Select(Addr); 969 Offset = CurDAG->getTargetConstant(0, MVT::i32); 970 return true; 971} 972 973bool SparcV8DAGToDAGISel::SelectADDRrr(SDOperand Addr, SDOperand &R1, 974 SDOperand &R2) { 975 if (Addr.getOpcode() == ISD::FrameIndex) return false; 976 if (Addr.getOpcode() == ISD::ADD) { 977 if (isa<ConstantSDNode>(Addr.getOperand(1)) && 978 Predicate_simm13(Addr.getOperand(1).Val)) 979 return false; // Let the reg+imm pattern catch this! 980 if (Addr.getOperand(0).getOpcode() == V8ISD::Lo || 981 Addr.getOperand(1).getOpcode() == V8ISD::Lo) 982 return false; // Let the reg+imm pattern catch this! 983 R1 = Select(Addr.getOperand(0)); 984 R2 = Select(Addr.getOperand(1)); 985 return true; 986 } 987 988 R1 = Select(Addr); 989 R2 = CurDAG->getRegister(V8::G0, MVT::i32); 990 return true; 991} 992 993SDOperand SparcV8DAGToDAGISel::Select(SDOperand Op) { 994 SDNode *N = Op.Val; 995 if (N->getOpcode() >= ISD::BUILTIN_OP_END && 996 N->getOpcode() < V8ISD::FIRST_NUMBER) 997 return Op; // Already selected. 998 // If this has already been converted, use it. 999 std::map<SDOperand, SDOperand>::iterator CGMI = CodeGenMap.find(Op); 1000 if (CGMI != CodeGenMap.end()) return CGMI->second; 1001 1002 switch (N->getOpcode()) { 1003 default: break; 1004 case ISD::FrameIndex: { 1005 int FI = cast<FrameIndexSDNode>(N)->getIndex(); 1006 if (N->hasOneUse()) 1007 return CurDAG->SelectNodeTo(N, V8::ADDri, MVT::i32, 1008 CurDAG->getTargetFrameIndex(FI, MVT::i32), 1009 CurDAG->getTargetConstant(0, MVT::i32)); 1010 return CodeGenMap[Op] = 1011 CurDAG->getTargetNode(V8::ADDri, MVT::i32, 1012 CurDAG->getTargetFrameIndex(FI, MVT::i32), 1013 CurDAG->getTargetConstant(0, MVT::i32)); 1014 } 1015 case ISD::ADD_PARTS: { 1016 SDOperand LHSL = Select(N->getOperand(0)); 1017 SDOperand LHSH = Select(N->getOperand(1)); 1018 SDOperand RHSL = Select(N->getOperand(2)); 1019 SDOperand RHSH = Select(N->getOperand(3)); 1020 // FIXME, handle immediate RHS. 1021 SDOperand Low = CurDAG->getTargetNode(V8::ADDCCrr, MVT::i32, MVT::Flag, 1022 LHSL, RHSL); 1023 SDOperand Hi = CurDAG->getTargetNode(V8::ADDXrr, MVT::i32, LHSH, RHSH, 1024 Low.getValue(1)); 1025 CodeGenMap[SDOperand(N, 0)] = Low; 1026 CodeGenMap[SDOperand(N, 1)] = Hi; 1027 return Op.ResNo ? Hi : Low; 1028 } 1029 case ISD::SUB_PARTS: { 1030 SDOperand LHSL = Select(N->getOperand(0)); 1031 SDOperand LHSH = Select(N->getOperand(1)); 1032 SDOperand RHSL = Select(N->getOperand(2)); 1033 SDOperand RHSH = Select(N->getOperand(3)); 1034 // FIXME, handle immediate RHS. 1035 SDOperand Low = CurDAG->getTargetNode(V8::SUBCCrr, MVT::i32, MVT::Flag, 1036 LHSL, RHSL); 1037 SDOperand Hi = CurDAG->getTargetNode(V8::SUBXrr, MVT::i32, LHSH, RHSH, 1038 Low.getValue(1)); 1039 CodeGenMap[SDOperand(N, 0)] = Low; 1040 CodeGenMap[SDOperand(N, 1)] = Hi; 1041 return Op.ResNo ? Hi : Low; 1042 } 1043 case ISD::SDIV: 1044 case ISD::UDIV: { 1045 // FIXME: should use a custom expander to expose the SRA to the dag. 1046 SDOperand DivLHS = Select(N->getOperand(0)); 1047 SDOperand DivRHS = Select(N->getOperand(1)); 1048 1049 // Set the Y register to the high-part. 1050 SDOperand TopPart; 1051 if (N->getOpcode() == ISD::SDIV) { 1052 TopPart = CurDAG->getTargetNode(V8::SRAri, MVT::i32, DivLHS, 1053 CurDAG->getTargetConstant(31, MVT::i32)); 1054 } else { 1055 TopPart = CurDAG->getRegister(V8::G0, MVT::i32); 1056 } 1057 TopPart = CurDAG->getTargetNode(V8::WRYrr, MVT::Flag, TopPart, 1058 CurDAG->getRegister(V8::G0, MVT::i32)); 1059 1060 // FIXME: Handle div by immediate. 1061 unsigned Opcode = N->getOpcode() == ISD::SDIV ? V8::SDIVrr : V8::UDIVrr; 1062 return CurDAG->SelectNodeTo(N, Opcode, MVT::i32, DivLHS, DivRHS, TopPart); 1063 } 1064 case ISD::MULHU: 1065 case ISD::MULHS: { 1066 // FIXME: Handle mul by immediate. 1067 SDOperand MulLHS = Select(N->getOperand(0)); 1068 SDOperand MulRHS = Select(N->getOperand(1)); 1069 unsigned Opcode = N->getOpcode() == ISD::MULHU ? V8::UMULrr : V8::SMULrr; 1070 SDOperand Mul = CurDAG->getTargetNode(Opcode, MVT::i32, MVT::Flag, 1071 MulLHS, MulRHS); 1072 // The high part is in the Y register. 1073 return CurDAG->SelectNodeTo(N, V8::RDY, MVT::i32, Mul.getValue(1)); 1074 } 1075 case V8ISD::CALL: 1076 // FIXME: This is a workaround for a bug in tblgen. 1077 { // Pattern #47: (call:Flag (tglobaladdr:i32):$dst, ICC:Flag) 1078 // Emits: (CALL:void (tglobaladdr:i32):$dst) 1079 // Pattern complexity = 2 cost = 1 1080 SDOperand N1 = N->getOperand(1); 1081 if (N1.getOpcode() != ISD::TargetGlobalAddress && 1082 N1.getOpcode() != ISD::ExternalSymbol) goto P47Fail; 1083 SDOperand InFlag = SDOperand(0, 0); 1084 SDOperand Chain = N->getOperand(0); 1085 SDOperand Tmp0 = N1; 1086 Chain = Select(Chain); 1087 SDOperand Result; 1088 if (N->getNumOperands() == 3) { 1089 InFlag = Select(N->getOperand(2)); 1090 Result = CurDAG->getTargetNode(V8::CALL, MVT::Other, MVT::Flag, Tmp0, 1091 Chain, InFlag); 1092 } else { 1093 Result = CurDAG->getTargetNode(V8::CALL, MVT::Other, MVT::Flag, Tmp0, 1094 Chain); 1095 } 1096 Chain = CodeGenMap[SDOperand(N, 0)] = Result.getValue(0); 1097 CodeGenMap[SDOperand(N, 1)] = Result.getValue(1); 1098 return Result.getValue(Op.ResNo); 1099 } 1100 P47Fail:; 1101 1102 } 1103 1104 return SelectCode(Op); 1105} 1106 1107 1108/// createSparcV8ISelDag - This pass converts a legalized DAG into a 1109/// SPARC-specific DAG, ready for instruction scheduling. 1110/// 1111FunctionPass *llvm::createSparcV8ISelDag(TargetMachine &TM) { 1112 return new SparcV8DAGToDAGISel(TM); 1113} 1114