Skip to content

[ASTGen] Misc fixes #79843

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Mar 8, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 14 additions & 16 deletions include/swift/AST/ASTBridging.h
Original file line number Diff line number Diff line change
Expand Up @@ -2885,29 +2885,27 @@ struct BridgedRequirementRepr {
BridgedNullableTypeRepr SecondType;
BridgedLayoutConstraint LayoutConstraint;
BridgedSourceLoc LayoutConstraintLoc;

// TODO: bool IsExpansionPattern;
bool IsExpansionPattern;

swift::RequirementRepr unbridged() const;
};

SWIFT_NAME(
"BridgedRequirementRepr.createTypeConstraint(subject:colonLoc:constraint:)")
BridgedRequirementRepr
BridgedRequirementRepr_createTypeConstraint(BridgedTypeRepr cSubject,
BridgedSourceLoc cColonLoc,
BridgedTypeRepr cConstraint);
SWIFT_NAME(
"BridgedRequirementRepr.createSameType(firstType:equalLoc:secondType:)")
BridgedRequirementRepr
BridgedRequirementRepr_createSameType(BridgedTypeRepr cFirstType,
BridgedSourceLoc cEqualLoc,
BridgedTypeRepr cSecondType);
SWIFT_NAME("BridgedRequirementRepr.createTypeConstraint(subject:colonLoc:"
"constraint:isExpansionPattern:)")
BridgedRequirementRepr BridgedRequirementRepr_createTypeConstraint(
BridgedTypeRepr cSubject, BridgedSourceLoc cColonLoc,
BridgedTypeRepr cConstraint, bool isExpansionPattern);
SWIFT_NAME("BridgedRequirementRepr.createSameType(firstType:equalLoc:"
"secondType:isExpansionPattern:)")
BridgedRequirementRepr BridgedRequirementRepr_createSameType(
BridgedTypeRepr cFirstType, BridgedSourceLoc cEqualLoc,
BridgedTypeRepr cSecondType, bool isExpansionPattern);
SWIFT_NAME("BridgedRequirementRepr.createLayoutConstraint(subject:colonLoc:"
"layout:layoutLoc:)")
"layout:layoutLoc:isExpansionPattern:)")
BridgedRequirementRepr BridgedRequirementRepr_createLayoutConstraint(
BridgedTypeRepr cSubject, BridgedSourceLoc cColonLoc,
BridgedLayoutConstraint cLayout, BridgedSourceLoc cLayoutLoc);
BridgedLayoutConstraint cLayout, BridgedSourceLoc cLayoutLoc,
bool isExpansionPattern);

enum ENUM_EXTENSIBILITY_ATTR(closed) BridgedGenericTypeParamKind : size_t {
/// A regular generic type parameter: 'T'
Expand Down
26 changes: 14 additions & 12 deletions lib/AST/Bridging/GenericsBridging.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -101,57 +101,59 @@ RequirementRepr BridgedRequirementRepr::unbridged() const {
case BridgedRequirementReprKindTypeConstraint:
return RequirementRepr::getTypeConstraint(
FirstType.unbridged(), SeparatorLoc.unbridged(), SecondType.unbridged(),
/*IsExpansionPattern=*/false);
IsExpansionPattern);
case BridgedRequirementReprKindSameType:
return RequirementRepr::getSameType(
FirstType.unbridged(), SeparatorLoc.unbridged(), SecondType.unbridged(),
/*IsExpansionPattern=*/false);
IsExpansionPattern);
case BridgedRequirementReprKindLayoutConstraint:
return RequirementRepr::getLayoutConstraint(
FirstType.unbridged(), SeparatorLoc.unbridged(),
{LayoutConstraint.unbridged(), LayoutConstraintLoc.unbridged()},
/*IsExpansionPattern=*/false);
IsExpansionPattern);
}
}

BridgedRequirementRepr
BridgedRequirementRepr_createTypeConstraint(BridgedTypeRepr cSubject,
BridgedSourceLoc cColonLoc,
BridgedTypeRepr cConstraint) {
BridgedRequirementRepr BridgedRequirementRepr_createTypeConstraint(
BridgedTypeRepr cSubject, BridgedSourceLoc cColonLoc,
BridgedTypeRepr cConstraint, bool isExpansionPattern) {
return {
/*SeparatorLoc=*/cColonLoc,
/*Kind=*/BridgedRequirementReprKindTypeConstraint,
/*FirstType=*/cSubject,
/*SecondType=*/cConstraint.unbridged(),
/*LayoutConstraint=*/{},
/*LayoutConstraintLoc=*/{},
/*IsExpansionPattern=*/isExpansionPattern,
};
}

BridgedRequirementRepr
BridgedRequirementRepr_createSameType(BridgedTypeRepr cFirstType,
BridgedSourceLoc cEqualLoc,
BridgedTypeRepr cSecondType) {
BridgedRequirementRepr BridgedRequirementRepr_createSameType(
BridgedTypeRepr cFirstType, BridgedSourceLoc cEqualLoc,
BridgedTypeRepr cSecondType, bool isExpansionPattern) {
return {
/*SeparatorLoc=*/cEqualLoc,
/*Kind=*/BridgedRequirementReprKindSameType,
/*FirstType=*/cFirstType,
/*SecondType=*/cSecondType.unbridged(),
/*LayoutConstraint=*/{},
/*LayoutConstraintLoc=*/{},
/*IsExpansionPattern=*/isExpansionPattern,
};
}

BridgedRequirementRepr BridgedRequirementRepr_createLayoutConstraint(
BridgedTypeRepr cSubject, BridgedSourceLoc cColonLoc,
BridgedLayoutConstraint cLayout, BridgedSourceLoc cLayoutLoc) {
BridgedLayoutConstraint cLayout, BridgedSourceLoc cLayoutLoc,
bool isExpansionPattern) {
return {
/*SeparatorLoc=*/cColonLoc,
/*Kind=*/BridgedRequirementReprKindLayoutConstraint,
/*FirstType=*/cSubject,
/*SecondType=*/nullptr,
/*LayoutConstraint=*/cLayout,
/*LayoutConstraintLoc=*/cLayoutLoc,
/*IsExpansionPattern=*/isExpansionPattern,
};
}

Expand Down
12 changes: 8 additions & 4 deletions lib/ASTGen/Sources/ASTGen/DeclAttrs.swift
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,10 @@ extension ASTGenVisitor {
return handle(self.generateUnavailableFromAsyncAttr(attribute: node)?.asDeclAttribute)
case .none where attrName == "_unavailableInEmbedded":
return handle(self.generateUnavailableInEmbeddedAttr(attribute: node)?.asDeclAttribute)
case .none where attrName == "_functionBuilder":
// TODO: Diagnostics. '_functionBuilder' is renamed to 'resultBuilder'
return handle(self.generateSimpleDeclAttr(attribute: node, kind: .resultBuilder))


// Simple attributes.
case .addressableSelf,
Expand Down Expand Up @@ -1682,7 +1686,7 @@ extension ASTGenVisitor {
return nil
}

guard let moveAsLike = args.isEmpty ? false : generateConsumingMoveAsLike() else {
guard let moveAsLike = args.isEmpty ? false : generateConsumingMovesAsLike() else {
return nil
}

Expand Down Expand Up @@ -1711,7 +1715,7 @@ extension ASTGenVisitor {
return nil
}

guard let moveAsLike = args.isEmpty ? false : generateConsumingMoveAsLike() else {
guard let moveAsLike = args.isEmpty ? false : generateConsumingMovesAsLike() else {
return nil
}

Expand All @@ -1738,10 +1742,10 @@ extension ASTGenVisitor {
}
}

func generateConsumingMoveAsLike() -> Bool? {
func generateConsumingMovesAsLike() -> Bool? {
self.generateConsumingPlainIdentifierAttrOption(args: &args) {
switch $0.rawText {
case "moveAsLike":
case "movesAsLike":
return true
default:
// TODO: Diagnose.
Expand Down
28 changes: 22 additions & 6 deletions lib/ASTGen/Sources/ASTGen/Generics.swift
Original file line number Diff line number Diff line change
Expand Up @@ -111,25 +111,41 @@ extension ASTGenVisitor {

func generate(genericWhereClause node: GenericWhereClauseSyntax) -> BridgedTrailingWhereClause {
let requirements = node.requirements.lazy.map { elem -> BridgedRequirementRepr in

// Unwrap 'repeat T' to (isRequirementExpansion: true, type: T)
func generateIsExpansionPattern<Node: SyntaxProtocol>(type node: Node) -> (isExpansionPattern: Bool, type: Node) {
if let expansion = node.as(PackExpansionTypeSyntax.self) {
// Force unwrapping is safe because both 'TypeSyntax' and 'SameTypeRequirementSyntax.LeftType' accept 'TypeSyntax'.
return (true, Node(expansion.repetitionPattern)!)
}
return (false, node)
}

switch elem.requirement {
case .conformanceRequirement(let conformance):
let (isExpansionPattern, leftType) = generateIsExpansionPattern(type: conformance.leftType)
return .createTypeConstraint(
subject: self.generate(type: conformance.leftType),
subject: self.generate(type: leftType),
colonLoc: self.generateSourceLoc(conformance.colon),
constraint: self.generate(type: conformance.rightType)
constraint: self.generate(type: conformance.rightType),
isExpansionPattern: isExpansionPattern
)
case .sameTypeRequirement(let sameType):
let (isExpansionPattern, leftType) = generateIsExpansionPattern(type: sameType.leftType)
return .createSameType(
firstType: self.generate(sameTypeLeftType: sameType.leftType),
firstType: self.generate(sameTypeLeftType: leftType),
equalLoc: self.generateSourceLoc(sameType.equal),
secondType: self.generate(sameTypeRightType: sameType.rightType)
secondType: self.generate(sameTypeRightType: sameType.rightType),
isExpansionPattern: isExpansionPattern
)
case .layoutRequirement(let layout):
let (isExpansionPattern, leftType) = generateIsExpansionPattern(type: layout.type)
return .createLayoutConstraint(
subject: self.generate(type: layout.type),
subject: self.generate(type: leftType),
colonLoc: self.generateSourceLoc(layout.colon),
layout: self.generate(layoutRequirement: layout),
layoutLoc: self.generateSourceLoc(layout.layoutSpecifier)
layoutLoc: self.generateSourceLoc(layout.layoutSpecifier),
isExpansionPattern: isExpansionPattern
)
}
}
Expand Down
1 change: 1 addition & 0 deletions test/ASTGen/attrs.swift
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,7 @@ struct ReferenceOwnershipModifierTest<X: AnyObject> {
}

@_rawLayout(like: T) struct RawStorage<T>: ~Copyable {}
@_rawLayout(like: T, movesAsLike) struct RawStorage2<T>: ~Copyable {}
@_rawLayout(likeArrayOf: T, count: 4) struct RawSmallArray<T>: ~Copyable {}
@_rawLayout(size: 4, alignment: 4) struct Lock: ~Copyable {}

Expand Down
2 changes: 2 additions & 0 deletions test/ASTGen/decls.swift
Original file line number Diff line number Diff line change
Expand Up @@ -346,3 +346,5 @@ func testBuilder() {
1
}
}

struct ExpansionRequirementTest<each T> where repeat each T: Comparable {}
3 changes: 3 additions & 0 deletions test/ASTGen/diagnostics.swift
Original file line number Diff line number Diff line change
Expand Up @@ -33,3 +33,6 @@ struct S {
subscript(x: Int) { _ = 1 } // expected-error@:23 {{expected '->' and return type in subscript}}
// expected-note@-1:23 {{insert '->' and return type}}
}

struct ExpansionRequirementTest<each T> {}
extension ExpansionRequirementTest where repeat each T == Int {} // expected-error {{same-element requirements are not yet supported}}