Skip to content

Commit e58c6b3

Browse files
authored
Merge pull request #7389 from huonw/protocol-type-aliases
[Generic Signature Builder] Improve the handling of typealiases in protocols.
2 parents c77d369 + d671a65 commit e58c6b3

File tree

4 files changed

+382
-76
lines changed

4 files changed

+382
-76
lines changed

include/swift/AST/DiagnosticsSema.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1581,6 +1581,9 @@ ERROR(requires_generic_param_same_type_does_not_conform,none,
15811581
(Type, Identifier))
15821582
ERROR(requires_same_concrete_type,none,
15831583
"generic signature requires types %0 and %1 to be the same", (Type, Type))
1584+
ERROR(protocol_typealias_conflict, none,
1585+
"typealias %0 requires types %1 and %2 to be the same",
1586+
(Identifier, Type, Type))
15841587

15851588
ERROR(mutiple_layout_constraints,none,
15861589
"multiple layout constraints cannot be used at the same time: %0 and %1",

include/swift/AST/GenericSignatureBuilder.h

Lines changed: 59 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -366,6 +366,9 @@ class GenericSignatureBuilder {
366366
/// type or some type derived from it.
367367
class PotentialArchetype;
368368

369+
using UnresolvedType = llvm::PointerUnion<PotentialArchetype *, Type>;
370+
struct ResolvedType;
371+
369372
using RequirementRHS =
370373
llvm::PointerUnion3<Type, PotentialArchetype *, LayoutConstraint>;
371374

@@ -419,6 +422,49 @@ class GenericSignatureBuilder {
419422
llvm::SmallPtrSetImpl<ProtocolDecl *> &Visited);
420423

421424
public:
425+
/// \brief Add a new same-type requirement between two fully resolved types
426+
/// (output of \c GenericSignatureBuilder::resolve).
427+
///
428+
/// If the types refer to two concrete types that are fundamentally
429+
/// incompatible (e.g. \c Foo<Bar<T>> and \c Foo<Baz>), \c diagnoseMismatch is
430+
/// called with the two types that don't match (\c Bar<T> and \c Baz for the
431+
/// previous example).
432+
bool
433+
addSameTypeRequirement(ResolvedType paOrT1, ResolvedType paOrT2,
434+
const RequirementSource *Source,
435+
llvm::function_ref<void(Type, Type)> diagnoseMismatch);
436+
437+
/// \brief Add a new same-type requirement between two fully resolved types
438+
/// (output of GenericSignatureBuilder::resolve).
439+
///
440+
/// The two types must not be incompatible concrete types.
441+
bool addSameTypeRequirement(ResolvedType paOrT1, ResolvedType paOrT2,
442+
const RequirementSource *Source);
443+
444+
/// \brief Add a new same-type requirement between two unresolved types.
445+
///
446+
/// The types are resolved with \c GenericSignatureBuilder::resolve, and must
447+
/// not be incompatible concrete types.
448+
bool addSameTypeRequirement(UnresolvedType paOrT1, UnresolvedType paOrT2,
449+
const RequirementSource *Source);
450+
451+
/// \brief Add a new same-type requirement between two unresolved types.
452+
///
453+
/// The types are resolved with \c GenericSignatureBuilder::resolve. \c
454+
/// diagnoseMismatch is called if the two types refer to incompatible concrete
455+
/// types.
456+
bool
457+
addSameTypeRequirement(UnresolvedType paOrT1, UnresolvedType paOrT2,
458+
const RequirementSource *Source,
459+
llvm::function_ref<void(Type, Type)> diagnoseMismatch);
460+
461+
private:
462+
/// \brief Add a new superclass requirement specifying that the given
463+
/// potential archetype has the given type as an ancestor.
464+
bool addSuperclassRequirement(PotentialArchetype *T,
465+
Type Superclass,
466+
const RequirementSource *Source);
467+
422468
/// \brief Add a new conformance requirement specifying that the given
423469
/// potential archetypes are equivalent.
424470
bool addSameTypeRequirementBetweenArchetypes(PotentialArchetype *T1,
@@ -431,21 +477,14 @@ class GenericSignatureBuilder {
431477
Type Concrete,
432478
const RequirementSource *Source);
433479

434-
private:
435-
/// \brief Add a new superclass requirement specifying that the given
436-
/// potential archetype has the given type as an ancestor.
437-
bool addSuperclassRequirement(PotentialArchetype *T,
438-
Type Superclass,
439-
const RequirementSource *Source);
440-
441480
/// \brief Add a new same-type requirement specifying that the given two
442481
/// types should be the same.
443482
///
444483
/// \param diagnoseMismatch Callback invoked when the types in the same-type
445484
/// requirement mismatch.
446-
bool addSameTypeRequirement(
447-
Type T1, Type T2, const RequirementSource *Source,
448-
llvm::function_ref<void(Type, Type)> diagnoseMismatch);
485+
bool addSameTypeRequirementBetweenConcrete(
486+
Type T1, Type T2, const RequirementSource *Source,
487+
llvm::function_ref<void(Type, Type)> diagnoseMismatch);
449488

450489
/// Add the requirements placed on the given type parameter
451490
/// to the given potential archetype.
@@ -587,6 +626,16 @@ class GenericSignatureBuilder {
587626
/// For any type that cannot refer to an archetype, this routine returns null.
588627
PotentialArchetype *resolveArchetype(Type type);
589628

629+
/// \brief Resolve the given type as far as this Builder knows how.
630+
///
631+
/// This returns either a non-typealias potential archetype or a Type, if \c
632+
/// type is concrete.
633+
// FIXME: the hackTypeFromGenericTypeAlias is just temporarily patching over
634+
// problems with generic typealiases (see the comment on the ResolvedType
635+
// function)
636+
ResolvedType resolve(UnresolvedType type,
637+
bool hackTypeFromGenericTypeAlias = false);
638+
590639
/// \brief Dump all of the requirements, both specified and inferred.
591640
LLVM_ATTRIBUTE_DEPRECATED(
592641
void dump(),

0 commit comments

Comments
 (0)