[llvm] e8bf011 - [LV] Emit better debug and opt-report messages when vectorization is disallowed in the LoopVectorizer (#158513)

via llvm-commits llvm-commits at lists.llvm.org
Tue Dec 2 03:46:46 PST 2025


Author: Tibor Győri
Date: 2025-12-02T11:46:41Z
New Revision: e8bf01108589be73f4057fe285cd7e04b4143f4a

URL: https://github.com/llvm/llvm-project/commit/e8bf01108589be73f4057fe285cd7e04b4143f4a
DIFF: https://github.com/llvm/llvm-project/commit/e8bf01108589be73f4057fe285cd7e04b4143f4a.diff

LOG: [LV] Emit better debug and opt-report messages when vectorization is disallowed in the LoopVectorizer (#158513)

While looking into fixing #158499, I found some other cases where the
messages emitted could be improved. This PR improves both the messages
printed to the debug output and the missed-optimization messages in
cases where:

- loop vectorization is explicitly disabled
- loop vectorization is implicitly disabled by disabling all loop
transformations
- loop vectorization is set to happen only where explicitly enabled

A branch that should currently be unreachable is also added. If the
related logic ever breaks (eg. due to changes to getForce() or the
ForceKind enum) this should alert devs and users. New test cases are
also added to verify that the correct messages (and only them) are
outputted.

---------

Co-authored-by: GYT <tiborgyri at gmail.com>
Co-authored-by: Florian Hahn <flo at fhahn.com>

Added: 
    llvm/test/Transforms/LoopVectorize/diag-disabled-vectorization-msgs.ll

Modified: 
    llvm/include/llvm/Transforms/Vectorize/LoopVectorizationLegality.h
    llvm/lib/Transforms/Vectorize/LoopVectorizationLegality.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/Transforms/Vectorize/LoopVectorizationLegality.h b/llvm/include/llvm/Transforms/Vectorize/LoopVectorizationLegality.h
index ecbd0ef7df5e5..1b37aabaafae8 100644
--- a/llvm/include/llvm/Transforms/Vectorize/LoopVectorizationLegality.h
+++ b/llvm/include/llvm/Transforms/Vectorize/LoopVectorizationLegality.h
@@ -196,6 +196,15 @@ class LoopVectorizeHints {
 
   /// Interface to emit optimization remarks.
   OptimizationRemarkEmitter &ORE;
+
+  /// Reports a condition where loop vectorization is disallowed: prints
+  /// \p DebugMsg for debugging purposes along with the corresponding
+  /// optimization remark \p RemarkName, with \p RemarkMsg as the user-facing
+  /// message. The loop \p L is used for the location of the remark.
+  void reportDisallowedVectorization(const StringRef DebugMsg,
+                                     const StringRef RemarkName,
+                                     const StringRef RemarkMsg,
+                                     const Loop *L) const;
 };
 
 /// This holds vectorization requirements that must be verified late in

diff  --git a/llvm/lib/Transforms/Vectorize/LoopVectorizationLegality.cpp b/llvm/lib/Transforms/Vectorize/LoopVectorizationLegality.cpp
index f2e9c3146b0e8..26e2d44bdc9e6 100644
--- a/llvm/lib/Transforms/Vectorize/LoopVectorizationLegality.cpp
+++ b/llvm/lib/Transforms/Vectorize/LoopVectorizationLegality.cpp
@@ -179,17 +179,37 @@ void LoopVectorizeHints::setAlreadyVectorized() {
   IsVectorized.Value = 1;
 }
 
+void LoopVectorizeHints::reportDisallowedVectorization(
+    const StringRef DebugMsg, const StringRef RemarkName,
+    const StringRef RemarkMsg, const Loop *L) const {
+  LLVM_DEBUG(dbgs() << "LV: Not vectorizing: " << DebugMsg << ".\n");
+  ORE.emit(OptimizationRemarkMissed(LV_NAME, RemarkName, L->getStartLoc(),
+                                    L->getHeader())
+           << "loop not vectorized: " << RemarkMsg);
+}
+
 bool LoopVectorizeHints::allowVectorization(
     Function *F, Loop *L, bool VectorizeOnlyWhenForced) const {
   if (getForce() == LoopVectorizeHints::FK_Disabled) {
-    LLVM_DEBUG(dbgs() << "LV: Not vectorizing: #pragma vectorize disable.\n");
-    emitRemarkWithHints();
+    if (Force.Value == LoopVectorizeHints::FK_Disabled) {
+      reportDisallowedVectorization("#pragma vectorize disable",
+                                    "MissedExplicitlyDisabled",
+                                    "vectorization is explicitly disabled", L);
+    } else if (hasDisableAllTransformsHint(L)) {
+      reportDisallowedVectorization("loop hasDisableAllTransformsHint",
+                                    "MissedTransformsDisabled",
+                                    "loop transformations are disabled", L);
+    } else {
+      llvm_unreachable("loop vect disabled for an unknown reason");
+    }
     return false;
   }
 
   if (VectorizeOnlyWhenForced && getForce() != LoopVectorizeHints::FK_Enabled) {
-    LLVM_DEBUG(dbgs() << "LV: Not vectorizing: No #pragma vectorize enable.\n");
-    emitRemarkWithHints();
+    reportDisallowedVectorization(
+        "VectorizeOnlyWhenForced is set, and no #pragma vectorize enable",
+        "MissedForceOnly", "only vectorizing loops that explicitly request it",
+        L);
     return false;
   }
 

diff  --git a/llvm/test/Transforms/LoopVectorize/diag-disabled-vectorization-msgs.ll b/llvm/test/Transforms/LoopVectorize/diag-disabled-vectorization-msgs.ll
new file mode 100644
index 0000000000000..31454401876b6
--- /dev/null
+++ b/llvm/test/Transforms/LoopVectorize/diag-disabled-vectorization-msgs.ll
@@ -0,0 +1,94 @@
+; REQUIRES: asserts
+
+; TEST 1
+; Checks that we emit only the correct debug messages and
+; optimization remark when the loop vectorizer is disabled by loop metadata.
+; RUN: opt -S -passes=loop-vectorize -pass-remarks=loop-vectorize \
+; RUN:     -pass-remarks-missed=loop-vectorize \
+; RUN:     -pass-remarks-analysis=loop-vectorize -debug \
+; RUN:     < %s 2>&1 | FileCheck --check-prefixes=METADATA,ALL %s
+; TEST 2
+; Checks that we emit only the correct debug messages and
+; optimization remark when the loop is not vectorized due to the
+; vectorize-forced-only pass option being set.
+; Strip metadata for FORCEDONLY run, keep it for METADATA run
+; RUN: sed 's/,[[:space:]]*!llvm\.loop[[:space:]]*!0//' %s | \
+; RUN: opt -S -passes='loop-vectorize<vectorize-forced-only>' \
+; RUN:   -pass-remarks=loop-vectorize \
+; RUN:   -pass-remarks-missed=loop-vectorize \
+; RUN:   -pass-remarks-analysis=loop-vectorize -debug \
+; RUN:   2>&1 | FileCheck --check-prefixes=FORCEDONLY,ALL %s
+; TEST 3
+; Checks that we emit only the correct debug messages and
+; optimization remark when the loop vectorizer is disabled by loop metadata
+; that requests no loop transformations.
+; RUN: opt -S -passes=loop-vectorize -pass-remarks=loop-vectorize \
+; RUN:     -pass-remarks-missed=loop-vectorize \
+; RUN:     -pass-remarks-analysis=loop-vectorize -debug \
+; RUN:     -force-vector-interleave=1 -force-vector-width=2 \
+; RUN:     < %s 2>&1 | FileCheck --check-prefix=ALL %s
+
+; ALL-LABEL: 'disabled_loop_vectorization' from <stdin>
+; ALL-NOT: LV: We can vectorize this loop
+; ALL-NOT: LV: Not vectorizing: loop hasDisableAllTransformsHint
+; ALL-NOT: LV: Not vectorizing: Disabled/already vectorized
+; ALL-NOT: LV: Not vectorizing: Cannot prove legality
+;
+; METADATA-NOT: LV: Not vectorizing: VectorizeOnlyWhenForced is set
+; METADATA: LV: Loop hints: force=disabled
+; METADATA: LV: Not vectorizing: #pragma vectorize disable.
+; METADATA: remark:
+; METADATA-SAME: loop not vectorized: vectorization is explicitly disabled
+;
+; FORCEDONLY-NOT: LV: Not vectorizing: #pragma vectorize disable
+; FORCEDONLY: LV: Loop hints: force=?
+; FORCEDONLY: LV: Not vectorizing: VectorizeOnlyWhenForced is set, and no #pragma vectorize enable
+; FORCEDONLY: remark:
+; FORCEDONLY-SAME: loop not vectorized: only vectorizing loops that explicitly request it
+;
+; ALL: LV: Loop hints prevent vectorization
+define void @disabled_loop_vectorization(ptr %src) {
+entry:
+  br label %loop
+
+loop:
+  %iv = phi i64 [ 0, %entry ], [ %inc, %loop ]
+  %arrayidx = getelementptr inbounds nuw double, ptr %src, i64 %iv
+  store double 0.0, ptr %arrayidx, align 8
+  %inc = add nuw nsw i64 %iv, 1
+  %exitcond.not = icmp eq i64 %inc, 15
+  br i1 %exitcond.not, label %exit, label %loop, !llvm.loop !0
+
+exit:
+  ret void
+}
+!0 = distinct !{!0, !1}
+!1 = !{!"llvm.loop.vectorize.enable", i1 false}
+
+; ALL-LABEL: 'disable_nonforced' from <stdin>
+; ALL-NOT: LV: We can vectorize this loop
+; ALL-NOT: LV: Not vectorizing: #pragma vectorize disable.
+; ALL-NOT: LV: Not vectorizing: VectorizeOnlyWhenForced is set
+; ALL-NOT: LV: Not vectorizing: Disabled/already vectorized
+; ALL-NOT: LV: Not vectorizing: Cannot prove legality
+; ALL: LV: Loop hints: force=disabled
+; ALL: LV: Not vectorizing: loop hasDisableAllTransformsHint.
+; ALL: remark:
+; ALL-SAME: loop not vectorized: loop transformations are disabled
+; ALL: LV: Loop hints prevent vectorization
+define void @disable_nonforced(ptr nocapture %a, i32 %n) {
+entry:
+  br label %loop
+
+loop:
+  %iv = phi i32 [ %iv.next, %loop ], [ 0, %entry ]
+  %arrayidx = getelementptr inbounds i32, ptr %a, i32 %iv
+  store i32 %iv, ptr %arrayidx, align 4
+  %iv.next = add i32 %iv, 1
+  %exitcond = icmp eq i32 %iv.next, %n
+  br i1 %exitcond, label %end, label %loop, !llvm.loop !2
+
+end:
+  ret void
+}
+!2 = !{!2, !{!"llvm.loop.disable_nonforced"}}


        


More information about the llvm-commits mailing list