Merge pull request #2282 from ferrous-systems/sovereign-module-of-syn · rust-lang/rust-bindgen@b5ec18e (original) (raw)
`@@ -88,7 +88,6 @@ use std::{env, iter};
`
88
88
`// Some convenient typedefs for a fast hash map and hash set.
`
89
89
`type HashMap<K, V> = ::rustc_hash::FxHashMap<K, V>;
`
90
90
`type HashSet = ::rustc_hash::FxHashSet;
`
91
``
`-
use quote::ToTokens;
`
92
91
`pub(crate) use std::collections::hash_map::Entry;
`
93
92
``
94
93
`/// Default prefix for the anon fields.
`
`@@ -2118,11 +2117,6 @@ struct BindgenOptions {
`
2118
2117
`impl ::std::panic::UnwindSafe for BindgenOptions {}
`
2119
2118
``
2120
2119
`impl BindgenOptions {
`
2121
``
`` -
/// Whether any of the enabled options requires syn
.
``
2122
``
`-
fn require_syn(&self) -> bool {
`
2123
``
`-
self.sort_semantically || self.merge_extern_blocks
`
2124
``
`-
}
`
2125
``
-
2126
2120
`fn build(&mut self) {
`
2127
2121
`let mut regex_sets = [
`
2128
2122
`&mut self.allowlisted_vars,
`
`@@ -2555,112 +2549,7 @@ impl Bindings {
`
2555
2549
`parse(&mut context)?;
`
2556
2550
`}
`
2557
2551
``
2558
``
`-
let (items, options, warnings) = codegen::codegen(context);
`
2559
``
-
2560
``
`-
let module = if options.require_syn() {
`
2561
``
`-
let module_wrapped_tokens =
`
2562
``
`-
quote!(mod wrapper_for_sorting_hack { #( #items )* });
`
2563
``
-
2564
``
`-
// This syn business is a hack, for now. This means that we are re-parsing already
`
2565
``
`` -
// generated code using syn
(as opposed to quote
) because syn
provides us more
``
2566
``
`-
// control over the elements.
`
2567
``
`` -
// One caveat is that some of the items coming from quote
d output might have
``
2568
``
`` -
// multiple items within them. Hence, we have to wrap the incoming in a mod
.
``
2569
``
`` -
// The two unwrap
s here are deliberate because
``
2570
``
`` -
// The first one won't panic because we build the mod
and know it is there
``
2571
``
`-
// The second one won't panic because we know original output has something in
`
2572
``
`-
// it already.
`
2573
``
`-
let mut syn_parsed_items =
`
2574
``
`-
syn::parse2::syn::ItemMod(module_wrapped_tokens)
`
2575
``
`-
.unwrap()
`
2576
``
`-
.content
`
2577
``
`-
.unwrap()
`
2578
``
`-
.1;
`
2579
``
-
2580
``
`-
if options.merge_extern_blocks {
`
2581
``
`-
// Here we will store all the items after deduplication.
`
2582
``
`-
let mut items = Vec::new();
`
2583
``
-
2584
``
`` -
// Keep all the extern blocks in a different Vec
for faster search.
``
2585
``
`-
let mut foreign_mods = Vec::syn::ItemForeignMod::new();
`
2586
``
`-
for item in syn_parsed_items {
`
2587
``
`-
match item {
`
2588
``
`-
syn::Item::ForeignMod(syn::ItemForeignMod {
`
2589
``
`-
attrs,
`
2590
``
`-
abi,
`
2591
``
`-
brace_token,
`
2592
``
`-
items: foreign_items,
`
2593
``
`-
}) => {
`
2594
``
`-
let mut exists = false;
`
2595
``
`-
for foreign_mod in &mut foreign_mods {
`
2596
``
`-
// Check if there is a extern block with the same ABI and
`
2597
``
`-
// attributes.
`
2598
``
`-
if foreign_mod.attrs == attrs &&
`
2599
``
`-
foreign_mod.abi == abi
`
2600
``
`-
{
`
2601
``
`-
// Merge the items of the two blocks.
`
2602
``
`-
foreign_mod
`
2603
``
`-
.items
`
2604
``
`-
.extend_from_slice(&foreign_items);
`
2605
``
`-
exists = true;
`
2606
``
`-
break;
`
2607
``
`-
}
`
2608
``
`-
}
`
2609
``
`-
// If no existing extern block had the same ABI and attributes, store
`
2610
``
`-
// it.
`
2611
``
`-
if !exists {
`
2612
``
`-
foreign_mods.push(syn::ItemForeignMod {
`
2613
``
`-
attrs,
`
2614
``
`-
abi,
`
2615
``
`-
brace_token,
`
2616
``
`-
items: foreign_items,
`
2617
``
`-
});
`
2618
``
`-
}
`
2619
``
`-
}
`
2620
``
`-
// If the item is not an extern block, we don't have to do anything.
`
2621
``
`-
_ => items.push(item),
`
2622
``
`-
}
`
2623
``
`-
}
`
2624
``
-
2625
``
`-
// Move all the extern blocks alongiside the rest of the items.
`
2626
``
`-
for foreign_mod in foreign_mods {
`
2627
``
`-
items.push(syn::Item::ForeignMod(foreign_mod));
`
2628
``
`-
}
`
2629
``
-
2630
``
`-
syn_parsed_items = items;
`
2631
``
`-
}
`
2632
``
-
2633
``
`-
if options.sort_semantically {
`
2634
``
`-
syn_parsed_items.sort_by_key(|item| match item {
`
2635
``
`-
syn::Item::Type(_) => 0,
`
2636
``
`-
syn::Item::Struct(_) => 1,
`
2637
``
`-
syn::Item::Const(_) => 2,
`
2638
``
`-
syn::Item::Fn(_) => 3,
`
2639
``
`-
syn::Item::Enum(_) => 4,
`
2640
``
`-
syn::Item::Union(_) => 5,
`
2641
``
`-
syn::Item::Static(_) => 6,
`
2642
``
`-
syn::Item::Trait(_) => 7,
`
2643
``
`-
syn::Item::TraitAlias(_) => 8,
`
2644
``
`-
syn::Item::Impl(_) => 9,
`
2645
``
`-
syn::Item::Mod(_) => 10,
`
2646
``
`-
syn::Item::Use(_) => 11,
`
2647
``
`-
syn::Item::Verbatim(_) => 12,
`
2648
``
`-
syn::Item::ExternCrate(_) => 13,
`
2649
``
`-
syn::Item::ForeignMod(_) => 14,
`
2650
``
`-
syn::Item::Macro(_) => 15,
`
2651
``
`-
syn::Item::Macro2(_) => 16,
`
2652
``
`-
_ => 18,
`
2653
``
`-
});
`
2654
``
`-
}
`
2655
``
-
2656
``
`-
let synful_items = syn_parsed_items
`
2657
``
`-
.into_iter()
`
2658
``
`-
.map(|item| item.into_token_stream());
`
2659
``
-
2660
``
`-
quote! { #( #synful_items )* }
`
2661
``
`-
} else {
`
2662
``
`-
quote! { #( #items )* }
`
2663
``
`-
};
`
``
2552
`+
let (module, options, warnings) = codegen::codegen(context);
`
2664
2553
``
2665
2554
`Ok(Bindings {
`
2666
2555
` options,
`