llvm.org GIT mirror llvm / 603ba13
[globalisel][tablegen] Generalize pointer-type inference by introducing ptypeN. NFC ptypeN is functionally the same as typeN except that it informs the SelectionDAG importer that an operand should be treated as a pointer even if it was written as iN. This is important for patterns that use iN instead of iPTR to represent pointers. E.g.: (set GPR64:$dst, (load GPR64:$addr)) Previously, this was handled as a hardcoded special case for the appropriate operands to G_LOAD and G_STORE. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318574 91177308-0d34-0410-b5e6-96231b3b80d8 Daniel Sanders 1 year, 11 months ago
5 changed file(s) with 30 addition(s) and 6 deletion(s). Raw diff Collapse all Expand all
468468 // Generic load. Expects a MachineMemOperand in addition to explicit operands.
469469 def G_LOAD : Instruction {
470470 let OutOperandList = (outs type0:$dst);
471 let InOperandList = (ins type1:$addr);
471 let InOperandList = (ins ptype1:$addr);
472472 let hasSideEffects = 0;
473473 let mayLoad = 1;
474474 }
476476 // Generic store. Expects a MachineMemOperand in addition to explicit operands.
477477 def G_STORE : Instruction {
478478 let OutOperandList = (outs);
479 let InOperandList = (ins type0:$src, type1:$addr);
479 let InOperandList = (ins type0:$src, ptype1:$addr);
480480 let hasSideEffects = 0;
481481 let mayStore = 1;
482482 }
791791 // have the same LLT).
792792 class TypedOperand : Operand {
793793 let OperandType = Ty;
794 bit IsPointer = 0;
794795 }
795796
796797 def type0 : TypedOperand<"OPERAND_GENERIC_0">;
799800 def type3 : TypedOperand<"OPERAND_GENERIC_3">;
800801 def type4 : TypedOperand<"OPERAND_GENERIC_4">;
801802 def type5 : TypedOperand<"OPERAND_GENERIC_5">;
803
804 let IsPointer = 1 in {
805 def ptype0 : TypedOperand<"OPERAND_GENERIC_0">;
806 def ptype1 : TypedOperand<"OPERAND_GENERIC_1">;
807 def ptype2 : TypedOperand<"OPERAND_GENERIC_2">;
808 def ptype3 : TypedOperand<"OPERAND_GENERIC_3">;
809 def ptype4 : TypedOperand<"OPERAND_GENERIC_4">;
810 def ptype5 : TypedOperand<"OPERAND_GENERIC_5">;
811 }
802812
803813 /// zero_reg definition - Special node to stand for the zero register.
804814 ///
429429 return Res;
430430 }
431431
432 bool CodeGenInstruction::isOperandAPointer(unsigned i) const {
433 if (DagInit *ConstraintList = TheDef->getValueAsDag("InOperandList")) {
434 if (i < ConstraintList->getNumArgs()) {
435 if (DefInit *Constraint = dyn_cast(ConstraintList->getArg(i))) {
436 return Constraint->getDef()->isSubClassOf("TypedOperand") &&
437 Constraint->getDef()->getValueAsBit("IsPointer");
438 }
439 }
440 }
441 return false;
442 }
432443
433444 //===----------------------------------------------------------------------===//
434445 /// CodeGenInstAlias Implementation
283283 /// include text from the specified variant, returning the new string.
284284 static std::string FlattenAsmStringVariants(StringRef AsmString,
285285 unsigned Variant);
286
287 // Is the specified operand in a generic instruction implicitly a pointer.
288 // This can be used on intructions that use typeN or ptypeN to identify
289 // operands that should be considered as pointers even though SelectionDAG
290 // didn't make a distinction between integer and pointers.
291 bool isOperandAPointer(unsigned i) const;
286292 };
287293
288294
25452545 // SelectionDAG allows pointers to be represented with iN since it doesn't
25462546 // distinguish between pointers and integers but they are different types in GlobalISel.
25472547 // Coerce integers to pointers to address space 0 if the context indicates a pointer.
2548 // TODO: Find a better way to do this, SDTCisPtrTy?
2549 bool OperandIsAPointer =
2550 (SrcGIOrNull->TheDef->getName() == "G_LOAD" && i == 0) ||
2551 (SrcGIOrNull->TheDef->getName() == "G_STORE" && i == 1);
2548 bool OperandIsAPointer = SrcGIOrNull->isOperandAPointer(i);
25522549
25532550 // For G_INTRINSIC/G_INTRINSIC_W_SIDE_EFFECTS, the operand immediately
25542551 // following the defs is an intrinsic ID.