Skip to content

Commit 9f11860

Browse files
committed
[WIP] Implement LTO support
Serializing and deserializing Cranelift IR is supported, but due to the lack of interprocedural optimizations in Cranelift there is no runtime perf benefit. Only a compile time hit. It may still be useful for things like the JIT mode where invoking a regular linker is not possible.
1 parent 9a5e766 commit 9f11860

File tree

15 files changed

+679
-20
lines changed

15 files changed

+679
-20
lines changed

Cargo.lock

Lines changed: 57 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,13 @@ cranelift-jit = { version = "0.109.0", optional = true }
1616
cranelift-object = { version = "0.109.0" }
1717
target-lexicon = "0.12.0"
1818
gimli = { version = "0.28", default-features = false, features = ["write"]}
19-
object = { version = "0.36", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] }
19+
object = { version = "0.36", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe", "unaligned"] }
2020

2121
indexmap = "2.0.0"
2222
libloading = { version = "0.8.0", optional = true }
2323
smallvec = "1.8.1"
24+
serde = { version = "1.0.203", features = ["derive"], optional = true }
25+
postcard = { version = "1.0.8", default-features = false, features = ["use-std"], optional = true }
2426

2527
[patch.crates-io]
2628
# Uncomment to use local checkout of cranelift
@@ -35,8 +37,9 @@ smallvec = "1.8.1"
3537

3638
[features]
3739
# Enable features not ready to be enabled when compiling as part of rustc
38-
unstable-features = ["jit", "inline_asm_sym"]
40+
unstable-features = ["jit", "inline_asm_sym", "lto"]
3941
jit = ["cranelift-jit", "libloading"]
42+
lto = ["serde", "postcard", "cranelift-codegen/enable-serde", "cranelift-module/enable-serde"]
4043
inline_asm_sym = []
4144

4245
[package.metadata.rust-analyzer]

build_system/build_sysroot.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -267,6 +267,9 @@ fn build_clif_sysroot_for_triple(
267267
prefix.to_str().unwrap()
268268
));
269269
}
270+
rustflags.push("-Clto=thin".to_owned());
271+
rustflags.push("-Zdylib-lto".to_owned());
272+
rustflags.push("-Cembed-bitcode=yes".to_owned());
270273
compiler.rustflags.extend(rustflags);
271274
let mut build_cmd = STANDARD_LIBRARY.build(&compiler, dirs);
272275
if channel == "release" {

build_system/prepare.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,12 @@ codegen-units = 10000
4545
debug-assertions = false
4646
overflow-checks = false
4747
codegen-units = 10000
48+
49+
[profile.dev]
50+
lto = "thin"
51+
52+
[profile.release]
53+
lto = "thin"
4854
"#,
4955
)
5056
.unwrap();

build_system/tests.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ impl TestCase {
5959
}
6060

6161
const NO_SYSROOT_SUITE: &[TestCase] = &[
62-
TestCase::build_lib("build.mini_core", "example/mini_core.rs", "lib,dylib"),
62+
TestCase::build_lib("build.mini_core", "example/mini_core.rs", "lib"),
6363
TestCase::build_lib("build.example", "example/example.rs", "lib"),
6464
TestCase::jit_bin("jit.mini_core_hello_world", "example/mini_core_hello_world.rs", "abc bcd"),
6565
TestCase::build_bin_and_run(
@@ -437,6 +437,7 @@ impl<'a> TestRunner<'a> {
437437
}
438438
spawn_and_wait(jit_cmd);
439439

440+
/*
440441
eprintln!("[JIT-lazy] {testname}");
441442
let mut jit_cmd = self.rustc_command([
442443
"-Zunstable-options",
@@ -450,6 +451,7 @@ impl<'a> TestRunner<'a> {
450451
jit_cmd.env("CG_CLIF_JIT_ARGS", args);
451452
}
452453
spawn_and_wait(jit_cmd);
454+
*/
453455
}
454456
}
455457
}
@@ -468,6 +470,7 @@ impl<'a> TestRunner<'a> {
468470
cmd.arg("--out-dir");
469471
cmd.arg(format!("{}", BUILD_EXAMPLE_OUT_DIR.to_path(&self.dirs).display()));
470472
cmd.arg("-Cdebuginfo=2");
473+
cmd.arg("-Clto=thin");
471474
cmd.arg("--target");
472475
cmd.arg(&self.target_compiler.triple);
473476
cmd.arg("-Cpanic=abort");

example/mini_core.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -735,6 +735,7 @@ struct PanicLocation {
735735
column: u32,
736736
}
737737

738+
/*
738739
#[no_mangle]
739740
#[cfg(not(all(windows, target_env = "gnu")))]
740741
pub fn get_tls() -> u8 {
@@ -743,3 +744,4 @@ pub fn get_tls() -> u8 {
743744
744745
A
745746
}
747+
*/

example/mini_core_hello_world.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,6 +333,7 @@ fn main() {
333333
#[cfg(all(not(jit), not(all(windows, target_env = "gnu"))))]
334334
test_tls();
335335

336+
/*
336337
#[cfg(all(
337338
not(jit),
338339
not(no_unstable_features),
@@ -343,6 +344,7 @@ fn main() {
343344
global_asm_test();
344345
naked_test();
345346
}
347+
*/
346348

347349
// Both statics have a reference that points to the same anonymous allocation.
348350
static REF1: &u8 = &42;
@@ -367,6 +369,7 @@ fn stack_val_align() {
367369
assert_eq!(&a as *const Foo as usize % 8192, 0);
368370
}
369371

372+
/*
370373
#[cfg(all(
371374
not(jit),
372375
not(no_unstable_features),
@@ -396,6 +399,7 @@ global_asm! {
396399
ret
397400
"
398401
}
402+
*/
399403

400404
#[cfg(all(not(jit), not(no_unstable_features), target_arch = "x86_64"))]
401405
#[naked]
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
From 0910cbe862990b0c3a17c67bca199ebb4452b0ec Mon Sep 17 00:00:00 2001
2+
From: bjorn3 <17426603+bjorn3@users.noreply.github.com>
3+
Date: Tue, 28 Mar 2023 17:09:01 +0000
4+
Subject: [PATCH] Disable dylib crate type
5+
6+
---
7+
library/std/Cargo.toml | 2 +-
8+
1 files changed, 1 insertions(+), 1 deletions(-)
9+
10+
diff --git a/library/std/Cargo.toml b/library/std/Cargo.toml
11+
index 598a4bf..3e68680 100644
12+
--- a/library/std/Cargo.toml
13+
+++ b/library/std/Cargo.toml
14+
@@ -7,7 +7,7 @@ description = "The Rust Standard Library"
15+
edition = "2021"
16+
17+
[lib]
18+
-crate-type = ["dylib", "rlib"]
19+
+crate-type = ["rlib"]
20+
21+
[dependencies]
22+
alloc = { path = "../alloc", public = true }
23+
--
24+
2.34.1
25+

src/base.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -248,6 +248,7 @@ pub(crate) fn compile_fn(
248248
}
249249
}
250250

251+
/*
251252
// Define debuginfo for function
252253
let debug_context = &mut cx.debug_context;
253254
cx.profiler.generic_activity("generate debug info").run(|| {
@@ -259,6 +260,7 @@ pub(crate) fn compile_fn(
259260
);
260261
}
261262
});
263+
*/
262264
}
263265

264266
pub(crate) fn verify_func(

src/driver/aot.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,7 @@ impl OngoingCodegen {
133133
}
134134

135135
// Adapted from https://github.com/rust-lang/rust/blob/73476d49904751f8d90ce904e16dfbc278083d2c/compiler/rustc_codegen_ssa/src/back/write.rs#L547C1-L706C2
136-
fn produce_final_output_artifacts(
136+
pub(super) fn produce_final_output_artifacts(
137137
sess: &Session,
138138
codegen_results: &CodegenResults,
139139
crate_output: &OutputFilenames,
@@ -320,7 +320,7 @@ fn produce_final_output_artifacts(
320320
// These are used in linking steps and will be cleaned up afterward.
321321
}
322322

323-
fn make_module(
323+
pub(super) fn make_module(
324324
sess: &Session,
325325
backend_config: &BackendConfig,
326326
name: String,
@@ -375,7 +375,7 @@ fn emit_cgu(
375375
})
376376
}
377377

378-
fn emit_module(
378+
pub(super) fn emit_module(
379379
output_filenames: &OutputFilenames,
380380
prof: &SelfProfilerRef,
381381
mut object: cranelift_object::object::write::Object<'_>,
@@ -479,7 +479,7 @@ fn reuse_workproduct_for_cgu(
479479
})
480480
}
481481

482-
fn codegen_cgu_content(
482+
pub(super) fn codegen_cgu_content(
483483
tcx: TyCtxt<'_>,
484484
module: &mut dyn Module,
485485
cgu_name: rustc_span::Symbol,
@@ -677,7 +677,7 @@ pub(crate) fn run_aot(
677677
})
678678
}
679679

680-
fn emit_allocator_module(
680+
pub(super) fn emit_allocator_module(
681681
tcx: TyCtxt<'_>,
682682
backend_config: &BackendConfig,
683683
) -> Option<CompiledModule> {
@@ -703,7 +703,7 @@ fn emit_allocator_module(
703703
}
704704
}
705705

706-
fn emit_metadata_module(tcx: TyCtxt<'_>, metadata: &EncodedMetadata) -> CompiledModule {
706+
pub(super) fn emit_metadata_module(tcx: TyCtxt<'_>, metadata: &EncodedMetadata) -> CompiledModule {
707707
tcx.sess.time("write compressed metadata", || {
708708
use rustc_middle::mir::mono::CodegenUnitNameBuilder;
709709

src/driver/jit.rs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,10 +70,17 @@ fn create_jit_module(
7070
let mut jit_builder = JITBuilder::with_isa(isa, cranelift_module::default_libcall_names());
7171
jit_builder.hotswap(hotswap);
7272
crate::compiler_builtins::register_functions_for_jit(&mut jit_builder);
73-
jit_builder.symbol_lookup_fn(dep_symbol_lookup_fn(tcx.sess, crate_info));
73+
//jit_builder.symbol_lookup_fn(dep_symbol_lookup_fn(tcx.sess, crate_info));
7474
jit_builder.symbol("__clif_jit_fn", clif_jit_fn as *const u8);
7575
let mut jit_module = UnwindModule::new(JITModule::new(jit_builder), false);
7676

77+
#[cfg(feature = "lto")]
78+
for (_name, module) in
79+
super::lto::load_lto_modules(tcx, &CrateInfo::new(tcx, "dummy".to_owned()), &backend_config)
80+
{
81+
module.apply_to(&mut jit_module);
82+
}
83+
7784
let cx = crate::CodegenCx::new(tcx, jit_module.isa(), false, Symbol::intern("dummy_cgu_name"));
7885

7986
crate::allocator::codegen(tcx, &mut jit_module);

0 commit comments

Comments
 (0)