@@ -45,7 +45,7 @@ use hir_def::{
45
45
hir:: { BindingAnnotation , BindingId , ExprOrPatId , LabelId , Pat } ,
46
46
item_tree:: ItemTreeNode ,
47
47
lang_item:: LangItemTarget ,
48
- layout:: { self , ReprOptions } ,
48
+ layout:: { self , ReprOptions , TargetDataLayout } ,
49
49
macro_id_to_def_id,
50
50
nameres:: { self , diagnostics:: DefDiagnostic , ModuleOrigin } ,
51
51
per_ns:: PerNs ,
@@ -62,7 +62,7 @@ use hir_ty::{
62
62
consteval:: { try_const_usize, unknown_const_as_generic, ConstEvalError , ConstExt } ,
63
63
diagnostics:: BodyValidationDiagnostic ,
64
64
display:: HexifiedConst ,
65
- layout:: { Layout as TyLayout , LayoutError , RustcEnumVariantIdx , TagEncoding } ,
65
+ layout:: { Layout as TyLayout , RustcEnumVariantIdx , TagEncoding } ,
66
66
method_resolution:: { self , TyFingerprint } ,
67
67
mir:: { self , interpret_mir} ,
68
68
primitive:: UintTy ,
@@ -133,6 +133,7 @@ pub use {
133
133
} ,
134
134
hir_ty:: {
135
135
display:: { ClosureStyle , HirDisplay , HirDisplayError , HirWrite } ,
136
+ layout:: LayoutError ,
136
137
mir:: MirEvalError ,
137
138
PointerCast , Safety ,
138
139
} ,
@@ -962,7 +963,8 @@ impl Field {
962
963
}
963
964
964
965
pub fn layout ( & self , db : & dyn HirDatabase ) -> Result < Layout , LayoutError > {
965
- db. layout_of_ty ( self . ty ( db) . ty . clone ( ) , self . parent . module ( db) . krate ( ) . into ( ) ) . map ( Layout )
966
+ db. layout_of_ty ( self . ty ( db) . ty . clone ( ) , self . parent . module ( db) . krate ( ) . into ( ) )
967
+ . map ( |layout| Layout ( layout, db. target_data_layout ( self . krate ( db) . into ( ) ) . unwrap ( ) ) )
966
968
}
967
969
968
970
pub fn parent_def ( & self , _db : & dyn HirDatabase ) -> VariantDef {
@@ -1135,23 +1137,8 @@ impl Enum {
1135
1137
self . variants ( db) . iter ( ) . any ( |v| !matches ! ( v. kind( db) , StructKind :: Unit ) )
1136
1138
}
1137
1139
1138
- pub fn layout ( self , db : & dyn HirDatabase ) -> Result < ( Layout , usize ) , LayoutError > {
1139
- let layout = Adt :: from ( self ) . layout ( db) ?;
1140
- let tag_size =
1141
- if let layout:: Variants :: Multiple { tag, tag_encoding, .. } = & layout. 0 . variants {
1142
- match tag_encoding {
1143
- TagEncoding :: Direct => {
1144
- let target_data_layout = db
1145
- . target_data_layout ( self . module ( db) . krate ( ) . id )
1146
- . ok_or ( LayoutError :: TargetLayoutNotAvailable ) ?;
1147
- tag. size ( & * target_data_layout) . bytes_usize ( )
1148
- }
1149
- TagEncoding :: Niche { .. } => 0 ,
1150
- }
1151
- } else {
1152
- 0
1153
- } ;
1154
- Ok ( ( layout, tag_size) )
1140
+ pub fn layout ( self , db : & dyn HirDatabase ) -> Result < Layout , LayoutError > {
1141
+ Adt :: from ( self ) . layout ( db)
1155
1142
}
1156
1143
}
1157
1144
@@ -1214,19 +1201,16 @@ impl Variant {
1214
1201
db. const_eval_discriminant ( self . into ( ) )
1215
1202
}
1216
1203
1217
- /// Return layout of the variant and tag size of the parent enum.
1218
- pub fn layout ( & self , db : & dyn HirDatabase ) -> Result < ( Layout , usize ) , LayoutError > {
1204
+ pub fn layout ( & self , db : & dyn HirDatabase ) -> Result < Layout , LayoutError > {
1219
1205
let parent_enum = self . parent_enum ( db) ;
1220
- let ( parent_layout, tag_size) = parent_enum. layout ( db) ?;
1221
- Ok ( (
1222
- match & parent_layout. 0 . variants {
1223
- layout:: Variants :: Multiple { variants, .. } => {
1224
- Layout ( Arc :: new ( variants[ RustcEnumVariantIdx ( self . id ) ] . clone ( ) ) )
1225
- }
1226
- _ => parent_layout,
1227
- } ,
1228
- tag_size,
1229
- ) )
1206
+ let parent_layout = parent_enum. layout ( db) ?;
1207
+ Ok ( match & parent_layout. 0 . variants {
1208
+ layout:: Variants :: Multiple { variants, .. } => Layout (
1209
+ Arc :: new ( variants[ RustcEnumVariantIdx ( self . id ) ] . clone ( ) ) ,
1210
+ db. target_data_layout ( parent_enum. krate ( db) . into ( ) ) . unwrap ( ) ,
1211
+ ) ,
1212
+ _ => parent_layout,
1213
+ } )
1230
1214
}
1231
1215
}
1232
1216
@@ -1259,7 +1243,9 @@ impl Adt {
1259
1243
if db. generic_params ( self . into ( ) ) . iter ( ) . count ( ) != 0 {
1260
1244
return Err ( LayoutError :: HasPlaceholder ) ;
1261
1245
}
1262
- db. layout_of_adt ( self . into ( ) , Substitution :: empty ( Interner ) , self . krate ( db) . id ) . map ( Layout )
1246
+ let krate = self . krate ( db) . id ;
1247
+ db. layout_of_adt ( self . into ( ) , Substitution :: empty ( Interner ) , krate)
1248
+ . map ( |layout| Layout ( layout, db. target_data_layout ( krate) . unwrap ( ) ) )
1263
1249
}
1264
1250
1265
1251
/// Turns this ADT into a type. Any type parameters of the ADT will be
@@ -4244,7 +4230,8 @@ impl Type {
4244
4230
}
4245
4231
4246
4232
pub fn layout ( & self , db : & dyn HirDatabase ) -> Result < Layout , LayoutError > {
4247
- db. layout_of_ty ( self . ty . clone ( ) , self . env . krate ) . map ( Layout )
4233
+ db. layout_of_ty ( self . ty . clone ( ) , self . env . krate )
4234
+ . map ( |layout| Layout ( layout, db. target_data_layout ( self . env . krate ) . unwrap ( ) ) )
4248
4235
}
4249
4236
}
4250
4237
@@ -4356,7 +4343,7 @@ fn closure_source(db: &dyn HirDatabase, closure: ClosureId) -> Option<ast::Closu
4356
4343
}
4357
4344
4358
4345
#[ derive( Clone , Debug , Eq , PartialEq ) ]
4359
- pub struct Layout ( Arc < TyLayout > ) ;
4346
+ pub struct Layout ( Arc < TyLayout > , Arc < TargetDataLayout > ) ;
4360
4347
4361
4348
impl Layout {
4362
4349
pub fn size ( & self ) -> u64 {
@@ -4367,8 +4354,8 @@ impl Layout {
4367
4354
self . 0 . align . abi . bytes ( )
4368
4355
}
4369
4356
4370
- pub fn niches ( & self , db : & dyn HirDatabase , krate : Crate ) -> Option < u128 > {
4371
- Some ( self . 0 . largest_niche ?. available ( & * db . target_data_layout ( krate . id ) ? ) )
4357
+ pub fn niches ( & self ) -> Option < u128 > {
4358
+ Some ( self . 0 . largest_niche ?. available ( & * self . 1 ) )
4372
4359
}
4373
4360
4374
4361
pub fn field_offset ( & self , idx : usize ) -> Option < u64 > {
@@ -4382,6 +4369,19 @@ impl Layout {
4382
4369
layout:: FieldsShape :: Arbitrary { ref offsets, .. } => Some ( offsets. get ( idx) ?. bytes ( ) ) ,
4383
4370
}
4384
4371
}
4372
+
4373
+ pub fn enum_tag_size ( & self ) -> Option < usize > {
4374
+ let tag_size =
4375
+ if let layout:: Variants :: Multiple { tag, tag_encoding, .. } = & self . 0 . variants {
4376
+ match tag_encoding {
4377
+ TagEncoding :: Direct => tag. size ( & * self . 1 ) . bytes_usize ( ) ,
4378
+ TagEncoding :: Niche { .. } => 0 ,
4379
+ }
4380
+ } else {
4381
+ return None ;
4382
+ } ;
4383
+ Some ( tag_size)
4384
+ }
4385
4385
}
4386
4386
4387
4387
#[ derive( Copy , Clone , Debug , Eq , PartialEq ) ]
0 commit comments