@@ -47,7 +47,6 @@ use std::ops::{Add, AddAssign, Deref, Mul, RangeInclusive, Sub};
47
47
use std:: str:: FromStr ;
48
48
49
49
use bitflags:: bitflags;
50
- use rustc_data_structures:: fx:: FxHashMap ;
51
50
#[ cfg( feature = "nightly" ) ]
52
51
use rustc_data_structures:: stable_hasher:: StableOrd ;
53
52
use rustc_hashes:: Hash64 ;
@@ -292,14 +291,14 @@ impl Default for TargetDataLayout {
292
291
( Size :: from_bits( 128 ) , AbiAlign :: new( align( 128 ) ) ) ,
293
292
] ,
294
293
default_address_space : AddressSpace :: ZERO ,
295
- address_space_info : FxHashMap :: from_iter ( [ (
294
+ address_space_info : vec ! [ (
296
295
AddressSpace :: ZERO ,
297
296
AddressSpaceInfo {
298
297
pointer_size: Size :: from_bits( 64 ) ,
299
298
pointer_align: AbiAlign :: new( align( 64 ) ) ,
300
299
pointer_index: Size :: from_bits( 64 ) ,
301
300
} ,
302
- ) ] ) ,
301
+ ) ] ,
303
302
instruction_address_space : AddressSpace :: ZERO ,
304
303
c_enum_min_size : Integer :: I32 ,
305
304
}
@@ -396,11 +395,16 @@ impl TargetDataLayout {
396
395
pointer_size,
397
396
pointer_align : parse_align ( a, p) ?,
398
397
} ;
399
-
400
- dl. address_space_info
401
- . entry ( addr_space)
402
- . and_modify ( |v| * v = info)
403
- . or_insert ( info) ;
398
+ match dl. address_space_info . iter_mut ( ) . find ( |( a, _) | * a == addr_space) {
399
+ Some ( e) => e. 1 = info,
400
+ None => {
401
+ if addr_space == default_address_space {
402
+ dl. address_space_info . insert ( 0 , ( addr_space, info) ) ;
403
+ } else {
404
+ dl. address_space_info . push ( ( addr_space, info) ) ;
405
+ }
406
+ }
407
+ }
404
408
}
405
409
[ p, s, _pr, i, a @ ..] if p. starts_with ( "p" ) => {
406
410
// Some targets, such as CHERI, use the 'f' suffix in the p- spec to signal that
@@ -419,10 +423,16 @@ impl TargetDataLayout {
419
423
pointer_index : parse_size ( i, p) ?,
420
424
} ;
421
425
422
- dl. address_space_info
423
- . entry ( addr_space)
424
- . and_modify ( |v| * v = info)
425
- . or_insert ( info) ;
426
+ match dl. address_space_info . iter_mut ( ) . find ( |( a, _) | * a == addr_space) {
427
+ Some ( e) => e. 1 = info,
428
+ None => {
429
+ if addr_space == default_address_space {
430
+ dl. address_space_info . insert ( 0 , ( addr_space, info) ) ;
431
+ } else {
432
+ dl. address_space_info . push ( ( addr_space, info) ) ;
433
+ }
434
+ }
435
+ }
426
436
}
427
437
428
438
[ s, a @ ..] if s. starts_with ( 'i' ) => {
@@ -460,7 +470,7 @@ impl TargetDataLayout {
460
470
}
461
471
}
462
472
463
- if ! dl. address_space_info . contains_key ( & default_address_space) {
473
+ if dl. address_space_info . iter ( ) . find ( | ( a , _ ) | * a == default_address_space) . is_none ( ) {
464
474
return Err ( TargetDataLayoutErrors :: MissingAddressSpaceInfo {
465
475
addr_space : default_address_space,
466
476
} ) ;
@@ -469,11 +479,17 @@ impl TargetDataLayout {
469
479
// Inherit, if not given, address space informations for specific LLVM elements from the
470
480
// default data address space.
471
481
472
- if !dl. address_space_info . contains_key ( & dl. instruction_address_space ) {
473
- dl. address_space_info . insert (
482
+ if dl. address_space_info . iter ( ) . find ( |( a, _) | * a == dl. instruction_address_space ) . is_none ( )
483
+ {
484
+ dl. address_space_info . push ( (
474
485
dl. instruction_address_space ,
475
- dl. address_space_info . get ( & default_address_space) . unwrap ( ) . clone ( ) ,
476
- ) ;
486
+ dl. address_space_info
487
+ . iter ( )
488
+ . find ( |( a, _) | * a == default_address_space)
489
+ . unwrap ( )
490
+ . 1
491
+ . clone ( ) ,
492
+ ) ) ;
477
493
}
478
494
479
495
Ok ( dl)
@@ -491,7 +507,12 @@ impl TargetDataLayout {
491
507
/// so we adopt such a more-constrained size bound due to its technical limitations.
492
508
#[ inline]
493
509
pub fn obj_size_bound ( & self ) -> u64 {
494
- self . obj_size_bound_in ( self . default_address_space )
510
+ match self . pointer_size ( ) . bits ( ) {
511
+ 16 => 1 << 15 ,
512
+ 32 => 1 << 31 ,
513
+ 64 => 1 << 61 ,
514
+ bits => panic ! ( "obj_size_bound: unknown pointer bit size {bits}" ) ,
515
+ }
495
516
}
496
517
497
518
/// Returns **exclusive** upper bound on object size in bytes.
@@ -515,7 +536,13 @@ impl TargetDataLayout {
515
536
516
537
#[ inline]
517
538
pub fn ptr_sized_integer ( & self ) -> Integer {
518
- self . ptr_sized_integer_in ( self . default_address_space )
539
+ use Integer :: * ;
540
+ match self . pointer_index ( ) . bits ( ) {
541
+ 16 => I16 ,
542
+ 32 => I32 ,
543
+ 64 => I64 ,
544
+ bits => panic ! ( "ptr_sized_integer: unknown pointer bit size {bits}" ) ,
545
+ }
519
546
}
520
547
521
548
#[ inline]
@@ -549,14 +576,14 @@ impl TargetDataLayout {
549
576
/// Get the pointer size in the default data address space.
550
577
#[ inline]
551
578
pub fn pointer_size ( & self ) -> Size {
552
- self . pointer_size_in ( self . default_address_space )
579
+ self . address_space_info [ 0 ] . 1 . pointer_size
553
580
}
554
581
555
582
/// Get the pointer size in a specific address space.
556
583
#[ inline]
557
584
pub fn pointer_size_in ( & self , c : AddressSpace ) -> Size {
558
- if let Some ( c ) = self . address_space_info . get ( & c) {
559
- c . pointer_size
585
+ if let Some ( e ) = self . address_space_info . iter ( ) . find ( | ( a , _ ) | a == & c) {
586
+ e . 1 . pointer_size
560
587
} else {
561
588
panic ! ( "Use of unknown address space {c:?}" ) ;
562
589
}
@@ -565,14 +592,14 @@ impl TargetDataLayout {
565
592
/// Get the pointer index in the default data address space.
566
593
#[ inline]
567
594
pub fn pointer_index ( & self ) -> Size {
568
- self . pointer_index_in ( self . default_address_space )
595
+ self . address_space_info [ 0 ] . 1 . pointer_index
569
596
}
570
597
571
598
/// Get the pointer index in a specific address space.
572
599
#[ inline]
573
600
pub fn pointer_index_in ( & self , c : AddressSpace ) -> Size {
574
- if let Some ( c ) = self . address_space_info . get ( & c) {
575
- c . pointer_index
601
+ if let Some ( e ) = self . address_space_info . iter ( ) . find ( | ( a , _ ) | a == & c) {
602
+ e . 1 . pointer_index
576
603
} else {
577
604
panic ! ( "Use of unknown address space {c:?}" ) ;
578
605
}
@@ -581,14 +608,14 @@ impl TargetDataLayout {
581
608
/// Get the pointer alignment in the default data address space.
582
609
#[ inline]
583
610
pub fn pointer_align ( & self ) -> AbiAlign {
584
- self . pointer_align_in ( self . default_address_space )
611
+ self . address_space_info [ 0 ] . 1 . pointer_align
585
612
}
586
613
587
614
/// Get the pointer alignment in a specific address space.
588
615
#[ inline]
589
616
pub fn pointer_align_in ( & self , c : AddressSpace ) -> AbiAlign {
590
- if let Some ( c ) = self . address_space_info . get ( & c) {
591
- c . pointer_align
617
+ if let Some ( e ) = self . address_space_info . iter ( ) . find ( | ( a , _ ) | a == & c) {
618
+ e . 1 . pointer_align
592
619
} else {
593
620
panic ! ( "Use of unknown address space {c:?}" ) ;
594
621
}
0 commit comments