Skip to content

Commit

Permalink
Add -Z small-data-threshold
Browse files Browse the repository at this point in the history
This flag allows specifying the threshold size above which LLVM should
consider placing small objects in a .sdata or .sbss section.
  • Loading branch information
paulmenage committed Oct 25, 2023
1 parent b66fe58 commit 27b2be8
Show file tree
Hide file tree
Showing 4 changed files with 73 additions and 0 deletions.
11 changes: 11 additions & 0 deletions compiler/rustc_codegen_llvm/src/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -351,6 +351,17 @@ pub unsafe fn create_module<'ll>(
);
}

if let Some(threshold) = sess.opts.unstable_opts.small_data_threshold {
if sess.target.arch.starts_with("riscv") {
llvm::LLVMRustAddModuleFlag(
llmod,
llvm::LLVMModFlagBehavior::Error,
"SmallDataLimit\0".as_ptr().cast(),
threshold as u32,
)
}
}

// Insert `llvm.ident` metadata.
//
// On the wasm targets it will get hooked up to the "producer" sections
Expand Down
15 changes: 15 additions & 0 deletions compiler/rustc_codegen_llvm/src/llvm_util.rs
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,21 @@ unsafe fn configure_llvm(sess: &Session) {
for arg in sess_args {
add(&(*arg), true);
}

if let Some(threshold) = sess.opts.unstable_opts.small_data_threshold {
match sess.target.arch.as_ref() {
"hexagon" => {
add(&format!("--hexagon-small-data-threshold={threshold}"), false);
add("--hexagon-statics-in-small-datax", false)
}
"m68k" => add(&format!("--m68k-ssection-threshold={threshold}"), false),
arch @ _ => {
if arch.starts_with("mips") {
add(&format!("--mips-ssection-threshold={threshold}"), false);
}
}
}
}
}

if sess.opts.unstable_opts.llvm_time_trace {
Expand Down
2 changes: 2 additions & 0 deletions compiler/rustc_session/src/options.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1805,6 +1805,8 @@ written to standard error output)"),
simulate_remapped_rust_src_base: Option<PathBuf> = (None, parse_opt_pathbuf, [TRACKED],
"simulate the effect of remap-debuginfo = true at bootstrapping by remapping path \
to rust's source base directory. only meant for testing purposes"),
small_data_threshold: Option<usize> = (None, parse_opt_number, [TRACKED],
"Set the threshold for objects to be stored in a \"small data\" section"),
span_debug: bool = (false, parse_bool, [UNTRACKED],
"forward proc_macro::Span's `Debug` impl to `Span`"),
/// o/w tests have closure@path
Expand Down
45 changes: 45 additions & 0 deletions tests/assembly/small_data_threshold.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// Test for -Z small_data_threshold=...
// revisions: RISCV MIPS HEXAGON M68K
// assembly-output: emit-asm
// compile-flags: -Z small_data_threshold=4
// [RISCV] compile-flags:--target=riscv32im-unknown-none-elf
// [MIPS] compile-flags:--target=mips-unknown-linux-musl
// [HEXAGON] compile-flags:--target=hexagon-unknown-linux-musl
// [M68K] compile-flags:--target=m68k-unknown-linux-gnu

#![feature(no_core, lang_items)]
#![no_std]
#![no_core]
#![crate_type = "lib"]

#[lang = "sized"]
trait Sized {}

#[lang = "drop_in_place"]
fn drop_in_place<T>(_: *mut T) {}

#[used]
#[no_mangle]
/// X is below the threshold, should be in sdata
static mut X: u16 = 123;

#[used]
#[no_mangle]
/// Y is at the threshold, should be in sdata
static mut Y: u32 = 123;

#[used]
#[no_mangle]
/// Z is over the threshold, should be in its own section
static mut Z: u64 = 123;

// Currently, only RISCV successfully puts any objects in the small data
// section.

// RISCV: .section .sdata,
// RISCV-NOT: .section
// RISCV: X:
// RISCV: Y:
// CHECK: .section .data.Z,
// CHECK-NOT: .section
// CHECK: Z:

0 comments on commit 27b2be8

Please sign in to comment.