Skip to content

Commit

Permalink
Recognize more "local addr" trees as invariant (#68484)
Browse files Browse the repository at this point in the history
This will ensure we do not evaluate e.g. the retbuffer into a temp when
unnecessary.
  • Loading branch information
jakobbotsch authored Apr 25, 2022
1 parent 09dc0fe commit 7adf454
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 11 deletions.
1 change: 1 addition & 0 deletions src/coreclr/jit/compiler.h
Original file line number Diff line number Diff line change
Expand Up @@ -4108,6 +4108,7 @@ class Compiler
static LONG jitNestingLevel;
#endif // DEBUG

static bool impIsInvariant(const GenTree* tree);
static bool impIsAddressInLocal(const GenTree* tree, GenTree** lclVarTreeOut = nullptr);

void impMakeDiscretionaryInlineObservations(InlineInfo* pInlineInfo, InlineResult* inlineResult);
Expand Down
4 changes: 2 additions & 2 deletions src/coreclr/jit/gentree.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16308,7 +16308,7 @@ bool GenTree::IsLocalExpr(Compiler* comp, GenTreeLclVarCommon** pLclVarTree, Fie
// If this tree evaluates some sum of a local address and some constants,
// return the node for the local being addressed

GenTreeLclVarCommon* GenTree::IsLocalAddrExpr()
const GenTreeLclVarCommon* GenTree::IsLocalAddrExpr() const
{
if (OperGet() == GT_ADDR)
{
Expand Down Expand Up @@ -22865,7 +22865,7 @@ bool GenTreeLclFld::IsOffsetMisaligned() const

bool GenTree::IsInvariant() const
{
return OperIsConst() || Compiler::impIsAddressInLocal(this);
return OperIsConst() || IsLocalAddrExpr();
}

//------------------------------------------------------------------------
Expand Down
6 changes: 5 additions & 1 deletion src/coreclr/jit/gentree.h
Original file line number Diff line number Diff line change
Expand Up @@ -1916,7 +1916,11 @@ struct GenTree

// Simpler variant of the above which just returns the local node if this is an expression that
// yields an address into a local
GenTreeLclVarCommon* IsLocalAddrExpr();
const GenTreeLclVarCommon* IsLocalAddrExpr() const;
GenTreeLclVarCommon* IsLocalAddrExpr()
{
return const_cast<GenTreeLclVarCommon*>(static_cast<const GenTree*>(this)->IsLocalAddrExpr());
}

// Determine if this tree represents the value of an entire implicit byref parameter,
// and if so return the tree for the parameter.
Expand Down
41 changes: 33 additions & 8 deletions src/coreclr/jit/importer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18902,14 +18902,39 @@ bool Compiler::impIsValueType(typeInfo* pTypeInfo)
}
}

/*****************************************************************************
* Check to see if the tree is the address of a local or
the address of a field in a local.

*lclVarTreeOut will contain the GT_LCL_VAR tree when it returns true.

*/
//------------------------------------------------------------------------
// impIsInvariant: check if a tree (created during import) is invariant.
//
// Arguments:
// tree -- The tree
//
// Returns:
// true if it is invariant
//
// Remarks:
// This is a variant of GenTree::IsInvariant that is more suitable for use
// during import. Unlike that function, this one handles GT_FIELD nodes.
//
bool Compiler::impIsInvariant(const GenTree* tree)
{
return tree->OperIsConst() || impIsAddressInLocal(tree);
}

//------------------------------------------------------------------------
// impIsAddressInLocal:
// Check to see if the tree is the address of a local or
// the address of a field in a local.
// Arguments:
// tree -- The tree
// lclVarTreeOut -- [out] the local that this points into
//
// Returns:
// true if it points into a local
//
// Remarks:
// This is a variant of GenTree::IsLocalAddrExpr that is more suitable for
// use during import. Unlike that function, this one handles GT_FIELD nodes.
//
bool Compiler::impIsAddressInLocal(const GenTree* tree, GenTree** lclVarTreeOut)
{
if (tree->gtOper != GT_ADDR)
Expand Down Expand Up @@ -19520,7 +19545,7 @@ void Compiler::impInlineRecordArgInfo(InlineInfo* pInlineInfo,
INDEBUG(curArgVal->AsLclVar()->gtLclILoffs = argNum;)
}

if (curArgVal->IsInvariant())
if (impIsInvariant(curArgVal))
{
inlCurArgInfo->argIsInvariant = true;
if (inlCurArgInfo->argIsThis && (curArgVal->gtOper == GT_CNS_INT) && (curArgVal->AsIntCon()->gtIconVal == 0))
Expand Down

0 comments on commit 7adf454

Please sign in to comment.