Skip to content

Commit b11667b

Browse files
committed
Build with clang by default
1 parent 793f7bd commit b11667b

40 files changed

+305
-11501
lines changed

.github/workflows/ci.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -135,7 +135,7 @@ jobs:
135135
source "$HOME/.cargo/env"
136136
"$HOME/.cargo/bin/espup" install -e -r
137137
source "$HOME/exports"
138-
echo "$PATH" >> "$GITHUB_PATH"
138+
echo "${LIBCLANG_PATH}/../bin:$PATH" >> "$GITHUB_PATH"
139139
echo "LIBCLANG_PATH=${LIBCLANG_PATH}" >> "$GITHUB_ENV"
140140
echo "CLANG_PATH=${CLANG_PATH}" >> "$GITHUB_ENV"
141141

esp-mbedtls-sys/Cargo.toml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,12 @@ harness = false
1313
default = []
1414
# Always generate the bindings during build, even if pre-built bindings for the build target are available
1515
force-generate-bindings = []
16+
# Use GCC instead of clang
17+
use-gcc = []
1618
# Force the use of the Espressif Riscv GCC toolchain, if the target is a `riscv32*-` target
1719
# If this feature is not enabled, the build will assume and use the "official" RiscV GCC toolchain:
1820
# https://github.com/riscv-collab/riscv-gnu-toolchain
19-
force-esp-riscv-toolchain = []
21+
force-esp-riscv-gcc = ["use-gcc"]
2022
# Disable all or some hooks; this would preclude hooking custom HW-accelerated algos
2123
nohook = ["nohook-sha1", "nohook-sha256", "nohook-sha512", "nohook-exp-mod"]
2224
nohook-sha1 = []

esp-mbedtls-sys/README.md

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,15 +18,19 @@
1818

1919
## Precompilation
2020

21-
For user-convenience, the MbedTLS C library also comes pre-compiled for the following Rust targets:
21+
For user-convenience, the MbedTLS C library also comes pre-built for the following Rust targets:
2222
- `rsicv32imc-unknown-none-elf`
2323
- `rsicv32imac-unknown-none-elf`
2424
- `xtensa-esp32-none-elf`
2525
- `xtensa-esp32s2-none-elf`
2626
- `xtensa-esp32s3-none-elf`
2727
- (PRs for other Rust baremetal targets appreciated!)
2828

29-
For other MCU baremetal targets as well as for STD platforms, the MbedTLS C library will be compiled on the fly, but that requires GCC (the cross-compiler flavor for your MCU) and Clang pre-installed.
29+
For other MCU baremetal targets as well as for STD platforms, the MbedTLS C library will be compiled on the fly with `clang` (by default), or with GCC (if the `use-gcc` feature is enabled).
30+
31+
Note that for the latter, you DO need to have the GCC cross-compiler flavor for your MCU pre-installed and on your $PATH, while with `clang` _ANY_ `clang` instance would do, as `clang` is natively a cross-compiler. `clang` is anyway always necessary during on-the-fly compilation for the Rust bindings' generation, so that's why it is used by default for compiling the MbedTLS C library as well.
32+
33+
The on-the-fly compilation process also needs `cmake` and `ninja` pre-installed (for now).
3034

3135
ESP-IDF is also supported and in that case `esp-mbedtls-sys` becomes just an alias for `esp-idf-sys` and uses the MbedTLS library which is built-in inside ESP-IDF.
3236

esp-mbedtls-sys/build.rs

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,9 @@ fn main() -> Result<()> {
1717
let host = env::var("HOST").unwrap();
1818
let target = env::var("TARGET").unwrap();
1919

20-
let force_esp_riscv_toolchain = env::var("CARGO_FEATURE_FORCE_ESP_RISCV_TOOLCHAIN").is_ok();
20+
let use_gcc = env::var("CARGO_FEATURE_USE_GCC").is_ok();
21+
let force_esp_riscv_gcc = env::var("CARGO_FEATURE_FORCE_ESP_RISCV_GCC").is_ok();
22+
2123
let pregen_bindings = env::var("CARGO_FEATURE_FORCE_GENERATE_BINDINGS").is_err();
2224
let pregen_bindings_rs_file = crate_root_path
2325
.join("src")
@@ -54,19 +56,22 @@ fn main() -> Result<()> {
5456
}
5557
}
5658

59+
// For clang, use our own cross-platform sysroot
60+
let sysroot = (!use_gcc).then(|| crate_root_path.join("gen").join("sysroot"));
61+
5762
// Need to do on-the-fly build and bindings' generation
5863
let out = PathBuf::from(env::var_os("OUT_DIR").unwrap());
5964

6065
let builder = builder::MbedtlsBuilder::new(
6166
removed_hooks.complement(),
62-
false,
67+
!use_gcc,
6368
crate_root_path.clone(),
6469
Some(target),
6570
Some(host),
6671
None,
72+
sysroot,
6773
None,
68-
None,
69-
force_esp_riscv_toolchain,
74+
force_esp_riscv_gcc,
7075
);
7176

7277
let libs_dir = builder.compile(&out, None)?;

esp-mbedtls-sys/gen/builder.rs

Lines changed: 42 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ impl MbedtlsBuilder {
3434
///
3535
/// Arguments:
3636
/// - `hooks` - Set of algorithm hooks to enable
37+
/// - `force_clang`: If true, force the use of Clang as the C/C++ compiler
3738
/// - `crate_root_path`: Path to the root of the crate
3839
/// - `cmake_rust_target`: Optional target for CMake when building MbedTLS, with Rust target-triple syntax. If not specified, the "TARGET" env variable will be used
3940
/// - `cmake_host_rust_target`: Optional host target for the build
@@ -54,16 +55,17 @@ impl MbedtlsBuilder {
5455
clang_path: Option<PathBuf>,
5556
clang_sysroot_path: Option<PathBuf>,
5657
clang_target: Option<String>,
57-
force_esp_riscv_toolchain: bool,
58+
force_esp_riscv_gcc: bool,
5859
) -> Self {
5960
Self {
6061
hooks,
6162
cmake_configurer: CMakeConfigurer::new(
6263
force_clang,
64+
clang_sysroot_path.clone(),
6365
crate_root_path.join("mbedtls"),
6466
cmake_rust_target,
6567
cmake_host_rust_target,
66-
force_esp_riscv_toolchain,
68+
force_esp_riscv_gcc,
6769
crate_root_path.join("gen").join("toolchain.cmake"),
6870
),
6971
crate_root_path,
@@ -291,37 +293,41 @@ impl MbedtlsBuilder {
291293
#[derive(Debug, Clone)]
292294
pub struct CMakeConfigurer {
293295
pub force_clang: bool,
296+
pub clang_sysroot_path: Option<PathBuf>,
294297
pub project_path: PathBuf,
295298
pub cmake_rust_target: Option<String>,
296299
pub cmake_host_rust_target: Option<String>,
297-
pub force_esp_riscv_toolchain: bool,
300+
pub force_esp_riscv_gcc: bool,
298301
pub empty_toolchain_file: PathBuf,
299302
}
300303

301304
impl CMakeConfigurer {
302305
/// Create a new CMakeConfigurer
303306
///
304307
/// Arguments:
308+
/// - `force_clang`: If true, force the use of Clang as the C/C++ compiler
305309
/// - `project_path`: Path to the root of the CMake project
306310
/// - `cmake_rust_target`: Optional target for CMake when building MbedTLS, with Rust target-triple syntax. If not specified, the "TARGET" env variable will be used
307311
/// - `cmake_host_rust_target`: Optional host target for the build
308-
/// - `force_esp_riscv_toolchain`: If true, and if the target is a riscv32 target, force the use of the Espressif RISCV GCC toolchain
312+
/// - `force_esp_riscv_gcc`: If true, and if the target is a riscv32 target, force the use of the Espressif RISCV GCC toolchain
309313
/// (`riscv32-esp-elf-gcc`) rather than the derived `riscv32-unknown-elf-gcc` toolchain which is the "official" RISC-V one
310314
/// (https://github.com/riscv-collab/riscv-gnu-toolchain)
311315
pub const fn new(
312316
force_clang: bool,
317+
clang_sysroot_path: Option<PathBuf>,
313318
project_path: PathBuf,
314319
cmake_rust_target: Option<String>,
315320
cmake_host_rust_target: Option<String>,
316-
force_esp_riscv_toolchain: bool,
321+
force_esp_riscv_gcc: bool,
317322
empty_toolchain_file: PathBuf,
318323
) -> Self {
319324
Self {
320325
force_clang,
326+
clang_sysroot_path,
321327
project_path,
322328
cmake_rust_target,
323329
cmake_host_rust_target,
324-
force_esp_riscv_toolchain,
330+
force_esp_riscv_gcc,
325331
empty_toolchain_file,
326332
}
327333
}
@@ -377,7 +383,7 @@ impl CMakeConfigurer {
377383
}
378384

379385
for arg in self.derive_c_args() {
380-
config.cflag(arg).cxxflag(arg);
386+
config.cflag(&arg).cxxflag(arg);
381387
}
382388

383389
if let Some(target) = &self.cmake_rust_target {
@@ -392,6 +398,13 @@ impl CMakeConfigurer {
392398
}
393399

394400
pub fn derive_sysroot(&self) -> Option<PathBuf> {
401+
if self.force_clang {
402+
if let Some(clang_sysroot_path) = self.clang_sysroot_path.clone() {
403+
// If clang is used and there is a pre-defined sysroot path for it, use it
404+
return Some(clang_sysroot_path);
405+
}
406+
}
407+
395408
// Only GCC has a sysroot, so try to locate the sysroot using GCC first
396409
let unforce_clang = Self {
397410
force_clang: false,
@@ -456,7 +469,7 @@ impl CMakeConfigurer {
456469
| "riscv32imac-esp-espidf"
457470
| "riscv32imafc-unknown-none-elf"
458471
| "riscv32imafc-esp-espidf" => {
459-
if self.force_esp_riscv_toolchain {
472+
if self.force_esp_riscv_gcc {
460473
Some((PathBuf::from("riscv32-esp-elf-gcc"), true))
461474
} else {
462475
None
@@ -467,7 +480,27 @@ impl CMakeConfigurer {
467480
}
468481
}
469482

470-
fn derive_c_args(&self) -> &[&str] {
483+
fn derive_c_args(&self) -> Vec<String> {
484+
let mut args = Vec::new();
485+
486+
args.extend(
487+
self.derive_c_target_args()
488+
.iter()
489+
.map(|arg| arg.to_string()),
490+
);
491+
492+
if self.force_clang {
493+
if let Some(sysroot_path) = self.derive_sysroot() {
494+
args.push("-fbuiltin".to_string());
495+
args.push(format!("-I{}", sysroot_path.join("include").display()));
496+
args.push(format!("--sysroot={}", sysroot_path.display()));
497+
}
498+
}
499+
500+
args
501+
}
502+
503+
fn derive_c_target_args(&self) -> &[&str] {
471504
if self.force_clang {
472505
match self.target().as_str() {
473506
"riscv32imc-unknown-none-elf" | "riscv32imc-esp-espidf" => {
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
#ifndef __ASSERT_H__
2+
#define __ASSERT_H__
3+
4+
#endif
5+
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
#ifndef __STDIO_H__
2+
#define __STDIO_H__
3+
4+
#define printf __builtin_printf
5+
#define snprintf __builtin_snprintf
6+
#define vsnprintf __builtin_vsnprintf
7+
8+
#endif
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#ifndef __STDLIB_H__
2+
#define __STDLIB_H__
3+
4+
#include <stddef.h>
5+
6+
void* calloc(size_t num, size_t size);
7+
void free(void *ptr);
8+
9+
int rand(void);
10+
11+
#endif
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#ifndef __STRING_H__
2+
#define __STRING_H__
3+
4+
#define memcpy __builtin_memcpy
5+
#define memcmp __builtin_memcmp
6+
#define memset __builtin_memset
7+
#define memmove __builtin_memmove
8+
9+
#define strlen __builtin_strlen
10+
#define strcmp __builtin_strcmp
11+
#define strncmp __builtin_strncmp
12+
#define strstr __builtin_strstr
13+
#define strchr __builtin_strchr
14+
#define strncpy __builtin_strncpy
15+
16+
#endif
Binary file not shown.

0 commit comments

Comments
 (0)