Skip to content

Commit

Permalink
add write_bindings to LanguageBackend for more flexible LB impls
Browse files Browse the repository at this point in the history
  • Loading branch information
fredszaq committed Mar 12, 2024
1 parent eaa4ac2 commit 83346c9
Show file tree
Hide file tree
Showing 9 changed files with 347 additions and 269 deletions.
135 changes: 9 additions & 126 deletions src/bindgen/bindings.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ use crate::bindgen::ir::{
Constant, Function, ItemContainer, ItemMap, Path as BindgenPath, Static, Struct, Type, Typedef,
};
use crate::bindgen::language_backend::{
CLikeLanguageBackend, CythonLanguageBackend, LanguageBackend, NamespaceOperation,
CLikeLanguageBackend, CythonLanguageBackend, LanguageBackend,
};
use crate::bindgen::writer::SourceWriter;

Expand All @@ -28,10 +28,10 @@ pub struct Bindings {
struct_map: ItemMap<Struct>,
typedef_map: ItemMap<Typedef>,
struct_fileds_memo: RefCell<HashMap<BindgenPath, Rc<Vec<String>>>>,
globals: Vec<Static>,
constants: Vec<Constant>,
items: Vec<ItemContainer>,
functions: Vec<Function>,
pub globals: Vec<Static>,
pub constants: Vec<Constant>,
pub items: Vec<ItemContainer>,
pub functions: Vec<Function>,
source_files: Vec<path::PathBuf>,
/// Bindings are generated by a recursive call to cbindgen
/// and shouldn't do anything when written anywhere.
Expand Down Expand Up @@ -202,142 +202,25 @@ impl Bindings {
pub fn write<F: Write>(&self, file: F) {
match self.config.language {
Language::Cxx | Language::C => {
self.write_with_backend(file, &CLikeLanguageBackend::new(&self.config))
self.write_with_backend(file, &mut CLikeLanguageBackend::new(&self.config))
}
Language::Cython => {
self.write_with_backend(file, &CythonLanguageBackend::new(&self.config))
self.write_with_backend(file, &mut CythonLanguageBackend::new(&self.config))
}
}
}

pub fn write_with_backend<F: Write, LB: LanguageBackend>(
&self,
file: F,
language_backend: &LB,
language_backend: &mut LB,
) {
if self.noop {
return;
}

let mut out = SourceWriter::new(file, self);

language_backend.write_headers(&mut out);

language_backend.open_close_namespaces(NamespaceOperation::Open, &mut out);

for constant in &self.constants {
if constant.uses_only_primitive_types() {
out.new_line_if_not_start();
constant.write(&self.config, language_backend, &mut out, None);
out.new_line();
}
}

for item in &self.items {
if item
.deref()
.annotations()
.bool("no-export")
.unwrap_or(false)
{
continue;
}

out.new_line_if_not_start();
match *item {
ItemContainer::Constant(..) => unreachable!(),
ItemContainer::Static(..) => unreachable!(),
ItemContainer::Enum(ref x) => language_backend.write_enum(&mut out, x),
ItemContainer::Struct(ref x) => language_backend.write_struct(&mut out, x),
ItemContainer::Union(ref x) => language_backend.write_union(&mut out, x),
ItemContainer::OpaqueItem(ref x) => language_backend.write_opaque_item(&mut out, x),
ItemContainer::Typedef(ref x) => language_backend.write_type_def(&mut out, x),
}
out.new_line();
}

for constant in &self.constants {
if !constant.uses_only_primitive_types() {
out.new_line_if_not_start();
constant.write(&self.config, language_backend, &mut out, None);
out.new_line();
}
}

if !self.functions.is_empty() || !self.globals.is_empty() {
if self.config.cpp_compatible_c() {
out.new_line_if_not_start();
out.write("#ifdef __cplusplus");
}

if self.config.language == Language::Cxx {
if let Some(ref using_namespaces) = self.config.using_namespaces {
for namespace in using_namespaces {
out.new_line();
write!(out, "using namespace {};", namespace);
}
out.new_line();
}
}

if self.config.language == Language::Cxx || self.config.cpp_compatible_c() {
out.new_line();
out.write("extern \"C\" {");
out.new_line();
}

if self.config.cpp_compatible_c() {
out.write("#endif // __cplusplus");
out.new_line();
}

for global in &self.globals {
out.new_line_if_not_start();
language_backend.write_static(&mut out, global);
out.new_line();
}

for function in &self.functions {
out.new_line_if_not_start();
language_backend.write_function(&mut out, function);
out.new_line();
}

if self.config.cpp_compatible_c() {
out.new_line();
out.write("#ifdef __cplusplus");
}

if self.config.language == Language::Cxx || self.config.cpp_compatible_c() {
out.new_line();
out.write("} // extern \"C\"");
out.new_line();
}

if self.config.cpp_compatible_c() {
out.write("#endif // __cplusplus");
out.new_line();
}
}

if self.config.language == Language::Cython
&& self.globals.is_empty()
&& self.constants.is_empty()
&& self.items.is_empty()
&& self.functions.is_empty()
{
out.write("pass");
}

language_backend.open_close_namespaces(NamespaceOperation::Close, &mut out);

language_backend.write_footers(&mut out);
if let Some(ref f) = self.config.trailer {
out.new_line_if_not_start();
write!(out, "{}", f);
if !f.ends_with('\n') {
out.new_line();
}
}
language_backend.write_bindings(&mut out, self);
}
}
12 changes: 6 additions & 6 deletions src/bindgen/cdecl.rs
Original file line number Diff line number Diff line change
Expand Up @@ -194,7 +194,7 @@ impl CDecl {

fn write<F: Write, LB: LanguageBackend>(
&self,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
ident: Option<&str>,
config: &Config,
Expand Down Expand Up @@ -305,7 +305,7 @@ impl CDecl {
}

fn write_vertical<F: Write, LB: LanguageBackend>(
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
config: &Config,
args: &[(Option<String>, CDecl)],
Expand All @@ -327,7 +327,7 @@ impl CDecl {
}

fn write_horizontal<F: Write, LB: LanguageBackend>(
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
config: &Config,
args: &[(Option<String>, CDecl)],
Expand Down Expand Up @@ -372,7 +372,7 @@ impl CDecl {
}

pub fn write_func<F: Write, LB: LanguageBackend>(
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
f: &Function,
layout: Layout,
Expand All @@ -382,7 +382,7 @@ pub fn write_func<F: Write, LB: LanguageBackend>(
}

pub fn write_field<F: Write, LB: LanguageBackend>(
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
t: &Type,
ident: &str,
Expand All @@ -392,7 +392,7 @@ pub fn write_field<F: Write, LB: LanguageBackend>(
}

pub fn write_type<F: Write, LB: LanguageBackend>(
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
t: &Type,
config: &Config,
Expand Down
4 changes: 2 additions & 2 deletions src/bindgen/ir/constant.rs
Original file line number Diff line number Diff line change
Expand Up @@ -595,7 +595,7 @@ impl Constant {
pub fn write_declaration<F: Write, LB: LanguageBackend>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
associated_to_struct: &Struct,
) {
Expand All @@ -617,7 +617,7 @@ impl Constant {
pub fn write<F: Write, LB: LanguageBackend>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
associated_to_struct: Option<&Struct>,
) {
Expand Down
16 changes: 8 additions & 8 deletions src/bindgen/ir/enumeration.rs
Original file line number Diff line number Diff line change
Expand Up @@ -637,11 +637,11 @@ impl Enum {
pub(crate) fn write_tag_enum<
F: Write,
LB: LanguageBackend,
WV: Fn(&LB, &mut SourceWriter<F>, &EnumVariant),
WV: Fn(&mut LB, &mut SourceWriter<F>, &EnumVariant),
>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
size: Option<&str>,
write_variant: WV,
Expand Down Expand Up @@ -809,7 +809,7 @@ impl Enum {
pub(crate) fn write_variant_defs<F: Write, LB: LanguageBackend>(
&self,
config: &Config,
language_backend: &LB, // TODO probably need only one of Config/LanguageBackend
language_backend: &mut LB, // TODO probably need only one of Config/LanguageBackend
out: &mut SourceWriter<F>,
) {
for variant in &self.variants {
Expand Down Expand Up @@ -870,11 +870,11 @@ impl Enum {
pub(crate) fn write_variant_fields<
F: Write,
LB: LanguageBackend,
WF: Fn(&LB, &mut SourceWriter<F>, &Field),
WF: Fn(&mut LB, &mut SourceWriter<F>, &Field),
>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
inline_tag_field: bool,
write_field: WF,
Expand Down Expand Up @@ -933,7 +933,7 @@ impl Enum {
fn write_derived_functions_enum<F: Write, LB: LanguageBackend>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
) {
let has_data = self.tag.is_some();
Expand Down Expand Up @@ -1089,11 +1089,11 @@ impl Enum {
pub(crate) fn write_derived_functions_data<
F: Write,
LB: LanguageBackend,
WF: Fn(&LB, &mut SourceWriter<F>, &Field),
WF: Fn(&mut LB, &mut SourceWriter<F>, &Field),
>(
&self,
config: &Config,
language_backend: &LB,
language_backend: &mut LB,
out: &mut SourceWriter<F>,
tag_name: &str,
write_field: WF,
Expand Down
4 changes: 2 additions & 2 deletions src/bindgen/ir/generic_path.rs
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ impl GenericParams {

pub(crate) fn write_internal<F: Write, LB: LanguageBackend>(
&self,
language_backend: &LB,
language_backend: &mut LB,
config: &Config,
out: &mut SourceWriter<F>,
with_default: bool,
Expand Down Expand Up @@ -130,7 +130,7 @@ impl GenericParams {

pub fn write_with_default<F: Write, LB: LanguageBackend>(
&self,
language_backend: &LB,
language_backend: &mut LB,
config: &Config,
out: &mut SourceWriter<F>,
) {
Expand Down
Loading

0 comments on commit 83346c9

Please sign in to comment.