Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 16 additions & 0 deletions bindgen-tests/tests/expectations/tests/unsafe-functions.rs

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

7 changes: 7 additions & 0 deletions bindgen-tests/tests/headers/unsafe-functions.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
// bindgen-flags: --safe-functions is_zero --safe-functions '^is_number_\d+$'

int is_zero(int n);
int is_zero_ptr(int *n);
int is_number_5(int n);
int is_number_42(int n);
int is_number_other_than_8(int n);
12 changes: 9 additions & 3 deletions bindgen/codegen/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4921,19 +4921,25 @@ impl CodeGenerator for Function {
};
let ret = utils::fnsig_return_ty(ctx, signature);

let ident = ctx.rust_ident(ident);

let safety = ctx
.options()
.rust_features
.unsafe_extern_blocks
.then(|| quote!(unsafe));

let mark_fn_safe = ctx
.options()
.safe_functions
.matches(ident)
.then(|| quote!(safe));

let ident = ctx.rust_ident(ident);

let tokens = quote! {
#block_attributes
#safety extern #abi {
#(#attributes)*
pub fn #ident ( #( #args ),* ) #ret;
pub #mark_fn_safe fn #ident ( #( #args ),* ) #ret;
}
};

Expand Down
4 changes: 3 additions & 1 deletion bindgen/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -471,7 +471,7 @@ impl Builder {

impl BindgenOptions {
fn build(&mut self) {
const REGEX_SETS_LEN: usize = 29;
const REGEX_SETS_LEN: usize = 30;

let regex_sets: [_; REGEX_SETS_LEN] = [
&mut self.blocklisted_types,
Expand Down Expand Up @@ -503,6 +503,7 @@ impl BindgenOptions {
&mut self.no_default_types,
&mut self.no_hash_types,
&mut self.must_use_types,
&mut self.safe_functions,
];

let record_matches = self.record_matches;
Expand Down Expand Up @@ -540,6 +541,7 @@ impl BindgenOptions {
"--no-default",
"--no-hash",
"--must-use",
"--safe-functions",
])
.chain((0..self.abi_overrides.len()).map(|_| "--override-abi"))
.map(Some)
Expand Down
5 changes: 5 additions & 0 deletions bindgen/options/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -496,6 +496,9 @@ struct BindgenCommand {
/// Wrap unsafe operations in unsafe blocks.
#[arg(long)]
wrap_unsafe_ops: bool,
/// Mark functions matching REGEX as `safe`.
#[arg(long, value_name = "REGEX")]
safe_functions: Vec<String>,
/// Enable fallback for clang macro parsing.
#[arg(long)]
clang_macro_fallback: bool,
Expand Down Expand Up @@ -694,6 +697,7 @@ where
merge_extern_blocks,
override_abi,
wrap_unsafe_ops,
safe_functions,
clang_macro_fallback,
clang_macro_fallback_build_dir,
flexarray_dst,
Expand Down Expand Up @@ -1000,6 +1004,7 @@ where
merge_extern_blocks,
override_abi => |b, (abi, regex)| b.override_abi(abi, regex),
wrap_unsafe_ops,
safe_functions => Builder::safe_function,
clang_macro_fallback => |b, _| b.clang_macro_fallback(),
clang_macro_fallback_build_dir,
flexarray_dst,
Expand Down
13 changes: 13 additions & 0 deletions bindgen/options/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2107,6 +2107,19 @@ options! {
},
as_args: "--wrap-unsafe-ops",
},
/// Functions that should be marked as `safe`.
safe_functions: RegexSet {
methods: {
regex_option! {
/// Mark the matching function as `safe`.
pub fn safe_function<T: AsRef<str>>(mut self, arg: T) -> Builder {
self.options.safe_functions.insert(arg);
self
}
}
},
as_args: "--safe-functions",
},
/// Use DSTs to represent structures with flexible array members.
flexarray_dst: bool {
methods: {
Expand Down
Loading