@@ -33,6 +33,7 @@ void ProfileSynthesis::Run(ProfileSynthesisOption option)
3333 m_dfsTree = m_comp->fgComputeDfs ();
3434 m_loops = FlowGraphNaturalLoops::Find (m_dfsTree);
3535 m_improperLoopHeaders = m_loops->ImproperLoopHeaders ();
36+ m_entryBlock = m_comp->opts .IsOSR () ? m_comp->fgEntryBB : m_comp->fgFirstBB ;
3637
3738 // Retain or compute edge likelihood information
3839 //
@@ -71,13 +72,18 @@ void ProfileSynthesis::Run(ProfileSynthesisOption option)
7172 break ;
7273 }
7374
75+ // Save entry block's weight.
76+ // If the entry block is a loop header, its weight will be overwritten by ComputeCyclicProbabilities.
77+ //
78+ weight_t entryBlockWeight = m_entryBlock->bbWeight ;
79+
7480 // Determine cyclic probabilities
7581 //
7682 ComputeCyclicProbabilities ();
7783
7884 // Assign weights to entry points in the flow graph
7985 //
80- AssignInputWeights (option );
86+ AssignInputWeights (entryBlockWeight );
8187
8288 // Compute the block weights given the inputs and edge likelihoods
8389 //
@@ -108,12 +114,13 @@ void ProfileSynthesis::Run(ProfileSynthesisOption option)
108114 m_approximate = false ;
109115 m_overflow = false ;
110116 m_cappedCyclicProbabilities = 0 ;
117+ entryBlockWeight = m_entryBlock->bbWeight ;
111118
112119 // Regularize the edge likelihoods...
113120 //
114121 BlendLikelihoods ();
115122 ComputeCyclicProbabilities ();
116- AssignInputWeights (option );
123+ AssignInputWeights (entryBlockWeight );
117124 ComputeBlockWeights ();
118125
119126 // Increase blend factor and decrease synthetic loop likelihoods
@@ -975,7 +982,7 @@ void ProfileSynthesis::ComputeCyclicProbabilities(FlowGraphNaturalLoop* loop)
975982// fgAssignInputWeights: provide initial profile weights for all blocks
976983//
977984// Arguments:
978- // option - profile synthesis option
985+ // entryBlockWeight - total flow (including method call count) into the entry block
979986//
980987// Notes:
981988// For finallys we will pick up new entry weights when we process
@@ -986,51 +993,26 @@ void ProfileSynthesis::ComputeCyclicProbabilities(FlowGraphNaturalLoop* loop)
986993//
987994// Some parts of the jit are sensitive to the absolute weights.
988995//
989- void ProfileSynthesis::AssignInputWeights (ProfileSynthesisOption option )
996+ void ProfileSynthesis::AssignInputWeights (weight_t entryBlockWeight )
990997{
991- // Determine input weight for method entry
998+ // Determine input weight for method entry.
999+ // Ideally, we'd use fgCalledCount, but it may not be available yet.
9921000 //
993- BasicBlock* const entryBlock = m_comp-> opts . IsOSR () ? m_comp-> fgEntryBB : m_comp-> fgFirstBB ;
994- weight_t entryWeight = BB_UNITY_WEIGHT ;
1001+ weight_t entryWeight = entryBlockWeight ;
1002+ FlowGraphNaturalLoop* const loop = m_loops-> GetLoopByHeader (m_entryBlock) ;
9951003
996- switch (option )
1004+ if (loop != nullptr )
9971005 {
998- case ProfileSynthesisOption::BlendLikelihoods:
999- case ProfileSynthesisOption::RepairLikelihoods:
1000- {
1001- // Try and retain entryBlock's weight.
1002- // Easiest to do when the block has no preds.
1003- //
1004- if (entryBlock->hasProfileWeight ())
1005- {
1006- weight_t currentEntryWeight = entryBlock->bbWeight ;
1007-
1008- if (!Compiler::fgProfileWeightsEqual (currentEntryWeight, 0.0 , epsilon))
1009- {
1010- if (entryBlock->bbPreds == nullptr )
1011- {
1012- entryWeight = currentEntryWeight;
1013- }
1014- else
1015- {
1016- // TODO: something similar to how we compute fgCalledCount;
1017- // try and sum return weights?
1018- }
1019- }
1020- else
1021- {
1022- // Entry weight was zero or nearly zero, just use default
1023- }
1024- }
1025- else
1026- {
1027- // Entry was unprofiled, just use default
1028- }
1029- break ;
1030- }
1006+ const weight_t cyclicProbability = m_cyclicProbabilities[loop->GetIndex ()];
1007+ assert (cyclicProbability != BB_ZERO_WEIGHT);
1008+ entryWeight /= cyclicProbability;
1009+ }
10311010
1032- default :
1033- break ;
1011+ // Fall back to BB_UNITY_WEIGHT if we have zero entry weight
1012+ //
1013+ if (Compiler::fgProfileWeightsEqual (entryWeight, BB_ZERO_WEIGHT, epsilon))
1014+ {
1015+ entryWeight = BB_UNITY_WEIGHT;
10341016 }
10351017
10361018 // Reset existing weights
@@ -1042,8 +1024,8 @@ void ProfileSynthesis::AssignInputWeights(ProfileSynthesisOption option)
10421024
10431025 // Set entry weight
10441026 //
1045- JITDUMP (" Synthesis: entry " FMT_BB " has input weight " FMT_WT " \n " , entryBlock ->bbNum , entryWeight);
1046- entryBlock ->setBBProfileWeight (entryWeight);
1027+ JITDUMP (" Synthesis: entry " FMT_BB " has input weight " FMT_WT " \n " , m_entryBlock ->bbNum , entryWeight);
1028+ m_entryBlock ->setBBProfileWeight (entryWeight);
10471029
10481030 // Determine input weight for EH regions, if any.
10491031 //
@@ -1210,9 +1192,6 @@ void ProfileSynthesis::GaussSeidelSolver()
12101192 bool checkEntryExitWeight = true ;
12111193 bool showDetails = false ;
12121194
1213- // Remember the entry block
1214- //
1215- BasicBlock* const entryBlock = m_comp->opts .IsOSR () ? m_comp->fgEntryBB : m_comp->fgFirstBB ;
12161195 JITDUMP (" Synthesis solver: flow graph has %u improper loop headers\n " , m_improperLoopHeaders);
12171196
12181197 // This is an iterative solver, and it may require a lot of iterations
@@ -1268,7 +1247,7 @@ void ProfileSynthesis::GaussSeidelSolver()
12681247
12691248 // Some blocks have additional profile weights that don't come from flow edges.
12701249 //
1271- if (block == entryBlock )
1250+ if (block == m_entryBlock )
12721251 {
12731252 newWeight = block->bbWeight ;
12741253 entryWeight = newWeight;
@@ -1459,7 +1438,7 @@ void ProfileSynthesis::GaussSeidelSolver()
14591438 if (entryExitRelResidual > relResidual)
14601439 {
14611440 relResidual = entryExitRelResidual;
1462- relResidualBlock = entryBlock ;
1441+ relResidualBlock = m_entryBlock ;
14631442 }
14641443 }
14651444
0 commit comments