@@ -1632,6 +1632,11 @@ static void licm(VPlan &Plan) {
16321632
16331633void VPlanTransforms::truncateToMinimalBitwidths (
16341634 VPlan &Plan, const MapVector<Instruction *, uint64_t > &MinBWs) {
1635+ #ifndef NDEBUG
1636+ // Count the processed recipes and cross check the count later with MinBWs
1637+ // size, to make sure all entries in MinBWs have been handled.
1638+ unsigned NumProcessedRecipes = 0 ;
1639+ #endif
16351640 // Keep track of created truncates, so they can be re-used. Note that we
16361641 // cannot use RAUW after creating a new truncate, as this would could make
16371642 // other uses have different types for their operands, making them invalidly
@@ -1654,12 +1659,38 @@ void VPlanTransforms::truncateToMinimalBitwidths(
16541659 if (!NewResSizeInBits)
16551660 continue ;
16561661
1662+ #ifndef NDEBUG
1663+ NumProcessedRecipes++;
1664+ #endif
16571665 // If the value wasn't vectorized, we must maintain the original scalar
16581666 // type. Skip those here, after incrementing NumProcessedRecipes. Also
16591667 // skip casts which do not need to be handled explicitly here, as
16601668 // redundant casts will be removed during recipe simplification.
1661- if (isa<VPReplicateRecipe, VPWidenCastRecipe>(&R))
1669+ if (isa<VPReplicateRecipe, VPWidenCastRecipe>(&R)) {
1670+ #ifndef NDEBUG
1671+ // If any of the operands is a live-in and not used by VPWidenRecipe or
1672+ // VPWidenSelectRecipe, but in MinBWs, make sure it is counted as
1673+ // processed as well. When MinBWs is currently constructed, there is no
1674+ // information about whether recipes are widened or replicated and in
1675+ // case they are reciplicated the operands are not truncated. Counting
1676+ // them them here ensures we do not miss any recipes in MinBWs.
1677+ // TODO: Remove once the analysis is done on VPlan.
1678+ for (VPValue *Op : R.operands ()) {
1679+ if (!Op->isLiveIn ())
1680+ continue ;
1681+ auto *UV = dyn_cast_or_null<Instruction>(Op->getUnderlyingValue ());
1682+ if (UV && MinBWs.contains (UV) && !ProcessedTruncs.contains (Op) &&
1683+ none_of (Op->users (),
1684+ IsaPred<VPWidenRecipe, VPWidenSelectRecipe>)) {
1685+ // Add an entry to ProcessedTruncs to avoid counting the same
1686+ // operand multiple times.
1687+ ProcessedTruncs[Op] = nullptr ;
1688+ NumProcessedRecipes += 1 ;
1689+ }
1690+ }
1691+ #endif
16621692 continue ;
1693+ }
16631694
16641695 Type *OldResTy = TypeInfo.inferScalarType (ResultVPV);
16651696 unsigned OldResSizeInBits = OldResTy->getScalarSizeInBits ();
@@ -1718,11 +1749,19 @@ void VPlanTransforms::truncateToMinimalBitwidths(
17181749 NewOp->insertBefore (&R);
17191750 } else {
17201751 PH->appendRecipe (NewOp);
1752+ #ifndef NDEBUG
1753+ auto *OpInst = dyn_cast<Instruction>(Op->getLiveInIRValue ());
1754+ bool IsContained = MinBWs.contains (OpInst);
1755+ NumProcessedRecipes += IsContained;
1756+ #endif
17211757 }
17221758 }
17231759
17241760 }
17251761 }
1762+
1763+ assert (MinBWs.size () == NumProcessedRecipes &&
1764+ " some entries in MinBWs haven't been processed" );
17261765}
17271766
17281767// / Remove BranchOnCond recipes with true conditions together with removing
0 commit comments