diff options
author | Carol Eidt <carol.eidt@microsoft.com> | 2019-03-26 16:13:40 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-03-26 16:13:40 -0700 |
commit | da6ed1197abcb1be420351af1bb3758de6048c8f (patch) | |
tree | ec26f10d197a21d7f3c80478da6fb728abd8aa31 /src/jit/codegenlinear.cpp | |
parent | aa072b639fc2eb0e60a8083e4c74426db91341e0 (diff) | |
download | coreclr-da6ed1197abcb1be420351af1bb3758de6048c8f.tar.gz coreclr-da6ed1197abcb1be420351af1bb3758de6048c8f.tar.bz2 coreclr-da6ed1197abcb1be420351af1bb3758de6048c8f.zip |
Handle addressing modes for HW intrinsics (#22944)
* Handle addressing modes for HW intrinsics
Also, eliminate some places where the code size estimates were over-estimating.
Contribute to #19550
Fix #19521
Diffstat (limited to 'src/jit/codegenlinear.cpp')
-rw-r--r-- | src/jit/codegenlinear.cpp | 77 |
1 files changed, 68 insertions, 9 deletions
diff --git a/src/jit/codegenlinear.cpp b/src/jit/codegenlinear.cpp index 7c5c01895e..72f9fa68db 100644 --- a/src/jit/codegenlinear.cpp +++ b/src/jit/codegenlinear.cpp @@ -1339,12 +1339,27 @@ void CodeGen::genConsumeRegs(GenTree* tree) // Update the life of the lcl var. genUpdateLife(tree); } -#endif // _TARGET_XARCH_ - else if (tree->OperIsInitVal()) +#ifdef FEATURE_HW_INTRINSICS + else if (tree->OperIs(GT_HWIntrinsic)) { - genConsumeReg(tree->gtGetOp1()); + // Only load/store HW intrinsics can be contained (and the address may also be contained). + HWIntrinsicCategory category = HWIntrinsicInfo::lookupCategory(tree->AsHWIntrinsic()->gtHWIntrinsicId); + assert((category == HW_Category_MemoryLoad) || (category == HW_Category_MemoryStore)); + int numArgs = HWIntrinsicInfo::lookupNumArgs(tree->AsHWIntrinsic()); + genConsumeAddress(tree->gtGetOp1()); + if (category == HW_Category_MemoryStore) + { + assert((numArgs == 2) && !tree->gtGetOp2()->isContained()); + genConsumeReg(tree->gtGetOp2()); + } + else + { + assert(numArgs == 1); + } } - else if (tree->OperIsHWIntrinsic()) +#endif // FEATURE_HW_INTRINSICS +#endif // _TARGET_XARCH_ + else if (tree->OperIsInitVal()) { genConsumeReg(tree->gtGetOp1()); } @@ -1374,11 +1389,6 @@ void CodeGen::genConsumeRegs(GenTree* tree) // Return Value: // None. // -// Notes: -// Note that this logic is localized here because we must do the liveness update in -// the correct execution order. This is important because we may have two operands -// that involve the same lclVar, and if one is marked "lastUse" we must handle it -// after the first. void CodeGen::genConsumeOperands(GenTreeOp* tree) { @@ -1395,6 +1405,55 @@ void CodeGen::genConsumeOperands(GenTreeOp* tree) } } +#ifdef FEATURE_HW_INTRINSICS +//------------------------------------------------------------------------ +// genConsumeHWIntrinsicOperands: Do liveness update for the operands of a GT_HWIntrinsic node +// +// Arguments: +// node - the GenTreeHWIntrinsic node whose operands will have their liveness updated. +// +// Return Value: +// None. +// + +void CodeGen::genConsumeHWIntrinsicOperands(GenTreeHWIntrinsic* node) +{ + int numArgs = HWIntrinsicInfo::lookupNumArgs(node); + GenTree* op1 = node->gtGetOp1(); + if (op1 == nullptr) + { + assert((numArgs == 0) && (node->gtGetOp2() == nullptr)); + return; + } + if (op1->OperIs(GT_LIST)) + { + int foundArgs = 0; + assert(node->gtGetOp2() == nullptr); + for (GenTreeArgList* list = op1->AsArgList(); list != nullptr; list = list->Rest()) + { + GenTree* operand = list->Current(); + genConsumeRegs(operand); + foundArgs++; + } + assert(foundArgs == numArgs); + } + else + { + genConsumeRegs(op1); + GenTree* op2 = node->gtGetOp2(); + if (op2 != nullptr) + { + genConsumeRegs(op2); + assert(numArgs == 2); + } + else + { + assert(numArgs == 1); + } + } +} +#endif // FEATURE_HW_INTRINSICS + #if FEATURE_PUT_STRUCT_ARG_STK //------------------------------------------------------------------------ // genConsumePutStructArgStk: Do liveness update for the operands of a PutArgStk node. |