2828#include " swift/AST/Pattern.h"
2929#include " swift/AST/PrettyStackTrace.h"
3030#include " swift/AST/PropertyWrappers.h"
31+ #include " swift/AST/ProtocolConformance.h"
3132#include " swift/AST/TypeDifferenceVisitor.h"
3233#include " swift/AST/Types.h"
3334#include " swift/ClangImporter/ClangModule.h"
@@ -3009,6 +3010,21 @@ void TypeConverter::verifyLexicalLowering(const TypeLowering &lowering,
30093010 }
30103011}
30113012
3013+ static bool isUnchecked (ProtocolConformanceRef conformance) {
3014+ if (!conformance)
3015+ return false ;
3016+ if (!conformance.isConcrete ())
3017+ return false ;
3018+ auto concrete = conformance.getConcrete ();
3019+ assert (concrete);
3020+ auto *root = concrete->getRootConformance ();
3021+ assert (root);
3022+ auto *normal = dyn_cast<NormalProtocolConformance>(root);
3023+ if (!normal)
3024+ return false ;
3025+ return normal->isUnchecked ();
3026+ }
3027+
30123028void TypeConverter::verifyTrivialLowering (const TypeLowering &lowering,
30133029 AbstractionPattern origType,
30143030 CanType substType,
@@ -3042,10 +3058,17 @@ void TypeConverter::verifyTrivialLowering(const TypeLowering &lowering,
30423058 if (!nominal)
30433059 return false ;
30443060
3045- // Nominals with generic parameters must be explicitly conformed to
3046- // BitwiseCopyable.
3047- auto *generic = ty.getAnyGeneric ();
3048- if (generic && generic->isGenericContext ()) {
3061+ // Don't walk into types whose conformance is unchecked--such
3062+ // conformances obstruct automatic inference of BitwiseCopyable.
3063+ auto conformance = M.checkConformance (ty, bitwiseCopyableProtocol);
3064+ if (isUnchecked (conformance)) {
3065+ return true ;
3066+ }
3067+
3068+ // Nominals with fields that conditionally conform to BitwiseCopyable
3069+ // must be explicitly conditionally conformed. Such a field must be a
3070+ // generic context.
3071+ if (nominal->isGenericContext ()) {
30493072 return true ;
30503073 }
30513074
@@ -3059,10 +3082,12 @@ void TypeConverter::verifyTrivialLowering(const TypeLowering &lowering,
30593082 // Return false to indicate seeing a leaf which justifies the type
30603083 // being trivial but not conforming to BitwiseCopyable.
30613084
3062- // A BitwiseCopyable conformer appearing within its layout doesn't
3063- // explain why substType doesn't itself conform.
3064- if (M.checkConformance (ty, bitwiseCopyableProtocol))
3065- return true ;
3085+ // A BitwiseCopyable conformer appearing within its layout explains a
3086+ // non-conformance iff the conformance is @unchecked.
3087+ auto conformance = M.checkConformance (ty, bitwiseCopyableProtocol);
3088+ if (conformance) {
3089+ return !isUnchecked (conformance);
3090+ }
30663091
30673092 // ModuleTypes are trivial but don't warrant being given a conformance
30683093 // to BitwiseCopyable.
@@ -3099,15 +3124,15 @@ void TypeConverter::verifyTrivialLowering(const TypeLowering &lowering,
30993124 return true ;
31003125 }
31013126
3102- // / A non-conforming generic nominal type justifies substType not
3103- // / conforming.
3104- auto *generic = ty. getAnyGeneric ();
3105- if (generic && generic ->isGenericContext ()) {
3127+ // / A field of conditionally-BitwiseCopyable type justifies the
3128+ // / aggregate not conforming because the aggregate must be conformed
3129+ // / explicitly in that case.
3130+ if (nominal ->isGenericContext ()) {
31063131 return false ;
31073132 }
31083133
31093134 // The field is trivial and the whole type is nonconforming. That's
3110- // legal iff the type is public.
3135+ // legal iff the field's type is public.
31113136 return !nominal
31123137 ->getFormalAccessScope (
31133138 /* useDC=*/ nullptr ,
@@ -3148,6 +3173,7 @@ void TypeConverter::verifyTrivialLowering(const TypeLowering &lowering,
31483173 llvm::errs () << " Non-trivial type with _BitwiseCopyable conformance!?:\n "
31493174 << substType << " \n " ;
31503175 conformance.print (llvm::errs ());
3176+ llvm::errs () << " \n " ;
31513177 assert (false );
31523178 }
31533179 }
0 commit comments