diff --git a/config.toml.example b/config.toml.example index 36587cc078441..fcb99e545c7b9 100644 --- a/config.toml.example +++ b/config.toml.example @@ -400,6 +400,10 @@ # Flag indicating whether tests are compiled with optimizations (the -O flag). #optimize-tests = true +# Flag indicating whether tests are optimized with Polly. If optimize-tests is false, +# polly-tests will be false regardless of its value here. +#polly-tests = false + # Flag indicating whether codegen tests will be run or not. If you get an error # saying that the FileCheck executable is missing, you may want to disable this. # Also see the target's llvm-filecheck option. @@ -456,6 +460,10 @@ # instead of LLVM's default of 100. #thin-lto-import-instr-limit = 100 +# Use Polly on the rust compiler itself. If optimize is false, this will be +# false as well. +#polly-self = false + # Map debuginfo paths to `/rust/$sha/...`, generally only set for releases #remap-debuginfo = false diff --git a/src/bootstrap/bin/rustc.rs b/src/bootstrap/bin/rustc.rs index 4dd71ebade1a4..d4221d783ba32 100644 --- a/src/bootstrap/bin/rustc.rs +++ b/src/bootstrap/bin/rustc.rs @@ -45,6 +45,7 @@ fn main() { ("RUSTC_REAL", "RUSTC_LIBDIR") }; let stage = env::var("RUSTC_STAGE").expect("RUSTC_STAGE was not set"); + let stage = usize::from_str(stage.as_str()).expect("RUSTC_STAGE not a usize"); let sysroot = env::var_os("RUSTC_SYSROOT").expect("RUSTC_SYSROOT was not set"); let on_fail = env::var_os("RUSTC_ON_FAIL").map(Command::new); @@ -100,7 +101,7 @@ fn main() { // workaround undefined references to `rust_eh_unwind_resume` generated // otherwise, see issue https://github.com/rust-lang/rust/issues/43095. if crate_name == Some("panic_abort") - || crate_name == Some("compiler_builtins") && stage != "0" + || crate_name == Some("compiler_builtins") && stage != 0 { cmd.arg("-C").arg("panic=abort"); } @@ -127,11 +128,19 @@ fn main() { cmd.arg("--remap-path-prefix").arg(&map); } + let use_polly = match env::var("RUSTC_USE_POLLY") { + Ok(v) => v != "0", + Err(_) => false, + }; + if use_polly && stage >= 1 { + cmd.arg("-Z").arg("polly"); + } + // Force all crates compiled by this compiler to (a) be unstable and (b) // allow the `rustc_private` feature to link to other unstable crates // also in the sysroot. We also do this for host crates, since those // may be proc macros, in which case we might ship them. - if env::var_os("RUSTC_FORCE_UNSTABLE").is_some() && (stage != "0" || target.is_some()) { + if env::var_os("RUSTC_FORCE_UNSTABLE").is_some() && (stage != 0 || target.is_some()) { cmd.arg("-Z").arg("force-unstable-if-unmarked"); } diff --git a/src/bootstrap/builder.rs b/src/bootstrap/builder.rs index 6446fa7550d53..24cb435b3ffa6 100644 --- a/src/bootstrap/builder.rs +++ b/src/bootstrap/builder.rs @@ -1323,6 +1323,18 @@ impl<'a> Builder<'a> { cargo.env("WINAPI_NO_BUNDLED_LIBRARIES", "1"); } + let use_polly = match cmd { + "test" | "bench" => { + self.config.rust_polly_tests + }, + _ => self.config.rust_polly_self + }; + if use_polly && stage > 1 { + cargo.env("RUSTC_USE_POLLY", "1"); + } else { + cargo.env("RUSTC_USE_POLLY", "0"); + } + for _ in 1..self.verbosity { cargo.arg("-v"); } diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs index 70b1c471ac3f0..0d9a606d6c3eb 100644 --- a/src/bootstrap/config.rs +++ b/src/bootstrap/config.rs @@ -107,12 +107,14 @@ pub struct Config { pub rustc_parallel: bool, pub rustc_default_linker: Option, pub rust_optimize_tests: bool, + pub rust_polly_tests: bool, pub rust_dist_src: bool, pub rust_codegen_backends: Vec>, pub rust_verify_llvm_ir: bool, pub rust_thin_lto_import_instr_limit: Option, pub rust_remap_debuginfo: bool, pub rust_new_symbol_mangling: bool, + pub rust_polly_self: bool, pub build: TargetSelection, pub hosts: Vec, @@ -394,6 +396,7 @@ struct Rust { rpath: Option, verbose_tests: Option, optimize_tests: Option, + polly_tests: Option, codegen_tests: Option, ignore_git: Option, dist_src: Option, @@ -412,6 +415,7 @@ struct Rust { llvm_libunwind: Option, control_flow_guard: Option, new_symbol_mangling: Option, + polly_self: Option, } /// TOML representation of how each build target is configured. @@ -641,6 +645,10 @@ impl Config { ignore_git = rust.ignore_git; set(&mut config.rust_new_symbol_mangling, rust.new_symbol_mangling); set(&mut config.rust_optimize_tests, rust.optimize_tests); + set(&mut config.rust_polly_tests, rust.polly_tests); + if !config.rust_optimize_tests { + config.rust_polly_tests = false; + } set(&mut config.codegen_tests, rust.codegen_tests); set(&mut config.rust_rpath, rust.rpath); set(&mut config.jemalloc, rust.jemalloc); @@ -675,6 +683,10 @@ impl Config { config.rust_codegen_units = rust.codegen_units.map(threads_from_config); config.rust_codegen_units_std = rust.codegen_units_std.map(threads_from_config); + + config.rust_polly_self = rust + .polly_self + .unwrap_or(false); } if let Some(ref t) = toml.target { @@ -747,6 +759,10 @@ impl Config { config.rust_debuginfo_level_tools = with_defaults(debuginfo_level_tools); config.rust_debuginfo_level_tests = debuginfo_level_tests.unwrap_or(0); + if !config.rust_optimize { + config.rust_polly_self = false; + } + let default = config.channel == "dev"; config.ignore_git = ignore_git.unwrap_or(default); diff --git a/src/bootstrap/native.rs b/src/bootstrap/native.rs index f1bc3d11d8b77..72847b2cd52a0 100644 --- a/src/bootstrap/native.rs +++ b/src/bootstrap/native.rs @@ -169,7 +169,6 @@ impl Step for Llvm { .define("LLVM_INCLUDE_TESTS", "OFF") .define("LLVM_INCLUDE_DOCS", "OFF") .define("LLVM_INCLUDE_BENCHMARKS", "OFF") - .define("WITH_POLLY", "OFF") .define("LLVM_ENABLE_TERMINFO", "OFF") .define("LLVM_ENABLE_LIBEDIT", "OFF") .define("LLVM_ENABLE_BINDINGS", "OFF") @@ -178,6 +177,11 @@ impl Step for Llvm { .define("LLVM_TARGET_ARCH", target_native.split('-').next().unwrap()) .define("LLVM_DEFAULT_TARGET_TRIPLE", target_native); + if !self.emscripten { + let polly_src = builder.src.join("src/polly"); + cfg.define("LLVM_EXTERNAL_POLLY_SOURCE_DIR", polly_src); + } + if !target.contains("netbsd") && target != "aarch64-apple-darwin" { cfg.define("LLVM_ENABLE_ZLIB", "ON"); } else { diff --git a/src/bootstrap/test.rs b/src/bootstrap/test.rs index ac833a55d4c53..cdeeba5d7922d 100644 --- a/src/bootstrap/test.rs +++ b/src/bootstrap/test.rs @@ -1060,6 +1060,9 @@ impl Step for Compiletest { flags.push(format!("-Cdebuginfo={}", builder.config.rust_debuginfo_level_tests)); flags.push("-Zunstable-options".to_string()); flags.push(builder.config.cmd.rustc_args().join(" ")); + if builder.config.rust_polly_self { + flags.push("-Zpolly".into()); + } // Don't use LLD here since we want to test that rustc finds and uses a linker by itself. if let Some(linker) = builder.linker(target, false) { diff --git a/src/librustc_codegen_llvm/back/lto.rs b/src/librustc_codegen_llvm/back/lto.rs index 6b02b5e8120db..a4166bb90c8b0 100644 --- a/src/librustc_codegen_llvm/back/lto.rs +++ b/src/librustc_codegen_llvm/back/lto.rs @@ -659,7 +659,7 @@ pub(crate) fn run_pass_manager( } let pm = llvm::LLVMCreatePassManager(); - llvm::LLVMAddAnalysisPasses(module.module_llvm.tm, pm); + llvm::LLVMAddAnalysisPasses(module.module_llvm.tm, pm, config.polly); if config.verify_llvm_ir { let pass = llvm::LLVMRustFindAndCreatePass("verify\0".as_ptr().cast()); diff --git a/src/librustc_codegen_llvm/back/write.rs b/src/librustc_codegen_llvm/back/write.rs index 1a5794d113366..bc95b3a230667 100644 --- a/src/librustc_codegen_llvm/back/write.rs +++ b/src/librustc_codegen_llvm/back/write.rs @@ -191,21 +191,197 @@ pub fn target_machine_factory( }) } -pub(crate) fn save_temp_bitcode( - cgcx: &CodegenContext, - module: &ModuleCodegen, - name: &str, -) { - if !cgcx.save_temps { - return; +/// Module-specific configuration for `optimize_and_codegen`. +pub struct ModuleConfig { + /// Names of additional optimization passes to run. + passes: Vec, + /// Some(level) to optimize at a certain level, or None to run + /// absolutely no optimizations (used for the metadata module). + pub opt_level: Option, + + /// Some(level) to optimize binary size, or None to not affect program size. + opt_size: Option, + + pgo_gen: Option, + pgo_use: String, + + // Flags indicating which outputs to produce. + pub emit_pre_thin_lto_bc: bool, + emit_no_opt_bc: bool, + emit_bc: bool, + emit_bc_compressed: bool, + emit_lto_bc: bool, + emit_ir: bool, + emit_asm: bool, + emit_obj: bool, + // Miscellaneous flags. These are mostly copied from command-line + // options. + pub verify_llvm_ir: bool, + no_prepopulate_passes: bool, + no_builtins: bool, + time_passes: bool, + vectorize_loop: bool, + vectorize_slp: bool, + merge_functions: bool, + inline_threshold: Option, + // Instead of creating an object file by doing LLVM codegen, just + // make the object file bitcode. Provides easy compatibility with + // emscripten's ecc compiler, when used as the linker. + obj_is_bitcode: bool, + no_integrated_as: bool, + embed_bitcode: bool, + embed_bitcode_marker: bool, +} + +impl ModuleConfig { + fn new(passes: Vec) -> ModuleConfig { + ModuleConfig { + passes, + opt_level: None, + opt_size: None, + + pgo_gen: None, + pgo_use: String::new(), + + emit_no_opt_bc: false, + emit_pre_thin_lto_bc: false, + emit_bc: false, + emit_bc_compressed: false, + emit_lto_bc: false, + emit_ir: false, + emit_asm: false, + emit_obj: false, + obj_is_bitcode: false, + embed_bitcode: false, + embed_bitcode_marker: false, + no_integrated_as: false, + + verify_llvm_ir: false, + no_prepopulate_passes: false, + no_builtins: false, + time_passes: false, + vectorize_loop: false, + vectorize_slp: false, + merge_functions: false, + inline_threshold: None + } } - unsafe { - let ext = format!("{}.bc", name); - let cgu = Some(&module.name[..]); - let path = cgcx.output_filenames.temp_path_ext(&ext, cgu); - let cstr = path_to_c_string(&path); - let llmod = module.module_llvm.llmod(); - llvm::LLVMWriteBitcodeToFile(llmod, cstr.as_ptr()); + + fn set_flags(&mut self, sess: &Session, no_builtins: bool) { + self.verify_llvm_ir = sess.verify_llvm_ir(); + self.no_prepopulate_passes = sess.opts.cg.no_prepopulate_passes; + self.no_builtins = no_builtins || sess.target.target.options.no_builtins; + self.time_passes = sess.time_passes(); + self.inline_threshold = sess.opts.cg.inline_threshold; + self.obj_is_bitcode = sess.target.target.options.obj_is_bitcode || + sess.opts.debugging_opts.cross_lang_lto.enabled(); + let embed_bitcode = sess.target.target.options.embed_bitcode || + sess.opts.debugging_opts.embed_bitcode; + if embed_bitcode { + match sess.opts.optimize { + config::OptLevel::No | + config::OptLevel::Less => { + self.embed_bitcode_marker = embed_bitcode; + } + _ => self.embed_bitcode = embed_bitcode, + } + } + + // Copy what clang does by turning on loop vectorization at O2 and + // slp vectorization at O3. Otherwise configure other optimization aspects + // of this pass manager builder. + // Turn off vectorization for emscripten, as it's not very well supported. + self.vectorize_loop = !sess.opts.cg.no_vectorize_loops && + (sess.opts.optimize == config::OptLevel::Default || + sess.opts.optimize == config::OptLevel::Aggressive) && + !sess.target.target.options.is_like_emscripten; + + self.vectorize_slp = !sess.opts.cg.no_vectorize_slp && + sess.opts.optimize == config::OptLevel::Aggressive && + !sess.target.target.options.is_like_emscripten; + + self.merge_functions = sess.opts.optimize == config::OptLevel::Default || + sess.opts.optimize == config::OptLevel::Aggressive; + } +} + +/// Assembler name and command used by codegen when no_integrated_as is enabled +struct AssemblerCommand { + name: PathBuf, + cmd: Command, +} + +/// Additional resources used by optimize_and_codegen (not module specific) +#[derive(Clone)] +pub struct CodegenContext { + // Resources needed when running LTO + pub time_passes: bool, + pub lto: Lto, + pub no_landing_pads: bool, + pub save_temps: bool, + pub fewer_names: bool, + pub exported_symbols: Option>, + pub opts: Arc, + pub crate_types: Vec, + pub each_linked_rlib_for_lto: Vec<(CrateNum, PathBuf)>, + output_filenames: Arc, + regular_module_config: Arc, + metadata_module_config: Arc, + allocator_module_config: Arc, + pub tm_factory: Arc Result<&'static mut llvm::TargetMachine, String> + Send + Sync>, + pub msvc_imps_needed: bool, + pub target_pointer_width: String, + debuginfo: config::DebugInfo, + + // Number of cgus excluding the allocator/metadata modules + pub total_cgus: usize, + // Handler to use for diagnostics produced during codegen. + pub diag_emitter: SharedEmitter, + // LLVM passes added by plugins. + pub plugin_passes: Vec, + // LLVM optimizations for which we want to print remarks. + pub remark: Passes, + // Worker thread number + pub worker: usize, + // The incremental compilation session directory, or None if we are not + // compiling incrementally + pub incr_comp_session_dir: Option, + // Used to update CGU re-use information during the thinlto phase. + pub cgu_reuse_tracker: CguReuseTracker, + // Channel back to the main control thread to send messages to + coordinator_send: Sender>, + // A reference to the TimeGraph so we can register timings. None means that + // measuring is disabled. + time_graph: Option, + // The assembler command if no_integrated_as option is enabled, None otherwise + assembler_cmd: Option>, +} + +impl CodegenContext { + pub fn create_diag_handler(&self) -> Handler { + Handler::with_emitter(true, false, Box::new(self.diag_emitter.clone())) + } + + pub(crate) fn config(&self, kind: ModuleKind) -> &ModuleConfig { + match kind { + ModuleKind::Regular => &self.regular_module_config, + ModuleKind::Metadata => &self.metadata_module_config, + ModuleKind::Allocator => &self.allocator_module_config, + } + } + + pub(crate) fn save_temp_bitcode(&self, module: &ModuleCodegen, name: &str) { + if !self.save_temps { + return + } + unsafe { + let ext = format!("{}.bc", name); + let cgu = Some(&module.name[..]); + let path = self.output_filenames.temp_path_ext(&ext, cgu); + let cstr = path2cstr(&path); + let llmod = module.module_llvm.llmod(); + llvm::LLVMWriteBitcodeToFile(llmod, cstr.as_ptr()); + } } } @@ -529,12 +705,16 @@ pub(crate) unsafe fn optimize( // we'll get errors in LLVM. let using_thin_buffers = config.bitcode_needed(); if !config.no_prepopulate_passes { - llvm::LLVMAddAnalysisPasses(tm, fpm); - llvm::LLVMAddAnalysisPasses(tm, mpm); - let opt_level = to_llvm_opt_settings(opt_level).0; - let prepare_for_thin_lto = cgcx.lto == Lto::Thin - || cgcx.lto == Lto::ThinLocal - || (cgcx.lto != Lto::Fat && cgcx.opts.cg.linker_plugin_lto.enabled()); + llvm::LLVMRustAddAnalysisPasses(tm, fpm, llmod); + llvm::LLVMRustAddAnalysisPasses(tm, mpm, llmod); + let opt_level = config.opt_level.unwrap_or(llvm::CodeGenOptLevel::None); + let prepare_for_thin_lto = cgcx.lto == Lto::Thin || cgcx.lto == Lto::ThinLocal || + (cgcx.lto != Lto::Fat && cgcx.opts.debugging_opts.cross_lang_lto.enabled()); + have_name_anon_globals_pass = have_name_anon_globals_pass || prepare_for_thin_lto; + if using_thin_buffers && !prepare_for_thin_lto { + assert!(addpass("name-anon-globals")); + have_name_anon_globals_pass = true; + } with_llvm_pmb(llmod, &config, opt_level, prepare_for_thin_lto, &mut |b| { llvm::LLVMRustAddLastExtensionPasses( b, @@ -644,17 +824,14 @@ pub(crate) unsafe fn codegen( // pass manager passed to the closure should be ensured to not // escape the closure itself, and the manager should only be // used once. - unsafe fn with_codegen<'ll, F, R>( - tm: &'ll llvm::TargetMachine, - llmod: &'ll llvm::Module, - no_builtins: bool, - f: F, - ) -> R - where - F: FnOnce(&'ll mut PassManager<'ll>) -> R, + unsafe fn with_codegen<'ll, F, R>(tm: &'ll llvm::TargetMachine, + llmod: &'ll llvm::Module, + no_builtins: bool, + f: F) -> R + where F: FnOnce(&'ll mut PassManager<'ll>) -> R, { let cpm = llvm::LLVMCreatePassManager(); - llvm::LLVMAddAnalysisPasses(tm, cpm); + llvm::LLVMRustAddAnalysisPasses(tm, cpm, llmod); llvm::LLVMRustAddLibraryInfo(cpm, llmod, no_builtins); f(cpm) } @@ -732,7 +909,11 @@ pub(crate) unsafe fn codegen( return 0; } - cursor.position() as size_t + with_codegen(tm, llmod, config.no_builtins, |cpm| { + llvm::LLVMRustPrintModule(cpm, llmod, out.as_ptr(), demangle_callback); + llvm::LLVMDisposePassManager(cpm); + }); + timeline.record("ir"); } let result = llvm::LLVMRustPrintModule(llmod, out_c.as_ptr(), demangle_callback); @@ -779,11 +960,16 @@ pub(crate) unsafe fn codegen( })?; } - EmitObj::Bitcode => { - debug!("copying bitcode {:?} to obj {:?}", bc_out, obj_out); - if let Err(e) = link_or_copy(&bc_out, &obj_out) { - diag_handler.err(&format!("failed to copy bitcode to object file: {}", e)); - } + if write_obj { + with_codegen(tm, llmod, config.no_builtins, |cpm| { + write_output_file(diag_handler, tm, cpm, llmod, &obj_out, + llvm::FileType::ObjectFile) + })?; + timeline.record("obj"); + } else if asm_to_obj { + let assembly = cgcx.output_filenames.temp_path(OutputType::Assembly, module_name); + run_assembler(cgcx, diag_handler, &assembly, &obj_out); + timeline.record("asm_to_obj"); if !config.emit_bc { debug!("removing_bitcode {:?}", bc_out); diff --git a/src/librustc_codegen_llvm/llvm/ffi.rs b/src/librustc_codegen_llvm/llvm/ffi.rs index 63b0aa64bd3d8..634d3c42d72e0 100644 --- a/src/librustc_codegen_llvm/llvm/ffi.rs +++ b/src/librustc_codegen_llvm/llvm/ffi.rs @@ -1675,7 +1675,7 @@ extern "C" { pub fn LLVMTimeTraceProfilerFinish(FileName: *const c_char); - pub fn LLVMAddAnalysisPasses(T: &'a TargetMachine, PM: &PassManager<'a>); + pub fn LLVMAddAnalysisPasses(T: &'a TargetMachine, PM: &PassManager<'a>, Polly: bool); pub fn LLVMPassManagerBuilderCreate() -> &'static mut PassManagerBuilder; pub fn LLVMPassManagerBuilderDispose(PMB: &'static mut PassManagerBuilder); @@ -2150,6 +2150,7 @@ extern "C" { PMB: &'a PassManagerBuilder, M: &'a Module, DisableSimplifyLibCalls: bool, + Polly: bool, ); pub fn LLVMRustConfigurePassManagerBuilder( PMB: &PassManagerBuilder, diff --git a/src/librustc_llvm/build.rs b/src/librustc_llvm/build.rs index 21b8080714c17..e7b25d2e9b6cd 100644 --- a/src/librustc_llvm/build.rs +++ b/src/librustc_llvm/build.rs @@ -164,6 +164,48 @@ fn main() { cfg.define("LLVM_RUSTLLVM", None); } + let (enable_polly, polly_link_kind, polly_link_isl) = { + let mut cmd = Command::new(&llvm_config); + cmd.arg("--libdir"); + let libdir = output(&mut cmd); + let libdir = libdir.lines().next().unwrap(); + let libdir = Path::new(&libdir); + assert!(libdir.exists()); + + // We can't specify the full libname to rust, so the linker will always expect (on unix) + // LLVMPolly to be libLLVMPolly, which won't be present. I didn't realize this fact until + // after I wrote the following, but maybe this issue will be resolved in the future. + let allow_shared = false; + let mut found_static = false; + let mut found_shared = false; + for entry in libdir.read_dir().unwrap() { + if let Ok(entry) = entry { + if let Some(name) = entry.path().file_name() { + let name = name.to_str().unwrap(); + if name.contains("Polly") { + if !found_static { + found_static = !name.contains("LLVM"); + } + if !found_shared { + found_shared = name.contains("LLVM"); + } + } + } + } + } + + let found_static = found_static; + let found_shared = allow_shared && found_shared; + let enabled = !cfg!(feature = "emscripten") && + (found_static || found_shared); + let (kind, isl) = match (found_static, found_shared) { + (false, false) => ("", false), + (true, _) => ("static", true), + (false, true) => ("dylib", false), + }; + (enabled, kind, isl) + }; + if tracked_env_var_os("LLVM_NDEBUG").is_some() { cfg.define("NDEBUG", None); cfg.debug(false); @@ -175,6 +217,7 @@ fn main() { .file("../rustllvm/ArchiveWrapper.cpp") .file("../rustllvm/CoverageMappingWrapper.cpp") .file("../rustllvm/Linker.cpp") + .define("ENABLE_POLLY", if enable_polly { "1" } else { "0" }) .cpp(true) .cpp_link_stdlib(None) // we handle this below .compile("rustllvm"); @@ -223,6 +266,20 @@ fn main() { println!("cargo:rustc-link-lib={}={}", kind, name); } + if enable_polly { + match polly_link_kind { + "dylib" => { + panic!("dynamically linking polly is not possible :("); + //println!("cargo:rustc-flags=-l:LLVMPolly") + }, + _ => println!("cargo:rustc-link-lib={}=Polly", polly_link_kind), + } + + if polly_link_isl { + println!("cargo:rustc-link-lib={}=PollyISL", polly_link_kind); + } + } + // LLVM ldflags // // If we're a cross-compile of LLVM then unfortunately we can't trust these diff --git a/src/rustllvm/PassWrapper.cpp b/src/rustllvm/PassWrapper.cpp index 76fe5e7f769f7..e2c8378b45bfb 100644 --- a/src/rustllvm/PassWrapper.cpp +++ b/src/rustllvm/PassWrapper.cpp @@ -52,6 +52,12 @@ DEFINE_STDCXX_CONVERSION_FUNCTIONS(TargetMachine, LLVMTargetMachineRef) #if LLVM_VERSION_LT(11, 0) DEFINE_STDCXX_CONVERSION_FUNCTIONS(PassManagerBuilder, LLVMPassManagerBuilderRef) + +#if ENABLE_POLLY +namespace polly { +void initializePollyPasses(llvm::PassRegistry &Registry); +void registerPollyPasses(llvm::legacy::PassManagerBase &PM); +} #endif extern "C" void LLVMInitializePasses() { @@ -66,6 +72,10 @@ extern "C" void LLVMInitializePasses() { initializeInstCombine(Registry); initializeInstrumentation(Registry); initializeTarget(Registry); + +#if ENABLE_POLLY + polly::initializePollyPasses(Registry); +#endif } extern "C" void LLVMTimeTraceProfilerInitialize() { diff --git a/src/tools/tidy/src/lib.rs b/src/tools/tidy/src/lib.rs index 19218cbd66a8a..68be7e9980913 100644 --- a/src/tools/tidy/src/lib.rs +++ b/src/tools/tidy/src/lib.rs @@ -63,6 +63,7 @@ fn filter_dirs(path: &Path) -> bool { "src/doc/book", // Filter RLS output directories "target/rls", + "src/polly", ]; skip.iter().any(|p| path.ends_with(p)) }