Merge remote-tracking branch 'origin/main' into rebranch

This commit is contained in:
swift-ci
2022-11-29 15:54:37 -08:00
7 changed files with 104 additions and 135 deletions

View File

@@ -1238,7 +1238,7 @@ void DeclAndTypeClangFunctionPrinter::printCxxThunkBody(
// Create the condition and the statement to throw an exception.
if (hasThrows) {
os << " if (opaqueError != nullptr)\n";
os << " throw (swift::Error(opaqueError));\n";
os << " throw (Swift::Error(opaqueError));\n";
}
// Return the function result value if it doesn't throw.

View File

@@ -156,26 +156,6 @@ static void printTypeMetadataResponseType(SwiftToClangInteropContext &ctx,
funcSig.parameterTypes[0]);
}
void printCxxNaiveException(raw_ostream &os) {
os << "/// Naive exception class that should be thrown\n";
os << "class NaiveException : public swift::Error {\n";
os << "public:\n";
os << " inline NaiveException(const char * _Nonnull msg) noexcept : "
<< "msg_(msg) { }\n";
os << " inline NaiveException(NaiveException&& other) noexcept : "
"msg_(other.msg_) { other.msg_ = nullptr; }\n";
os << " inline ~NaiveException() noexcept { }\n";
os << " void operator =(NaiveException&& other) noexcept { auto temp = msg_;"
<< " msg_ = other.msg_; other.msg_ = temp; }\n";
os << " void operator =(const NaiveException&) noexcept = delete;";
os << "\n";
os << " inline const char * _Nonnull getMessage() const noexcept { "
<< "return(msg_); }\n";
os << "private:\n";
os << " const char * _Nonnull msg_;\n";
os << "};\n";
}
void printPrimitiveGenericTypeTraits(raw_ostream &os, ASTContext &astContext,
PrimitiveTypeMapping &typeMapping,
bool isCForwardDefinition) {
@@ -239,7 +219,6 @@ void swift::printSwiftToClangCoreScaffold(SwiftToClangInteropContext &ctx,
/*isCForwardDefinition=*/true);
});
os << "\n";
printCxxNaiveException(os);
});
os << "\n";
// C++ only supports inline variables from C++17.

View File

@@ -195,95 +195,6 @@ template <class T> inline void *_Nonnull getOpaquePointer(T &value) {
} // namespace _impl
extern "C" void *_Nonnull swift_errorRetain(void *_Nonnull swiftError) noexcept;
extern "C" void swift_errorRelease(void *_Nonnull swiftError) noexcept;
extern "C" int $ss5ErrorMp; // external global %swift.protocol, align 4
extern "C"
const void * _Nullable
swift_getTypeByMangledNameInContext(
const char *_Nullable typeNameStart,
size_t typeNameLength,
const void *_Nullable context,
const void *_Nullable const *_Nullable genericArgs) SWIFT_CALL;
extern "C" bool swift_dynamicCast(void *_Nullable dest, void *_Nullable src,
const void *_Nullable srcType,
const void * _Nullable targetType,
uint32_t flags);
struct SymbolicP {
alignas(2) uint8_t _1;
uint32_t _2;
uint8_t _3[2];
uint8_t _4;
} __attribute__((packed));
inline const void *_Nullable getErrorMetadata() {
static swift::SymbolicP errorSymbol;
static int *_Nonnull got_ss5ErrorMp = &$ss5ErrorMp;
errorSymbol._1 = 2;
errorSymbol._2 = static_cast<uint32_t>(reinterpret_cast<uintptr_t>(&got_ss5ErrorMp) - reinterpret_cast<uintptr_t>(&errorSymbol._2));
errorSymbol._3[0] = '_';
errorSymbol._3[1] = 'p';
errorSymbol._4 = 0;
static_assert(sizeof(errorSymbol) == 8, "");
auto charErrorSymbol = reinterpret_cast<const char *>(&errorSymbol);
const void *ptr2 =
swift::swift_getTypeByMangledNameInContext(charErrorSymbol,
sizeof(errorSymbol) - 1,
nullptr, nullptr);
return ptr2;
}
class Error {
public:
Error() {}
Error(void* _Nonnull swiftError) { opaqueValue = swiftError; }
~Error() {
if (opaqueValue)
swift_errorRelease(opaqueValue);
}
void* _Nonnull getPointerToOpaquePointer() { return opaqueValue; }
Error(Error &&other) : opaqueValue(other.opaqueValue) {
other.opaqueValue = nullptr;
}
Error(const Error &other) {
if (other.opaqueValue)
swift_errorRetain(other.opaqueValue);
opaqueValue = other.opaqueValue;
}
// FIXME: Return a Swift::Optional instead.
template<class T>
T as() {
alignas(alignof(T)) char buffer[sizeof(T)];
const void *em = getErrorMetadata();
void *ep = getPointerToOpaquePointer();
auto metadata = swift::TypeMetadataTrait<T>::getTypeMetadata();
// Dynamic cast will release the error, so we need to retain it.
swift::swift_errorRetain(ep);
bool dynamicCast =
swift::swift_dynamicCast(buffer, &ep, em, metadata,
/*take on success destroy on failure*/ 6);
if (dynamicCast) {
return swift::_impl::implClassFor<T>::type::returnNewValue([&](char *dest) {
swift::_impl::implClassFor<T>::type::initializeWithTake(dest, buffer);
});
}
abort();
// FIXME: return nil.
}
private:
void * _Nonnull opaqueValue = nullptr;
};
#pragma clang diagnostic pop
} // namespace swift

View File

@@ -91,4 +91,92 @@ SWIFT_INLINE_THUNK cxxOverlay::IterationEndSentinel end(const Array<T> &) {
return {};
}
extern "C" void *_Nonnull swift_errorRetain(void *_Nonnull swiftError) noexcept;
extern "C" void swift_errorRelease(void *_Nonnull swiftError) noexcept;
extern "C" int $ss5ErrorMp; // external global %swift.protocol, align 4
extern "C" const void *_Nullable swift_getTypeByMangledNameInContext(
const char *_Nullable typeNameStart, size_t typeNameLength,
const void *_Nullable context,
const void *_Nullable const *_Nullable genericArgs) SWIFT_CALL;
extern "C" bool swift_dynamicCast(void *_Nullable dest, void *_Nullable src,
const void *_Nullable srcType,
const void *_Nullable targetType,
uint32_t flags);
struct SymbolicP {
alignas(2) uint8_t _1;
uint32_t _2;
uint8_t _3[2];
uint8_t _4;
} __attribute__((packed));
inline const void *_Nullable getErrorMetadata() {
static SymbolicP errorSymbol;
static int *_Nonnull got_ss5ErrorMp = &$ss5ErrorMp;
errorSymbol._1 = 2;
errorSymbol._2 =
static_cast<uint32_t>(reinterpret_cast<uintptr_t>(&got_ss5ErrorMp) -
reinterpret_cast<uintptr_t>(&errorSymbol._2));
errorSymbol._3[0] = '_';
errorSymbol._3[1] = 'p';
errorSymbol._4 = 0;
static_assert(sizeof(errorSymbol) == 8, "");
auto charErrorSymbol = reinterpret_cast<const char *>(&errorSymbol);
const void *ptr2 = swift_getTypeByMangledNameInContext(
charErrorSymbol, sizeof(errorSymbol) - 1, nullptr, nullptr);
return ptr2;
}
class Error {
public:
Error() {}
Error(void *_Nonnull swiftError) { opaqueValue = swiftError; }
~Error() {
if (opaqueValue)
swift_errorRelease(opaqueValue);
}
void *_Nonnull getPointerToOpaquePointer() { return opaqueValue; }
Error(Error &&other) : opaqueValue(other.opaqueValue) {
other.opaqueValue = nullptr;
}
Error(const Error &other) {
if (other.opaqueValue)
swift_errorRetain(other.opaqueValue);
opaqueValue = other.opaqueValue;
}
template <class T>
Swift::Optional<T> as() {
alignas(alignof(T)) char buffer[sizeof(T)];
const void *em = getErrorMetadata();
void *ep = getPointerToOpaquePointer();
auto metadata = swift::TypeMetadataTrait<T>::getTypeMetadata();
// Dynamic cast will release the error, so we need to retain it.
swift_errorRetain(ep);
bool dynamicCast =
swift_dynamicCast(buffer, &ep, em, metadata,
/*take on success destroy on failure*/ 6);
if (dynamicCast) {
auto result = swift::_impl::implClassFor<T>::type::returnNewValue(
[&](char *dest) {
swift::_impl::implClassFor<T>::type::initializeWithTake(dest,
buffer);
});
return Swift::Optional<T>::init(result);
}
return Swift::Optional<T>::none();
}
private:
void *_Nonnull opaqueValue = nullptr;
};
#endif

View File

@@ -98,18 +98,6 @@
// CHECK-NEXT: }
// CHECK-NEXT: #endif
// CHECK-EMPTY:
// CHECK-NEXT: /// Naive exception class that should be thrown
// CHECK-NEXT: class NaiveException : public swift::Error {
// CHECK-NEXT: public:
// CHECK-NEXT: inline NaiveException(const char * _Nonnull msg) noexcept : msg_(msg) { }
// CHECK-NEXT: inline NaiveException(NaiveException&& other) noexcept : msg_(other.msg_) { other.msg_ = nullptr; }
// CHECK-NEXT: inline ~NaiveException() noexcept { }
// CHECK-NEXT: void operator =(NaiveException&& other) noexcept { auto temp = msg_; msg_ = other.msg_; other.msg_ = temp; }
// CHECK-NEXT: void operator =(const NaiveException&) noexcept = delete;
// CHECK-NEXT: inline const char * _Nonnull getMessage() const noexcept { return(msg_); }
// CHECK-NEXT: private:
// CHECK-NEXT: const char * _Nonnull msg_;
// CHECK-NEXT: };
// CHECK-EMPTY:
// CHECK-NEXT: } // namespace _impl
// CHECK-EMPTY:

View File

@@ -1,6 +1,6 @@
// RUN: %empty-directory(%t)
// RUN: %target-swift-frontend %S/swift-functions-errors.swift -typecheck -module-name Functions -clang-header-expose-decls=has-expose-attr -emit-clang-header-path %t/functions.h
// RUN: %target-swift-frontend %S/swift-functions-errors.swift -typecheck -module-name Functions -enable-experimental-cxx-interop -emit-clang-header-path %t/functions.h
// RUN: %target-interop-build-clangxx -c %s -I %t -o %t/swift-functions-errors-execution.o
// RUN: %target-interop-build-swift %S/swift-functions-errors.swift -o %t/swift-functions-errors-execution -Xlinker %t/swift-functions-errors-execution.o -module-name Functions -Xfrontend -entry-point-function-name -Xfrontend swiftMain
@@ -25,24 +25,27 @@ int main() {
try {
Functions::emptyThrowFunction();
} catch (swift::Error& e) {
} catch (Swift::Error& e) {
printf("Exception\n");
}
try {
Functions::throwFunction();
} catch (swift::Error& e) {
auto errorVal = e.as<Functions::NaiveErrors>();
} catch (Swift::Error& e) {
auto errorOpt = e.as<Functions::NaiveErrors>();
assert(errorOpt.isSome());
auto errorVal = errorOpt.get();
assert(errorVal == Functions::NaiveErrors::throwError);
errorVal.getMessage();
}
try {
Functions::throwFunctionWithReturn();
} catch (swift::Error& e) {
} catch (Swift::Error& e) {
printf("Exception\n");
}
try {
Functions::testDestroyedError();
} catch(const swift::Error &e) { }
} catch(const Swift::Error &e) { }
return 0;
}

View File

@@ -1,8 +1,8 @@
// RUN: %empty-directory(%t)
// RUN: %target-swift-frontend %s -typecheck -module-name Functions -clang-header-expose-decls=has-expose-attr -emit-clang-header-path %t/functions.h
// RUN: %target-swift-frontend %s -typecheck -module-name Functions -enable-experimental-cxx-interop -emit-clang-header-path %t/functions.h
// RUN: %FileCheck %s < %t/functions.h
// RUN: %check-interop-cxx-header-in-clang(%t/functions.h)
// RUN: %check-interop-cxx-header-in-clang(%t/functions.h -Wno-shadow -Wno-unused-function)
// CHECK-LABEL: namespace Functions __attribute__((swift_private)) {
@@ -31,7 +31,7 @@ public func emptyThrowFunction() throws { print("passEmptyThrowFunction") }
// CHECK: void* _ctx = nullptr;
// CHECK: _impl::$s9Functions18emptyThrowFunctionyyKF(_ctx, &opaqueError);
// CHECK: if (opaqueError != nullptr)
// CHECK: throw (swift::Error(opaqueError))
// CHECK: throw (Swift::Error(opaqueError))
// CHECK: }
class TestDestroyed {
@@ -53,7 +53,7 @@ public func testDestroyedError() throws { throw DestroyedError() }
// CHECK: void* _ctx = nullptr;
// CHECK: _impl::$s9Functions18testDestroyedErroryyKF(_ctx, &opaqueError);
// CHECK: if (opaqueError != nullptr)
// CHECK: throw (swift::Error(opaqueError))
// CHECK: throw (Swift::Error(opaqueError))
// CHECK: }
@_expose(Cxx)
@@ -67,7 +67,7 @@ public func throwFunction() throws {
// CHECK: void* _ctx = nullptr;
// CHECK: _impl::$s9Functions13throwFunctionyyKF(_ctx, &opaqueError);
// CHECK: if (opaqueError != nullptr)
// CHECK: throw (swift::Error(opaqueError))
// CHECK: throw (Swift::Error(opaqueError))
// CHECK: }
@_expose(Cxx)
@@ -82,6 +82,6 @@ public func throwFunctionWithReturn() throws -> Int {
// CHECK: void* _ctx = nullptr;
// CHECK: auto returnValue = _impl::$s9Functions23throwFunctionWithReturnSiyKF(_ctx, &opaqueError);
// CHECK: if (opaqueError != nullptr)
// CHECK: throw (swift::Error(opaqueError))
// CHECK: throw (Swift::Error(opaqueError))
// CHECK: return returnValue;
// CHECK: }