@@ -21,7 +21,7 @@ use abi;
21
21
use value:: Value ;
22
22
23
23
use llvm;
24
- use llvm:: debuginfo:: { DIType , DIFile , DIScope , DIDescriptor ,
24
+ use llvm:: debuginfo:: { DIArray , DIType , DIFile , DIScope , DIDescriptor ,
25
25
DICompositeType , DILexicalBlock , DIFlags } ;
26
26
27
27
use rustc_data_structures:: stable_hasher:: { HashStable , StableHasher } ;
@@ -34,6 +34,7 @@ use rustc::ty::Instance;
34
34
use common:: CodegenCx ;
35
35
use rustc:: ty:: { self , AdtKind , ParamEnv , Ty , TyCtxt } ;
36
36
use rustc:: ty:: layout:: { self , Align , LayoutOf , PrimitiveExt , Size , TyLayout } ;
37
+ use rustc:: ty:: subst:: UnpackedKind ;
37
38
use rustc:: session:: config;
38
39
use rustc:: util:: nodemap:: FxHashMap ;
39
40
use rustc_fs_util:: path2cstr;
@@ -266,6 +267,7 @@ impl RecursiveTypeDescription<'ll, 'tcx> {
266
267
267
268
// ... and attach them to the stub to complete it.
268
269
set_members_of_composite_type ( cx,
270
+ unfinished_type,
269
271
metadata_stub,
270
272
member_descriptions) ;
271
273
return MetadataCreationResult :: new ( metadata_stub, true ) ;
@@ -1174,6 +1176,7 @@ impl EnumMemberDescriptionFactory<'ll, 'tcx> {
1174
1176
member_description_factory. create_member_descriptions ( cx) ;
1175
1177
1176
1178
set_members_of_composite_type ( cx,
1179
+ self . enum_type ,
1177
1180
variant_type_metadata,
1178
1181
member_descriptions) ;
1179
1182
vec ! [
@@ -1204,6 +1207,7 @@ impl EnumMemberDescriptionFactory<'ll, 'tcx> {
1204
1207
. create_member_descriptions ( cx) ;
1205
1208
1206
1209
set_members_of_composite_type ( cx,
1210
+ self . enum_type ,
1207
1211
variant_type_metadata,
1208
1212
member_descriptions) ;
1209
1213
MemberDescription {
@@ -1231,6 +1235,7 @@ impl EnumMemberDescriptionFactory<'ll, 'tcx> {
1231
1235
member_description_factory. create_member_descriptions ( cx) ;
1232
1236
1233
1237
set_members_of_composite_type ( cx,
1238
+ self . enum_type ,
1234
1239
variant_type_metadata,
1235
1240
variant_member_descriptions) ;
1236
1241
@@ -1534,13 +1539,15 @@ fn composite_type_metadata(
1534
1539
containing_scope) ;
1535
1540
// ... and immediately create and add the member descriptions.
1536
1541
set_members_of_composite_type ( cx,
1542
+ composite_type,
1537
1543
composite_type_metadata,
1538
1544
member_descriptions) ;
1539
1545
1540
1546
composite_type_metadata
1541
1547
}
1542
1548
1543
- fn set_members_of_composite_type ( cx : & CodegenCx < ' ll , ' _ > ,
1549
+ fn set_members_of_composite_type ( cx : & CodegenCx < ' ll , ' tcx > ,
1550
+ composite_type : Ty < ' tcx > ,
1544
1551
composite_type_metadata : & ' ll DICompositeType ,
1545
1552
member_descriptions : Vec < MemberDescription < ' ll > > ) {
1546
1553
// In some rare cases LLVM metadata uniquing would lead to an existing type
@@ -1580,10 +1587,57 @@ fn set_members_of_composite_type(cx: &CodegenCx<'ll, '_>,
1580
1587
} )
1581
1588
. collect ( ) ;
1582
1589
1590
+ let type_params = compute_type_parameters ( cx, composite_type) ;
1583
1591
unsafe {
1584
1592
let type_array = create_DIArray ( DIB ( cx) , & member_metadata[ ..] ) ;
1585
- llvm:: LLVMRustDICompositeTypeSetTypeArray (
1586
- DIB ( cx) , composite_type_metadata, type_array) ;
1593
+ llvm:: LLVMRustDICompositeTypeReplaceArrays (
1594
+ DIB ( cx) , composite_type_metadata, Some ( type_array) , type_params) ;
1595
+ }
1596
+ }
1597
+
1598
+ // Compute the type parameters for a type, if any, for the given
1599
+ // metadata.
1600
+ fn compute_type_parameters ( cx : & CodegenCx < ' ll , ' tcx > , ty : Ty < ' tcx > ) -> Option < & ' ll DIArray > {
1601
+ if let ty:: Adt ( def, substs) = ty. sty {
1602
+ if !substs. types ( ) . next ( ) . is_none ( ) {
1603
+ let generics = cx. tcx . generics_of ( def. did ) ;
1604
+ let names = get_parameter_names ( cx, generics) ;
1605
+ let template_params: Vec < _ > = substs. iter ( ) . zip ( names) . filter_map ( |( kind, name) | {
1606
+ if let UnpackedKind :: Type ( ty) = kind. unpack ( ) {
1607
+ let actual_type = cx. tcx . normalize_erasing_regions ( ParamEnv :: reveal_all ( ) , ty) ;
1608
+ let actual_type_metadata =
1609
+ type_metadata ( cx, actual_type, syntax_pos:: DUMMY_SP ) ;
1610
+ let name = SmallCStr :: new ( & name. as_str ( ) ) ;
1611
+ Some ( unsafe {
1612
+
1613
+ Some ( llvm:: LLVMRustDIBuilderCreateTemplateTypeParameter (
1614
+ DIB ( cx) ,
1615
+ None ,
1616
+ name. as_ptr ( ) ,
1617
+ actual_type_metadata,
1618
+ unknown_file_metadata ( cx) ,
1619
+ 0 ,
1620
+ 0 ,
1621
+ ) )
1622
+ } )
1623
+ } else {
1624
+ None
1625
+ }
1626
+ } ) . collect ( ) ;
1627
+
1628
+ return Some ( create_DIArray ( DIB ( cx) , & template_params[ ..] ) ) ;
1629
+ }
1630
+ }
1631
+ return None ;
1632
+
1633
+ fn get_parameter_names ( cx : & CodegenCx ,
1634
+ generics : & ty:: Generics )
1635
+ -> Vec < InternedString > {
1636
+ let mut names = generics. parent . map_or ( vec ! [ ] , |def_id| {
1637
+ get_parameter_names ( cx, cx. tcx . generics_of ( def_id) )
1638
+ } ) ;
1639
+ names. extend ( generics. params . iter ( ) . map ( |param| param. name ) ) ;
1640
+ names
1587
1641
}
1588
1642
}
1589
1643
0 commit comments