11use indexmap:: { IndexMap , IndexSet } ;
22use rustc_hir:: { def:: DefKind , def_id:: DefId } ;
3+ use rustc_span:: DUMMY_SP ;
34
45use crate :: {
56 ctx:: { TranslatedItem , TranslationCtx } ,
@@ -9,6 +10,8 @@ use std::ops::{Deref, DerefMut};
910
1011pub ( crate ) use clone_map:: * ;
1112
13+ use self :: { dependency:: Dependency , ty_inv:: TyInvKind } ;
14+
1215pub ( crate ) mod clone_map;
1316pub ( crate ) mod constant;
1417pub ( crate ) mod dependency;
@@ -21,13 +24,26 @@ pub(crate) mod signature;
2124pub ( crate ) mod term;
2225pub ( crate ) mod traits;
2326pub ( crate ) mod ty;
27+ pub ( crate ) mod ty_inv;
28+
29+ #[ derive( Copy , Clone , PartialEq , Eq , Hash , PartialOrd , Ord , Debug ) ]
30+ pub ( crate ) enum TransId {
31+ Item ( DefId ) ,
32+ TyInv ( TyInvKind ) ,
33+ }
34+
35+ impl From < DefId > for TransId {
36+ fn from ( def_id : DefId ) -> Self {
37+ TransId :: Item ( def_id)
38+ }
39+ }
2440
2541pub struct Why3Generator < ' tcx > {
2642 ctx : TranslationCtx < ' tcx > ,
27- dependencies : IndexMap < DefId , CloneSummary < ' tcx > > ,
28- functions : IndexMap < DefId , TranslatedItem > ,
29- translated_items : IndexSet < DefId > ,
30- in_translation : Vec < IndexSet < DefId > > ,
43+ dependencies : IndexMap < TransId , CloneSummary < ' tcx > > ,
44+ functions : IndexMap < TransId , TranslatedItem > ,
45+ translated_items : IndexSet < TransId > ,
46+ in_translation : Vec < IndexSet < TransId > > ,
3147}
3248
3349impl < ' tcx > Deref for Why3Generator < ' tcx > {
@@ -56,12 +72,13 @@ impl<'tcx> Why3Generator<'tcx> {
5672 }
5773
5874 // Checks if we are allowed to recurse into
59- fn safe_cycle ( & self , def_id : DefId ) -> bool {
60- self . in_translation . last ( ) . map ( |l| l. contains ( & def_id ) ) . unwrap_or_default ( )
75+ fn safe_cycle ( & self , trans_id : TransId ) -> bool {
76+ self . in_translation . last ( ) . map ( |l| l. contains ( & trans_id ) ) . unwrap_or_default ( )
6177 }
6278
6379 pub ( crate ) fn translate ( & mut self , def_id : DefId ) {
64- if self . translated_items . contains ( & def_id) || self . safe_cycle ( def_id) {
80+ let tid = def_id. into ( ) ;
81+ if self . translated_items . contains ( & tid) || self . safe_cycle ( tid) {
6582 return ;
6683 }
6784 debug ! ( "translating {:?}" , def_id) ;
@@ -72,17 +89,17 @@ impl<'tcx> Why3Generator<'tcx> {
7289 ItemType :: Trait => {
7390 self . start ( def_id) ;
7491 let tr = self . translate_trait ( def_id) ;
75- self . dependencies . insert ( def_id , CloneSummary :: new ( ) ) ;
76- self . functions . insert ( def_id , tr) ;
92+ self . dependencies . insert ( tid , CloneSummary :: new ( ) ) ;
93+ self . functions . insert ( tid , tr) ;
7794 self . finish ( def_id) ;
7895 }
7996 ItemType :: Impl => {
8097 if self . tcx . impl_trait_ref ( def_id) . is_some ( ) {
8198 self . start ( def_id) ;
8299 let impl_ = traits:: lower_impl ( self , def_id) ;
83100
84- self . dependencies . insert ( def_id , CloneSummary :: new ( ) ) ;
85- self . functions . insert ( def_id , TranslatedItem :: Impl { modl : impl_ } ) ;
101+ self . dependencies . insert ( tid , CloneSummary :: new ( ) ) ;
102+ self . functions . insert ( tid , TranslatedItem :: Impl { modl : impl_ } ) ;
86103 self . finish ( def_id) ;
87104 }
88105 }
@@ -95,15 +112,15 @@ impl<'tcx> Why3Generator<'tcx> {
95112 self . start ( def_id) ;
96113 let ( modl, dependencies) = self . translate_assoc_ty ( def_id) ;
97114 self . finish ( def_id) ;
98- self . dependencies . insert ( def_id , dependencies) ;
99- self . functions . insert ( def_id , TranslatedItem :: AssocTy { modl } ) ;
115+ self . dependencies . insert ( tid , dependencies) ;
116+ self . functions . insert ( tid , TranslatedItem :: AssocTy { modl } ) ;
100117 }
101118 ItemType :: Constant => {
102119 self . start ( def_id) ;
103120 let ( constant, dependencies) = self . translate_constant ( def_id) ;
104121 self . finish ( def_id) ;
105- self . dependencies . insert ( def_id , dependencies) ;
106- self . functions . insert ( def_id , constant) ;
122+ self . dependencies . insert ( tid , dependencies) ;
123+ self . functions . insert ( tid , constant) ;
107124 }
108125 ItemType :: Type => {
109126 let bg = self . binding_group ( def_id) . clone ( ) ;
@@ -116,7 +133,7 @@ impl<'tcx> Why3Generator<'tcx> {
116133 self . finish ( * d) ;
117134 }
118135
119- let repr = self . representative_type ( def_id) ;
136+ let repr = self . representative_type ( def_id) . into ( ) ;
120137 if let Some ( modl) = modl {
121138 self . functions
122139 . insert ( repr, TranslatedItem :: Type { modl, accessors : Default :: default ( ) } ) ;
@@ -148,31 +165,31 @@ impl<'tcx> Why3Generator<'tcx> {
148165 debug ! ( "translating {:?} as logical" , def_id) ;
149166 let ( stub, modl, proof_modl, has_axioms, deps) =
150167 crate :: backend:: logic:: translate_logic_or_predicate ( self , def_id) ;
151- self . dependencies . insert ( def_id, deps) ;
168+ self . dependencies . insert ( def_id. into ( ) , deps) ;
152169
153170 TranslatedItem :: Logic { stub, interface, modl, proof_modl, has_axioms }
154171 }
155172 ItemType :: Closure => {
156173 let ( ty_modl, modl) = program:: translate_closure ( self , def_id) ;
157- self . dependencies . insert ( def_id, deps) ;
174+ self . dependencies . insert ( def_id. into ( ) , deps) ;
158175
159176 TranslatedItem :: Closure { interface : vec ! [ ty_modl, interface] , modl }
160177 }
161178 ItemType :: Program => {
162179 debug ! ( "translating {def_id:?} as program" ) ;
163180
164- self . dependencies . insert ( def_id, deps) ;
181+ self . dependencies . insert ( def_id. into ( ) , deps) ;
165182 let modl = program:: translate_function ( self , def_id) ;
166183 TranslatedItem :: Program { interface, modl }
167184 }
168185 _ => unreachable ! ( ) ,
169186 } ;
170187
171- self . functions . insert ( def_id, translated) ;
188+ self . functions . insert ( def_id. into ( ) , translated) ;
172189 }
173190
174191 pub ( crate ) fn translate_accessor ( & mut self , field_id : DefId ) {
175- if !self . translated_items . insert ( field_id) {
192+ if !self . translated_items . insert ( field_id. into ( ) ) {
176193 return ;
177194 }
178195
@@ -187,30 +204,52 @@ impl<'tcx> Why3Generator<'tcx> {
187204 self . translate ( adt_did) ;
188205
189206 let accessor = ty:: translate_accessor ( self , adt_did, variant_did, field_id) ;
190- let repr_id = self . representative_type ( adt_did) ;
207+ let repr_id: TransId = self . representative_type ( adt_did) . into ( ) ;
191208 if let TranslatedItem :: Type { ref mut accessors, .. } = & mut self . functions [ & repr_id] {
192209 accessors. entry ( variant_did) . or_default ( ) . insert ( field_id, accessor) ;
193210 } ;
194211 // self.types[&repr_id].accessors;
195212 }
196213
214+ pub ( crate ) fn translate_tyinv ( & mut self , inv_kind : TyInvKind ) {
215+ let tid = TransId :: TyInv ( inv_kind) ;
216+ if self . dependencies . contains_key ( & tid) {
217+ return ;
218+ }
219+
220+ if let TyInvKind :: Adt ( adt_did) = inv_kind {
221+ self . translate ( adt_did) ;
222+ }
223+
224+ let ( modl, deps) = ty_inv:: build_inv_module ( self , inv_kind) ;
225+ self . dependencies . insert ( tid, deps) ;
226+ self . functions . insert ( tid, TranslatedItem :: TyInv { modl } ) ;
227+ }
228+
197229 pub ( crate ) fn item ( & self , def_id : DefId ) -> Option < & TranslatedItem > {
198- let def_id = if matches ! ( util:: item_type( * * * self , def_id) , ItemType :: Type ) {
230+ let tid : TransId = if matches ! ( util:: item_type( * * * self , def_id) , ItemType :: Type ) {
199231 self . representative_type ( def_id)
200232 } else {
201233 def_id
202- } ;
203- self . functions . get ( & def_id)
234+ }
235+ . into ( ) ;
236+ self . functions . get ( & tid)
204237 }
205238
206- pub ( crate ) fn modules ( self ) -> impl Iterator < Item = ( DefId , TranslatedItem ) > + ' tcx {
239+ pub ( crate ) fn modules ( self ) -> impl Iterator < Item = ( TransId , TranslatedItem ) > + ' tcx {
207240 self . functions . into_iter ( )
208241 }
209242
210243 pub ( crate ) fn start_group ( & mut self , ids : IndexSet < DefId > ) {
211244 assert ! ( !ids. is_empty( ) ) ;
245+ let ids = ids. into_iter ( ) . map ( Into :: into) . collect ( ) ;
212246 if self . in_translation . iter ( ) . rev ( ) . any ( |s| !s. is_disjoint ( & ids) ) {
213- let span = self . def_span ( ids. first ( ) . unwrap ( ) ) ;
247+ let span = if let TransId :: Item ( def_id) = ids. first ( ) . unwrap ( ) {
248+ self . def_span ( def_id)
249+ } else {
250+ DUMMY_SP
251+ } ;
252+
214253 self . in_translation . push ( ids) ;
215254
216255 self . crash_and_error (
@@ -229,7 +268,8 @@ impl<'tcx> Why3Generator<'tcx> {
229268
230269 // Indicate we have finished translating a given id
231270 pub ( crate ) fn finish ( & mut self , def_id : DefId ) {
232- if !self . in_translation . last_mut ( ) . unwrap ( ) . remove ( & def_id) {
271+ let tid = def_id. into ( ) ;
272+ if !self . in_translation . last_mut ( ) . unwrap ( ) . remove ( & tid) {
233273 self . crash_and_error (
234274 self . def_span ( def_id) ,
235275 & format ! ( "{:?} is not in translation" , def_id) ,
@@ -240,10 +280,14 @@ impl<'tcx> Why3Generator<'tcx> {
240280 self . in_translation . pop ( ) ;
241281 }
242282
243- self . translated_items . insert ( def_id ) ;
283+ self . translated_items . insert ( tid ) ;
244284 }
245285
246- pub ( crate ) fn dependencies ( & self , def_id : DefId ) -> Option < & CloneSummary < ' tcx > > {
247- self . dependencies . get ( & def_id)
286+ pub ( crate ) fn dependencies ( & self , key : Dependency < ' tcx > ) -> Option < & CloneSummary < ' tcx > > {
287+ let tid = match key {
288+ Dependency :: TyInv ( ty) => TransId :: TyInv ( TyInvKind :: from_ty ( ty) ) ,
289+ _ => key. did ( ) . map ( |( def_id, _) | TransId :: Item ( def_id) ) ?,
290+ } ;
291+ self . dependencies . get ( & tid)
248292 }
249293}
0 commit comments