MipsISelDAGToDAG.cpp (199481) | MipsISelDAGToDAG.cpp (199511) |
---|---|
1//===-- MipsISelDAGToDAG.cpp - A dag to dag inst selector for Mips --------===// 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//===----------------------------------------------------------------------===// --- 76 unchanged lines hidden (view full) --- 85 86 SDNode *getGlobalBaseReg(); 87 SDNode *Select(SDValue N); 88 89 // Complex Pattern. 90 bool SelectAddr(SDValue Op, SDValue N, 91 SDValue &Base, SDValue &Offset); 92 | 1//===-- MipsISelDAGToDAG.cpp - A dag to dag inst selector for Mips --------===// 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//===----------------------------------------------------------------------===// --- 76 unchanged lines hidden (view full) --- 85 86 SDNode *getGlobalBaseReg(); 87 SDNode *Select(SDValue N); 88 89 // Complex Pattern. 90 bool SelectAddr(SDValue Op, SDValue N, 91 SDValue &Base, SDValue &Offset); 92 |
93 SDNode *SelectLoadFp64(SDValue N); 94 SDNode *SelectStoreFp64(SDValue N); |
|
93 94 // getI32Imm - Return a target constant with the specified 95 // value, of type i32. 96 inline SDValue getI32Imm(unsigned Imm) { 97 return CurDAG->getTargetConstant(Imm, MVT::i32); 98 } 99 100 --- 92 unchanged lines hidden (view full) --- 193 } 194 } 195 196 Base = Addr; 197 Offset = CurDAG->getTargetConstant(0, MVT::i32); 198 return true; 199} 200 | 95 96 // getI32Imm - Return a target constant with the specified 97 // value, of type i32. 98 inline SDValue getI32Imm(unsigned Imm) { 99 return CurDAG->getTargetConstant(Imm, MVT::i32); 100 } 101 102 --- 92 unchanged lines hidden (view full) --- 195 } 196 } 197 198 Base = Addr; 199 Offset = CurDAG->getTargetConstant(0, MVT::i32); 200 return true; 201} 202 |
203SDNode *MipsDAGToDAGISel::SelectLoadFp64(SDValue N) { 204 MVT::SimpleValueType NVT = 205 N.getNode()->getValueType(0).getSimpleVT().SimpleTy; 206 207 if (!Subtarget.isMips1() || NVT != MVT::f64) 208 return NULL; 209 210 if (!Predicate_unindexedload(N.getNode()) || 211 !Predicate_load(N.getNode())) 212 return NULL; 213 214 SDValue Chain = N.getOperand(0); 215 SDValue N1 = N.getOperand(1); 216 SDValue Offset0, Offset1, Base; 217 218 if (!SelectAddr(N, N1, Offset0, Base) || 219 N1.getValueType() != MVT::i32) 220 return NULL; 221 222 MachineSDNode::mmo_iterator MemRefs0 = MF->allocateMemRefsArray(1); 223 MemRefs0[0] = cast<MemSDNode>(N)->getMemOperand(); 224 DebugLoc dl = N.getDebugLoc(); 225 226 // The second load should start after for 4 bytes. 227 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Offset0)) 228 Offset1 = CurDAG->getTargetConstant(C->getSExtValue()+4, MVT::i32); 229 else if (ConstantPoolSDNode *CP = dyn_cast<ConstantPoolSDNode>(Offset0)) 230 Offset1 = CurDAG->getTargetConstantPool(CP->getConstVal(), 231 MVT::i32, 232 CP->getAlignment(), 233 CP->getOffset()+4, 234 CP->getTargetFlags()); 235 else 236 return NULL; 237 238 // Instead of: 239 // ldc $f0, X($3) 240 // Generate: 241 // lwc $f0, X($3) 242 // lwc $f1, X+4($3) 243 SDNode *LD0 = CurDAG->getMachineNode(Mips::LWC1, dl, MVT::f32, 244 MVT::Other, Offset0, Base, Chain); 245 SDValue Undef = SDValue(CurDAG->getMachineNode(TargetInstrInfo::IMPLICIT_DEF, 246 dl, NVT), 0); 247 SDValue I0 = CurDAG->getTargetInsertSubreg(Mips::SUBREG_FPEVEN, dl, 248 MVT::f64, Undef, SDValue(LD0, 0)); 249 250 SDNode *LD1 = CurDAG->getMachineNode(Mips::LWC1, dl, MVT::f32, 251 MVT::Other, Offset1, Base, SDValue(LD0, 1)); 252 SDValue I1 = CurDAG->getTargetInsertSubreg(Mips::SUBREG_FPODD, dl, 253 MVT::f64, I0, SDValue(LD1, 0)); 254 255 ReplaceUses(N, I1); 256 ReplaceUses(N.getValue(1), Chain); 257 cast<MachineSDNode>(LD0)->setMemRefs(MemRefs0, MemRefs0 + 1); 258 cast<MachineSDNode>(LD1)->setMemRefs(MemRefs0, MemRefs0 + 1); 259 return I1.getNode(); 260} 261 262SDNode *MipsDAGToDAGISel::SelectStoreFp64(SDValue N) { 263 264 if (!Subtarget.isMips1() || 265 N.getOperand(1).getValueType() != MVT::f64) 266 return NULL; 267 268 SDValue Chain = N.getOperand(0); 269 270 if (!Predicate_unindexedstore(N.getNode()) || 271 !Predicate_store(N.getNode())) 272 return NULL; 273 274 SDValue N1 = N.getOperand(1); 275 SDValue N2 = N.getOperand(2); 276 SDValue Offset0, Offset1, Base; 277 278 if (!SelectAddr(N, N2, Offset0, Base) || 279 N1.getValueType() != MVT::f64 || 280 N2.getValueType() != MVT::i32) 281 return NULL; 282 283 MachineSDNode::mmo_iterator MemRefs0 = MF->allocateMemRefsArray(1); 284 MemRefs0[0] = cast<MemSDNode>(N)->getMemOperand(); 285 DebugLoc dl = N.getDebugLoc(); 286 287 // Get the even and odd part from the f64 register 288 SDValue FPOdd = CurDAG->getTargetExtractSubreg(Mips::SUBREG_FPODD, 289 dl, MVT::f32, N1); 290 SDValue FPEven = CurDAG->getTargetExtractSubreg(Mips::SUBREG_FPEVEN, 291 dl, MVT::f32, N1); 292 293 // The second store should start after for 4 bytes. 294 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Offset0)) 295 Offset1 = CurDAG->getTargetConstant(C->getSExtValue()+4, MVT::i32); 296 else 297 return NULL; 298 299 // Instead of: 300 // sdc $f0, X($3) 301 // Generate: 302 // swc $f0, X($3) 303 // swc $f1, X+4($3) 304 SDValue Ops0[] = { FPEven, Offset0, Base, Chain }; 305 Chain = SDValue(CurDAG->getMachineNode(Mips::SWC1, dl, 306 MVT::Other, Ops0, 4), 0); 307 cast<MachineSDNode>(Chain.getNode())->setMemRefs(MemRefs0, MemRefs0 + 1); 308 309 SDValue Ops1[] = { FPOdd, Offset1, Base, Chain }; 310 Chain = SDValue(CurDAG->getMachineNode(Mips::SWC1, dl, 311 MVT::Other, Ops1, 4), 0); 312 cast<MachineSDNode>(Chain.getNode())->setMemRefs(MemRefs0, MemRefs0 + 1); 313 314 ReplaceUses(N.getValue(0), Chain); 315 return Chain.getNode(); 316} 317 |
|
201/// Select instructions not customized! Used for 202/// expanded, promoted and normal instructions 203SDNode* MipsDAGToDAGISel::Select(SDValue N) { 204 SDNode *Node = N.getNode(); 205 unsigned Opcode = Node->getOpcode(); 206 DebugLoc dl = Node->getDebugLoc(); 207 208 // Dump information about the Node being selected --- 131 unchanged lines hidden (view full) --- 340 if (N.getValueType() == MVT::f64 && CN->isExactlyValue(+0.0)) { 341 SDValue Zero = CurDAG->getRegister(Mips::ZERO, MVT::i32); 342 ReplaceUses(N, Zero); 343 return Zero.getNode(); 344 } 345 break; 346 } 347 | 318/// Select instructions not customized! Used for 319/// expanded, promoted and normal instructions 320SDNode* MipsDAGToDAGISel::Select(SDValue N) { 321 SDNode *Node = N.getNode(); 322 unsigned Opcode = Node->getOpcode(); 323 DebugLoc dl = Node->getDebugLoc(); 324 325 // Dump information about the Node being selected --- 131 unchanged lines hidden (view full) --- 457 if (N.getValueType() == MVT::f64 && CN->isExactlyValue(+0.0)) { 458 SDValue Zero = CurDAG->getRegister(Mips::ZERO, MVT::i32); 459 ReplaceUses(N, Zero); 460 return Zero.getNode(); 461 } 462 break; 463 } 464 |
465 case ISD::LOAD: 466 if (SDNode *ResNode = SelectLoadFp64(N)) 467 return ResNode; 468 // Other cases are autogenerated. 469 break; 470 471 case ISD::STORE: 472 if (SDNode *ResNode = SelectStoreFp64(N)) 473 return ResNode; 474 // Other cases are autogenerated. 475 break; 476 |
|
348 /// Handle direct and indirect calls when using PIC. On PIC, when 349 /// GOT is smaller than about 64k (small code) the GA target is 350 /// loaded with only one instruction. Otherwise GA's target must 351 /// be loaded with 3 instructions. 352 case MipsISD::JmpLink: { 353 if (TM.getRelocationModel() == Reloc::PIC_) { 354 SDValue Chain = Node->getOperand(0); 355 SDValue Callee = Node->getOperand(1); --- 52 unchanged lines hidden --- | 477 /// Handle direct and indirect calls when using PIC. On PIC, when 478 /// GOT is smaller than about 64k (small code) the GA target is 479 /// loaded with only one instruction. Otherwise GA's target must 480 /// be loaded with 3 instructions. 481 case MipsISD::JmpLink: { 482 if (TM.getRelocationModel() == Reloc::PIC_) { 483 SDValue Chain = Node->getOperand(0); 484 SDValue Callee = Node->getOperand(1); --- 52 unchanged lines hidden --- |