Skip to content

Commit fd6fa68

Browse files
committed
linker: Add more markup and comments to code producing linker arguments
1 parent 7f42d81 commit fd6fa68

File tree

1 file changed

+61
-23
lines changed
  • src/librustc_codegen_ssa/back

1 file changed

+61
-23
lines changed

src/librustc_codegen_ssa/back/link.rs

Lines changed: 61 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,7 @@ pub fn get_linker(sess: &Session, linker: &Path, flavor: LinkerFlavor) -> Comman
193193
_ => None,
194194
};
195195
if let Some(ref a) = arch {
196+
// FIXME: Move this to `fn linker_with_args`.
196197
let mut arg = OsString::from("/LIBPATH:");
197198
arg.push(format!("{}\\lib\\{}\\store", root_lib_path.display(), a.to_string()));
198199
cmd.arg(&arg);
@@ -1254,9 +1255,29 @@ fn add_post_link_args(cmd: &mut dyn Linker, sess: &'a Session, flavor: LinkerFla
12541255
}
12551256
}
12561257

1258+
/// Add sysroot and other globally set directories to the directory search list.
1259+
fn add_library_search_dirs(cmd: &mut dyn Linker, sess: &'a Session) {
1260+
// The default library location, we need this to find the runtime.
1261+
// The location of crates will be determined as needed.
1262+
let lib_path = sess.target_filesearch(PathKind::All).get_lib_path();
1263+
1264+
// prefer system mingw-w64 libs, see get_crt_libs_path comment for more details
1265+
if cfg!(windows) && sess.target.target.llvm_target.contains("windows-gnu") {
1266+
if let Some(compiler_libs_path) = get_crt_libs_path(sess) {
1267+
cmd.include_path(&compiler_libs_path);
1268+
}
1269+
}
1270+
1271+
cmd.include_path(&fix_windows_verbatim_for_gcc(&lib_path));
1272+
}
1273+
12571274
/// Produce the linker command line containing linker path and arguments.
12581275
/// `NO-OPT-OUT` marks the arguments that cannot be removed from the command line
12591276
/// by the user without creating a custom target specification.
1277+
/// `OBJECT-FILES` specify whether the arguments can add object files.
1278+
/// `CUSTOMIZATION-POINT` means that arbitrary arguments defined by the user
1279+
/// or by the target spec can be inserted here.
1280+
/// `AUDIT-ORDER` - need to figure out whether the option is order-dependent or not.
12601281
fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
12611282
path: &Path,
12621283
flavor: LinkerFlavor,
@@ -1273,9 +1294,10 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
12731294
assert!(base_cmd.get_args().is_empty() || sess.target.target.target_vendor == "uwp");
12741295
let cmd = &mut *codegen_results.linker_info.to_linker(base_cmd, &sess, flavor, target_cpu);
12751296

1276-
// NO-OPT-OUT
1297+
// NO-OPT-OUT, OBJECT-FILES-MAYBE, CUSTOMIZATION-POINT
12771298
add_pre_link_args(cmd, sess, flavor, crate_type);
12781299

1300+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
12791301
if sess.target.target.options.is_like_fuchsia {
12801302
let prefix = match sess.opts.debugging_opts.sanitizer {
12811303
Some(Sanitizer::Address) => "asan/",
@@ -1284,9 +1306,10 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
12841306
cmd.arg(format!("--dynamic-linker={}ld.so.1", prefix));
12851307
}
12861308

1287-
// NO-OPT-OUT
1309+
// NO-OPT-OUT, OBJECT-FILES-YES
12881310
add_pre_link_objects(cmd, sess, crate_type);
12891311

1312+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
12901313
if sess.target.target.options.is_like_emscripten {
12911314
cmd.arg("-s");
12921315
cmd.arg(if sess.panic_strategy() == PanicStrategy::Abort {
@@ -1296,43 +1319,40 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
12961319
});
12971320
}
12981321

1322+
// OBJECT-FILES-YES, AUDIT-ORDER
12991323
link_sanitizer_runtime(sess, crate_type, cmd);
13001324

1325+
// OBJECT-FILES-NO, AUDIT-ORDER
13011326
// Linker plugins should be specified early in the list of arguments
1327+
// FIXME: How "early" exactly?
13021328
cmd.linker_plugin_lto();
13031329

1304-
// The default library location, we need this to find the runtime.
1305-
// The location of crates will be determined as needed.
1306-
let lib_path = sess.target_filesearch(PathKind::All).get_lib_path();
1307-
1308-
// target descriptor
1309-
let t = &sess.target.target;
1310-
1311-
// prefer system mingw-w64 libs, see get_crt_libs_path comment for more details
1312-
if cfg!(windows) && sess.target.target.llvm_target.contains("windows-gnu") {
1313-
if let Some(compiler_libs_path) = get_crt_libs_path(sess) {
1314-
cmd.include_path(&compiler_libs_path);
1315-
}
1316-
}
1317-
1318-
cmd.include_path(&fix_windows_verbatim_for_gcc(&lib_path));
1330+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
1331+
// FIXME: Order-dependent, at least relatively to other args adding searh directories.
1332+
add_library_search_dirs(cmd, sess);
13191333

1334+
// OBJECT-FILES-YES
13201335
for obj in codegen_results.modules.iter().filter_map(|m| m.object.as_ref()) {
13211336
cmd.add_object(obj);
13221337
}
1338+
1339+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
13231340
cmd.output_filename(out_filename);
13241341

1342+
// OBJECT-FILES-NO, AUDIT-ORDER
13251343
if crate_type == config::CrateType::Executable && sess.target.target.options.is_like_windows {
13261344
if let Some(ref s) = codegen_results.windows_subsystem {
13271345
cmd.subsystem(s);
13281346
}
13291347
}
13301348

1349+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
13311350
// If we're building something like a dynamic library then some platforms
13321351
// need to make sure that all symbols are exported correctly from the
13331352
// dynamic library.
13341353
cmd.export_symbols(tmpdir, crate_type);
13351354

1355+
// OBJECT-FILES-YES
13361356
// When linking a dynamic library, we put the metadata into a section of the
13371357
// executable. This metadata is in a separate object file from the main
13381358
// object file, so we link that in here.
@@ -1343,22 +1363,26 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
13431363
}
13441364
}
13451365

1366+
// OBJECT-FILES-YES
13461367
let obj = codegen_results.allocator_module.as_ref().and_then(|m| m.object.as_ref());
13471368
if let Some(obj) = obj {
13481369
cmd.add_object(obj);
13491370
}
13501371

1372+
// OBJECT-FILES-NO, AUDIT-ORDER
1373+
// FIXME: Order dependent, applies to the following objects. Where should it be placed?
13511374
// Try to strip as much out of the generated object by removing unused
13521375
// sections if possible. See more comments in linker.rs
13531376
if !sess.opts.cg.link_dead_code {
13541377
let keep_metadata = crate_type == config::CrateType::Dylib;
13551378
cmd.gc_sections(keep_metadata);
13561379
}
13571380

1381+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
13581382
if crate_type == config::CrateType::Executable {
13591383
let mut position_independent_executable = false;
13601384

1361-
if t.options.position_independent_executables {
1385+
if sess.target.target.options.position_independent_executables {
13621386
if is_pic(sess)
13631387
&& !sess.crt_static(Some(crate_type))
13641388
&& !sess
@@ -1385,9 +1409,10 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
13851409
}
13861410
}
13871411

1412+
// OBJECT-FILES-NO, AUDIT-ORDER
13881413
let relro_level = match sess.opts.debugging_opts.relro_level {
13891414
Some(level) => level,
1390-
None => t.options.relro_level,
1415+
None => sess.target.target.options.relro_level,
13911416
};
13921417
match relro_level {
13931418
RelroLevel::Full => {
@@ -1402,23 +1427,29 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
14021427
RelroLevel::None => {}
14031428
}
14041429

1430+
// OBJECT-FILES-NO, AUDIT-ORDER
14051431
// Pass optimization flags down to the linker.
14061432
cmd.optimize();
14071433

1434+
// OBJECT-FILES-NO, AUDIT-ORDER
14081435
// Pass debuginfo flags down to the linker.
14091436
cmd.debuginfo();
14101437

1438+
// OBJECT-FILES-NO, AUDIT-ORDER
14111439
// We want to, by default, prevent the compiler from accidentally leaking in
14121440
// any system libraries, so we may explicitly ask linkers to not link to any
14131441
// libraries by default. Note that this does not happen for windows because
14141442
// windows pulls in some large number of libraries and I couldn't quite
14151443
// figure out which subset we wanted.
14161444
//
14171445
// This is all naturally configurable via the standard methods as well.
1418-
if !sess.opts.cg.default_linker_libraries.unwrap_or(false) && t.options.no_default_libraries {
1446+
if !sess.opts.cg.default_linker_libraries.unwrap_or(false)
1447+
&& sess.target.target.options.no_default_libraries
1448+
{
14191449
cmd.no_default_libraries();
14201450
}
14211451

1452+
// OBJECT-FILES-YES
14221453
// Take careful note of the ordering of the arguments we pass to the linker
14231454
// here. Linkers will assume that things on the left depend on things to the
14241455
// right. Things on the right cannot depend on things on the left. This is
@@ -1456,6 +1487,8 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
14561487
if sess.opts.debugging_opts.link_native_libraries.unwrap_or(true) {
14571488
add_upstream_native_libraries(cmd, sess, codegen_results, crate_type);
14581489
}
1490+
1491+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
14591492
// Tell the linker what we're doing.
14601493
if crate_type != config::CrateType::Executable {
14611494
cmd.build_dylib(out_filename);
@@ -1464,14 +1497,17 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
14641497
cmd.build_static_executable();
14651498
}
14661499

1500+
// OBJECT-FILES-NO, AUDIT-ORDER
14671501
if sess.opts.cg.profile_generate.enabled() {
14681502
cmd.pgo_gen();
14691503
}
14701504

1505+
// OBJECT-FILES-NO, AUDIT-ORDER
14711506
if sess.opts.debugging_opts.control_flow_guard != CFGuard::Disabled {
14721507
cmd.control_flow_guard();
14731508
}
14741509

1510+
// OBJECT-FILES-NO, AUDIT-ORDER
14751511
// FIXME (#2397): At some point we want to rpath our guesses as to
14761512
// where extern libraries might live, based on the
14771513
// addl_lib_search_paths
@@ -1496,17 +1532,19 @@ fn linker_with_args<'a, B: ArchiveBuilder<'a>>(
14961532
cmd.args(&rpath::get_rpath_flags(&mut rpath_config));
14971533
}
14981534

1535+
// OBJECT-FILES-MAYBE, CUSTOMIZATION-POINT
14991536
add_user_defined_link_args(cmd, sess, codegen_results);
15001537

1538+
// NO-OPT-OUT, OBJECT-FILES-NO, AUDIT-ORDER
15011539
cmd.finalize();
15021540

1503-
// NO-OPT-OUT
1541+
// NO-OPT-OUT, OBJECT-FILES-MAYBE, CUSTOMIZATION-POINT
15041542
add_late_link_args(cmd, sess, flavor, crate_type, codegen_results);
15051543

1506-
// NO-OPT-OUT
1544+
// NO-OPT-OUT, OBJECT-FILES-YES
15071545
add_post_link_objects(cmd, sess, crate_type);
15081546

1509-
// NO-OPT-OUT
1547+
// NO-OPT-OUT, OBJECT-FILES-MAYBE, CUSTOMIZATION-POINT
15101548
add_post_link_args(cmd, sess, flavor);
15111549

15121550
cmd.take_cmd()

0 commit comments

Comments
 (0)