Skip to content

Commit e3167c8

Browse files
committed
expose discovered composite types and aliases to parse callbacks
1 parent f518815 commit e3167c8

File tree

2 files changed

+96
-1
lines changed

2 files changed

+96
-1
lines changed

bindgen/callbacks.rs

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,62 @@ pub trait ParseCallbacks: fmt::Debug {
162162
fn wrap_as_variadic_fn(&self, _name: &str) -> Option<String> {
163163
None
164164
}
165+
166+
/// This will get called everytime an item (currently struct, union, and alias) is found with some information about it
167+
fn new_item_found(&self, _id: DiscoveredItemId, _item: DiscoveredItem) {}
168+
169+
// TODO add callback for ResolvedTypeRef
170+
}
171+
172+
/// An identifier for a discovered item. Used to identify an aliased type (see [DiscoveredItem::Alias])
173+
#[derive(Ord, PartialOrd, PartialEq, Eq, Hash, Debug, Clone, Copy)]
174+
pub struct DiscoveredItemId(usize);
175+
176+
impl DiscoveredItemId {
177+
/// Constructor
178+
pub fn new(value: usize) -> Self {
179+
Self(value)
180+
}
181+
}
182+
183+
/// Struct passed to [ParseCallbacks::new_item_found] containing information about discovered
184+
/// items (struct, union, and alias)
185+
#[derive(Debug, Hash, Clone, Ord, PartialOrd, Eq, PartialEq)]
186+
pub enum DiscoveredItem {
187+
/// Represents a struct with its original name in C and its generated binding name
188+
Struct {
189+
/// The original name (learnt from C) of the structure
190+
/// Can be None if the union is anonymous.
191+
original_name: Option<String>,
192+
193+
/// The name of the generated binding
194+
final_name: String,
195+
},
196+
197+
/// Represents a union with its original name in C and its generated binding name
198+
Union {
199+
/// The original name (learnt from C) of the structure.
200+
/// Can be None if the union is anonymous.
201+
original_name: Option<String>,
202+
203+
/// The name of the generated binding
204+
final_name: String,
205+
},
206+
207+
/// Represents an alias like a typedef
208+
/// ```c
209+
/// typedef struct MyStruct {
210+
/// ...
211+
/// } StructAlias;
212+
/// ```
213+
/// Here, the name of the alias is `StructAlias` and it's an alias for `MyStruct`
214+
Alias {
215+
/// The name of the alias in C (`StructAlias`)
216+
alias_name: String,
217+
218+
/// The identifier of the discovered type
219+
alias_for: DiscoveredItemId,
220+
}, // functions, modules, etc.
165221
}
166222

167223
/// Relevant information about a type to which new derive attributes will be added using

bindgen/codegen/mod.rs

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,8 @@ use self::struct_layout::StructLayoutTracker;
2121
use super::BindgenOptions;
2222

2323
use crate::callbacks::{
24-
AttributeInfo, DeriveInfo, FieldInfo, TypeKind as DeriveTypeKind,
24+
AttributeInfo, DeriveInfo, DiscoveredItem, DiscoveredItemId, FieldInfo,
25+
TypeKind as DeriveTypeKind,
2526
};
2627
use crate::codegen::error::Error;
2728
use crate::ir::analysis::{HasVtable, Sizedness};
@@ -982,6 +983,18 @@ impl CodeGenerator for Type {
982983

983984
let rust_name = ctx.rust_ident(&name);
984985

986+
ctx.options().for_each_callback(|cb| {
987+
cb.new_item_found(
988+
DiscoveredItemId::new(item.id().as_usize()),
989+
DiscoveredItem::Alias {
990+
alias_name: rust_name.to_string(),
991+
alias_for: DiscoveredItemId::new(
992+
inner_item.id().as_usize(),
993+
),
994+
},
995+
);
996+
});
997+
985998
let mut tokens = if let Some(comment) = item.comment(ctx) {
986999
attributes::doc(comment)
9871000
} else {
@@ -2374,6 +2387,32 @@ impl CodeGenerator for CompInfo {
23742387

23752388
let is_rust_union = is_union && struct_layout.is_rust_union();
23762389

2390+
ctx.options().for_each_callback(|cb| {
2391+
let discovered_item = match self.kind() {
2392+
CompKind::Struct => DiscoveredItem::Struct {
2393+
original_name: item
2394+
.kind()
2395+
.expect_type()
2396+
.name()
2397+
.map(String::from),
2398+
final_name: canonical_ident.to_string(),
2399+
},
2400+
CompKind::Union => DiscoveredItem::Union {
2401+
original_name: item
2402+
.kind()
2403+
.expect_type()
2404+
.name()
2405+
.map(String::from),
2406+
final_name: canonical_ident.to_string(),
2407+
},
2408+
};
2409+
2410+
cb.new_item_found(
2411+
DiscoveredItemId::new(item.id().as_usize()),
2412+
discovered_item,
2413+
);
2414+
});
2415+
23772416
// The custom derives callback may return a list of derive attributes;
23782417
// add them to the end of the list.
23792418
let custom_derives = ctx.options().all_callbacks(|cb| {

0 commit comments

Comments
 (0)