summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--llvm/docs/LangRef.rst7
-rw-r--r--llvm/lib/Transforms/Scalar/LowerGuardIntrinsic.cpp3
-rw-r--r--llvm/test/Transforms/LowerGuardIntrinsic/basic.ll12
3 files changed, 21 insertions, 1 deletions
diff --git a/llvm/docs/LangRef.rst b/llvm/docs/LangRef.rst
index dc8b4d14bc0..7c6ff7a72c3 100644
--- a/llvm/docs/LangRef.rst
+++ b/llvm/docs/LangRef.rst
@@ -12375,7 +12375,7 @@ equivalent to:
define void @llvm.experimental.guard(i1 %pred, <args...>) {
%realPred = and i1 %pred, undef
- br i1 %realPred, label %continue, label %leave
+ br i1 %realPred, label %continue, label %leave [, !make.implicit !{}]
leave:
call void @llvm.experimental.deoptimize(<args...>) [ "deopt"() ]
@@ -12385,6 +12385,11 @@ equivalent to:
ret void
}
+
+with the optional ``[, !make.implicit !{}]`` present if and only if it
+is present on the call site. For more details on ``!make.implicit``,
+see :doc:`FaultMaps`.
+
In words, ``@llvm.experimental.guard`` executes the attached
``"deopt"`` continuation if (but **not** only if) its first argument
is ``false``. Since the optimizer is allowed to replace the ``undef``
diff --git a/llvm/lib/Transforms/Scalar/LowerGuardIntrinsic.cpp b/llvm/lib/Transforms/Scalar/LowerGuardIntrinsic.cpp
index a58346c2b1c..7ba17069f42 100644
--- a/llvm/lib/Transforms/Scalar/LowerGuardIntrinsic.cpp
+++ b/llvm/lib/Transforms/Scalar/LowerGuardIntrinsic.cpp
@@ -56,6 +56,9 @@ static void MakeGuardControlFlowExplicit(Function *DeoptIntrinsic,
CheckBI->getSuccessor(0)->setName("guarded");
CheckBI->getSuccessor(1)->setName("deopt");
+ if (auto *MD = CI->getMetadata(LLVMContext::MD_make_implicit))
+ CheckBI->setMetadata(LLVMContext::MD_make_implicit, MD);
+
IRBuilder<> B(DeoptBlockTerm);
auto *DeoptCall = B.CreateCall(DeoptIntrinsic, Args, {DeoptOB}, "");
diff --git a/llvm/test/Transforms/LowerGuardIntrinsic/basic.ll b/llvm/test/Transforms/LowerGuardIntrinsic/basic.ll
index ae696cf4269..ade24eb7b22 100644
--- a/llvm/test/Transforms/LowerGuardIntrinsic/basic.ll
+++ b/llvm/test/Transforms/LowerGuardIntrinsic/basic.ll
@@ -60,3 +60,15 @@ define i32 @f_zero_args(i1* %c_ptr) {
; CHECK: guarded:
; CHECK-NEXT: ret i32 500
}
+
+define i8 @f_with_make_implicit_md(i32* %ptr) {
+; CHECK-LABEL: @f_with_make_implicit_md(
+; CHECK: br i1 %notNull, label %guarded, label %deopt, !make.implicit !0
+; CHECK: deopt:
+; CHECK-NEXT: %deoptcall = call i8 (...) @llvm.experimental.deoptimize.i8(i32 1) [ "deopt"(i32 1) ]
+; CHECK-NEXT: ret i8 %deoptcall
+
+ %notNull = icmp ne i32* %ptr, null
+ call void(i1, ...) @llvm.experimental.guard(i1 %notNull, i32 1) [ "deopt"(i32 1) ], !make.implicit !{}
+ ret i8 5
+}
OpenPOWER on IntegriCloud