Skip to content

Commit 8551b32

Browse files
committed
[NFC] Make EnumElementPattern carry a DeclName
This has the side effect of threading compound name support through more enum pattern code, although it’s still not complete.
1 parent 93b9c0b commit 8551b32

7 files changed

+72
-59
lines changed

include/swift/AST/DiagnosticsSema.def

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3576,22 +3576,22 @@ ERROR(cannot_convert_single_tuple_into_multiple_arguments,none,
35763576

35773577
ERROR(enum_element_pattern_assoc_values_mismatch,none,
35783578
"pattern with associated values does not match enum case %0",
3579-
(Identifier))
3579+
(DeclName))
35803580
NOTE(enum_element_pattern_assoc_values_remove,none,
35813581
"remove associated values to make the pattern match", ())
35823582
ERROR(tuple_pattern_length_mismatch,none,
35833583
"tuple pattern has the wrong length for tuple type %0", (Type))
35843584
ERROR(tuple_pattern_label_mismatch,none,
35853585
"tuple pattern element label %0 must be %1", (Identifier, Identifier))
35863586
ERROR(enum_element_pattern_member_not_found,none,
3587-
"enum case '%0' not found in type %1", (StringRef, Type))
3587+
"enum case %0 not found in type %1", (DeclName, Type))
35883588
ERROR(optional_element_pattern_not_valid_type,none,
35893589
"'?' pattern cannot match values of type %0", (Type))
35903590
ERROR(condition_optional_element_pattern_not_valid_type,none,
35913591
"initializer for conditional binding must have Optional type, not %0",
35923592
(Type))
35933593
ERROR(enum_element_pattern_not_member_of_enum,none,
3594-
"enum case '%0' is not a member of type %1", (StringRef, Type))
3594+
"enum case %0 is not a member of type %1", (DeclName, Type))
35953595
ERROR(ambiguous_enum_pattern_type,none,
35963596
"generic enum type %0 is ambiguous without explicit generic parameters "
35973597
"when matching value of type %1", (Type, Type))

include/swift/AST/Pattern.h

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -504,14 +504,14 @@ class IsPattern : public Pattern {
504504
class EnumElementPattern : public Pattern {
505505
TypeLoc ParentType;
506506
SourceLoc DotLoc;
507-
SourceLoc NameLoc;
508-
Identifier Name;
507+
DeclNameLoc NameLoc;
508+
DeclName Name;
509509
PointerUnion<EnumElementDecl *, Expr*> ElementDeclOrUnresolvedOriginalExpr;
510510
Pattern /*nullable*/ *SubPattern;
511511

512512
public:
513-
EnumElementPattern(TypeLoc ParentType, SourceLoc DotLoc, SourceLoc NameLoc,
514-
Identifier Name, EnumElementDecl *Element,
513+
EnumElementPattern(TypeLoc ParentType, SourceLoc DotLoc, DeclNameLoc NameLoc,
514+
DeclName Name, EnumElementDecl *Element,
515515
Pattern *SubPattern, Optional<bool> Implicit = None)
516516
: Pattern(PatternKind::EnumElement),
517517
ParentType(ParentType), DotLoc(DotLoc), NameLoc(NameLoc), Name(Name),
@@ -524,8 +524,8 @@ class EnumElementPattern : public Pattern {
524524
/// Create an unresolved EnumElementPattern for a `.foo` pattern relying on
525525
/// contextual type.
526526
EnumElementPattern(SourceLoc DotLoc,
527-
SourceLoc NameLoc,
528-
Identifier Name,
527+
DeclNameLoc NameLoc,
528+
DeclName Name,
529529
Pattern *SubPattern,
530530
Expr *UnresolvedOriginalExpr)
531531
: Pattern(PatternKind::EnumElement),
@@ -551,7 +551,7 @@ class EnumElementPattern : public Pattern {
551551

552552
void setSubPattern(Pattern *p) { SubPattern = p; }
553553

554-
Identifier getName() const { return Name; }
554+
DeclName getName() const { return Name; }
555555

556556
EnumElementDecl *getElementDecl() const {
557557
return ElementDeclOrUnresolvedOriginalExpr.dyn_cast<EnumElementDecl*>();
@@ -567,18 +567,18 @@ class EnumElementPattern : public Pattern {
567567
return ElementDeclOrUnresolvedOriginalExpr.is<Expr*>();
568568
}
569569

570-
SourceLoc getNameLoc() const { return NameLoc; }
571-
SourceLoc getLoc() const { return NameLoc; }
570+
DeclNameLoc getNameLoc() const { return NameLoc; }
571+
SourceLoc getLoc() const { return NameLoc.getBaseNameLoc(); }
572572
SourceLoc getStartLoc() const {
573573
return ParentType.hasLocation() ? ParentType.getSourceRange().Start :
574574
DotLoc.isValid() ? DotLoc
575-
: NameLoc;
575+
: NameLoc.getBaseNameLoc();
576576
}
577577
SourceLoc getEndLoc() const {
578578
if (SubPattern && SubPattern->getSourceRange().isValid()) {
579579
return SubPattern->getSourceRange().End;
580580
}
581-
return NameLoc;
581+
return NameLoc.getEndLoc();
582582
}
583583
SourceRange getSourceRange() const { return {getStartLoc(), getEndLoc()}; }
584584

lib/Sema/DerivedConformanceCodingKey.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -213,8 +213,8 @@ deriveBodyCodingKey_enum_stringValue(AbstractFunctionDecl *strValDecl, void *) {
213213
SmallVector<ASTNode, 4> cases;
214214
for (auto *elt : elements) {
215215
auto *pat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
216-
SourceLoc(), SourceLoc(),
217-
Identifier(), elt, nullptr);
216+
SourceLoc(), DeclNameLoc(),
217+
DeclName(), elt, nullptr);
218218
pat->setImplicit();
219219

220220
auto labelItem = CaseLabelItem(pat);

lib/Sema/DerivedConformanceEquatableHashable.cpp

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -308,8 +308,8 @@ static DeclRefExpr *convertEnumToIndex(SmallVectorImpl<ASTNode> &stmts,
308308
for (auto elt : enumDecl->getAllElements()) {
309309
// generate: case .<Case>:
310310
auto pat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
311-
SourceLoc(), SourceLoc(),
312-
Identifier(), elt, nullptr);
311+
SourceLoc(), DeclNameLoc(),
312+
DeclName(), elt, nullptr);
313313
pat->setImplicit();
314314
pat->setType(enumType);
315315

@@ -511,8 +511,8 @@ deriveBodyEquatable_enum_hasAssociatedValues_eq(AbstractFunctionDecl *eqDecl,
511511
auto lhsSubpattern = enumElementPayloadSubpattern(elt, 'l', eqDecl,
512512
lhsPayloadVars);
513513
auto lhsElemPat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
514-
SourceLoc(), SourceLoc(),
515-
Identifier(), elt,
514+
SourceLoc(), DeclNameLoc(),
515+
DeclName(), elt,
516516
lhsSubpattern);
517517
lhsElemPat->setImplicit();
518518

@@ -521,8 +521,8 @@ deriveBodyEquatable_enum_hasAssociatedValues_eq(AbstractFunctionDecl *eqDecl,
521521
auto rhsSubpattern = enumElementPayloadSubpattern(elt, 'r', eqDecl,
522522
rhsPayloadVars);
523523
auto rhsElemPat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
524-
SourceLoc(), SourceLoc(),
525-
Identifier(), elt,
524+
SourceLoc(), DeclNameLoc(),
525+
DeclName(), elt,
526526
rhsSubpattern);
527527
rhsElemPat->setImplicit();
528528

@@ -1033,8 +1033,9 @@ deriveBodyHashable_enum_hasAssociatedValues_hashInto(
10331033
auto payloadPattern = enumElementPayloadSubpattern(elt, 'a', hashIntoDecl,
10341034
payloadVars);
10351035
auto pat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
1036-
SourceLoc(), SourceLoc(),
1037-
elt->getName(), elt, payloadPattern);
1036+
SourceLoc(), DeclNameLoc(),
1037+
elt->getName(), elt,
1038+
payloadPattern);
10381039
pat->setImplicit();
10391040

10401041
auto labelItem = CaseLabelItem(pat);

lib/Sema/DerivedConformanceRawRepresentable.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -109,8 +109,8 @@ deriveBodyRawRepresentable_raw(AbstractFunctionDecl *toRawDecl, void *) {
109109
SmallVector<ASTNode, 4> cases;
110110
for (auto elt : enumDecl->getAllElements()) {
111111
auto pat = new (C) EnumElementPattern(TypeLoc::withoutLoc(enumType),
112-
SourceLoc(), SourceLoc(),
113-
Identifier(), elt, nullptr);
112+
SourceLoc(), DeclNameLoc(),
113+
DeclName(), elt, nullptr);
114114
pat->setImplicit();
115115

116116
auto labelItem = CaseLabelItem(pat);

lib/Sema/TypeCheckPattern.cpp

Lines changed: 36 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -113,8 +113,11 @@ filterForEnumElement(DeclContext *DC, SourceLoc UseLoc,
113113

114114
/// Find an unqualified enum element.
115115
static EnumElementDecl *
116-
lookupUnqualifiedEnumMemberElement(DeclContext *DC,
117-
Identifier name, SourceLoc UseLoc) {
116+
lookupUnqualifiedEnumMemberElement(DeclContext *DC, DeclName name,
117+
SourceLoc UseLoc) {
118+
// FIXME: We should probably pay attention to argument labels someday.
119+
name = name.getBaseName();
120+
118121
auto lookupOptions = defaultUnqualifiedLookupOptions;
119122
lookupOptions |= NameLookupFlags::KnownPrivate;
120123
auto lookup =
@@ -126,10 +129,13 @@ lookupUnqualifiedEnumMemberElement(DeclContext *DC,
126129
/// Find an enum element in an enum type.
127130
static EnumElementDecl *
128131
lookupEnumMemberElement(DeclContext *DC, Type ty,
129-
Identifier name, SourceLoc UseLoc) {
132+
DeclName name, SourceLoc UseLoc) {
130133
if (!ty->mayHaveMembers())
131134
return nullptr;
132135

136+
// FIXME: We should probably pay attention to argument labels someday.
137+
name = name.getBaseName();
138+
133139
// Look up the case inside the enum.
134140
// FIXME: We should be able to tell if this is a private lookup.
135141
NameLookupOptions lookupOptions = defaultMemberLookupOptions;
@@ -440,10 +446,9 @@ class ResolvePattern : public ASTVisitor<ResolvePattern,
440446
if (ume->getName().getBaseName().isSpecial())
441447
return nullptr;
442448

443-
// FIXME: Compound names.
444449
return new (Context)
445-
EnumElementPattern(ume->getDotLoc(), ume->getNameLoc().getBaseNameLoc(),
446-
ume->getName().getBaseIdentifier(), subPattern, ume);
450+
EnumElementPattern(ume->getDotLoc(), ume->getNameLoc(), ume->getName(),
451+
subPattern, ume);
447452
}
448453

449454
// Member syntax 'T.Element' forms a pattern if 'T' is an enum and the
@@ -467,20 +472,17 @@ class ResolvePattern : public ASTVisitor<ResolvePattern,
467472
if (!enumDecl)
468473
return nullptr;
469474

470-
// FIXME: Argument labels?
471475
EnumElementDecl *referencedElement
472-
= lookupEnumMemberElement(DC, ty, ude->getName().getBaseIdentifier(),
473-
ude->getLoc());
476+
= lookupEnumMemberElement(DC, ty, ude->getName(), ude->getLoc());
474477
if (!referencedElement)
475478
return nullptr;
476479

477480
// Build a TypeRepr from the head of the full path.
478-
// FIXME: Compound names.
479481
TypeLoc loc(repr);
480482
loc.setType(ty);
481483
return new (Context) EnumElementPattern(
482-
loc, ude->getDotLoc(), ude->getNameLoc().getBaseNameLoc(),
483-
ude->getName().getBaseIdentifier(), referencedElement, nullptr);
484+
loc, ude->getDotLoc(), ude->getNameLoc(), ude->getName(),
485+
referencedElement, nullptr);
484486
}
485487

486488
// A DeclRef 'E' that refers to an enum element forms an EnumElementPattern.
@@ -492,8 +494,8 @@ class ResolvePattern : public ASTVisitor<ResolvePattern,
492494
// Use the type of the enum from context.
493495
TypeLoc loc = TypeLoc::withoutLoc(
494496
elt->getParentEnum()->getDeclaredTypeInContext());
495-
return new (Context) EnumElementPattern(loc, SourceLoc(), de->getLoc(),
496-
elt->getName(), elt, nullptr);
497+
return new (Context) EnumElementPattern(loc, SourceLoc(), de->getNameLoc(),
498+
elt->createNameRef(), elt, nullptr);
497499
}
498500
Pattern *visitUnresolvedDeclRefExpr(UnresolvedDeclRefExpr *ude) {
499501
// FIXME: This shouldn't be needed. It is only necessary because of the
@@ -502,15 +504,14 @@ class ResolvePattern : public ASTVisitor<ResolvePattern,
502504
//
503505
// Try looking up an enum element in context.
504506
if (EnumElementDecl *referencedElement
505-
= lookupUnqualifiedEnumMemberElement(DC,
506-
ude->getName().getBaseIdentifier(),
507+
= lookupUnqualifiedEnumMemberElement(DC, ude->getName(),
507508
ude->getLoc())) {
508509
auto *enumDecl = referencedElement->getParentEnum();
509510
auto enumTy = enumDecl->getDeclaredTypeInContext();
510511
TypeLoc loc = TypeLoc::withoutLoc(enumTy);
511512

512513
return new (Context) EnumElementPattern(
513-
loc, SourceLoc(), ude->getLoc(), ude->getName().getBaseIdentifier(),
514+
loc, SourceLoc(), ude->getNameLoc(), ude->getName(),
514515
referencedElement, nullptr);
515516
}
516517

@@ -585,8 +586,9 @@ class ResolvePattern : public ASTVisitor<ResolvePattern,
585586

586587
auto *subPattern = getSubExprPattern(ce->getArg());
587588
return new (Context) EnumElementPattern(
588-
loc, SourceLoc(), tailComponent->getIdLoc(),
589-
tailComponent->getIdentifier(), referencedElement, subPattern);
589+
loc, SourceLoc(), DeclNameLoc(tailComponent->getIdLoc()),
590+
tailComponent->getIdentifier(), referencedElement,
591+
subPattern);
590592
}
591593
};
592594

@@ -1131,8 +1133,9 @@ bool TypeChecker::coercePatternToType(Pattern *&P, TypeResolution resolution,
11311133
if (auto *NLE = dyn_cast<NilLiteralExpr>(EP->getSubExpr())) {
11321134
auto *NoneEnumElement = Context.getOptionalNoneDecl();
11331135
P = new (Context) EnumElementPattern(TypeLoc::withoutLoc(type),
1134-
NLE->getLoc(), NLE->getLoc(),
1135-
NoneEnumElement->getName(),
1136+
NLE->getLoc(),
1137+
DeclNameLoc(NLE->getLoc()),
1138+
NoneEnumElement->getFullName(),
11361139
NoneEnumElement, nullptr, false);
11371140
return TypeChecker::coercePatternToType(P, resolution, type, options);
11381141
}
@@ -1166,8 +1169,8 @@ bool TypeChecker::coercePatternToType(Pattern *&P, TypeResolution resolution,
11661169
auto some = Context.getOptionalDecl()->getUniqueElement(/*hasVal*/true);
11671170
sub = new (Context) EnumElementPattern(TypeLoc(),
11681171
IP->getStartLoc(),
1169-
IP->getEndLoc(),
1170-
some->getName(),
1172+
DeclNameLoc(IP->getEndLoc()),
1173+
some->getFullName(),
11711174
nullptr, sub,
11721175
/*Implicit=*/true);
11731176
}
@@ -1251,14 +1254,17 @@ bool TypeChecker::coercePatternToType(Pattern *&P, TypeResolution resolution,
12511254
// isn't a static VarDecl, so the existing mechanics in
12521255
// extractEnumElement won't work.
12531256
if (type->getAnyNominal() == Context.getOptionalDecl()) {
1254-
if (EEP->getName().str() == "None" ||
1255-
EEP->getName().str() == "Some") {
1257+
if (EEP->getName().isSimpleName("None") ||
1258+
EEP->getName().isSimpleName("Some")) {
12561259
SmallString<4> Rename;
1257-
camel_case::toLowercaseWord(EEP->getName().str(), Rename);
1260+
camel_case::toLowercaseWord(EEP->getName()
1261+
.getBaseIdentifier().str(),
1262+
Rename);
12581263
diags.diagnose(
12591264
EEP->getLoc(), diag::availability_decl_unavailable_rename,
1260-
/*"getter" prefix*/ 2, EEP->getName(), /*replaced*/ false,
1261-
/*special kind*/ 0, Rename.str(), /*message*/ StringRef())
1265+
/*"getter" prefix*/ 2, EEP->getName().getBaseName(),
1266+
/*replaced*/ false, /*special kind*/ 0, Rename.str(),
1267+
/*message*/ StringRef())
12621268
.fixItReplace(EEP->getLoc(), Rename.str());
12631269

12641270
return true;
@@ -1288,7 +1294,7 @@ bool TypeChecker::coercePatternToType(Pattern *&P, TypeResolution resolution,
12881294
} else {
12891295
diags.diagnose(EEP->getLoc(),
12901296
diag::enum_element_pattern_member_not_found,
1291-
EEP->getName().str(), type);
1297+
EEP->getName(), type);
12921298
return true;
12931299
}
12941300
}
@@ -1341,7 +1347,7 @@ bool TypeChecker::coercePatternToType(Pattern *&P, TypeResolution resolution,
13411347
} else {
13421348
diags.diagnose(EEP->getLoc(),
13431349
diag::enum_element_pattern_not_member_of_enum,
1344-
EEP->getName().str(), type);
1350+
EEP->getName(), type);
13451351
return true;
13461352
}
13471353
}

lib/Sema/TypeCheckSwitchStmt.cpp

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1451,7 +1451,9 @@ namespace {
14511451
if (!SP) {
14521452
// If there's no sub-pattern then there's no further recursive
14531453
// structure here. Yield the constructor space.
1454-
return Space::forConstructor(item->getType(), VP->getName(), None);
1454+
// FIXME: Compound names.
1455+
return Space::forConstructor(item->getType(),
1456+
VP->getName().getBaseIdentifier(), None);
14551457
}
14561458

14571459
SmallVector<Space, 4> conArgSpace;
@@ -1463,7 +1465,9 @@ namespace {
14631465
[&](TuplePatternElt pate) {
14641466
return projectPattern(pate.getPattern());
14651467
});
1466-
return Space::forConstructor(item->getType(), VP->getName(),
1468+
// FIXME: Compound names.
1469+
return Space::forConstructor(item->getType(),
1470+
VP->getName().getBaseIdentifier(),
14671471
conArgSpace);
14681472
}
14691473
case PatternKind::Paren: {
@@ -1497,7 +1501,9 @@ namespace {
14971501
} else {
14981502
conArgSpace.push_back(projectPattern(SP));
14991503
}
1500-
return Space::forConstructor(item->getType(), VP->getName(),
1504+
// FIXME: Compound names.
1505+
return Space::forConstructor(item->getType(),
1506+
VP->getName().getBaseIdentifier(),
15011507
conArgSpace);
15021508
}
15031509
default:

0 commit comments

Comments
 (0)