diff --git a/lib/IRGen/DebugTypeInfo.cpp b/lib/IRGen/DebugTypeInfo.cpp index 34fa19bd537f0..51e1868b76d66 100644 --- a/lib/IRGen/DebugTypeInfo.cpp +++ b/lib/IRGen/DebugTypeInfo.cpp @@ -60,20 +60,25 @@ DebugTypeInfo DebugTypeInfo::getFromTypeInfo(swift::Type Ty, DebugTypeInfo DebugTypeInfo::getLocalVariable(VarDecl *Decl, swift::Type Ty, const TypeInfo &Info) { - - auto DeclType = Decl->getInterfaceType(); - auto RealType = Ty; - - // DynamicSelfType is also sugar as far as debug info is concerned. - auto Sugared = DeclType; - if (auto DynSelfTy = DeclType->getAs()) - Sugared = DynSelfTy->getSelfType(); - // Prefer the original, potentially sugared version of the type if // the type hasn't been mucked with by an optimization pass. - auto *Type = Sugared->isEqual(RealType) ? DeclType.getPointer() - : RealType.getPointer(); - return getFromTypeInfo(Type, Info); + swift::Type DeclType = Decl->getInterfaceType(); + swift::Type RealType = Ty; + + swift::Type DebugType; + if (auto DynSelfTy = DeclType->getAs()) { + // DynamicSelfType is also sugar as far as debug info is concerned. + auto DesugaredSelf = DynSelfTy->getSelfType(); + DebugType = DesugaredSelf->isEqual(RealType) ? DynSelfTy : RealType; + } else { + // Map the sugared type into the context to resolve bound generics and + // generic type aliases. + DeclContext *DeclCtx = Decl->getDeclContext(); + swift::Type Sugared = + DeclCtx ? DeclCtx->mapTypeIntoContext(DeclType) : DeclType; + DebugType = Sugared->isEqual(RealType) ? Sugared : RealType; + } + return getFromTypeInfo(DebugType, Info); } DebugTypeInfo DebugTypeInfo::getMetadata(swift::Type Ty, llvm::Type *StorageTy, diff --git a/lib/IRGen/IRGenSIL.cpp b/lib/IRGen/IRGenSIL.cpp index 7292f9e0160ca..81d885aaeac80 100644 --- a/lib/IRGen/IRGenSIL.cpp +++ b/lib/IRGen/IRGenSIL.cpp @@ -3660,7 +3660,7 @@ void IRGenSILFunction::visitDebugValueInst(DebugValueInst *i) { llvm::SmallVector Copy; emitShadowCopyIfNeeded(SILVal, i->getDebugScope(), *VarInfo, IsAnonymous, Copy); - bindArchetypes(DbgTy.getType()); + bindArchetypes(RealTy); if (!IGM.DebugInfo) return; @@ -3691,7 +3691,7 @@ void IRGenSILFunction::visitDebugValueAddrInst(DebugValueAddrInst *i) { auto DbgTy = DebugTypeInfo::getLocalVariable( Decl, RealType, getTypeInfo(SILVal->getType())); - bindArchetypes(DbgTy.getType()); + bindArchetypes(RealType); if (!IGM.DebugInfo) return; @@ -3991,7 +3991,7 @@ void IRGenSILFunction::emitDebugInfoForAllocStack(AllocStackInst *i, auto RealType = SILTy.getASTType(); auto DbgTy = DebugTypeInfo::getLocalVariable(Decl, RealType, type); - bindArchetypes(DbgTy.getType()); + bindArchetypes(RealType); if (IGM.DebugInfo) emitDebugVariableDeclaration(addr, DbgTy, SILTy, DS, Decl, *VarInfo, Indirection); diff --git a/test/DebugInfo/bound-generic-struct-extension.swift b/test/DebugInfo/bound-generic-struct-extension.swift new file mode 100644 index 0000000000000..ec6e13aa235f2 --- /dev/null +++ b/test/DebugInfo/bound-generic-struct-extension.swift @@ -0,0 +1,28 @@ +// RUN: %target-swift-frontend %s -emit-ir -g -o - | %FileCheck %s + +// Test that a bound generic type is fully resolved in the debug info. + +public protocol P {} + +public struct S : P { + var x: Int +} +// This is significant, it must be bound to S: main.BoundGeneric +// CHECK-DAG: ![[S:[0-9]+]] = !DICompositeType({{.*}}identifier: "$s4main12BoundGenericVyAA1SVGD") + +public extension BoundGeneric where T == S { + func f() { +// CHECK-DAG: !DILocalVariable(name: "self", arg: 1,{{.*}} line: [[@LINE-1]],{{.*}} type: ![[C_BGS:[0-9]+]], +// CHECK-DAG: ![[C_BGS]] = !DIDerivedType(tag: DW_TAG_const_type,{{.*}} baseType: ![[BGS:[0-9]+]]) +// CHECK-DAG: ![[BGS]] = !DICompositeType(tag: DW_TAG_structure_type,{{.*}} elements: ![[ELTS:[0-9]+]], +// CHECK-DAG: ![[ELTS]] = !{![[MEMBER:[0-9]+]]} +// CHECK-DAG: ![[MEMBER]] = !DIDerivedType(tag: DW_TAG_member,{{.*}} baseType: ![[S]], + } +} + +public struct BoundGeneric where T : P { + let x : T +} + +public let pat = BoundGeneric(x: S(x: 23)) +pat.f() diff --git a/test/DebugInfo/generic-typealias.swift b/test/DebugInfo/generic-typealias.swift new file mode 100644 index 0000000000000..3b4c4399e4008 --- /dev/null +++ b/test/DebugInfo/generic-typealias.swift @@ -0,0 +1,19 @@ +// RUN: %target-swift-frontend %s -emit-ir -g -o - | %FileCheck %s + +// Test that a generic type alias is represented in the debug info. + +public struct S { + public typealias Alias = (T, T) + // CHECK: ![[T_T:[0-9]+]] = !DICompositeType(tag: DW_TAG_structure_type, name: "$sx_xtD" + public let member : Alias + public func f(t : Alias) -> Alias { return t } + // CHECK: !DILocalVariable(name: "t", arg: 1,{{.*}} line: [[@LINE-1]], + // CHECK-SAME: type: ![[C_ALIAS:[0-9]+]]) + // CHECK: ![[C_ALIAS]] = !DIDerivedType(tag: DW_TAG_const_type, + // CHECK-SAME: baseType: ![[ALIAS:[0-9]+]]) + // CHECK: ![[ALIAS]] = !DIDerivedType(tag: DW_TAG_typedef, name: "$ + // CHECK-SAME: baseType: ![[T_T]]) + +} + +public let s = S(member: (4, 2))