llvm.resume is similar to llvm.return except that has to be exactly one operand and that should be derived from a llvm.landingpad instruction.
Any function having llvm.landingpad instruction must have a personality attribute.
Example:
LLVM IR
define dso_local i32 @main() personality i32 (...)* @__gxx_personality_v0 { invoke void @foo(i32 42) to label %3 unwind label %1 1: ; preds = %0 %2 = landingpad i8* catch i8** @_ZTIi catch i8* bitcast (i8** @_ZTIi to i8*) resume i8* %2 3: ; preds = %0 ret i32 1 }
MLIR - LLVM IR Dialect
llvm.func @main() -> !llvm.i32 attributes {personality = @__gxx_personality_v0} { %0 = llvm.mlir.constant(1 : i32) : !llvm.i32 %1 = llvm.mlir.addressof @_ZTIi : !llvm<"i8**"> %2 = llvm.bitcast %1 : !llvm<"i8**"> to !llvm<"i8*"> %3 = llvm.mlir.addressof @_ZTIi : !llvm<"i8**"> %4 = llvm.mlir.constant(42 : i32) : !llvm.i32 llvm.invoke @foo(%4) to ^bb2 unwind ^bb1 : (!llvm.i32) -> () ^bb1: // pred: ^bb0 %5 = llvm.landingpad (catch %3 : !llvm<"i8**">) (catch %2 : !llvm<"i8*">) : !llvm<"i8*"> llvm.resume %5 : !llvm<"i8*"> ^bb2: // pred: ^bb0 llvm.return %0 : !llvm.i32 }
Value is not guaranteed to have a defining op, use isa_and_nonnull instead to avoid a crash here.
Nit: add a space between if and (.