Skip to content

Commit 04cebc5

Browse files
[IRGen][wasm] Disable manual indirection for coroutine yielding results
`clang::CodeGen::swiftcall::shouldPassIndirectly` now returns true for multiple scalar values on wasm targets because the Wasm MVP does not support multiple return values. For such targets where we can't directly return two pointers, we should not attempt to indirect at this stage because the later MC lowering will also indirect the return.
1 parent 3e0ea3a commit 04cebc5

File tree

3 files changed

+28
-15
lines changed

3 files changed

+28
-15
lines changed

lib/IRGen/GenCall.cpp

Lines changed: 17 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -870,22 +870,26 @@ void SignatureExpansion::expandCoroutineResult(bool forContinuation) {
870870
}
871871

872872
// Find the maximal sequence of the component types that we can
873-
// convince the ABI to pass directly.
873+
// convince the ABI to pass directly if the target supports
874+
// directly returning at least two pointers.
874875
// When counting components, ignore the continuation pointer.
875876
unsigned numDirectComponents = components.size() - 1;
876877
SmallVector<llvm::Type*, 8> overflowTypes;
877-
while (clang::CodeGen::swiftcall::
878-
shouldPassIndirectly(IGM.ClangCodeGen->CGM(), components,
879-
/*asReturnValue*/ true)) {
880-
// If we added a pointer to the end of components, remove it.
881-
if (!overflowTypes.empty()) components.pop_back();
882-
883-
// Remove the last component and add it as an overflow type.
884-
overflowTypes.push_back(components.pop_back_val());
885-
--numDirectComponents;
886-
887-
// Add a pointer to the end of components.
888-
components.push_back(IGM.Int8PtrTy);
878+
if (IGM.TargetInfo.SupportsDirectReturningAtLeastTwoPointers) {
879+
while (clang::CodeGen::swiftcall::shouldPassIndirectly(
880+
IGM.ClangCodeGen->CGM(), components,
881+
/*asReturnValue*/ true)) {
882+
// If we added a pointer to the end of components, remove it.
883+
if (!overflowTypes.empty())
884+
components.pop_back();
885+
886+
// Remove the last component and add it as an overflow type.
887+
overflowTypes.push_back(components.pop_back_val());
888+
--numDirectComponents;
889+
890+
// Add a pointer to the end of components.
891+
components.push_back(IGM.Int8PtrTy);
892+
}
889893
}
890894

891895
// We'd better have been able to pass at least two pointers.

lib/IRGen/SwiftTargetInfo.cpp

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,13 @@
1717

1818
#include "SwiftTargetInfo.h"
1919
#include "IRGenModule.h"
20-
#include "llvm/TargetParser/Triple.h"
21-
#include "llvm/IR/DataLayout.h"
2220
#include "swift/ABI/System.h"
2321
#include "swift/AST/ASTContext.h"
2422
#include "swift/AST/IRGenOptions.h"
2523
#include "swift/Basic/Platform.h"
24+
#include "clang/CodeGen/SwiftCallingConv.h"
25+
#include "llvm/IR/DataLayout.h"
26+
#include "llvm/TargetParser/Triple.h"
2627

2728
using namespace swift;
2829
using namespace irgen;
@@ -194,6 +195,11 @@ static void configureWasm32(IRGenModule &IGM, const llvm::Triple &triple,
194195
SwiftTargetInfo &target) {
195196
target.LeastValidPointerValue =
196197
SWIFT_ABI_WASM32_LEAST_VALID_POINTER;
198+
199+
target.SupportsDirectReturningAtLeastTwoPointers =
200+
clang::CodeGen::swiftcall::shouldPassIndirectly(IGM.getClangCGM(),
201+
{IGM.PtrTy, IGM.PtrTy},
202+
/*asReturnValue*/ true);
197203
}
198204

199205
/// Configure a default target.

lib/IRGen/SwiftTargetInfo.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,9 @@ class SwiftTargetInfo {
118118
bool HasSwiftClientRRLibrary = false;
119119

120120
bool UsableSwiftAsyncContextAddrIntrinsic = false;
121+
122+
/// True if the target supports directly returning at least two pointers.
123+
bool SupportsDirectReturningAtLeastTwoPointers = true;
121124
};
122125

123126
}

0 commit comments

Comments
 (0)