diff options
Diffstat (limited to 'src/coreclr/jit/morph.cpp')
-rw-r--r-- | src/coreclr/jit/morph.cpp | 108 |
1 files changed, 30 insertions, 78 deletions
diff --git a/src/coreclr/jit/morph.cpp b/src/coreclr/jit/morph.cpp index a40cc67b451..15ceeb5f013 100644 --- a/src/coreclr/jit/morph.cpp +++ b/src/coreclr/jit/morph.cpp @@ -3147,7 +3147,7 @@ GenTreeCall* Compiler::fgMorphArgs(GenTreeCall* call) { GenTree** parentArgx = &arg.EarlyNodeRef(); - // Morph the arg node, and update the parent and argEntry pointers. + // Morph the arg node and update the node pointer. GenTree* argx = *parentArgx; if (argx == nullptr) { @@ -4548,8 +4548,8 @@ GenTree* Compiler::fgMorphIndexAddr(GenTreeIndexAddr* indexAddr) { unsigned arrRefTmpNum = lvaGrabTemp(true DEBUGARG("arr expr")); arrRefDefn = gtNewTempAssign(arrRefTmpNum, arrRef); - arrRef = gtNewLclvNode(arrRefTmpNum, arrRef->TypeGet()); - arrRef2 = gtNewLclvNode(arrRefTmpNum, arrRef->TypeGet()); + arrRef = gtNewLclvNode(arrRefTmpNum, lvaGetDesc(arrRefTmpNum)->TypeGet()); + arrRef2 = gtNewLclvNode(arrRefTmpNum, lvaGetDesc(arrRefTmpNum)->TypeGet()); } else { @@ -4563,8 +4563,8 @@ GenTree* Compiler::fgMorphIndexAddr(GenTreeIndexAddr* indexAddr) { unsigned indexTmpNum = lvaGrabTemp(true DEBUGARG("index expr")); indexDefn = gtNewTempAssign(indexTmpNum, index); - index = gtNewLclvNode(indexTmpNum, index->TypeGet()); - index2 = gtNewLclvNode(indexTmpNum, index->TypeGet()); + index = gtNewLclvNode(indexTmpNum, lvaGetDesc(indexTmpNum)->TypeGet()); + index2 = gtNewLclvNode(indexTmpNum, lvaGetDesc(indexTmpNum)->TypeGet()); } else { @@ -4807,7 +4807,7 @@ GenTree* Compiler::fgMorphExpandStackArgForVarArgs(GenTreeLclVarCommon* lclNode) } GenTree* argNode; - if (varTypeIsStruct(lclNode)) + if (lclNode->TypeIs(TYP_STRUCT)) { argNode = gtNewObjNode(lclNode->GetLayout(this), argAddr); } @@ -4887,7 +4887,7 @@ GenTree* Compiler::fgMorphExpandImplicitByRefArg(GenTreeLclVarCommon* lclNode) unsigned offset = lclNode->GetLclOffs() + fieldOffset; var_types argNodeType = lclNode->TypeGet(); ClassLayout* argNodeLayout = nullptr; - if (varTypeIsStruct(argNodeType)) + if (argNodeType == TYP_STRUCT) { argNodeLayout = lclNode->GetLayout(this); } @@ -4909,7 +4909,7 @@ GenTree* Compiler::fgMorphExpandImplicitByRefArg(GenTreeLclVarCommon* lclNode) GenTree* newArgNode; if (!isAddress) { - if (varTypeIsStruct(argNodeType)) + if (argNodeType == TYP_STRUCT) { newArgNode = gtNewObjNode(argNodeLayout, addrNode); } @@ -8505,7 +8505,7 @@ GenTree* Compiler::fgExpandVirtualVtableCallTarget(GenTreeCall* call) // [tmp + vtabOffsOfIndirection] GenTree* tmpTree1 = gtNewOperNode(GT_ADD, TYP_I_IMPL, gtNewLclvNode(varNum1, TYP_I_IMPL), gtNewIconNode(vtabOffsOfIndirection, TYP_I_IMPL)); - tmpTree1 = gtNewOperNode(GT_IND, TYP_I_IMPL, tmpTree1, false); + tmpTree1 = gtNewOperNode(GT_IND, TYP_I_IMPL, tmpTree1); tmpTree1->gtFlags |= GTF_IND_NONFAULTING; tmpTree1->gtFlags |= GTF_IND_INVARIANT; @@ -8519,7 +8519,7 @@ GenTree* Compiler::fgExpandVirtualVtableCallTarget(GenTreeCall* call) GenTree* asgVar2 = gtNewTempAssign(varNum2, tmpTree2); // var2 = <expression> // This last indirection is not invariant, but is non-faulting - result = gtNewOperNode(GT_IND, TYP_I_IMPL, gtNewLclvNode(varNum2, TYP_I_IMPL), false); // [var2] + result = gtNewOperNode(GT_IND, TYP_I_IMPL, gtNewLclvNode(varNum2, TYP_I_IMPL)); // [var2] result->gtFlags |= GTF_IND_NONFAULTING; result = gtNewOperNode(GT_ADD, TYP_I_IMPL, result, gtNewLclvNode(varNum2, TYP_I_IMPL)); // [var2] + var2 @@ -8532,7 +8532,7 @@ GenTree* Compiler::fgExpandVirtualVtableCallTarget(GenTreeCall* call) { // result = [vtab + vtabOffsOfIndirection] result = gtNewOperNode(GT_ADD, TYP_I_IMPL, vtab, gtNewIconNode(vtabOffsOfIndirection, TYP_I_IMPL)); - result = gtNewOperNode(GT_IND, TYP_I_IMPL, result, false); + result = gtNewOperNode(GT_IND, TYP_I_IMPL, result); result->gtFlags |= GTF_IND_NONFAULTING; result->gtFlags |= GTF_IND_INVARIANT; } @@ -8549,7 +8549,7 @@ GenTree* Compiler::fgExpandVirtualVtableCallTarget(GenTreeCall* call) // result = [result + vtabOffsAfterIndirection] result = gtNewOperNode(GT_ADD, TYP_I_IMPL, result, gtNewIconNode(vtabOffsAfterIndirection, TYP_I_IMPL)); // This last indirection is not invariant, but is non-faulting - result = gtNewOperNode(GT_IND, TYP_I_IMPL, result, false); + result = gtNewOperNode(GT_IND, TYP_I_IMPL, result); result->gtFlags |= GTF_IND_NONFAULTING; } @@ -9138,7 +9138,7 @@ GenTree* Compiler::fgMorphOneAsgBlockOp(GenTree* tree) noway_assert(src->IsIntegralConst(0)); noway_assert(destVarDsc != nullptr); - src = gtNewZeroConNode(asgType, CORINFO_TYPE_FLOAT); + src = gtNewZeroConNode(asgType); } else #endif @@ -11403,97 +11403,49 @@ DONE_MORPHING_CHILDREN: } case GT_ADDR: - - // Can not remove op1 if it is currently a CSE candidate. - if (gtIsActiveCSE_Candidate(op1)) + // Can not remove a GT_ADDR if it is currently a CSE candidate. + if (gtIsActiveCSE_Candidate(tree)) { break; } - if (op1->OperGet() == GT_IND) + // Perform the transform ADDR(IND(...)) == (...). + if (op1->OperIsIndir()) { - // Can not remove a GT_ADDR if it is currently a CSE candidate. - if (gtIsActiveCSE_Candidate(tree)) - { - break; - } - - // Perform the transform ADDR(IND(...)) == (...). GenTree* addr = op1->AsIndir()->Addr(); - noway_assert(varTypeIsI(addr)); - - DEBUG_DESTROY_NODE(op1); - DEBUG_DESTROY_NODE(tree); - - return addr; - } - else if (op1->OperGet() == GT_OBJ) - { - // Can not remove a GT_ADDR if it is currently a CSE candidate. - if (gtIsActiveCSE_Candidate(tree)) - { - break; - } - - // Perform the transform ADDR(OBJ(...)) == (...). - GenTree* addr = op1->AsObj()->Addr(); - - noway_assert(varTypeIsGC(addr->gtType) || addr->gtType == TYP_I_IMPL); + noway_assert(varTypeIsI(genActualType(addr))); DEBUG_DESTROY_NODE(op1); DEBUG_DESTROY_NODE(tree); return addr; } - else if ((op1->gtOper == GT_COMMA) && !optValnumCSE_phase) + // Perform the transform ADDR(COMMA(x, ..., z)) == COMMA(x, ..., ADDR(z)). + else if (op1->OperIs(GT_COMMA) && !optValnumCSE_phase) { - // Perform the transform ADDR(COMMA(x, ..., z)) == COMMA(x, ..., ADDR(z)). - // (Be sure to mark "z" as an l-value...) - ArrayStack<GenTree*> commas(getAllocator(CMK_ArrayStack)); for (GenTree* comma = op1; comma != nullptr && comma->gtOper == GT_COMMA; comma = comma->gtGetOp2()) { commas.Push(comma); } - GenTree* commaNode = commas.Top(); - tree = op1; - commaNode->AsOp()->gtOp2->gtFlags |= GTF_DONT_CSE; - - // If the node we're about to put under a GT_ADDR is an indirection, it - // doesn't need to be materialized, since we only want the addressing mode. Because - // of this, this GT_IND is not a faulting indirection and we don't have to extract it - // as a side effect. - GenTree* commaOp2 = commaNode->AsOp()->gtOp2; - if (commaOp2->OperIsBlk()) - { - commaOp2->SetOper(GT_IND); - } - if (commaOp2->gtOper == GT_IND) - { - commaOp2->gtFlags |= GTF_IND_NONFAULTING; - commaOp2->gtFlags &= ~GTF_EXCEPT; - commaOp2->gtFlags |= (commaOp2->AsOp()->gtOp1->gtFlags & GTF_EXCEPT); - } - - op1 = gtNewOperNode(GT_ADDR, TYP_BYREF, commaOp2); - commaNode->AsOp()->gtOp2 = op1; - // Originally, I gave all the comma nodes type "byref". But the ADDR(IND(x)) == x transform - // might give op1 a type different from byref (like, say, native int). So now go back and give - // all the comma nodes the type of op1. + GenTree* commaNode = commas.Top(); + GenTree* addr = gtNewOperNode(GT_ADDR, TYP_BYREF, commaNode->AsOp()->gtOp2); + commaNode->AsOp()->gtOp2 = addr; + // Retype the comma nodes to match "addr" and update their side effects. while (!commas.Empty()) { GenTree* comma = commas.Pop(); - comma->gtType = op1->gtType; + comma->gtType = addr->TypeGet(); #ifdef DEBUG comma->gtDebugFlags |= GTF_DEBUG_NODE_MORPHED; #endif gtUpdateNodeSideEffects(comma); } - return tree; + return op1; } break; @@ -12389,7 +12341,7 @@ GenTree* Compiler::fgOptimizeHWIntrinsic(GenTreeHWIntrinsic* node) if (GenTreeVecCon::IsHWIntrinsicCreateConstant(node, simd32Val)) { - GenTreeVecCon* vecCon = gtNewVconNode(node->TypeGet(), node->GetSimdBaseJitType()); + GenTreeVecCon* vecCon = gtNewVconNode(node->TypeGet()); for (GenTree* arg : node->Operands()) { @@ -13626,8 +13578,8 @@ GenTree* Compiler::fgMorphModToSubMulDiv(GenTreeOp* tree) GenTree* dividend = div->IsReverseOp() ? opB : opA; GenTree* divisor = div->IsReverseOp() ? opA : opB; - div->gtOp1 = gtClone(dividend); - div->gtOp2 = gtClone(divisor); + div->gtOp1 = gtCloneExpr(dividend); + div->gtOp2 = gtCloneExpr(divisor); var_types type = div->gtType; GenTree* const mul = gtNewOperNode(GT_MUL, type, div, divisor); @@ -17333,7 +17285,7 @@ bool Compiler::fgMorphArrayOpsStmt(MorphMDArrayTempCache* pTempCache, BasicBlock // Side-effect; create a temp. // unsigned newIdxLcl = m_compiler->lvaGrabTemp(true DEBUGARG("MD array index copy")); unsigned newIdxLcl = m_pTempCache->GrabTemp(idx->TypeGet()); - GenTree* newIdx = m_compiler->gtNewLclvNode(newIdxLcl, idx->TypeGet()); + GenTree* newIdx = m_compiler->gtNewLclvNode(newIdxLcl, genActualType(idx)); idxToUse[i] = newIdx; idxToCopy[i] = newIdxLcl; anyIdxWithSideEffects = true; |