tools/corrosion/doc/src/advanced.md
author unC0Rr
Wed, 28 Aug 2024 15:31:51 +0200
branchtransitional_engine
changeset 16050 6a3dc15b78b9
permissions -rw-r--r--
Add corrosion as a subdirectory, CMake fixes
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
16050
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     1
## What does corrosion do?
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     2
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     3
The specifics of what corrosion does should be regarded as an implementation detail and not relied on
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     4
when writing user code. However, a basic understanding of what corrosion does may be helpful when investigating
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     5
issues.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     6
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     7
### FindRust
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     8
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
     9
Corrosion maintains a CMake module `FindRust` which is executed when Corrosion is loaded, i.e. at the time
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    10
of `find_package(corrosion)`, `FetchContent_MakeAvailable(corrosion)` or `add_subdirectory(corrosion)` depending
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    11
on the method used to include Corrosion.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    12
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    13
`FindRust` will search for installed rust toolchains, respecting the options prefixed with `Rust_` documented in
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    14
the [Usage](usage.md#corrosion-options) chapter.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    15
It will select _one_ Rust toolchain to be used for the compilation of Rust code. Toolchains managed by `rustup`
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    16
will be resolved and corrosion will always select a specific toolchain, not a `rustup` proxy.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    17
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    18
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    19
### Importing Rust crates
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    20
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    21
Corrosion's main function is `corrosion_import_crate`, which internally will call `cargo metadata` to provide
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    22
structured information based on the `Cargo.toml` manifest.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    23
Corrosion will then iterate over all workspace and/or package members and find all rust crates that are either
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    24
a static (`staticlib`) or shared (`cdylib`) library or a `bin` target and create CMake targets matching the
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    25
crate name. Additionally, a build target is created for each imported target, containing the required build
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    26
command to create the imported artifact. This build command can be influenced by various arguments to 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    27
`corrosion_import_crate` as well as corrosion specific target properties which are documented int the  
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    28
[Usage](usage.md) chapter.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    29
Corrosion adds the necessary dependencies and also copies the target artifacts out of the cargo build tree
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    30
to standard CMake locations, even respecting `OUTPUT_DIRECTORY` target properties if set.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    31
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    32
### Linking
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    33
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    34
Depending on the type of the crate the linker will either be invoked by CMake or by `rustc`.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    35
Rust `staticlib`s are linked into C/C++ code via `target_link_libraries()` and the linker is
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    36
invoked by CMake.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    37
For rust `cdylib`s and `bin`s, the linker is invoked via `rustc` and CMake just gets the final artifact.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    38
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    39
#### CMake invokes the linker
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    40
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    41
When CMake invokes the linker, everything is as usual. CMake will call the linker with
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    42
the compiler as the linker driver and users can just use the regular CMake functions to
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    43
modify linking behaviour. `corrosion_set_linker()` has **no effect**.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    44
As a convenience, `corrosion_link_libraries()` will forward its arguments to `target_link_libraries()`.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    45
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    46
#### Rustc invokes the linker 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    47
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    48
Rust `cdylib`s and `bin`s are linked via `rustc`. Corrosion provides several helper functions
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    49
to influence the linker invocation for such targets. 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    50
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    51
`corrosion_link_libraries()` is a limited version of `target_link_libraries()` 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    52
for rust `cdylib` or `bin` targets.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    53
Under the hood this function passes `-l` and `-L` flags to the linker invocation and
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    54
ensures the linked libraries are built first.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    55
Much of the advanced functionality available in `target_link_libraries()` is not implemented yet,
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    56
but pull-requests are welcome! In the meantime, users may want to use 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    57
`corrosion_add_target_local_rustflags()` to pass customized linking flags.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    58
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    59
`corrosion_set_linker()` can be used to specify a custom linker, in case the default one
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    60
chosen by corrosion is not what you want.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    61
Corrosion currently instructs `rustc` to use the C/C++ compiler as the linker driver.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    62
This is done because:
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    63
- For C++ code we must link with `libstdc++` or `libc++` (depending on the compiler), so we must
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    64
  either specify the library on the link line or use a `c++` compiler as the linker driver.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    65
- `Rustc`s default linker selection currently is not so great. For a number of platforms
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    66
  `rustc` will fallback to `cc` as the linker driver. When cross-compiling, this leads
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    67
  to linking failures, since the linker driver is for the host architecture.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    68
  Corrosion avoids this by specifying the C/C++ compiler as the linker driver.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    69
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    70
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    71
In some cases, especially in older rust versions (pre 1.68), the linker flavor detection 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    72
of `rustc` is also not correct, so when setting a custom linker you may want to pass the
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    73
[`-C linker-flavor`](https://doc.rust-lang.org/rustc/codegen-options/index.html#linker-flavor)
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    74
rustflag via `corrosion_add_target_local_rustflags()`.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    75
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    76
## FFI bindings
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    77
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    78
For interaction between Rust and other languages there need to be some FFI bindings of some sort.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    79
For simple cases manually defining the interfaces may be sufficient, but in many cases users
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    80
wish to use tools like [bindgen], [cbindgen], [cxx] or [autocxx] to automate the generating of
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    81
bindings.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    82
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    83
In principle there are two different ways to generate the bindings:
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    84
- use a `build.rs` script to generate the bindings when cargo is invoked, using
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    85
  library versions of the tools to generate the bindings.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    86
- use the cli versions of the tools and setup custom CMake targets/commands to
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    87
  generate the bindings. This approach should be preferred if the bindings are needed
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    88
  by the C/C++ side.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    89
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    90
Corrosion currently provides 2 experimental functions to integrate cbindgen and cxx into
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    91
the build process. They are not 100% production ready yet, but should work well as a 
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    92
template on how to integrate generating bindings into your build process.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    93
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    94
Todo: expand this documentation and link to other resources.
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    95
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    96
[bindgen]: https://rust-lang.github.io/rust-bindgen/
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    97
[cbindgen]: https://github.com/eqrion/cbindgen
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    98
[cxx]: https://cxx.rs/
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
    99
[autocxx]: https://google.github.io/autocxx/index.html
6a3dc15b78b9 Add corrosion as a subdirectory, CMake fixes
unC0Rr
parents:
diff changeset
   100