@@ -15,7 +15,7 @@ use provenance_map::*;
15
15
use rustc_abi:: { Align , HasDataLayout , Size } ;
16
16
use rustc_ast:: Mutability ;
17
17
use rustc_data_structures:: intern:: Interned ;
18
- use rustc_macros:: { HashStable , TyDecodable , TyEncodable } ;
18
+ use rustc_macros:: HashStable ;
19
19
20
20
use super :: {
21
21
AllocId , BadBytesAccess , CtfeProvenance , InterpErrorKind , InterpResult , Pointer ,
@@ -77,7 +77,7 @@ impl AllocBytes for Box<[u8]> {
77
77
/// module provides higher-level access.
78
78
// Note: for performance reasons when interning, some of the `Allocation` fields can be partially
79
79
// hashed. (see the `Hash` impl below for more details), so the impl is not derived.
80
- #[ derive( Clone , Eq , PartialEq , TyEncodable , TyDecodable ) ]
80
+ #[ derive( Clone , Eq , PartialEq ) ]
81
81
#[ derive( HashStable ) ]
82
82
pub struct Allocation < Prov : Provenance = CtfeProvenance , Extra = ( ) , Bytes = Box < [ u8 ] > > {
83
83
/// The actual bytes of the allocation.
@@ -101,6 +101,53 @@ pub struct Allocation<Prov: Provenance = CtfeProvenance, Extra = (), Bytes = Box
101
101
pub extra : Extra ,
102
102
}
103
103
104
+ use rustc_serialize:: { Decodable , Encodable } ;
105
+ use rustc_type_ir:: { TyDecoder , TyEncoder } ;
106
+
107
+ impl < Prov : Provenance , Extra , Bytes , E : TyEncoder > Encodable < E > for Allocation < Prov , Extra , Bytes >
108
+ where
109
+ Bytes : AllocBytes ,
110
+ ProvenanceMap < Prov > : Encodable < E > ,
111
+ Extra : Encodable < E > ,
112
+ {
113
+ fn encode ( & self , encoder : & mut E ) {
114
+ let len = self . bytes . len ( ) << 1 ;
115
+ let all_zero = self . bytes . iter ( ) . all ( |b| * b == 0 ) ;
116
+ encoder. emit_usize ( len | all_zero as usize ) ;
117
+ if !all_zero {
118
+ encoder. emit_raw_bytes ( & self . bytes ) ;
119
+ }
120
+ self . provenance . encode ( encoder) ;
121
+ self . init_mask . encode ( encoder) ;
122
+ self . align . encode ( encoder) ;
123
+ self . mutability . encode ( encoder) ;
124
+ self . extra . encode ( encoder) ;
125
+ }
126
+ }
127
+
128
+ impl < Prov : Provenance , Extra , Bytes , D : TyDecoder > Decodable < D > for Allocation < Prov , Extra , Bytes >
129
+ where
130
+ Bytes : AllocBytes ,
131
+ ProvenanceMap < Prov > : Decodable < D > ,
132
+ Extra : Decodable < D > ,
133
+ {
134
+ fn decode ( decoder : & mut D ) -> Self {
135
+ let len = decoder. read_usize ( ) ;
136
+ let all_zero = ( len & 0b1 ) == 1 ;
137
+ let len = len >> 1 ;
138
+ let bytes = if all_zero { vec ! [ 0u8 ; len] } else { decoder. read_raw_bytes ( len) . to_vec ( ) } ;
139
+
140
+ let provenance = Decodable :: decode ( decoder) ;
141
+ let init_mask = Decodable :: decode ( decoder) ;
142
+ let align = Decodable :: decode ( decoder) ;
143
+ let mutability = Decodable :: decode ( decoder) ;
144
+ let extra = Decodable :: decode ( decoder) ;
145
+ let bytes = Bytes :: from_bytes ( bytes, align) ;
146
+
147
+ Self { bytes, provenance, init_mask, align, mutability, extra }
148
+ }
149
+ }
150
+
104
151
/// This is the maximum size we will hash at a time, when interning an `Allocation` and its
105
152
/// `InitMask`. Note, we hash that amount of bytes twice: at the start, and at the end of a buffer.
106
153
/// Used when these two structures are large: we only partially hash the larger fields in that
0 commit comments