Skip to content

Commit b5fed15

Browse files
Merge pull request #84763 from nate-chandler/cherrypick/release/6.2/rdar161606892_2
6.2: [VariadicGenerics] Fix memeffect of metadata accessor.
2 parents d42b260 + dab39bb commit b5fed15

File tree

7 files changed

+66
-13
lines changed

7 files changed

+66
-13
lines changed

include/swift/IRGen/GenericRequirement.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,11 @@ class GenericRequirement {
109109
bool isAnyWitnessTable() const {
110110
return kind == Kind::WitnessTable || kind == Kind::WitnessTablePack;
111111
}
112+
113+
bool isAnyPack() const {
114+
return kind == Kind::MetadataPack || kind == Kind::WitnessTablePack;
115+
}
116+
112117
bool isValue() const {
113118
return kind == Kind::Value;
114119
}

lib/IRGen/GenMeta.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2996,8 +2996,9 @@ void irgen::emitLazyMetadataAccessor(IRGenModule &IGM,
29962996
if (IGM.getOptions().optimizeForSize())
29972997
accessor->addFnAttr(llvm::Attribute::NoInline);
29982998

2999-
bool isReadNone = (genericArgs.Types.size() <=
3000-
NumDirectGenericTypeMetadataAccessFunctionArgs);
2999+
bool isReadNone =
3000+
!genericArgs.hasPacks && (genericArgs.Types.size() <=
3001+
NumDirectGenericTypeMetadataAccessFunctionArgs);
30013002

30023003
emitCacheAccessFunction(
30033004
IGM, accessor, /*cache*/ nullptr, /*cache type*/ nullptr,

lib/IRGen/GenericArguments.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,15 +50,17 @@ struct GenericArguments {
5050
/// The values to use to initialize the arguments structure.
5151
SmallVector<llvm::Value *, 8> Values;
5252
SmallVector<llvm::Type *, 8> Types;
53+
bool hasPacks = false;
5354

54-
void collectTypes(IRGenModule &IGM, NominalTypeDecl *nominal) {
55+
void collectTypes(IRGenModule &IGM, NominalTypeDecl *nominal) {
5556
GenericTypeRequirements requirements(IGM, nominal);
5657
collectTypes(IGM, requirements);
5758
}
5859

5960
void collectTypes(IRGenModule &IGM,
6061
const GenericTypeRequirements &requirements) {
6162
for (auto &requirement : requirements.getRequirements()) {
63+
hasPacks = hasPacks || requirement.isAnyPack();
6264
Types.push_back(requirement.getType(IGM));
6365
}
6466
}

lib/IRGen/IRGenFunction.h

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -395,9 +395,8 @@ class IRGenFunction {
395395

396396
// Emit a call to the given generic type metadata access function.
397397
MetadataResponse emitGenericTypeMetadataAccessFunctionCall(
398-
llvm::Function *accessFunction,
399-
ArrayRef<llvm::Value *> args,
400-
DynamicMetadataRequest request);
398+
llvm::Function *accessFunction, ArrayRef<llvm::Value *> args,
399+
DynamicMetadataRequest request, bool hasPacks = false);
401400

402401
// Emit a reference to the canonical type metadata record for the given AST
403402
// type. This can be used to identify the type at runtime. For types with

lib/IRGen/MetadataRequest.cpp

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -750,7 +750,7 @@ static MetadataResponse emitNominalMetadataRef(IRGenFunction &IGF,
750750
theDecl, genericArgs.Types, NotForDefinition);
751751

752752
response = IGF.emitGenericTypeMetadataAccessFunctionCall(
753-
accessor, genericArgs.Values, request);
753+
accessor, genericArgs.Values, request, genericArgs.hasPacks);
754754
}
755755

756756
IGF.setScopedLocalTypeMetadata(theType, response);
@@ -2467,11 +2467,9 @@ void irgen::emitCacheAccessFunction(IRGenModule &IGM, llvm::Function *accessor,
24672467
IGF.Builder.CreateRet(ret);
24682468
}
24692469

2470-
MetadataResponse
2471-
IRGenFunction::emitGenericTypeMetadataAccessFunctionCall(
2472-
llvm::Function *accessFunction,
2473-
ArrayRef<llvm::Value *> args,
2474-
DynamicMetadataRequest request) {
2470+
MetadataResponse IRGenFunction::emitGenericTypeMetadataAccessFunctionCall(
2471+
llvm::Function *accessFunction, ArrayRef<llvm::Value *> args,
2472+
DynamicMetadataRequest request, bool hasPacks) {
24752473

24762474
SmallVector<llvm::Value *, 8> callArgs;
24772475

@@ -2495,7 +2493,7 @@ IRGenFunction::emitGenericTypeMetadataAccessFunctionCall(
24952493
accessFunction, callArgs);
24962494
call->setDoesNotThrow();
24972495
call->setCallingConv(IGM.SwiftCC);
2498-
call->setMemoryEffects(allocatedArgsBuffer
2496+
call->setMemoryEffects(hasPacks || allocatedArgsBuffer
24992497
? llvm::MemoryEffects::inaccessibleOrArgMemOnly()
25002498
: llvm::MemoryEffects::none());
25012499

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// RUN: %target-swift-frontend %s -target %target-swift-5.9-abi-triple -emit-irgen | %IRGenFileCheck %s
2+
3+
// CHECK: Attrs: noinline nounwind{{$}}
4+
// CHECK-NEXT: define {{.*}}@"$s13rdar1616068921PVMa"
5+
6+
public struct P<each T> {
7+
public var teas: (repeat each T)
8+
}
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
// RUN: %empty-directory(%t)
2+
// RUN: split-file %s %t
3+
4+
// RUN: %target-build-swift \
5+
// RUN: -emit-module \
6+
// RUN: -target %target-swift-5.9-abi-triple \
7+
// RUN: %t/Library.swift \
8+
// RUN: -parse-as-library \
9+
// RUN: -module-name Library \
10+
// RUN: -emit-module-path %t/Library.swiftmodule
11+
12+
// RUN: %target-swift-frontend \
13+
// RUN: %t/Downstream.swift \
14+
// RUN: -emit-irgen \
15+
// RUN: -target %target-swift-5.9-abi-triple \
16+
// RUN: -module-name main \
17+
// RUN: -lLibrary \
18+
// RUN: -I %t \
19+
// RUN: | %FileCheck %t/Downstream.swift --check-prefixes=CHECK,CHECK-OLD
20+
21+
//--- Library.swift
22+
23+
public struct Pack<each T> {
24+
public init() {}
25+
}
26+
27+
public func sink<T>(_ t: T) {}
28+
29+
//--- Downstream.swift
30+
31+
import Library
32+
33+
// CHECK: doit
34+
// CHECK: @"$s7Library4PackVMa"{{.*}} [[CALL:#[^,]+]]
35+
36+
// CHECK: attributes [[CALL]] = { nounwind memory(argmem: readwrite, inaccessiblemem: readwrite) }
37+
@_silgen_name("doit")
38+
func doit<each T, each U>(ts: repeat each T, us: repeat each U) {
39+
sink(Pack<repeat each T, repeat each U>())
40+
}

0 commit comments

Comments
 (0)