@@ -2721,6 +2721,21 @@ bool SpillManagerGRF::checkUniqueDefAligned(G4_DstRegRegion *dst,
27212721 return true ;
27222722}
27232723
2724+ bool SpillManagerGRF::isFirstLexicalDef (G4_DstRegRegion *dst) {
2725+ // Check whether dst is lexically first def
2726+ auto dcl = dst->getTopDcl ();
2727+ auto *defs = refs.getDefs (dcl);
2728+
2729+ // Check whether any def has lower lexical id than dst
2730+ for (auto & def : *defs) {
2731+ auto *defInst = std::get<0 >(def);
2732+ if (defInst->getLexicalId () < dst->getInst ()->getLexicalId ())
2733+ return false ;
2734+ }
2735+
2736+ return true ;
2737+ }
2738+
27242739// This function checks whether each spill dst region requires a
27252740// read-modify-write operation when inserting spill code. Dominator/unique defs
27262741// don't require redundant read operation. Dst regions that do not need RMW are
@@ -2746,7 +2761,9 @@ void SpillManagerGRF::updateRMWNeeded() {
27462761 // inner loop nest,
27472762 // Check3 : Flowgraph is reducible
27482763 // Check4 : Dcl is not a split around loop temp
2749- // RMW_Not_Needed = (Check0 || (Check1 && Check2 && Check3)) && Check4
2764+ // Check5 : bb is entryBB and spilledRegion is lexically first definition
2765+ // RMW_Not_Needed = Check5 || ((Check0 || (Check1 && Check2 && Check3)) &&
2766+ // Check4)
27502767 bool RMW_Needed = true ;
27512768
27522769 // Reason for Check4:
@@ -2800,6 +2817,11 @@ void SpillManagerGRF::updateRMWNeeded() {
28002817 }
28012818 }
28022819
2820+ // Check5
2821+ if (RMW_Needed && bb == builder_->kernel .fg .getEntryBB ()) {
2822+ RMW_Needed = !isFirstLexicalDef (spilledRegion);
2823+ }
2824+
28032825 return RMW_Needed;
28042826 };
28052827
@@ -2818,20 +2840,23 @@ void SpillManagerGRF::updateRMWNeeded() {
28182840 continue ;
28192841
28202842 auto dst = inst->getDst ();
2821- if (dst) {
2822- if (dst->getBase ()->isRegVar ()) {
2823- auto dstRegVar = dst->getBase ()->asRegVar ();
2824- if (dstRegVar && shouldSpillRegister (dstRegVar)) {
2825- if (getRFType (dstRegVar) == G4_GRF) {
2826- auto RMW_Needed = isRMWNeededForSpilledDst (bb, dst);
2827- if (!RMW_Needed) {
2828- // Any spilled dst region that doesnt need RMW
2829- // is added to noRMWNeeded set. This set is later
2830- // checked when inserting spill/fill code.
2831- noRMWNeeded.insert (dst);
2832- }
2833- }
2834- }
2843+ if (!dst)
2844+ continue ;
2845+
2846+ if (!dst->getBase ()->isRegVar ())
2847+ continue ;
2848+
2849+ auto dstRegVar = dst->getBase ()->asRegVar ();
2850+ if (dstRegVar && shouldSpillRegister (dstRegVar)) {
2851+ if (getRFType (dstRegVar) != G4_GRF)
2852+ continue ;
2853+
2854+ auto RMW_Needed = isRMWNeededForSpilledDst (bb, dst);
2855+ if (!RMW_Needed) {
2856+ // Any spilled dst region that doesnt need RMW
2857+ // is added to noRMWNeeded set. This set is later
2858+ // checked when inserting spill/fill code.
2859+ noRMWNeeded.insert (dst);
28352860 }
28362861 }
28372862 }
0 commit comments