Skip to content

Commit 4c7015a

Browse files
committed
[interop][SwiftToCxx] ensure LoadableByAddress lowering is done on the SILFunction for while we're lowering the signature for
This correctly now passes self parameters for direct values that are too large to be direct
1 parent 661ae6b commit 4c7015a

7 files changed

+112
-0
lines changed

lib/IRGen/IRABIDetailsProvider.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,7 @@ class IRABIDetailsProviderImpl {
127127
llvm::Optional<LoweredFunctionSignature>
128128
getFunctionLoweredSignature(AbstractFunctionDecl *fd) {
129129
auto function = SILFunction::getFunction(SILDeclRef(fd), *silMod);
130+
IGM.lowerSILFunction(function);
130131
auto silFuncType = function->getLoweredFunctionType();
131132
// FIXME: Async function support.
132133
if (silFuncType->isAsync())

lib/IRGen/IRGenModule.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1762,6 +1762,11 @@ private: \
17621762
/// Emit a resilient class stub.
17631763
llvm::Constant *emitObjCResilientClassStub(ClassDecl *D, bool isPublic);
17641764

1765+
/// Runs additional lowering logic on the given SIL function to ensure that
1766+
/// the SIL function is correctly lowered even if the lowering passes do not
1767+
/// run on the SIL module that owns this function.
1768+
void lowerSILFunction(SILFunction *f);
1769+
17651770
private:
17661771
llvm::Constant *
17671772
getAddrOfSharedContextDescriptor(LinkEntity entity,

lib/IRGen/LoadableByAddress.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2909,6 +2909,17 @@ void LoadableByAddress::updateLoweredTypes(SILFunction *F) {
29092909
F->rewriteLoweredTypeUnsafe(newFuncTy);
29102910
}
29112911

2912+
void IRGenModule::lowerSILFunction(SILFunction *f) {
2913+
CanSILFunctionType funcType = f->getLoweredFunctionType();
2914+
GenericEnvironment *genEnv = getSubstGenericEnvironment(f);
2915+
if (!genEnv && funcType->getSubstGenericSignature()) {
2916+
genEnv = getSubstGenericEnvironment(funcType);
2917+
}
2918+
LargeSILTypeMapper MapperCache;
2919+
auto newFuncTy = MapperCache.getNewSILFunctionType(genEnv, funcType, *this);
2920+
f->rewriteLoweredTypeUnsafe(newFuncTy);
2921+
}
2922+
29122923
bool LoadableByAddress::shouldTransformGlobal(SILGlobalVariable *global) {
29132924
SILInstruction *init = global->getStaticInitializerValue();
29142925
if (!init)
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// RUN: %empty-directory(%t)
2+
3+
// RUN: %target-swift-frontend %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -typecheck -module-name Generics -clang-header-expose-public-decls -emit-clang-header-path %t/generics.h
4+
5+
// RUN: %target-interop-build-clangxx -std=gnu++20 -c %s -I %t -o %t/swift-generics-execution.o
6+
// RUN: %target-interop-build-swift %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -o %t/swift-generics-execution -Xlinker %t/swift-generics-execution.o -module-name Generics -Xfrontend -entry-point-function-name -Xfrontend swiftMain
7+
8+
// RUN: %target-codesign %t/swift-generics-execution
9+
// RUN: %target-run %t/swift-generics-execution | %FileCheck %s
10+
11+
// REQUIRES: executable_test
12+
13+
#include "generic-struct-execution.cpp"
14+
15+
// CHECK: GenericPair<Int32, Int32>(x_: ClassWithT(11), y_: ClassWithT(42), val1: 0, val2: 0, val3: 0, val4: 0)
16+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(11), y_: ClassWithT(42), val1: 0, val2: 0, val3: 0, val4: 0)
17+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(11), y_: ClassWithT(-995), val1: 0, val2: 0, val3: 0, val4: 0)
18+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(255), y_: ClassWithT(42), val1: 0, val2: 0, val3: 0, val4: 0)
19+
// CHECK-NEXT: GenericPair<T, T2>::testme::255,42;
20+
// CHECK-NEXT: GenericPair<T, T2>::testme::-995,11;
21+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(-995), y_: ClassWithT(11), val1: 0, val2: 0, val3: 0, val4: 0)
22+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(11), y_: ClassWithT(-995), val1: 0, val2: 0, val3: 0, val4: 0)
23+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(-995), y_: ClassWithT(561), val1: 0, val2: 0, val3: 0, val4: 0)
24+
// CHECK-NEXT: GenericPair<T, T2>::computeVar::get
25+
// CHECK-NEXT: GenericPair<T, T2>::computeVar::set
26+
// CHECK-NEXT: GenericPair<T, T2>::computeVar::get
27+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(-123456), y_: ClassWithT(561), val1: 0, val2: 0, val3: 0, val4: 0)
28+
// CHECK-NEXT: GenericPair<T, T2>::genericMethod<T>::2.25,4221;
29+
// CHECK-NEXT: GenericPair<UInt16, UInt16>(x_: ClassWithT(10000), y_: ClassWithT(65255), val1: 0, val2: 0, val3: 0, val4: 0)
30+
// CHECK-NEXT: CONCRETE pair of UInt16: 10000 65255 ;
31+
// CHECK-NEXT: CONCRETE pair of UInt16: 10000 65255 ;
32+
// CHECK-NEXT: CONCRETE pair of UInt16: 10000 918 ;
33+
// CHECK-NEXT: GenericPair<UInt16, UInt16>(x_: ClassWithT(10000), y_: ClassWithT(918), val1: 0, val2: 0, val3: 0, val4: 0)
34+
// CHECK-NEXT: CONCRETE pair of UInt16: 77 65255 ;
35+
// CHECK-NEXT: GenericPair<T, T2>::testme::77,65255;
36+
// CHECK-NEXT: GenericPair<T, T2>::testme::918,10000;
37+
// CHECK-NEXT: CONCRETE pair of UInt16: 10000 918 ;
38+
// CHECK-NEXT: GenericPair<T, T2>::init::11,44,234242;
39+
// CHECK-NEXT: GenericPair<Int32, Int32>(x_: ClassWithT(11), y_: ClassWithT(44), val1: 0, val2: 0, val3: 0, val4: 0)
40+
// CHECK-NEXT: GenericPair<T, T2>::testme::11,44;
41+
// CHECK-NEXT: GenericPair<T, T2>::init::0,3425,-987;
42+
// CHECK-NEXT: CONCRETE pair of UInt16: 0 3425 ;
43+
// CHECK-NEXT: GenericPair<T, T2>::testme::0,3425;
44+
// CHECK-NEXT: GenericPair<T, T2>::genericMethod<T>::PairOfUInt64(x: 719610, y: 205891),4221;
45+
// CHECK-NEXT: EOF

test/Interop/SwiftToCxx/generics/generic-struct-in-cxx.swift

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,9 @@ public struct GenericPair<T, T2> {
5656
y_ = ClassWithT<T2>(newValue)
5757
}
5858
}
59+
#if INDIRECT_KNOWN_LAYOUT
60+
let val1, val2, val3, val4: Int
61+
#endif
5962
#else
6063
var x: T
6164
public var y: T2
@@ -65,6 +68,12 @@ public struct GenericPair<T, T2> {
6568
#if KNOWN_LAYOUT
6669
self.x_ = ClassWithT<T>(x)
6770
self.y_ = ClassWithT<T2>(y)
71+
#if INDIRECT_KNOWN_LAYOUT
72+
val1 = 0
73+
val2 = 0
74+
val3 = 0
75+
val4 = 0
76+
#endif
6877
#else
6978
self.x = x
7079
self.y = y
@@ -75,6 +84,12 @@ public struct GenericPair<T, T2> {
7584
#if KNOWN_LAYOUT
7685
self.x_ = ClassWithT<T>(x)
7786
self.y_ = ClassWithT<T2>(y)
87+
#if INDIRECT_KNOWN_LAYOUT
88+
val1 = 0
89+
val2 = 0
90+
val3 = 0
91+
val4 = 0
92+
#endif
7893
#else
7994
self.x = x
8095
self.y = y
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// RUN: %empty-directory(%t)
2+
// RUN: %target-swift-frontend %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -typecheck -module-name Generics -clang-header-expose-public-decls -emit-clang-header-path %t/generics.h
3+
// RUN: %FileCheck %s < %t/generics.h
4+
// RUN: %check-generic-interop-cxx-header-in-clang(%t/generics.h -Wno-reserved-identifier)
5+
6+
// RUN: %empty-directory(%t)
7+
// RUN: %target-swift-frontend %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -enable-library-evolution -typecheck -module-name Generics -clang-header-expose-public-decls -emit-clang-header-path %t/generics.h
8+
// RUN: %FileCheck %s < %t/generics.h
9+
// RUN: %check-generic-interop-cxx-header-in-clang(%t/generics.h -Wno-reserved-identifier)
10+
11+
// CHECK: SWIFT_EXTERN void $s8Generics11GenericPairV1yq_vg(SWIFT_INDIRECT_RESULT void * _Nonnull, void * _Nonnull , SWIFT_CONTEXT const void * _Nonnull _self) SWIFT_NOEXCEPT SWIFT_CALL; // _
12+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics11GenericPairV1yq_vs(const void * _Nonnull newValue, void * _Nonnull , SWIFT_CONTEXT void * _Nonnull _self) SWIFT_NOEXCEPT SWIFT_CALL; // _
13+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics11GenericPairVyACyxq_Gx_Siq_tcfC(SWIFT_INDIRECT_RESULT void * _Nonnull, const void * _Nonnull x, ptrdiff_t i, const void * _Nonnull y, void * _Nonnull , void * _Nonnull ) SWIFT_NOEXCEPT SWIFT_CALL; // init(_:_:_:)
14+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics11GenericPairV6methodyyF(void * _Nonnull , SWIFT_CONTEXT const void * _Nonnull _self) SWIFT_NOEXCEPT SWIFT_CALL; // method()
15+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics11GenericPairV14mutatingMethodyyACyq_xGF(const void * _Nonnull other, void * _Nonnull , SWIFT_CONTEXT void * _Nonnull _self) SWIFT_NOEXCEPT SWIFT_CALL; // mutatingMethod(_:)
16+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics11GenericPairV13genericMethodyqd__qd___q_tlF(SWIFT_INDIRECT_RESULT void * _Nonnull, const void * _Nonnull x, const void * _Nonnull y, void * _Nonnull , void * _Nonnull , SWIFT_CONTEXT const void * _Nonnull _self) SWIFT_NOEXCEPT SWIFT_CALL; // genericMethod(_:_:)
17+
18+
19+
// CHECK: SWIFT_EXTERN void $s8Generics17inoutConcretePairyys6UInt16V_AA07GenericD0VyA2DGztF(uint16_t x, void * _Nonnull y) SWIFT_NOEXCEPT SWIFT_CALL; // inoutConcretePair(_:_:)
20+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics16inoutGenericPairyyAA0cD0Vyxq_Gz_xtr0_lF(void * _Nonnull x, const void * _Nonnull y, void * _Nonnull , void * _Nonnull ) SWIFT_NOEXCEPT SWIFT_CALL; // inoutGenericPair(_:_:)
21+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics16makeConcretePairyAA07GenericD0Vys6UInt16VAFGAF_AFtF(SWIFT_INDIRECT_RESULT void * _Nonnull, uint16_t x, uint16_t y) SWIFT_NOEXCEPT SWIFT_CALL; // makeConcretePair(_:_:)
22+
// CHECK-NEXT: SWIFT_EXTERN void $s8Generics15makeGenericPairyAA0cD0Vyxq_Gx_q_tr0_lF(SWIFT_INDIRECT_RESULT void * _Nonnull, const void * _Nonnull x, const void * _Nonnull y, void * _Nonnull , void * _Nonnull ) SWIFT_NOEXCEPT SWIFT_CALL; // makeGenericPair(_:_:)
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
// RUN: %empty-directory(%t)
2+
3+
// RUN: %target-swift-frontend %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -typecheck -enable-library-evolution -module-name Generics -clang-header-expose-public-decls -emit-clang-header-path %t/generics.h
4+
5+
// RUN: %target-interop-build-clangxx -std=gnu++20 -c %s -I %t -o %t/swift-generics-execution.o
6+
// RUN: %target-interop-build-swift %S/generic-struct-in-cxx.swift -D KNOWN_LAYOUT -D INDIRECT_KNOWN_LAYOUT -o %t/swift-generics-execution -Xlinker %t/swift-generics-execution.o -enable-library-evolution -module-name Generics -Xfrontend -entry-point-function-name -Xfrontend swiftMain
7+
8+
// RUN: %target-codesign %t/swift-generics-execution
9+
// RUN: %target-run %t/swift-generics-execution | %FileCheck %S/generic-struct-execution-known-layout-indirect.cpp
10+
11+
// REQUIRES: executable_test
12+
13+
#include "generic-struct-execution-known-layout-indirect.cpp"

0 commit comments

Comments
 (0)