--- /dev/null
+; Test keeping one module flag
+; RUN: llvm-reduce --abort-on-invalid-reduction --delta-passes=named-metadata --test=FileCheck --test-arg=--check-prefix=CHECK-INTERESTINGNESS0 --test-arg=%s --test-arg=--input-file %s -o %t.0
+; RUN: FileCheck --check-prefix=RESULT0 %s < %t.0
+
+; Test keeping two module flags
+; RUN: llvm-reduce --abort-on-invalid-reduction --delta-passes=named-metadata --test=FileCheck --test-arg=--check-prefix=CHECK-INTERESTINGNESS1 --test-arg=%s --test-arg=--input-file %s -o %t.1
+; RUN: FileCheck --check-prefix=RESULT1 %s < %t.1
+
+
+; Test removing all module flags
+; RUN: llvm-reduce --abort-on-invalid-reduction --delta-passes=named-metadata --test=FileCheck --test-arg=--check-prefix=CHECK-INTERESTINGNESS2 --test-arg=%s --test-arg=--input-file %s -o %t.2
+; RUN: FileCheck --check-prefix=RESULT2 %s < %t.2
+
+
+; CHECK-INTERESTINGNESS0: "openmp-device"
+
+; CHECK-INTERESTINGNESS1: "wchar_size"
+; CHECK-INTERESTINGNESS1: "openmp"
+
+; CHECK-INTERESTINGNESS2: !llvm.module.flags
+
+; RESULT0: !llvm.module.flags = !{!0}
+; RESULT0: !0 = !{i32 7, !"openmp-device", i32 50}
+
+
+; RESULT1: !llvm.module.flags = !{!0, !1}
+; RESULT1: !0 = !{i32 1, !"wchar_size", i32 4}
+; RESULT1: !1 = !{i32 7, !"openmp", i32 50}
+
+
+; RESULT2: !llvm.module.flags = !{}
+
+!llvm.module.flags = !{!0, !1, !2, !3, !4, !5}
+
+!0 = !{i32 1, !"amdgpu_code_object_version", i32 400}
+!1 = !{i32 1, !"wchar_size", i32 4}
+!2 = !{i32 7, !"openmp", i32 50}
+!3 = !{i32 7, !"openmp-device", i32 50}
+!4 = !{i32 8, !"PIC Level", i32 1}
+!5 = !{i32 1, !"LTOPostLink", i32 1}
--- /dev/null
+; RUN: llvm-reduce --abort-on-invalid-reduction --delta-passes=named-metadata --test=FileCheck --test-arg=--check-prefix=CHECK-INTERESTINGNESS --test-arg=%s --test-arg=--input-file %s -o %t
+; RUN: FileCheck --check-prefix=RESULT %s < %t
+; Test the various named metadata recognized for simple list behavior.
+
+; CHECK-INTERESTINGNESS: !llvm.ident = !{![[LLVM_IDENT:[0-9]+]]
+; CHECK-INTERESTINGNESS: !opencl.spir.version = !{{{.*}}![[SPIR_VERSION:[0-9]+]]}
+; CHECK-INTERESTINGNESS: !opencl.ocl.version = !{{{.*}}![[OCL_VERSION:[0-9]+]]}
+; CHECK-INTERESTINGNESS: !opencl.used.extensions = !{{{.*}}![[OCL_EXTENSION:[0-9]+]]}
+; CHECK-INTERESTINGNESS: !opencl.used.optional.core.features = !{{{.*}}![[OCL_OPTIONAL_CORE_FEATURE:[0-9]+]]}
+; CHECK-INTERESTINGNESS: !opencl.compiler.options = !{{{.*}}![[OCL_COMPILER_OPTIONS:[0-9]+]]}
+
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[LLVM_IDENT]] = !{!"some llvm version 0"}
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[SPIR_VERSION]] = !{!"some spir version 1"}
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[OCL_VERSION]] = !{!"some ocl version 1"}
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[OCL_EXTENSION]] = !{!"some ocl extension 1"}
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[OCL_OPTIONAL_CORE_FEATURE]] = !{!"some ocl optional core feature 1"}
+; CHECK-DAG: CHECK-INTERESTINGNESS: ![[OCL_COMPILER_OPTIONS]] = !{!"some ocl compiler option 1"}
+
+
+; RESULT: !llvm.ident = !{![[LLVM_IDENT:[0-9]+]]
+; RESULT: !opencl.spir.version = !{![[SPIR_VERSION:[0-9]+]]}
+; RESULT: !opencl.ocl.version = !{![[OCL_VERSION:[0-9]+]]}
+; RESULT: !opencl.used.extensions = !{![[OCL_EXTENSION:[0-9]+]]}
+; RESULT: !opencl.used.optional.core.features = !{![[OCL_OPTIONAL_CORE_FEATURE:[0-9]+]]}
+; RESULT: !opencl.compiler.options = !{![[OCL_COMPILER_OPTION:[0-9]+]]}
+; RESULT: !some.unknown.named = !{![[UNKNOWN_0:[0-9]+]], ![[UNKNOWN_1:[0-9]+]]}
+
+
+; RESULT: ![[LLVM_IDENT]] = !{!"some llvm version 0"}
+; RESULT: ![[SPIR_VERSION]] = !{!"some spir version 1"}
+; RESULT: ![[OCL_VERSION]] = !{!"some ocl version 1"}
+; RESULT: ![[OCL_EXTENSION]] = !{!"some ocl extension 1"}
+; RESULT: ![[OCL_OPTIONAL_CORE_FEATURE]] = !{!"some ocl optional core feature 1"}
+; RESULT: ![[OCL_COMPILER_OPTION]] = !{!"some ocl compiler option 1"}
+; RESULT: ![[UNKNOWN_0]] = !{!"some unknown option 0"}
+; RESULT: ![[UNKNOWN_1]] = !{!"some unknown option 1"}
+
+!llvm.ident = !{!0, !1, !0}
+!opencl.spir.version = !{!2, !3}
+!opencl.ocl.version = !{!4, !5}
+!opencl.used.extensions = !{!6, !7}
+!opencl.used.optional.core.features = !{!8, !9}
+!opencl.compiler.options = !{!10, !11}
+!some.unknown.named = !{!12, !13}
+
+!0 = !{!"some llvm version 0"}
+!1 = !{!"some llvm version 1"}
+!2 = !{!"some spir version 0"}
+!3 = !{!"some spir version 1"}
+!4 = !{!"some ocl version 0"}
+!5 = !{!"some ocl version 1"}
+!6 = !{!"some ocl extension 0"}
+!7 = !{!"some ocl extension 1"}
+!8 = !{!"some ocl optional core feature 0"}
+!9 = !{!"some ocl optional core feature 1"}
+!10 = !{!"some ocl compiler option 0"}
+!11 = !{!"some ocl compiler option 1"}
+!12 = !{!"some unknown option 0"}
+!13 = !{!"some unknown option 1"}
DELTA_PASS("global-variables", reduceGlobalsDeltaPass) \
DELTA_PASS("di-metadata", reduceDIMetadataDeltaPass) \
DELTA_PASS("metadata", reduceMetadataDeltaPass) \
+ DELTA_PASS("named-metadata", reduceNamedMetadataDeltaPass) \
DELTA_PASS("arguments", reduceArgumentsDeltaPass) \
DELTA_PASS("instructions", reduceInstructionsDeltaPass) \
DELTA_PASS("simplify-instructions", simplifyInstructionsDeltaPass) \
return MD.getName() == "llvm.dbg.cu" && MD.getNumOperands() != 0;
}
+// Named metadata with simple list-like behavior, so that it's valid to remove
+// operands individually.
+static constexpr StringLiteral ListNamedMetadata[] = {
+ "llvm.module.flags",
+ "llvm.ident",
+ "opencl.spir.version",
+ "opencl.ocl.version",
+ "opencl.used.extensions",
+ "opencl.used.optional.core.features",
+ "opencl.compiler.options"
+};
+
+/// Remove unneeded arguments to named metadata.
+static void reduceNamedMetadataOperands(Oracle &O, Module &M) {
+ for (StringRef MDName : ListNamedMetadata) {
+ NamedMDNode *NamedNode = M.getNamedMetadata(MDName);
+ if (!NamedNode)
+ continue;
+
+ bool MadeChange = false;
+ SmallVector<MDNode *, 16> KeptOperands;
+ for (auto I : seq<unsigned>(0, NamedNode->getNumOperands())) {
+ if (O.shouldKeep())
+ KeptOperands.push_back(NamedNode->getOperand(I));
+ else
+ MadeChange = true;
+ }
+
+ if (MadeChange) {
+ NamedNode->clearOperands();
+ for (MDNode *KeptOperand : KeptOperands)
+ NamedNode->addOperand(KeptOperand);
+ }
+ }
+}
+
/// Removes all the Named and Unnamed Metadata Nodes, as well as any debug
/// functions that aren't inside the desired Chunks.
static void extractMetadataFromModule(Oracle &O, Module &Program) {
void llvm::reduceMetadataDeltaPass(TestRunner &Test) {
runDeltaPass(Test, extractMetadataFromModule, "Reducing Metadata");
}
+
+void llvm::reduceNamedMetadataDeltaPass(TestRunner &Test) {
+ runDeltaPass(Test, reduceNamedMetadataOperands, "Reducing Named Metadata");
+}
namespace llvm {
void reduceMetadataDeltaPass(TestRunner &Test);
+void reduceNamedMetadataDeltaPass(TestRunner &Test);
} // namespace llvm
#endif