Skip to content
This repository was archived by the owner on Jan 23, 2023. It is now read-only.

Improvements for object stack allocation. #21950

Merged
merged 1 commit into from
Jan 15, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions src/jit/compiler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9269,6 +9269,10 @@ int cTreeFlagsIR(Compiler* comp, GenTree* tree)
{
chars += printf("[IND_TGTANYWHERE]");
}
if (tree->gtFlags & GTF_IND_TGT_NOT_HEAP)
{
chars += printf("[IND_TGT_NOT_HEAP]");
}
if (tree->gtFlags & GTF_IND_TLS_REF)
{
chars += printf("[IND_TLS_REF]");
Expand Down
28 changes: 0 additions & 28 deletions src/jit/gcencode.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4245,7 +4245,6 @@ void GCInfo::gcMakeRegPtrTable(
// Or in byref_OFFSET_FLAG for 'byref' pointer tracking
flags = (GcSlotFlags)(flags | GC_SLOT_INTERIOR);
}
gcUpdateFlagForStackAllocatedObjects(flags);

if (varDsc->lvPinned)
{
Expand Down Expand Up @@ -4345,7 +4344,6 @@ void GCInfo::gcMakeRegPtrTable(
{
flags = (GcSlotFlags)(flags | GC_SLOT_INTERIOR);
}
gcUpdateFlagForStackAllocatedObjects(flags);

GcStackSlotBase stackSlotBase = GC_SP_REL;
if (compiler->isFramePointerUsed())
Expand Down Expand Up @@ -4730,7 +4728,6 @@ void GCInfo::gcInfoRecordGCRegStateChange(GcInfoEncoder* gcInfoEncoder,
{
regFlags = (GcSlotFlags)(regFlags | GC_SLOT_INTERIOR);
}
gcUpdateFlagForStackAllocatedObjects(regFlags);

RegSlotIdKey rskey(regNum, regFlags);
GcSlotId regSlotId;
Expand Down Expand Up @@ -4821,7 +4818,6 @@ void GCInfo::gcMakeVarPtrTable(GcInfoEncoder* gcInfoEncoder, MakeRegPtrMode mode
{
flags = (GcSlotFlags)(flags | GC_SLOT_INTERIOR);
}
gcUpdateFlagForStackAllocatedObjects(flags);

if ((lowBits & pinned_OFFSET_FLAG) != 0)
{
Expand Down Expand Up @@ -4925,30 +4921,6 @@ void GCInfo::gcInfoRecordGCStackArgsDead(GcInfoEncoder* gcInfoEncoder,
}
}

//------------------------------------------------------------------------
// gcUpdateFlagForStackAllocatedObjects: Update the flags to handle a possibly stack-allocated object.
// allocation.
// Arguments:
// flags - flags to update
//
//
// Notes:
// TODO-ObjectStackAllocation: This is a temporary conservative implementation.
// Currently variables pointing to heap and/or stack allocated objects have type TYP_REF so we
// conservatively report them as INTERIOR.
// Ideally we should have the following types for object pointers:
// 1. TYP_I_IMPL for variables always pointing to stack-allocated objects (not reporting to GC)
// 2. TYP_REF for variables always pointing to heap-allocated objects (reporting as normal objects to GC)
// 3. TYP_BYREF for variables that may point to the stack or to the heap (reporting as interior objects to GC)

void GCInfo::gcUpdateFlagForStackAllocatedObjects(GcSlotFlags& flags)
{
if ((compiler->optMethodFlags & OMF_HAS_OBJSTACKALLOC) != 0)
{
flags = (GcSlotFlags)(flags | GC_SLOT_INTERIOR);
}
}

#undef GCENCODER_WITH_LOGGING

#endif // !JIT32_GCENCODER
Expand Down
6 changes: 6 additions & 0 deletions src/jit/gcinfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -267,6 +267,12 @@ GCInfo::WriteBarrierForm GCInfo::gcIsWriteBarrierCandidate(GenTree* tgt, GenTree
// This case occurs for Span<T>.
return WBF_NoBarrier;
}
if (tgt->gtFlags & GTF_IND_TGT_NOT_HEAP)
{
// This indirection is not from to the heap.
// This case occurs for stack-allocated objects.
return WBF_NoBarrier;
}
return gcWriteBarrierFormFromTargetAddress(tgt->gtOp.gtOp1);

case GT_LEA:
Expand Down
11 changes: 11 additions & 0 deletions src/jit/gentree.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9337,6 +9337,12 @@ void Compiler::gtDispNode(GenTree* tree, IndentStack* indentStack, __in __in_z _
--msgLength;
break;
}
if (tree->gtFlags & GTF_IND_TGT_NOT_HEAP)
{
printf("s");
--msgLength;
break;
}
if (tree->gtFlags & GTF_IND_INVARIANT)
{
printf("#");
Expand Down Expand Up @@ -14439,6 +14445,11 @@ GenTree* Compiler::gtNewTempAssign(
{
ok = true;
}
// 3) TYP_BYREF = TYP_REF when object stack allocation is enabled
else if (JitConfig.JitObjectStackAllocation() && (dstTyp == TYP_BYREF) && (valTyp == TYP_REF))
{
ok = true;
}

if (!ok)
{
Expand Down
10 changes: 7 additions & 3 deletions src/jit/gentree.h
Original file line number Diff line number Diff line change
Expand Up @@ -798,6 +798,7 @@ struct GenTree
#define GTF_INX_REFARR_LAYOUT 0x20000000 // GT_INDEX
#define GTF_INX_STRING_LAYOUT 0x40000000 // GT_INDEX -- this uses the special string array layout

#define GTF_IND_TGT_NOT_HEAP 0x80000000 // GT_IND -- the target is not on the heap
#define GTF_IND_VOLATILE 0x40000000 // GT_IND -- the load or store must use volatile sematics (this is a nop on X86)
#define GTF_IND_NONFAULTING 0x20000000 // Operations for which OperIsIndir() is true -- An indir that cannot fault.
// Same as GTF_ARRLEN_NONFAULTING.
Expand All @@ -818,7 +819,7 @@ struct GenTree

#define GTF_IND_FLAGS \
(GTF_IND_VOLATILE | GTF_IND_TGTANYWHERE | GTF_IND_NONFAULTING | GTF_IND_TLS_REF | \
GTF_IND_UNALIGNED | GTF_IND_INVARIANT | GTF_IND_ARR_INDEX)
GTF_IND_UNALIGNED | GTF_IND_INVARIANT | GTF_IND_ARR_INDEX | GTF_IND_TGT_NOT_HEAP)

#define GTF_CLS_VAR_VOLATILE 0x40000000 // GT_FIELD/GT_CLS_VAR -- same as GTF_IND_VOLATILE
#define GTF_CLS_VAR_INITCLASS 0x20000000 // GT_FIELD/GT_CLS_VAR -- same as GTF_FLD_INITCLASS
Expand Down Expand Up @@ -1807,8 +1808,11 @@ struct GenTree
while (node->gtOper == GT_COMMA)
{
node = node->gtGetOp2();
assert(node->gtType == oldType);
node->gtType = newType;
if (node->gtType != newType)
{
assert(node->gtType == oldType);
node->gtType = newType;
}
}
}

Expand Down
3 changes: 0 additions & 3 deletions src/jit/jitgcinfo.h
Original file line number Diff line number Diff line change
Expand Up @@ -231,9 +231,6 @@ class GCInfo
regPtrDsc* genStackPtrFirst,
regPtrDsc* genStackPtrLast);

// Update the flags for a stack allocated object
void gcUpdateFlagForStackAllocatedObjects(GcSlotFlags& flags);

#endif

#if MEASURE_PTRTAB_SIZE
Expand Down
4 changes: 0 additions & 4 deletions src/jit/morph.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16857,14 +16857,10 @@ void Compiler::fgMorph()
// local variable allocation on the stack.
ObjectAllocator objectAllocator(this); // PHASE_ALLOCATE_OBJECTS

// TODO-ObjectStackAllocation: Enable the optimization for architectures using
// JIT32_GCENCODER (i.e., x86).
#ifndef JIT32_GCENCODER
if (JitConfig.JitObjectStackAllocation() && opts.OptimizationEnabled())
{
objectAllocator.EnableObjectStackAllocation();
}
#endif // JIT32_GCENCODER

objectAllocator.Run();

Expand Down
Loading