@@ -17,116 +17,95 @@ impl NestingLevel {
17
17
Self :: Top
18
18
}
19
19
20
- const fn bitfield ( self ) -> Self {
20
+ pub ( crate ) const fn bitfield ( self ) -> Self {
21
21
// This is a bit irrelevant, since bitfields can only contain integral
22
22
// types
23
23
self
24
24
}
25
25
26
- const fn atomic ( self ) -> Self {
27
- // Move all the way down
28
- Self :: Bottom
29
- }
30
-
31
- const fn pointer ( self ) -> Self {
32
- // Move one step down
33
- match self {
34
- Self :: Top => Self :: Within ,
35
- Self :: Bottom | Self :: Within => Self :: Bottom ,
26
+ pub ( crate ) const fn indirection ( self , kind : IndirectionKind ) -> Self {
27
+ match kind {
28
+ // Move all the way down
29
+ IndirectionKind :: Atomic => Self :: Bottom ,
30
+ // Move one step down
31
+ IndirectionKind :: Pointer => match self {
32
+ Self :: Top => Self :: Within ,
33
+ Self :: Bottom | Self :: Within => Self :: Bottom ,
34
+ } ,
36
35
}
37
36
}
38
37
39
- const fn array ( self ) -> Self {
38
+ pub ( crate ) const fn array ( self ) -> Self {
40
39
// TODO: Is this correct?
41
40
self
42
41
}
43
42
44
- const fn container ( self ) -> Self {
43
+ pub ( crate ) const fn container_include_fields ( self ) -> Option < Self > {
45
44
match self {
46
- // Move top one step down
47
- Self :: Top | Self :: Within => Self :: Within ,
48
- Self :: Bottom => Self :: Bottom ,
49
- }
50
- }
51
-
52
- pub ( crate ) const fn include_container_fields ( self ) -> bool {
53
- match self {
54
- Self :: Top | Self :: Within => true ,
55
- Self :: Bottom => false ,
45
+ Self :: Top | Self :: Within => {
46
+ // Move top one step down
47
+ Some ( Self :: Within )
48
+ }
49
+ Self :: Bottom => None ,
56
50
}
57
51
}
58
52
}
59
53
60
54
pub ( crate ) fn compare_encodings < E1 : EncodingType , E2 : EncodingType > (
61
55
enc1 : & E1 ,
62
- level1 : NestingLevel ,
63
56
enc2 : & E2 ,
64
- level2 : NestingLevel ,
57
+ level : NestingLevel ,
65
58
include_all : bool ,
66
59
) -> bool {
67
60
use Helper :: * ;
68
61
// Note: Ideally `Block` and sequence of `Object, Unknown` in struct
69
62
// should compare equivalent, but we don't bother since in practice a
70
63
// plain `Unknown` will never appear.
71
64
72
- let level1 = if include_all {
73
- NestingLevel :: new ( )
74
- } else {
75
- level1
76
- } ;
77
- let level2 = if include_all {
65
+ let level = if include_all {
78
66
NestingLevel :: new ( )
79
67
} else {
80
- level2
68
+ level
81
69
} ;
82
70
83
- // TODO: Are level1 and level2 ever different?
84
-
85
- match ( enc1. helper ( level1) , enc2. helper ( level2) ) {
71
+ match ( enc1. helper ( ) , enc2. helper ( ) ) {
86
72
( Primitive ( p1) , Primitive ( p2) ) => p1 == p2,
87
- (
88
- BitField ( size1, Some ( ( offset1, type1) ) , level1) ,
89
- BitField ( size2, Some ( ( offset2, type2) ) , level2) ,
90
- ) => {
73
+ ( BitField ( size1, Some ( ( offset1, type1) ) ) , BitField ( size2, Some ( ( offset2, type2) ) ) ) => {
91
74
size1 == size2
92
75
&& offset1 == offset2
93
- && compare_encodings ( type1, level1 , type2, level2 , include_all)
76
+ && compare_encodings ( type1, type2, level . bitfield ( ) , include_all)
94
77
}
95
- ( BitField ( size1, None , _level1 ) , BitField ( size2, None , _level2 ) ) => size1 == size2,
78
+ ( BitField ( size1, None ) , BitField ( size2, None ) ) => size1 == size2,
96
79
// The type-encoding of a bitfield is always either available, or it
97
80
// is not (depends on platform); so if it was available in one, but
98
81
// not the other, we should compare the encodings unequal.
99
- ( BitField ( _, _, _ ) , BitField ( _ , _, _) ) => false ,
100
- ( Indirection ( kind1, t1, level1 ) , Indirection ( kind2, t2, level2 ) ) => {
101
- kind1 == kind2 && compare_encodings ( t1, level1 , t2, level2 , include_all)
82
+ ( BitField ( _, _) , BitField ( _, _) ) => false ,
83
+ ( Indirection ( kind1, t1) , Indirection ( kind2, t2) ) => {
84
+ kind1 == kind2 && compare_encodings ( t1, t2, level . indirection ( kind1 ) , include_all)
102
85
}
103
- ( Array ( len1, item1, level1 ) , Array ( len2, item2, level2 ) ) => {
104
- len1 == len2 && compare_encodings ( item1, level1 , item2, level2 , include_all)
86
+ ( Array ( len1, item1) , Array ( len2, item2) ) => {
87
+ len1 == len2 && compare_encodings ( item1, item2, level . array ( ) , include_all)
105
88
}
106
- ( Container ( kind1, name1, items1, level1) , Container ( kind2, name2, items2, level2) ) => {
107
- kind1 == kind2
108
- && name1 == name2
109
- && match (
110
- items1,
111
- items2,
112
- level1. include_container_fields ( ) && level2. include_container_fields ( ) ,
113
- ) {
114
- ( _, _, false ) => true ,
115
- // If one container is empty, then they are equivalent
116
- ( [ ] , _, true ) => true ,
117
- ( _, [ ] , true ) => true ,
118
- ( items1, items2, true ) => {
119
- if items1. len ( ) != items2. len ( ) {
89
+ ( Container ( kind1, name1, items1) , Container ( kind2, name2, items2) ) => {
90
+ kind1 == kind2 && name1 == name2 && {
91
+ if let Some ( level) = level. container_include_fields ( ) {
92
+ // If either container is empty, then they are equivalent
93
+ if items1. is_empty ( ) || items2. is_empty ( ) {
94
+ return true ;
95
+ }
96
+ if items1. len ( ) != items2. len ( ) {
97
+ return false ;
98
+ }
99
+ for ( item1, item2) in items1. iter ( ) . zip ( items2. iter ( ) ) {
100
+ if !compare_encodings ( item1, item2, level, include_all) {
120
101
return false ;
121
102
}
122
- for ( item1, item2) in items1. iter ( ) . zip ( items2. iter ( ) ) {
123
- if !compare_encodings ( item1, level1, item2, level2, include_all) {
124
- return false ;
125
- }
126
- }
127
- true
128
103
}
104
+ true
105
+ } else {
106
+ true
129
107
}
108
+ }
130
109
}
131
110
( _, _) => false ,
132
111
}
@@ -252,52 +231,61 @@ impl fmt::Display for ContainerKind {
252
231
}
253
232
254
233
pub ( crate ) trait EncodingType : Sized + fmt:: Debug {
255
- fn helper ( & self , level : NestingLevel ) -> Helper < ' _ , Self > ;
234
+ fn helper ( & self ) -> Helper < ' _ , Self > ;
256
235
}
257
236
258
237
#[ derive( Clone , Debug , PartialEq , Eq , Hash ) ]
259
238
#[ non_exhaustive]
260
239
pub ( crate ) enum Helper < ' a , E = Encoding > {
261
240
Primitive ( Primitive ) ,
262
- BitField ( u8 , Option < & ' a ( u64 , E ) > , NestingLevel ) ,
263
- Indirection ( IndirectionKind , & ' a E , NestingLevel ) ,
264
- Array ( u64 , & ' a E , NestingLevel ) ,
265
- Container ( ContainerKind , & ' a str , & ' a [ E ] , NestingLevel ) ,
241
+ BitField ( u8 , Option < & ' a ( u64 , E ) > ) ,
242
+ Indirection ( IndirectionKind , & ' a E ) ,
243
+ Array ( u64 , & ' a E ) ,
244
+ Container ( ContainerKind , & ' a str , & ' a [ E ] ) ,
266
245
}
267
246
268
- impl < E : EncodingType > fmt :: Display for Helper < ' _ , E > {
269
- fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
247
+ impl < E : EncodingType > Helper < ' _ , E > {
248
+ pub ( crate ) fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > , level : NestingLevel ) -> fmt:: Result {
270
249
match self {
271
- Self :: Primitive ( primitive) => write ! ( f, "{}" , primitive. to_str( ) ) ,
272
- Self :: BitField ( size, None , _level) => {
273
- write ! ( f, "b{size}" )
250
+ Self :: Primitive ( primitive) => {
251
+ write ! ( f, "{}" , primitive. to_str( ) ) ?;
252
+ }
253
+ Self :: BitField ( size, None ) => {
254
+ write ! ( f, "b{size}" ) ?;
274
255
}
275
- Self :: BitField ( size, Some ( ( offset, t) ) , level) => {
276
- write ! ( f, "b{offset}{}{size}" , t. helper( * level) )
256
+ Self :: BitField ( size, Some ( ( offset, t) ) ) => {
257
+ write ! ( f, "b{offset}" ) ?;
258
+ t. helper ( ) . fmt ( f, level. bitfield ( ) ) ?;
259
+ write ! ( f, "{size}" ) ?;
277
260
}
278
- Self :: Indirection ( kind, t, level) => {
279
- write ! ( f, "{}{}" , kind. prefix( ) , t. helper( * level) )
261
+ Self :: Indirection ( kind, t) => {
262
+ write ! ( f, "{}" , kind. prefix( ) ) ?;
263
+ t. helper ( ) . fmt ( f, level. indirection ( * kind) ) ?;
280
264
}
281
- Self :: Array ( len, item, level) => {
282
- write ! ( f, "[{}{}]" , len, item. helper( * level) )
265
+ Self :: Array ( len, item) => {
266
+ write ! ( f, "[" ) ?;
267
+ write ! ( f, "{len}" ) ?;
268
+ item. helper ( ) . fmt ( f, level. array ( ) ) ?;
269
+ write ! ( f, "]" ) ?;
283
270
}
284
- Self :: Container ( kind, name, items, level ) => {
271
+ Self :: Container ( kind, name, items) => {
285
272
write ! ( f, "{}" , kind. start( ) ) ?;
286
273
write ! ( f, "{name}" ) ?;
287
- if level. include_container_fields ( ) {
274
+ if let Some ( level) = level . container_include_fields ( ) {
288
275
write ! ( f, "=" ) ?;
289
276
for item in * items {
290
- write ! ( f , "{}" , item. helper( * level ) ) ?;
277
+ item. helper ( ) . fmt ( f , level ) ?;
291
278
}
292
279
}
293
- write ! ( f, "{}" , kind. end( ) )
280
+ write ! ( f, "{}" , kind. end( ) ) ? ;
294
281
}
295
282
}
283
+ Ok ( ( ) )
296
284
}
297
285
}
298
286
299
287
impl Helper < ' _ > {
300
- pub ( crate ) const fn new ( encoding : & Encoding , level : NestingLevel ) -> Self {
288
+ pub ( crate ) const fn new ( encoding : & Encoding ) -> Self {
301
289
use Encoding :: * ;
302
290
match encoding {
303
291
Char => Self :: Primitive ( Primitive :: Char ) ,
@@ -324,28 +312,28 @@ impl Helper<'_> {
324
312
Class => Self :: Primitive ( Primitive :: Class ) ,
325
313
Sel => Self :: Primitive ( Primitive :: Sel ) ,
326
314
Unknown => Self :: Primitive ( Primitive :: Unknown ) ,
327
- BitField ( b, t) => Self :: BitField ( * b, * t, level . bitfield ( ) ) ,
328
- Pointer ( t) => Self :: Indirection ( IndirectionKind :: Pointer , t, level . pointer ( ) ) ,
329
- Atomic ( t) => Self :: Indirection ( IndirectionKind :: Atomic , t, level . atomic ( ) ) ,
330
- Array ( len, item) => Self :: Array ( * len, item, level . array ( ) ) ,
315
+ BitField ( b, t) => Self :: BitField ( * b, * t) ,
316
+ Pointer ( t) => Self :: Indirection ( IndirectionKind :: Pointer , t) ,
317
+ Atomic ( t) => Self :: Indirection ( IndirectionKind :: Atomic , t) ,
318
+ Array ( len, item) => Self :: Array ( * len, item) ,
331
319
Struct ( name, fields) => {
332
320
if !verify_name ( name) {
333
321
panic ! ( "Struct name was not a valid identifier" ) ;
334
322
}
335
- Self :: Container ( ContainerKind :: Struct , name, fields, level . container ( ) )
323
+ Self :: Container ( ContainerKind :: Struct , name, fields)
336
324
}
337
325
Union ( name, members) => {
338
326
if !verify_name ( name) {
339
327
panic ! ( "Union name was not a valid identifier" ) ;
340
328
}
341
- Self :: Container ( ContainerKind :: Union , name, members, level . container ( ) )
329
+ Self :: Container ( ContainerKind :: Union , name, members)
342
330
}
343
331
}
344
332
}
345
333
}
346
334
347
335
impl < ' a > Helper < ' a , EncodingBox > {
348
- pub ( crate ) fn from_box ( encoding : & ' a EncodingBox , level : NestingLevel ) -> Self {
336
+ pub ( crate ) fn from_box ( encoding : & ' a EncodingBox ) -> Self {
349
337
use EncodingBox :: * ;
350
338
match encoding {
351
339
Char => Self :: Primitive ( Primitive :: Char ) ,
@@ -372,34 +360,34 @@ impl<'a> Helper<'a, EncodingBox> {
372
360
Class => Self :: Primitive ( Primitive :: Class ) ,
373
361
Sel => Self :: Primitive ( Primitive :: Sel ) ,
374
362
Unknown => Self :: Primitive ( Primitive :: Unknown ) ,
375
- BitField ( b, t) => Self :: BitField ( * b, t. as_deref ( ) , level . bitfield ( ) ) ,
376
- Pointer ( t) => Self :: Indirection ( IndirectionKind :: Pointer , t, level . pointer ( ) ) ,
377
- Atomic ( t) => Self :: Indirection ( IndirectionKind :: Atomic , t, level . atomic ( ) ) ,
378
- Array ( len, item) => Self :: Array ( * len, item, level . array ( ) ) ,
363
+ BitField ( b, t) => Self :: BitField ( * b, t. as_deref ( ) ) ,
364
+ Pointer ( t) => Self :: Indirection ( IndirectionKind :: Pointer , t) ,
365
+ Atomic ( t) => Self :: Indirection ( IndirectionKind :: Atomic , t) ,
366
+ Array ( len, item) => Self :: Array ( * len, item) ,
379
367
Struct ( name, fields) => {
380
368
if !verify_name ( name) {
381
369
panic ! ( "Struct name was not a valid identifier" ) ;
382
370
}
383
- Self :: Container ( ContainerKind :: Struct , name, fields, level . container ( ) )
371
+ Self :: Container ( ContainerKind :: Struct , name, fields)
384
372
}
385
373
Union ( name, members) => {
386
374
if !verify_name ( name) {
387
375
panic ! ( "Union name was not a valid identifier" ) ;
388
376
}
389
- Self :: Container ( ContainerKind :: Union , name, members, level . container ( ) )
377
+ Self :: Container ( ContainerKind :: Union , name, members)
390
378
}
391
379
}
392
380
}
393
381
}
394
382
395
383
impl EncodingType for Encoding {
396
- fn helper ( & self , level : NestingLevel ) -> Helper < ' _ , Self > {
397
- Helper :: new ( self , level )
384
+ fn helper ( & self ) -> Helper < ' _ , Self > {
385
+ Helper :: new ( self )
398
386
}
399
387
}
400
388
401
389
impl EncodingType for EncodingBox {
402
- fn helper ( & self , level : NestingLevel ) -> Helper < ' _ , Self > {
403
- Helper :: from_box ( self , level )
390
+ fn helper ( & self ) -> Helper < ' _ , Self > {
391
+ Helper :: from_box ( self )
404
392
}
405
393
}
0 commit comments