[llvm] 9a423a2 - [InstCombine] Avoid propagating invalid metadata in FoldOpIntoSelect (#199155)

via llvm-commits llvm-commits at lists.llvm.org
Thu Jun 4 09:15:13 PDT 2026


Author: Muhammed Shiyas N
Date: 2026-06-05T00:15:08+08:00
New Revision: 9a423a22f4047a8e4daf678cc00393a8f3b7700a

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

LOG: [InstCombine] Avoid propagating invalid metadata in FoldOpIntoSelect (#199155)

Fixes #186471

FoldOpIntoSelect may create a select with a different result type from
the original instruction. The existing implementation blindly copied all
metadata from the original select, which could propagate invalid
type-specific metadata to the transformed instruction.

In particular, folding an fcmp over a floating-point select could copy
!fpmath metadata onto a non-FP select, producing invalid IR and causing
verifier failures.

This change preserves only metadata that remains valid for the
transformed select and propagates !fpmath only for FP-typed selects.
Debug locations are also preserved explicitly.

Added: 
    

Modified: 
    llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
    llvm/test/Transforms/InstCombine/select_meta.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
index e1ff11b8cf7c8..9182454b74bfb 100644
--- a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
@@ -1820,7 +1820,17 @@ Instruction *InstCombinerImpl::FoldOpIntoSelect(Instruction &Op, SelectInst *SI,
     NewTV = foldOperationIntoSelectOperand(Op, SI, TV, *this);
   if (!NewFV)
     NewFV = foldOperationIntoSelectOperand(Op, SI, FV, *this);
-  return SelectInst::Create(SI->getCondition(), NewTV, NewFV, "", nullptr, SI);
+
+  SelectInst *NewSel = SelectInst::Create(SI->getCondition(), NewTV, NewFV);
+
+  // Preserve metadata that remains valid for the transformed select.
+  NewSel->copyMetadata(*SI,
+                       {LLVMContext::MD_prof, LLVMContext::MD_unpredictable});
+
+  // Preserve source location information.
+  NewSel->setDebugLoc(SI->getDebugLoc());
+
+  return NewSel;
 }
 
 static Value *simplifyInstructionWithPHI(Instruction &I, PHINode *PN,

diff  --git a/llvm/test/Transforms/InstCombine/select_meta.ll b/llvm/test/Transforms/InstCombine/select_meta.ll
index f22b5a4fd3c5f..41f912482b90e 100644
--- a/llvm/test/Transforms/InstCombine/select_meta.ll
+++ b/llvm/test/Transforms/InstCombine/select_meta.ll
@@ -380,13 +380,28 @@ define <2 x float> @select_fdiv(i1 %cond, <2 x float> %x, <2 x float> %y) {
   ret <2 x float> %ret
 }
 
+;PR 186471
+
+define i1 @fold_select_fcmp_fpmath(i1 %cond, float %a) {
+; CHECK-LABEL: @fold_select_fcmp_fpmath(
+; CHECK-NEXT:    [[CMP:%.*]] = fcmp olt float [[A:%.*]], 0.000000e+00
+; CHECK-NEXT:    [[RES:%.*]] = select i1 [[COND:%.*]], i1 [[CMP]], i1 false
+; CHECK-NEXT:    ret i1 [[RES]]
+;
+  %lhs = select i1 %cond, float %a, float 0.000000e+00, !fpmath !4
+  %res = fcmp olt float %lhs, 0.000000e+00
+  ret i1 %res
+}
+
 !1 = !{!"branch_weights", i32 2, i32 10}
 !2 = !{!"branch_weights", i32 3, i32 10}
 !3 = !{}
+!4 = !{float 2.500000e+00}
 
 ;.
 ; CHECK: attributes #[[ATTR0:[0-9]+]] = { nounwind }
-; CHECK: attributes #[[ATTR1:[0-9]+]] = { nocallback nofree nosync nounwind speculatable willreturn memory(none) }
+; CHECK: attributes #[[ATTR1:[0-9]+]] = { nocallback nocreateundeforpoison nofree nosync nounwind speculatable willreturn memory(none) }
+; CHECK: attributes #[[ATTR2:[0-9]+]] = { nocallback nofree nosync nounwind speculatable willreturn memory(none) }
 ;.
 ; CHECK: [[PROF0]] = !{!"branch_weights", i32 2, i32 10}
 ; CHECK: [[PROF1]] = !{!"branch_weights", i32 10, i32 2}


        


More information about the llvm-commits mailing list