diff options
author | Brian Bohe <brianbohe@gmail.com> | 2019-03-29 16:38:53 -0700 |
---|---|---|
committer | Bruce Forstall <brucefo@microsoft.com> | 2019-03-29 16:38:53 -0700 |
commit | 493023e6e1bc03ec04ee4aa9f390e37dc4d0906e (patch) | |
tree | a7e0994c783217f0bcbc0fe23a2bbf5517a2b79d /src/jit/codegencommon.cpp | |
parent | 1df87c785e0e43392abf4bcba56e2bf4d9249fd4 (diff) | |
download | coreclr-493023e6e1bc03ec04ee4aa9f390e37dc4d0906e.tar.gz coreclr-493023e6e1bc03ec04ee4aa9f390e37dc4d0906e.tar.bz2 coreclr-493023e6e1bc03ec04ee4aa9f390e37dc4d0906e.zip |
A new way of tracking variables (#23373)
* Defining VariableLiveRange class
* Adding some typedefs to avoid rewriting
* Defining VariableLiveDescriptor class
* Initializing VariableLiveRange structures before BasicBlock code is being generated
* Getting a siVarLoc for variable homes from a given LclVarDsc and stack level
* Defining VariableLiveKeeper class
* Reporting VariableLiveRanges on changes of variable livenesss or variable homes
* Adding USING_VARIABLE_LIVE_RANGE flag to enable disable VariableLiveRange
* Send VariableLiveRanges to debugger
* Reporting variable homes on prolog
* Wrong argument
* Miss to change variable homes count before sending them to debugger
* Adding dumper of VariableLiveRanges for each blocks and end of code generation
* Close all open VaribleLiveRanges on last BasicBlock
* Changing order of properties initialization on VariableLiveRange constructor
* Type error on assignation
* Rephrasing comments, moving dumps and fixing typos
* Changing const VARSET_TP* for VARSET_VALARG_TP on args
* Variable home was variable location in VariableLiveRange context
* Rephrase and rename of VariableLiveKeeper properties
* Missing some renames
* Adding const where BasicBlock should not be modified
* siBeginBlock and siInit have support for debug code for VariableLiveRange and siScope info
* Adding USING_VARIABLE_LIVE_RANGE flags on methods definition.
* Variable home -> variable location
* Renaming and rephrasing names and uses of VariableLiveRange
* Moving LiveRangeDumper ctor to class declation
* Removing destructors
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Removing blank spaces and reordering functions inside class definition
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Miss to increment the index after refactoring
* Logic for keeping the last BasicBlock end IL offset is shared between siScope and VariableLiverange for debug code
* Missing to print on debug the last block VariableLiveRanges
* Avoid updating VariableLiveRange when unspilling and dying at the same assembly instruction
* Rephrasing #ifs and #ifdefs
* Calling VariableLiveKeeper in one line
* Avoid copying siVarLoc on genSetScopeInfo
* Removing unused args from eeSetLVinfo
* Changing VariableLiveKeeper ctor
* Typo
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Updating VariableLiveDescriptor ctor
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Error on first argument
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Changing reference for pointer
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Renaming assembly offset -> native offset
* removing unnecesary comments and asserts
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Update VariableLiveRange dump message
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Moving VariableLiveRanges classes inside VariableLiveKeeper
* Wrong flag name
* Adding documentation about how we track variables for debug info
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Adding opened issues to doc file
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Changing dump tittle
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Renaming VariableLiveKeeper property
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Update documentation
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Updating comments on flags
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
* Setting Scope Info as default way of tracking variables for debug info
Signed-off-by: Brian Bohe <brianbohe@gmail.com>
Diffstat (limited to 'src/jit/codegencommon.cpp')
-rw-r--r-- | src/jit/codegencommon.cpp | 114 |
1 files changed, 98 insertions, 16 deletions
diff --git a/src/jit/codegencommon.cpp b/src/jit/codegencommon.cpp index e54342a1d5..781f0fc549 100644 --- a/src/jit/codegencommon.cpp +++ b/src/jit/codegencommon.cpp @@ -694,6 +694,11 @@ void Compiler::compChangeLife(VARSET_VALARG_TP newLife) VarSetOps::RemoveElemD(this, codeGen->gcInfo.gcVarPtrSetCur, deadVarIndex); JITDUMP("\t\t\t\t\t\t\tV%02u becoming dead\n", varNum); } + +#ifdef USING_VARIABLE_LIVE_RANGE + VariableLiveKeeper* varLiveKeeper = getVariableLiveKeeper(); + varLiveKeeper->siEndVariableLiveRange(varNum); +#endif // USING_VARIABLE_LIVE_RANGE } VarSetOps::Iter bornIter(this, bornSet); @@ -731,7 +736,13 @@ void Compiler::compChangeLife(VARSET_VALARG_TP newLife) VarSetOps::AddElemD(this, codeGen->gcInfo.gcVarPtrSetCur, bornVarIndex); JITDUMP("\t\t\t\t\t\t\tV%02u becoming live\n", varNum); } + +#ifdef USING_VARIABLE_LIVE_RANGE + VariableLiveKeeper* varLiveKeeper = getVariableLiveKeeper(); + varLiveKeeper->siStartVariableLiveRange(varDsc, varNum); +#endif // USING_VARIABLE_LIVE_RANGE } + #ifdef USING_SCOPE_INFO codeGen->siUpdate(); #endif // USING_SCOPE_INFO @@ -2284,6 +2295,13 @@ void CodeGen::genGenerateCode(void** codePtr, ULONG* nativeSizeOfCode) genSetScopeInfo(); +#if defined(USING_VARIABLE_LIVE_RANGE) && defined(DEBUG) + if (compiler->verbose) + { + compiler->getVariableLiveKeeper()->dumpLvaVariableLiveRanges(); + } +#endif // defined(USING_VARIABLE_LIVE_RANGE) && defined(DEBUG) + #ifdef LATE_DISASM unsigned finalHotCodeSize; unsigned finalColdCodeSize; @@ -7631,13 +7649,12 @@ void CodeGen::genFnProlog() printf("\n__prolog:\n"); } #endif -#ifdef USING_SCOPE_INFO + if (compiler->opts.compScopeInfo && (compiler->info.compVarScopesCount > 0)) { // Create new scopes for the method-parameters for the prolog-block. psiBegProlog(); } -#endif // USING_SCOPE_INFO #ifdef DEBUG @@ -8284,12 +8301,11 @@ void CodeGen::genFnProlog() genPrologPadForReJit(); getEmitter()->emitMarkPrologEnd(); } -#ifdef USING_SCOPE_INFO if (compiler->opts.compScopeInfo && (compiler->info.compVarScopesCount > 0)) { psiEndProlog(); } -#endif // USING_SCOPE_INFO + if (hasGCRef) { getEmitter()->emitSetFrameRangeGCRs(GCrefLo, GCrefHi); @@ -10478,7 +10494,22 @@ void CodeGen::genSetScopeInfo() } #endif - if (compiler->info.compVarScopesCount == 0) + unsigned varsLocationsCount = 0; + +#ifdef USING_SCOPE_INFO + if (compiler->info.compVarScopesCount > 0) + { + varsLocationsCount = siScopeCnt + psiScopeCnt; + } +#else // USING_SCOPE_INFO + +#ifdef USING_VARIABLE_LIVE_RANGE + varsLocationsCount = (unsigned int)compiler->getVariableLiveKeeper()->getLiveRangesCount(); +#endif // USING_VARIABLE_LIVE_RANGE + +#endif // USING_SCOPE_INFO + + if (varsLocationsCount == 0) { compiler->eeSetLVcount(0); compiler->eeSetLVdone(); @@ -10487,22 +10518,27 @@ void CodeGen::genSetScopeInfo() noway_assert(compiler->opts.compScopeInfo && (compiler->info.compVarScopesCount > 0)); - unsigned varsHomeCount = 0; -#ifdef USING_SCOPE_INFO - varsHomeCount = siScopeCnt + psiScopeCnt; -#endif // USING_SCOPE_INFO - compiler->eeSetLVcount(varsHomeCount); + compiler->eeSetLVcount(varsLocationsCount); #ifdef DEBUG - genTrnslLocalVarCount = varsHomeCount; - if (varsHomeCount) + genTrnslLocalVarCount = varsLocationsCount; + if (varsLocationsCount) { - genTrnslLocalVarInfo = new (compiler, CMK_DebugOnly) TrnslLocalVarInfo[varsHomeCount]; + genTrnslLocalVarInfo = new (compiler, CMK_DebugOnly) TrnslLocalVarInfo[varsLocationsCount]; } #endif #ifdef USING_SCOPE_INFO genSetScopeInfoUsingsiScope(); +#else // USING_SCOPE_INFO +#ifdef USING_VARIABLE_LIVE_RANGE + // We can have one of both flags defined, both, or none. Specially if we need to compare both + // both results. But we cannot report both to the debugger, since there would be overlapping + // intervals, and may not indicate the same variable location. + + genSetScopeInfoUsingVariableRanges(); + +#endif // USING_VARIABLE_LIVE_RANGE #endif // USING_SCOPE_INFO compiler->eeSetLVdone(); @@ -10579,6 +10615,53 @@ void CodeGen::genSetScopeInfoUsingsiScope() } #endif // USING_SCOPE_INFO +#ifdef USING_VARIABLE_LIVE_RANGE +//------------------------------------------------------------------------ +// genSetScopeInfoUsingVariableRanges: Call "genSetScopeInfo" with the +// "VariableLiveRanges" created for the arguments, special arguments and +// IL local variables. +// +// Notes: +// This function is called from "genSetScopeInfo" once the code is generated +// and we want to send debug info to the debugger. +// +void CodeGen::genSetScopeInfoUsingVariableRanges() +{ + VariableLiveKeeper* varLiveKeeper = compiler->getVariableLiveKeeper(); + unsigned int liveRangeIndex = 0; + + for (unsigned int varNum = 0; varNum < compiler->info.compLocalsCount; varNum++) + { + LclVarDsc* varDsc = compiler->lvaGetDesc(varNum); + + if (compiler->compMap2ILvarNum(varNum) != (unsigned int)ICorDebugInfo::UNKNOWN_ILNUM) + { + VariableLiveKeeper::LiveRangeList* liveRanges = varLiveKeeper->getLiveRangesForVar(varNum); + + for (VariableLiveKeeper::VariableLiveRange& liveRange : *liveRanges) + { + UNATIVE_OFFSET startOffs = liveRange.m_StartEmitLocation.CodeOffset(getEmitter()); + UNATIVE_OFFSET endOffs = liveRange.m_EndEmitLocation.CodeOffset(getEmitter()); + + if (varDsc->lvIsParam && (startOffs == endOffs)) + { + // If the length is zero, it means that the prolog is empty. In that case, + // CodeGen::genSetScopeInfo will report the liveness of all arguments + // as spanning the first instruction in the method, so that they can + // at least be inspected on entry to the method. + endOffs++; + } + + genSetScopeInfo(liveRangeIndex, startOffs, endOffs - startOffs, varNum, + varNum /* I dont know what is the which in eeGetLvInfo */, true, + &liveRange.m_VarLocation); + liveRangeIndex++; + } + } + } +} +#endif // USING_VARIABLE_LIVE_RANGE + //------------------------------------------------------------------------ // genSetScopeInfo: Record scope information for debug info // @@ -10612,7 +10695,6 @@ void CodeGen::genSetScopeInfo(unsigned which, // so we don't need this code. // Is this a varargs function? - if (compiler->info.compIsVarArgs && varNum != compiler->lvaVarargsHandleArg && varNum < compiler->info.compArgsCount && !compiler->lvaTable[varNum].lvIsRegArg) { @@ -10673,7 +10755,7 @@ void CodeGen::genSetScopeInfo(unsigned which, #endif // DEBUG - compiler->eeSetLVinfo(which, startOffs, length, ilVarNum, LVnum, name, avail, varLoc); + compiler->eeSetLVinfo(which, startOffs, length, ilVarNum, *varLoc); } /*****************************************************************************/ @@ -10728,7 +10810,7 @@ const char* CodeGen::siStackVarName(size_t offs, size_t size, unsigned reg, unsi for (unsigned i = 0; i < genTrnslLocalVarCount; i++) { - if ((genTrnslLocalVarInfo[i].tlviVarLoc.vlIsOnStk((regNumber)reg, stkOffs)) && + if ((genTrnslLocalVarInfo[i].tlviVarLoc.vlIsOnStack((regNumber)reg, stkOffs)) && (genTrnslLocalVarInfo[i].tlviAvailable == true) && (genTrnslLocalVarInfo[i].tlviStartPC <= offs + size) && (genTrnslLocalVarInfo[i].tlviStartPC + genTrnslLocalVarInfo[i].tlviLength > offs)) { |