@@ -1226,8 +1226,7 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
12261226 return DITy;
12271227 }
12281228
1229- std::pair<bool , Type>
1230- getUnsubstituedType (Type Ty, StringRef MangledName) {
1229+ std::pair<bool , Type> getUnsubstitutedType (Type Ty, StringRef MangledName) {
12311230 if (!Ty)
12321231 return {false ,{}};
12331232 // Go from Pair<Int, Double> to Pair<T, U>.
@@ -1252,7 +1251,7 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
12521251 llvm::DIScope *Scope, llvm::DIFile *File,
12531252 unsigned Line, llvm::DINode::DIFlags Flags) {
12541253 auto [IsUnsubstituted, UnsubstitutedTy] =
1255- getUnsubstituedType (EnumTy, MangledName);
1254+ getUnsubstitutedType (EnumTy, MangledName);
12561255 auto UnsubstitutedDbgTy = DebugTypeInfo::getFromTypeInfo (
12571256 UnsubstitutedTy, IGM.getTypeInfoForUnlowered (UnsubstitutedTy), IGM);
12581257 if (IsUnsubstituted)
@@ -1301,7 +1300,7 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
13011300 Name);
13021301
13031302 auto [IsUnsubstitued, UnsubstitutedType] =
1304- getUnsubstituedType (Type, MangledName);
1303+ getUnsubstitutedType (Type, MangledName);
13051304 auto UnsubstitutedDbgTy = DebugTypeInfo::getFromTypeInfo (
13061305 UnsubstitutedType, IGM.getTypeInfoForUnlowered (UnsubstitutedType), IGM);
13071306 if (IsUnsubstitued)
@@ -1326,19 +1325,24 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
13261325 }
13271326 }
13281327
1329- // Recursive types such as `class A<B> { let a : A<A<B>> }` would produce an
1330- // infinite chain of expansions for the type of `a`. Break these cycles by
1331- // emitting any bound generics that still have type parameters as forward
1332- // declarations.
1333- if (Type->hasTypeParameter () || Type->hasPrimaryArchetype ())
1334- return createOpaqueStructWithSizedContainer (
1335- Scope, Decl ? Decl->getNameStr () : " " , File, Line, SizeInBits,
1336- AlignInBits, Flags, MangledName, collectGenericParams (Type, true ),
1337- UnsubstitutedDITy);
1328+ // Generally, we don't emit members of a specialized bound generic, because
1329+ // these can be reconstructed by substituting the "template parameters" in
1330+ // the unspecialized type. We make an exception for inline arrays, because
1331+ // DWARF has special support for arrays.
1332+ if (Type->isInlineArray () && !Type->hasTypeParameter () &&
1333+ !Type->hasPrimaryArchetype ())
1334+ // Create the substituted type.
1335+ return createStructType (Type, Decl, Scope, File, Line, SizeInBits,
1336+ AlignInBits, Flags, MangledName,
1337+ UnsubstitutedDITy);
13381338
1339- // Create the substituted type.
1340- return createStructType (Type, Decl, Scope, File, Line, SizeInBits,
1341- AlignInBits, Flags, MangledName, UnsubstitutedDITy);
1339+ // Create the substituted type (without members).
1340+ llvm::DIType *SpecializedDITy = createOpaqueStructWithSizedContainer (
1341+ Scope, Decl ? Decl->getNameStr () : " " , File, Line, SizeInBits,
1342+ AlignInBits, Flags, MangledName, collectGenericParams (Type),
1343+ UnsubstitutedDITy);
1344+ DBuilder.replaceTemporary (std::move (FwdDecl), SpecializedDITy);
1345+ return SpecializedDITy;
13421346 }
13431347
13441348 // / Create debug information for an enum with a raw type (enum E : Int {}).
@@ -1600,6 +1604,10 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
16001604
16011605 llvm::Metadata *Elements[] = {DBuilder.createMemberType (
16021606 Scope, " " , File, 0 , SizeInBits, AlignInBits, 0 , Flags, UniqueType)};
1607+ // FIXME: It's a limitation of LLVM that a forward declaration cannot have a
1608+ // specificationOf, so this attritbute is put on the sized container type
1609+ // instead. This is confusing consumers, and LLDB has to go out of its way
1610+ // to parse these confusing types as intended.
16031611 return DBuilder.createStructType (
16041612 Scope, " " , File, Line, SizeInBits, AlignInBits, Flags,
16051613 /* DerivedFrom */ nullptr , DBuilder.getOrCreateArray (Elements),
@@ -2338,7 +2346,7 @@ class IRGenDebugInfoImpl : public IRGenDebugInfo {
23382346 if (!isa<llvm::DICompositeType>(CachedType))
23392347 return true ;
23402348 bool IsUnsubstituted =
2341- getUnsubstituedType (DbgTy.getType (), getMangledName (DbgTy).Canonical )
2349+ getUnsubstitutedType (DbgTy.getType (), getMangledName (DbgTy).Canonical )
23422350 .first ;
23432351 std::optional<uint64_t > SizeInBits;
23442352 if (!IsUnsubstituted)
0 commit comments