bindgen/callbacks.rs
1//! A public API for more fine-grained customization of bindgen behavior.
2
3pub use crate::ir::analysis::DeriveTrait;
4pub use crate::ir::derive::CanDerive as ImplementsTrait;
5pub use crate::ir::enum_ty::{EnumVariantCustomBehavior, EnumVariantValue};
6pub use crate::ir::int::IntKind;
7pub use cexpr::token::Kind as TokenKind;
8pub use cexpr::token::Token;
9use std::fmt;
10
11/// An enum to allow ignoring parsing of macros.
12#[derive(Copy, Clone, Debug, PartialEq, Eq, Default)]
13pub enum MacroParsingBehavior {
14 /// Ignore the macro, generating no code for it, or anything that depends on
15 /// it.
16 Ignore,
17 /// The default behavior bindgen would have otherwise.
18 #[default]
19 Default,
20}
21
22/// A trait to allow configuring different kinds of types in different
23/// situations.
24pub trait ParseCallbacks: fmt::Debug {
25 #[cfg(feature = "__cli")]
26 #[doc(hidden)]
27 fn cli_args(&self) -> Vec<String> {
28 vec![]
29 }
30
31 /// This function will be run on every macro that is identified.
32 fn will_parse_macro(&self, _name: &str) -> MacroParsingBehavior {
33 MacroParsingBehavior::Default
34 }
35
36 /// This function will run for every extern variable and function. The returned value determines
37 /// the name visible in the bindings.
38 fn generated_name_override(
39 &self,
40 _item_info: ItemInfo<'_>,
41 ) -> Option<String> {
42 None
43 }
44
45 /// This function will run for every extern variable and function. The returned value determines
46 /// the link name in the bindings.
47 fn generated_link_name_override(
48 &self,
49 _item_info: ItemInfo<'_>,
50 ) -> Option<String> {
51 None
52 }
53
54 /// Modify the contents of a macro
55 fn modify_macro(&self, _name: &str, _tokens: &mut Vec<Token>) {}
56
57 /// The integer kind an integer macro should have, given a name and the
58 /// value of that macro, or `None` if you want the default to be chosen.
59 fn int_macro(&self, _name: &str, _value: i64) -> Option<IntKind> {
60 None
61 }
62
63 /// This will be run on every string macro. The callback cannot influence the further
64 /// treatment of the macro, but may use the value to generate additional code or configuration.
65 fn str_macro(&self, _name: &str, _value: &[u8]) {}
66
67 /// This will be run on every function-like macro. The callback cannot
68 /// influence the further treatment of the macro, but may use the value to
69 /// generate additional code or configuration.
70 ///
71 /// The first parameter represents the name and argument list (including the
72 /// parentheses) of the function-like macro. The second parameter represents
73 /// the expansion of the macro as a sequence of tokens.
74 fn func_macro(&self, _name: &str, _value: &[&[u8]]) {}
75
76 /// This function should return whether, given an enum variant
77 /// name, and value, this enum variant will forcibly be a constant.
78 fn enum_variant_behavior(
79 &self,
80 _enum_name: Option<&str>,
81 _original_variant_name: &str,
82 _variant_value: EnumVariantValue,
83 ) -> Option<EnumVariantCustomBehavior> {
84 None
85 }
86
87 /// Allows to rename an enum variant, replacing `_original_variant_name`.
88 fn enum_variant_name(
89 &self,
90 _enum_name: Option<&str>,
91 _original_variant_name: &str,
92 _variant_value: EnumVariantValue,
93 ) -> Option<String> {
94 None
95 }
96
97 /// Allows to rename an item, replacing `_item_info.name`.
98 fn item_name(&self, _item_info: ItemInfo) -> Option<String> {
99 None
100 }
101
102 /// This will be called on every header filename passed to (`Builder::header`)[`crate::Builder::header`].
103 fn header_file(&self, _filename: &str) {}
104
105 /// This will be called on every file inclusion, with the full path of the included file.
106 fn include_file(&self, _filename: &str) {}
107
108 /// This will be called every time `bindgen` reads an environment variable whether it has any
109 /// content or not.
110 fn read_env_var(&self, _key: &str) {}
111
112 /// This will be called to determine whether a particular blocklisted type
113 /// implements a trait or not. This will be used to implement traits on
114 /// other types containing the blocklisted type.
115 ///
116 /// * `None`: use the default behavior
117 /// * `Some(ImplementsTrait::Yes)`: `_name` implements `_derive_trait`
118 /// * `Some(ImplementsTrait::Manually)`: any type including `_name` can't
119 /// derive `_derive_trait` but can implemented it manually
120 /// * `Some(ImplementsTrait::No)`: `_name` doesn't implement `_derive_trait`
121 fn blocklisted_type_implements_trait(
122 &self,
123 _name: &str,
124 _derive_trait: DeriveTrait,
125 ) -> Option<ImplementsTrait> {
126 None
127 }
128
129 /// Provide a list of custom derive attributes.
130 ///
131 /// If no additional attributes are wanted, this function should return an
132 /// empty `Vec`.
133 fn add_derives(&self, _info: &DeriveInfo<'_>) -> Vec<String> {
134 vec![]
135 }
136
137 /// Provide a list of custom attributes.
138 ///
139 /// If no additional attributes are wanted, this function should return an
140 /// empty `Vec`.
141 fn add_attributes(&self, _info: &AttributeInfo<'_>) -> Vec<String> {
142 vec![]
143 }
144
145 /// Process a source code comment.
146 fn process_comment(&self, _comment: &str) -> Option<String> {
147 None
148 }
149
150 /// Potentially override the visibility of a composite type field.
151 ///
152 /// Caution: This allows overriding standard C++ visibility inferred by
153 /// `respect_cxx_access_specs`.
154 fn field_visibility(
155 &self,
156 _info: FieldInfo<'_>,
157 ) -> Option<crate::FieldVisibilityKind> {
158 None
159 }
160
161 /// Process a function name that as exactly one `va_list` argument
162 /// to be wrapped as a variadic function with the wrapped static function
163 /// feature.
164 ///
165 /// The returned string is new function name.
166 #[cfg(feature = "experimental")]
167 fn wrap_as_variadic_fn(&self, _name: &str) -> Option<String> {
168 None
169 }
170
171 /// This will get called everytime an item (currently struct, union, and alias) is found with some information about it
172 fn new_item_found(&self, _id: DiscoveredItemId, _item: DiscoveredItem) {}
173
174 // TODO add callback for ResolvedTypeRef
175}
176
177/// An identifier for a discovered item. Used to identify an aliased type (see [`DiscoveredItem::Alias`])
178#[derive(Ord, PartialOrd, PartialEq, Eq, Hash, Debug, Clone, Copy)]
179pub struct DiscoveredItemId(usize);
180
181impl DiscoveredItemId {
182 /// Constructor
183 pub fn new(value: usize) -> Self {
184 Self(value)
185 }
186}
187
188/// Struct passed to [`ParseCallbacks::new_item_found`] containing information about discovered
189/// items (struct, union, and alias)
190#[derive(Debug, Hash, Clone, Ord, PartialOrd, Eq, PartialEq)]
191pub enum DiscoveredItem {
192 /// Represents a struct with its original name in C and its generated binding name
193 Struct {
194 /// The original name (learnt from C) of the structure
195 /// Can be None if the union is anonymous.
196 original_name: Option<String>,
197
198 /// The name of the generated binding
199 final_name: String,
200 },
201
202 /// Represents a union with its original name in C and its generated binding name
203 Union {
204 /// The original name (learnt from C) of the structure.
205 /// Can be None if the union is anonymous.
206 original_name: Option<String>,
207
208 /// The name of the generated binding
209 final_name: String,
210 },
211
212 /// Represents an alias like a typedef
213 /// ```c
214 /// typedef struct MyStruct {
215 /// ...
216 /// } StructAlias;
217 /// ```
218 /// Here, the name of the alias is `StructAlias` and it's an alias for `MyStruct`
219 Alias {
220 /// The name of the alias in C (`StructAlias`)
221 alias_name: String,
222
223 /// The identifier of the discovered type
224 alias_for: DiscoveredItemId,
225 },
226
227 /// Represents an enum.
228 Enum {
229 /// The final name of the generated binding
230 final_name: String,
231 },
232
233 /// A function or method.
234 Function {
235 /// The final name used.
236 final_name: String,
237 },
238
239 /// A method.
240 Method {
241 /// The final name used.
242 final_name: String,
243
244 /// Type to which this method belongs.
245 parent: DiscoveredItemId,
246 }, // modules, etc.
247}
248
249/// Relevant information about a type to which new derive attributes will be added using
250/// [`ParseCallbacks::add_derives`].
251#[derive(Debug)]
252#[non_exhaustive]
253pub struct DeriveInfo<'a> {
254 /// The name of the type.
255 pub name: &'a str,
256 /// The kind of the type.
257 pub kind: TypeKind,
258}
259
260/// Relevant information about a type to which new attributes will be added using
261/// [`ParseCallbacks::add_attributes`].
262#[derive(Debug)]
263#[non_exhaustive]
264pub struct AttributeInfo<'a> {
265 /// The name of the type.
266 pub name: &'a str,
267 /// The kind of the type.
268 pub kind: TypeKind,
269}
270
271#[derive(Debug, Clone, Copy, PartialEq, Eq)]
272/// The kind of the current type.
273pub enum TypeKind {
274 /// The type is a Rust `struct`.
275 Struct,
276 /// The type is a Rust `enum`.
277 Enum,
278 /// The type is a Rust `union`.
279 Union,
280}
281
282/// A struct providing information about the item being passed to [`ParseCallbacks::generated_name_override`].
283#[derive(Clone, Copy)]
284#[non_exhaustive]
285pub struct ItemInfo<'a> {
286 /// The name of the item
287 pub name: &'a str,
288 /// The kind of item
289 pub kind: ItemKind,
290}
291
292/// An enum indicating the kind of item for an `ItemInfo`.
293#[derive(Clone, Copy)]
294#[non_exhaustive]
295pub enum ItemKind {
296 /// A module
297 Module,
298 /// A type
299 Type,
300 /// A Function
301 Function,
302 /// A Variable
303 Var,
304}
305
306/// Relevant information about a field for which visibility can be determined using
307/// [`ParseCallbacks::field_visibility`].
308#[derive(Debug)]
309#[non_exhaustive]
310pub struct FieldInfo<'a> {
311 /// The name of the type.
312 pub type_name: &'a str,
313 /// The name of the field.
314 pub field_name: &'a str,
315 /// The name of the type of the field.
316 pub field_type_name: Option<&'a str>,
317}