@@ -28,7 +28,7 @@ use cexpr;
28
28
use clang_sys;
29
29
use proc_macro2:: { Ident , Span } ;
30
30
use std:: borrow:: Cow ;
31
- use std:: cell:: Cell ;
31
+ use std:: cell:: { Cell , RefCell } ;
32
32
use std:: collections:: HashMap as StdHashMap ;
33
33
use std:: iter:: IntoIterator ;
34
34
use std:: mem;
@@ -380,6 +380,9 @@ pub struct BindgenContext {
380
380
/// computed after parsing our IR, and before running any of our analyses.
381
381
allowlisted : Option < ItemSet > ,
382
382
383
+ /// Cache for calls to `ParseCallbacks::blocklisted_type_implements_trait`
384
+ blocklisted_types_implement_traits : RefCell < HashMap < DeriveTrait , HashMap < ItemId , CanDerive > > > ,
385
+
383
386
/// The set of `ItemId`s that are allowlisted for code generation _and_ that
384
387
/// we should generate accounting for the codegen options.
385
388
///
@@ -560,6 +563,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
560
563
options,
561
564
generated_bindgen_complex : Cell :: new ( false ) ,
562
565
allowlisted : None ,
566
+ blocklisted_types_implement_traits : Default :: default ( ) ,
563
567
codegen_items : None ,
564
568
used_template_parameters : None ,
565
569
need_bitfield_allocation : Default :: default ( ) ,
@@ -2205,6 +2209,30 @@ If you encounter an error missing from this list, please file an issue or a PR!"
2205
2209
self . allowlisted . as_ref ( ) . unwrap ( )
2206
2210
}
2207
2211
2212
+ /// Check whether a particular blocklisted type implements a trait or not.
2213
+ /// Results may be cached.
2214
+ pub fn blocklisted_type_implements_trait ( & self , item : & Item , derive_trait : DeriveTrait ) -> CanDerive {
2215
+ assert ! ( self . in_codegen_phase( ) ) ;
2216
+ assert ! ( self . current_module == self . root_module) ;
2217
+
2218
+ let cb = match self . options . parse_callbacks {
2219
+ Some ( ref cb) => cb,
2220
+ None => return CanDerive :: No ,
2221
+ } ;
2222
+
2223
+ * self . blocklisted_types_implement_traits
2224
+ . borrow_mut ( )
2225
+ . entry ( derive_trait)
2226
+ . or_default ( )
2227
+ . entry ( item. id ( ) )
2228
+ . or_insert_with ( ||
2229
+ item. expect_type ( )
2230
+ . name ( )
2231
+ . and_then ( |name| cb. blocklisted_type_implements_trait ( name, derive_trait) )
2232
+ . unwrap_or ( CanDerive :: No )
2233
+ )
2234
+ }
2235
+
2208
2236
/// Get a reference to the set of items we should generate.
2209
2237
pub fn codegen_items ( & self ) -> & ItemSet {
2210
2238
assert ! ( self . in_codegen_phase( ) ) ;
0 commit comments