When return out of __try block. In this test case, currently "false" is
passed to the OutlinedFinally call, "true" should be passed to indicate abnormal
terminations.
The rule: Except _leave and fall-through at the end, all other exits
in a _try (return/goto/continue/break) are considered as abnormal
terminations, NormalCleanupDestSlot is used to indicate abnormal
terminations.
The problem is, during the processing abnormal termination,
the ExitSwitch is used. However, in this case, Existswitch is route out.
One way to fix is to skip route it without a switch. So proper
abnormal termination's code could be generated.
IR before change:
invoke.cont: ; preds = %entry
invoke void @llvm.seh.try.begin() to label %invoke.cont1 unwind label %ehcleanup
invoke.cont1: ; preds = %invoke.cont
%1 = load volatile i32, ptr @y, align 4 %inc2 = add nsw i32 %1, 1 store volatile i32 %inc2, ptr @y, align 4 invoke void @llvm.seh.try.end() to label %invoke.cont3 unwind label %ehcleanup
invoke.cont3: ; preds = %invoke.cont1
%2 = call ptr @llvm.localaddress() call void @"?fin$0@0@foo@@"(i8 noundef 0, ptr noundef %2) ret void
IR after change:
invoke.cont: ; preds = %entry
invoke void @llvm.seh.try.begin() to label %invoke.cont1 unwind label %ehcleanup
invoke.cont1: ; preds = %invoke.cont
%1 = load volatile i32, ptr @y, align 4 %inc2 = add nsw i32 %1, 1 store volatile i32 %inc2, ptr @y, align 4 store volatile i32 1, ptr %cleanup.dest.slot, align 4 invoke void @llvm.seh.try.end() to label %invoke.cont3 unwind label %ehcleanup
invoke.cont3: ; preds = %invoke.cont1
%2 = call ptr @llvm.localaddress() %cleanup.dest = load i32, ptr %cleanup.dest.slot, align 4 %3 = icmp ne i32 %cleanup.dest, 0 %4 = zext i1 %3 to i8 call void @"?fin$0@0@foo@@"(i8 noundef %4, ptr noundef %2)
...
I think FD is unused now that you use currentFunctionUsesSEHTry