Index: llvm/trunk/lib/Transforms/IPO/ArgumentPromotion.cpp =================================================================== --- llvm/trunk/lib/Transforms/IPO/ArgumentPromotion.cpp +++ llvm/trunk/lib/Transforms/IPO/ArgumentPromotion.cpp @@ -124,6 +124,10 @@ } else if (I->use_empty()) { // Dead argument (which are always marked as promotable) ++NumArgumentsDead; + + // There may be remaining metadata uses of the argument for things like + // llvm.dbg.value. Replace them with undef. + I->replaceAllUsesWith(UndefValue::get(I->getType())); } else { // Okay, this is being promoted. This means that the only uses are loads // or GEPs which are only used by loads Index: llvm/trunk/test/Transforms/ArgumentPromotion/pr33641_remove_arg_dbgvalue.ll =================================================================== --- llvm/trunk/test/Transforms/ArgumentPromotion/pr33641_remove_arg_dbgvalue.ll +++ llvm/trunk/test/Transforms/ArgumentPromotion/pr33641_remove_arg_dbgvalue.ll @@ -0,0 +1,38 @@ +; RUN: opt -argpromotion -verify -dse -S %s -o - | FileCheck %s + +; Fix for PR33641. ArgumentPromotion removed the argument to bar but left the call to +; dbg.value which still used the removed argument. + +%p_t = type i16* +%fun_t = type void (%p_t)* + +define void @foo() { + %tmp = alloca %fun_t + store %fun_t @bar, %fun_t* %tmp + ret void +} + +define internal void @bar(%p_t %p) { + call void @llvm.dbg.value(metadata %p_t %p, i64 0, metadata !4, metadata !5), !dbg !6 + ret void +} + +declare void @llvm.dbg.value(metadata, i64, metadata, metadata) + +!llvm.dbg.cu = !{!0} +!llvm.module.flags = !{!2} + +!0 = distinct !DICompileUnit(language: DW_LANG_C, file: !1) +!1 = !DIFile(filename: "test.c", directory: "") +!2 = !{i32 2, !"Debug Info Version", i32 3} +!3 = distinct !DISubprogram(name: "bar", unit: !0) +!4 = !DILocalVariable(name: "p", scope: !3) +!5 = !DIExpression() +!6 = !DILocation(line: 1, column: 1, scope: !3) + +; The %p argument should be removed, and the use of it in dbg.value should be +; changed to undef. +; CHECK: define internal void @bar() { +; CHECK-NEXT: call void @llvm.dbg.value(metadata i16* undef +; CHECK-NEXT: ret void +; CHECK-NEXT: }