mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
Runtime: Work around rdar://problem/18950072 to avoid paying for .cxx_destruct on Swift objects.
Clang overzealously infects SwiftObject with the HasCXXStructors bit because it contained a struct (with trivial constructor). Manually explode the struct to avoid this. Swift SVN r23259
This commit is contained in:
@@ -83,11 +83,22 @@ struct SwiftObject_s {
|
|||||||
long refCount __attribute__((unavailable));
|
long refCount __attribute__((unavailable));
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static_assert(std::is_trivially_constructible<SwiftObject_s>::value,
|
||||||
|
"SwiftObject must be trivially constructible");
|
||||||
|
static_assert(std::is_trivially_destructible<SwiftObject_s>::value,
|
||||||
|
"SwiftObject must be trivially destructible");
|
||||||
|
|
||||||
#if __has_attribute(objc_root_class)
|
#if __has_attribute(objc_root_class)
|
||||||
__attribute__((objc_root_class))
|
__attribute__((objc_root_class))
|
||||||
#endif
|
#endif
|
||||||
@interface SwiftObject<NSObject> {
|
@interface SwiftObject<NSObject> {
|
||||||
SwiftObject_s magic;
|
// FIXME: rdar://problem/18950072 Clang emits ObjC++ classes as having
|
||||||
|
// non-trivial structors if they contain any struct fields at all, regardless of
|
||||||
|
// whether they in fact have nontrivial default constructors. Dupe the body
|
||||||
|
// of SwiftObject_s into here as a workaround because we don't want to pay
|
||||||
|
// the cost of .cxx_destruct method dispatch at deallocation time.
|
||||||
|
void *magic_isa __attribute__((unavailable));
|
||||||
|
long magic_refCount __attribute__((unavailable));
|
||||||
}
|
}
|
||||||
|
|
||||||
- (BOOL)isEqual:(id)object;
|
- (BOOL)isEqual:(id)object;
|
||||||
|
|||||||
@@ -216,3 +216,36 @@ println("done ValueLike hashValue")
|
|||||||
// CHECK-NEXT: sh2 20
|
// CHECK-NEXT: sh2 20
|
||||||
// CHECK-NEXT: sh3 10
|
// CHECK-NEXT: sh3 10
|
||||||
// CHECK-NEXT: done ValueLike hashValue
|
// CHECK-NEXT: done ValueLike hashValue
|
||||||
|
|
||||||
|
// Native Swift objects should not have nontrivial structors from ObjC's point
|
||||||
|
// of view.
|
||||||
|
class NativeSwift {}
|
||||||
|
class GenericNativeSwift<T> {}
|
||||||
|
|
||||||
|
var native: AnyObject = NativeSwift()
|
||||||
|
|
||||||
|
if native.respondsToSelector(".cxx_construct") {
|
||||||
|
println("SwiftObject has nontrivial constructor")
|
||||||
|
} else {
|
||||||
|
println("no nontrivial constructor") // CHECK-NEXT: no nontrivial constructor
|
||||||
|
}
|
||||||
|
if native.respondsToSelector(".cxx_destruct") {
|
||||||
|
println("SwiftObject has nontrivial destructor")
|
||||||
|
} else {
|
||||||
|
println("no nontrivial destructor") // CHECK-NEXT: no nontrivial destructor
|
||||||
|
}
|
||||||
|
|
||||||
|
native = GenericNativeSwift<Int>()
|
||||||
|
|
||||||
|
if native.respondsToSelector(".cxx_construct") {
|
||||||
|
println("SwiftObject has nontrivial constructor")
|
||||||
|
} else {
|
||||||
|
println("no nontrivial constructor") // CHECK-NEXT: no nontrivial constructor
|
||||||
|
}
|
||||||
|
if native.respondsToSelector(".cxx_destruct") {
|
||||||
|
println("SwiftObject has nontrivial destructor")
|
||||||
|
} else {
|
||||||
|
println("no nontrivial destructor") // CHECK-NEXT: no nontrivial destructor
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user