immunant / c2rust

Migrate C code to Rust
https://c2rust.com/
Other
3.98k stars 237 forks source link

Option to disable pruning of static functions #287

Closed chrysn closed 4 years ago

chrysn commented 4 years ago

C2Rust, by default and since 8bcb5c97b746f16d2181c64b089cc4545080b16b, removes unneeded definitions, which includes static inline functions.

Exporting them is useful when C2Rust is used outside a full transpilation setting -- for example when a C library is accessed by cbindgen, but some functions are declared static inline. (Exporting them anyhow there might be an option; however, as they are static inline, chances are they're used in hot loops, and avoiding the function call would be really nice there. There's some discussion already at https://github.com/rust-lang/rust-bindgen/issues/1344; I'm trying to get that done in a step-by-step fashion).

As a crude proof-of-concept, making TypedAstContext::prune_unused_decls return immediately does the trick; as a next refinement, so does matching on any CDeclKind::Function with Some body by ripping out the conditions -- but that's not really feasible outside experimental setups.

thedataking commented 4 years ago

Thanks for doing some initial research on this @chrysn; I don't know how to preserve these functions without adding a new flag. c2rust transpile already has options that disable internal features that are otherwise on by default (--no-incremental-relooper, --no-simplify-structures) so the matching flag here would be --no-prune-unused-functions IMO.

The transpiler flags are defined in transpile.yaml in the c2rust/src folder.

Re. the attributes you mention (is_global, is_inline and is_inline_externally_visible): why not add a new match case in prune_unused_decls that match any function if the --no-prune-unused-functions flag is set?

rinon commented 4 years ago

I'd call it --preserve-unused-functions or something, but that sounds great. This should probably be added as an option to TranspilerConfig in c2rust-translate/lib.rs.