summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bindgen-integration/build.rs18
-rw-r--r--bindgen-integration/cpp/Test.h2
-rw-r--r--src/callbacks.rs (renamed from src/chooser.rs)6
-rw-r--r--src/ir/context.rs8
-rw-r--r--src/ir/enum_ty.rs2
-rw-r--r--src/ir/var.rs7
-rw-r--r--src/lib.rs14
7 files changed, 43 insertions, 14 deletions
diff --git a/bindgen-integration/build.rs b/bindgen-integration/build.rs
index 9b157c5a..fe7ffb1f 100644
--- a/bindgen-integration/build.rs
+++ b/bindgen-integration/build.rs
@@ -1,9 +1,23 @@
extern crate bindgen;
extern crate gcc;
+use std::collections::HashSet;
use std::env;
use std::path::PathBuf;
+use std::sync::{Arc, RwLock};
use bindgen::Builder;
+use bindgen::callbacks::ParseCallbacks;
+
+#[derive(Debug)]
+struct MacroCallback {
+ macros: Arc<RwLock<HashSet<String>>>,
+}
+
+impl ParseCallbacks for MacroCallback {
+ fn parsed_macro(&self, _name: &str) {
+ self.macros.write().unwrap().insert(String::from(_name));
+ }
+}
fn main() {
gcc::Config::new()
@@ -11,6 +25,8 @@ fn main() {
.file("cpp/Test.cc")
.compile("libtest.a");
+ let macros = Arc::new(RwLock::new(HashSet::new()));
+
let bindings = Builder::default()
.no_unstable_rust()
.enable_cxx_namespaces()
@@ -19,9 +35,11 @@ fn main() {
.clang_arg("-x")
.clang_arg("c++")
.clang_arg("-std=c++11")
+ .parse_callbacks(Box::new(MacroCallback {macros: macros.clone()}))
.generate()
.expect("Unable to generate bindings");
+ assert!(macros.read().unwrap().contains("TESTMACRO"));
let out_path = PathBuf::from(env::var("OUT_DIR").unwrap());
bindings
diff --git a/bindgen-integration/cpp/Test.h b/bindgen-integration/cpp/Test.h
index c060984d..310478bb 100644
--- a/bindgen-integration/cpp/Test.h
+++ b/bindgen-integration/cpp/Test.h
@@ -1,5 +1,7 @@
#pragma once
+#define TESTMACRO
+
class Test {
int m_int;
double m_double;
diff --git a/src/chooser.rs b/src/callbacks.rs
index 29090a42..ef85fdd7 100644
--- a/src/chooser.rs
+++ b/src/callbacks.rs
@@ -7,7 +7,11 @@ use std::panic::UnwindSafe;
/// A trait to allow configuring different kinds of types in different
/// situations.
-pub trait TypeChooser: fmt::Debug + UnwindSafe {
+pub trait ParseCallbacks: fmt::Debug + UnwindSafe {
+
+ /// This function will be run on every macro that is identified
+ fn parsed_macro(&self, _name: &str) {}
+
/// The integer kind an integer macro should have, given a name and the
/// value of that macro, or `None` if you want the default to be chosen.
fn int_macro(&self, _name: &str, _value: i64) -> Option<IntKind> {
diff --git a/src/ir/context.rs b/src/ir/context.rs
index 1dc4f4a4..4a6785b1 100644
--- a/src/ir/context.rs
+++ b/src/ir/context.rs
@@ -11,7 +11,7 @@ use super::traversal::{self, Edge, ItemTraversal};
use super::ty::{FloatKind, TemplateDeclaration, Type, TypeKind};
use BindgenOptions;
use cexpr;
-use chooser::TypeChooser;
+use callbacks::ParseCallbacks;
use clang::{self, Cursor};
use clang_sys;
use parse::ClangItemParser;
@@ -233,9 +233,9 @@ impl<'ctx> BindgenContext<'ctx> {
.expect("should have been parsing a type, if we finished parsing a type")
}
- /// Get the user-provided type chooser by reference, if any.
- pub fn type_chooser(&self) -> Option<&TypeChooser> {
- self.options().type_chooser.as_ref().map(|t| &**t)
+ /// Get the user-provided callbacks by reference, if any.
+ pub fn parse_callbacks(&self) -> Option<&ParseCallbacks> {
+ self.options().parse_callbacks.as_ref().map(|t| &**t)
}
/// Define a new item.
diff --git a/src/ir/enum_ty.rs b/src/ir/enum_ty.rs
index d2385a29..175af691 100644
--- a/src/ir/enum_ty.rs
+++ b/src/ir/enum_ty.rs
@@ -91,7 +91,7 @@ impl Enum {
};
if let Some(val) = value {
let name = cursor.spelling();
- let custom_behavior = ctx.type_chooser()
+ let custom_behavior = ctx.parse_callbacks()
.and_then(|t| {
t.enum_variant_behavior(type_name, &name, val)
})
diff --git a/src/ir/var.rs b/src/ir/var.rs
index 2e56e9f5..656a1a6d 100644
--- a/src/ir/var.rs
+++ b/src/ir/var.rs
@@ -116,6 +116,11 @@ impl ClangSubItemParser for Var {
use cexpr::literal::CChar;
match cursor.kind() {
CXCursor_MacroDefinition => {
+
+ if let Some(visitor) = ctx.parse_callbacks() {
+ visitor.parsed_macro(&cursor.spelling());
+ }
+
let value = parse_macro(ctx, &cursor, ctx.translation_unit());
let (id, value) = match value {
@@ -170,7 +175,7 @@ impl ClangSubItemParser for Var {
(TypeKind::Pointer(char_ty), VarType::String(val))
}
EvalResult::Int(Wrapping(value)) => {
- let kind = ctx.type_chooser()
+ let kind = ctx.parse_callbacks()
.and_then(|c| c.int_macro(&name, value))
.unwrap_or_else(|| if value < 0 {
if value < i32::min_value() as i64 {
diff --git a/src/lib.rs b/src/lib.rs
index 30d9987b..e92be92b 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -63,7 +63,7 @@ mod parse;
mod regex_set;
mod uses;
-pub mod chooser;
+pub mod callbacks;
#[cfg(rustfmt)]
mod codegen;
@@ -445,10 +445,10 @@ impl Builder {
self
}
- /// Allows configuring types in different situations, see the `TypeChooser`
+ /// Allows configuring types in different situations, see the `ParseCallbacks`
/// documentation.
- pub fn type_chooser(mut self, cb: Box<chooser::TypeChooser>) -> Self {
- self.options.type_chooser = Some(cb);
+ pub fn parse_callbacks(mut self, cb: Box<callbacks::ParseCallbacks>) -> Self {
+ self.options.parse_callbacks = Some(cb);
self
}
@@ -567,9 +567,9 @@ pub struct BindgenOptions {
/// of all types defined therein. See the `uses` module for more.
pub dummy_uses: Option<String>,
- /// A user-provided type chooser to allow customizing different kinds of
+ /// A user-provided visitor to allow customizing different kinds of
/// situations.
- pub type_chooser: Option<Box<chooser::TypeChooser>>,
+ pub parse_callbacks: Option<Box<callbacks::ParseCallbacks>>,
/// Which kind of items should we generate? By default, we'll generate all
/// of them.
@@ -650,7 +650,7 @@ impl Default for BindgenOptions {
clang_args: vec![],
input_header: None,
dummy_uses: None,
- type_chooser: None,
+ parse_callbacks: None,
codegen_config: CodegenConfig::all(),
conservative_inline_namespaces: false,
generate_comments: true,