未验证 提交 a78211be 编写于 作者: J Joni Aromaa 提交者: GitHub

Unpin locals, attempt 2 (#70655)

Contributes to #40553
上级 5fc5c68d
......@@ -614,6 +614,8 @@ public:
unsigned char lvSingleDefDisqualifyReason = 'H';
#endif
unsigned char lvAllDefsAreNoGc : 1; // For pinned locals: true if all defs of this local are no-gc
#if FEATURE_MULTIREG_ARGS
regNumber lvRegNumForSlot(unsigned slotNum)
{
......
......@@ -1104,6 +1104,11 @@ public:
return true;
}
bool IsNotGcDef() const
{
return IsIntegralConst(0) || IsLocalAddrExpr();
}
// LIR flags
// These helper methods, along with the flag values they manipulate, are defined in lir.h
//
......
......@@ -4234,49 +4234,57 @@ void Compiler::lvaMarkLclRefs(GenTree* tree, BasicBlock* block, Statement* stmt,
/* Is this an assignment to a local variable? */
if (op1->gtOper == GT_LCL_VAR && op2->gtType != TYP_BOOL)
if (op1->gtOper == GT_LCL_VAR)
{
/* Only simple assignments allowed for booleans */
LclVarDsc* varDsc = lvaGetDesc(op1->AsLclVarCommon());
if (tree->gtOper != GT_ASG)
if (varDsc->lvPinned && varDsc->lvAllDefsAreNoGc)
{
goto NOT_BOOL;
if (!op2->IsNotGcDef())
{
varDsc->lvAllDefsAreNoGc = false;
}
}
/* Is the RHS clearly a boolean value? */
switch (op2->gtOper)
if (op2->gtType != TYP_BOOL)
{
unsigned lclNum;
/* Only simple assignments allowed for booleans */
case GT_CNS_INT:
if (tree->gtOper != GT_ASG)
{
goto NOT_BOOL;
}
if (op2->AsIntCon()->gtIconVal == 0)
{
break;
}
if (op2->AsIntCon()->gtIconVal == 1)
{
break;
}
/* Is the RHS clearly a boolean value? */
// Not 0 or 1, fall through ....
FALLTHROUGH;
switch (op2->gtOper)
{
case GT_CNS_INT:
default:
if (op2->AsIntCon()->gtIconVal == 0)
{
break;
}
if (op2->AsIntCon()->gtIconVal == 1)
{
break;
}
if (op2->OperIsCompare())
{
break;
}
// Not 0 or 1, fall through ....
FALLTHROUGH;
NOT_BOOL:
default:
lclNum = op1->AsLclVarCommon()->GetLclNum();
noway_assert(lclNum < lvaCount);
if (op2->OperIsCompare())
{
break;
}
lvaTable[lclNum].lvIsBoolean = false;
break;
NOT_BOOL:
varDsc->lvIsBoolean = false;
break;
}
}
}
}
......@@ -4331,7 +4339,8 @@ void Compiler::lvaMarkLclRefs(GenTree* tree, BasicBlock* block, Statement* stmt,
{
if (lvaVarAddrExposed(lclNum))
{
varDsc->lvIsBoolean = false;
varDsc->lvIsBoolean = false;
varDsc->lvAllDefsAreNoGc = false;
}
if (tree->gtOper == GT_LCL_FLD)
......@@ -4803,6 +4812,8 @@ void Compiler::lvaComputeRefCounts(bool isRecompute, bool setSlotNumbers)
{
varDsc->lvSingleDef = varDsc->lvIsParam;
varDsc->lvSingleDefRegCandidate = varDsc->lvIsParam;
varDsc->lvAllDefsAreNoGc = (varDsc->lvImplicitlyReferenced == false);
}
}
......@@ -4921,6 +4932,13 @@ void Compiler::lvaComputeRefCounts(bool isRecompute, bool setSlotNumbers)
varDsc->lvImplicitlyReferenced = 1;
}
}
if (varDsc->lvPinned && varDsc->lvAllDefsAreNoGc)
{
varDsc->lvPinned = 0;
JITDUMP("V%02u was unpinned as all def candidates were local.\n", lclNum);
}
}
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册