[cxx-interop] use SWIFT_NOEXCEPT for Swift function prototypes

This will allow these functions to be used from C.

Also add a static_assert to verify that noexcept is actually used.
This commit is contained in:
Alex Lorenz
2022-03-13 11:08:32 -07:00
parent 2c2fa566d8
commit 858a847d27
6 changed files with 22 additions and 12 deletions

View File

@@ -848,7 +848,7 @@ private:
// Swift functions can't throw exceptions, we can only
// throw them from C++ when emitting C++ inline thunks for the Swift
// functions.
os << " noexcept";
os << " SWIFT_NOEXCEPT";
if (!funcABI.useCCallingConvention())
os << " SWIFT_CALL";
printAvailability(FD);

View File

@@ -272,6 +272,12 @@ static void writePrologue(raw_ostream &out, ASTContext &ctx,
out << "#endif\n";
};
emitMacro("SWIFT_CALL", "__attribute__((swiftcall))");
// SWIFT_NOEXCEPT applies 'noexcept' in C++ mode only.
out << "#if defined(__cplusplus)\n";
emitMacro("SWIFT_NOEXCEPT", "noexcept");
out << "#else\n";
emitMacro("SWIFT_NOEXCEPT", "");
out << "#endif\n";
static_assert(SWIFT_MAX_IMPORTED_SIMD_ELEMENTS == 4,
"need to add SIMD typedefs here if max elements is increased");
}

View File

@@ -7,7 +7,7 @@
// CHECK-LABEL: namespace CdeclFunctions {
// CHECK: namespace _impl {
// CHECK: extern "C" int cfuncPassTwo(int x, int y) noexcept;
// CHECK: extern "C" int cfuncPassTwo(int x, int y) SWIFT_NOEXCEPT;
// CHECK: }
@_cdecl("cfuncPassTwo")

View File

@@ -8,11 +8,11 @@
// CHECK-LABEL: namespace _impl {
// CHECK: extern "C" void $s9Functions16alwaysDeprecatedyyF(void) noexcept SWIFT_CALL SWIFT_DEPRECATED; // alwaysDeprecated()
// CHECK: extern "C" void $s9Functions19alwaysDeprecatedTwoyyF(void) noexcept SWIFT_CALL SWIFT_DEPRECATED_MSG("it should not be used"); // alwaysDeprecatedTwo()
// CHECK: extern "C" void $s9Functions17alwaysUnavailableyyF(void) noexcept SWIFT_CALL SWIFT_UNAVAILABLE; // alwaysUnavailable()
// CHECK: extern "C" void $s9Functions24alwaysUnavailableMessageyyF(void) noexcept SWIFT_CALL SWIFT_UNAVAILABLE_MSG("stuff happened"); // alwaysUnavailableMessage()
// CHECK: extern "C" void $s9Functions22singlePlatAvailabilityyyF(void) noexcept SWIFT_CALL SWIFT_AVAILABILITY(macos,introduced=11); // singlePlatAvailability()
// CHECK: extern "C" void $s9Functions16alwaysDeprecatedyyF(void) SWIFT_NOEXCEPT SWIFT_CALL SWIFT_DEPRECATED; // alwaysDeprecated()
// CHECK: extern "C" void $s9Functions19alwaysDeprecatedTwoyyF(void) SWIFT_NOEXCEPT SWIFT_CALL SWIFT_DEPRECATED_MSG("it should not be used"); // alwaysDeprecatedTwo()
// CHECK: extern "C" void $s9Functions17alwaysUnavailableyyF(void) SWIFT_NOEXCEPT SWIFT_CALL SWIFT_UNAVAILABLE; // alwaysUnavailable()
// CHECK: extern "C" void $s9Functions24alwaysUnavailableMessageyyF(void) SWIFT_NOEXCEPT SWIFT_CALL SWIFT_UNAVAILABLE_MSG("stuff happened"); // alwaysUnavailableMessage()
// CHECK: extern "C" void $s9Functions22singlePlatAvailabilityyyF(void) SWIFT_NOEXCEPT SWIFT_CALL SWIFT_AVAILABILITY(macos,introduced=11); // singlePlatAvailability()
// CHECK: }

View File

@@ -14,6 +14,10 @@
#include "functions.h"
int main() {
static_assert(noexcept(Functions::passVoidReturnVoid()), "noexcept function");
static_assert(noexcept(Functions::_impl::$s9Functions014passVoidReturnC0yyF()),
"noexcept function");
Functions::passVoidReturnVoid();
Functions::passIntReturnVoid(-1);
assert(Functions::passTwoIntReturnIntNoArgLabel(1, 2) == 42);

View File

@@ -8,11 +8,11 @@
// CHECK-LABEL: namespace _impl {
// CHECK: extern "C" void $s9Functions17passIntReturnVoid1xys5Int32V_tF(int x) noexcept SWIFT_CALL; // passIntReturnVoid(x:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD01x1ys5Int32VAF_AFtF(int x, int y) noexcept SWIFT_CALL; // passTwoIntReturnInt(x:y:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD10NoArgLabelys5Int32VAD_ADtF(int, int) noexcept SWIFT_CALL; // passTwoIntReturnIntNoArgLabel(_:_:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD19NoArgLabelParamNameys5Int32VAD_ADtF(int x2, int y2) noexcept SWIFT_CALL; // passTwoIntReturnIntNoArgLabelParamName(_:_:)
// CHECK: extern "C" void $s9Functions014passVoidReturnC0yyF(void) noexcept SWIFT_CALL; // passVoidReturnVoid()
// CHECK: extern "C" void $s9Functions17passIntReturnVoid1xys5Int32V_tF(int x) SWIFT_NOEXCEPT SWIFT_CALL; // passIntReturnVoid(x:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD01x1ys5Int32VAF_AFtF(int x, int y) SWIFT_NOEXCEPT SWIFT_CALL; // passTwoIntReturnInt(x:y:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD10NoArgLabelys5Int32VAD_ADtF(int, int) SWIFT_NOEXCEPT SWIFT_CALL; // passTwoIntReturnIntNoArgLabel(_:_:)
// CHECK: extern "C" int $s9Functions016passTwoIntReturnD19NoArgLabelParamNameys5Int32VAD_ADtF(int x2, int y2) SWIFT_NOEXCEPT SWIFT_CALL; // passTwoIntReturnIntNoArgLabelParamName(_:_:)
// CHECK: extern "C" void $s9Functions014passVoidReturnC0yyF(void) SWIFT_NOEXCEPT SWIFT_CALL; // passVoidReturnVoid()
// CHECK: }