Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit b1363a7

Browse files
authoredSep 13, 2016
Auto merge of #35021 - japaric:rustc-builtins, r=alexcrichton
crate-ify compiler-rt into compiler-builtins libcompiler-rt.a is dead, long live libcompiler-builtins.rlib This commit moves the logic that used to build libcompiler-rt.a into a compiler-builtins crate on top of the core crate and below the std crate. This new crate still compiles the compiler-rt instrinsics using gcc-rs but produces an .rlib instead of a static library. Also, with this commit rustc no longer passes -lcompiler-rt to the linker. This effectively makes the "no-compiler-rt" field of target specifications a no-op. Users of `no_std` will have to explicitly add the compiler-builtins crate to their crate dependency graph *if* they need the compiler-rt intrinsics - this is a [breaking-change]. Users of the `std` have to do nothing extra as the std crate depends on compiler-builtins. Finally, this a step towards lazy compilation of std with Cargo as the compiler-rt intrinsics can now be built by Cargo instead of having to be supplied by the user by some other method. closes #34400 --- r? @alexcrichton
2 parents 2fd0608 + 848cfe2 commit b1363a7

File tree

28 files changed

+739
-616
lines changed

28 files changed

+739
-616
lines changed
 

‎mk/clean.mk

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,6 @@ define CLEAN_TARGET_STAGE_N
102102
clean$(1)_T_$(2)_H_$(3): \
103103
$$(foreach crate,$$(CRATES),clean$(1)_T_$(2)_H_$(3)-lib-$$(crate)) \
104104
$$(foreach tool,$$(TOOLS) $$(DEBUGGER_BIN_SCRIPTS_ALL),clean$(1)_T_$(2)_H_$(3)-tool-$$(tool))
105-
$$(Q)rm -f $$(TLIB$(1)_T_$(2)_H_$(3))/libcompiler-rt.a
106105
$(Q)rm -f $$(TLIB$(1)_T_$(2)_H_$(3))/librun_pass_stage* # For unix
107106
$(Q)rm -f $$(TLIB$(1)_T_$(2)_H_$(3))/run_pass_stage* # For windows
108107

‎mk/crates.mk

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@
5151

5252
TARGET_CRATES := libc std term \
5353
getopts collections test rand \
54-
core alloc \
54+
compiler_builtins core alloc \
5555
rustc_unicode rustc_bitflags \
5656
alloc_system alloc_jemalloc \
5757
panic_abort panic_unwind unwind
@@ -65,6 +65,7 @@ HOST_CRATES := syntax syntax_ext proc_macro syntax_pos $(RUSTC_CRATES) rustdoc f
6565
TOOLS := compiletest rustdoc rustc rustbook error_index_generator
6666

6767
DEPS_core :=
68+
DEPS_compiler_builtins := core
6869
DEPS_alloc := core libc alloc_system
6970
DEPS_alloc_system := core libc
7071
DEPS_alloc_jemalloc := core libc native:jemalloc
@@ -77,12 +78,14 @@ DEPS_panic_abort := libc alloc
7778
DEPS_panic_unwind := libc alloc unwind
7879
DEPS_unwind := libc
7980

81+
RUSTFLAGS_compiler_builtins := -lstatic=compiler-rt
82+
8083
# FIXME(stage0): change this to just `RUSTFLAGS_panic_abort := ...`
8184
RUSTFLAGS1_panic_abort := -C panic=abort
8285
RUSTFLAGS2_panic_abort := -C panic=abort
8386
RUSTFLAGS3_panic_abort := -C panic=abort
8487

85-
DEPS_std := core libc rand alloc collections rustc_unicode \
88+
DEPS_std := core libc rand alloc collections compiler_builtins rustc_unicode \
8689
native:backtrace \
8790
alloc_system panic_abort panic_unwind unwind
8891
DEPS_arena := std
@@ -153,6 +156,7 @@ TOOL_SOURCE_rustc := $(S)src/driver/driver.rs
153156
TOOL_SOURCE_rustbook := $(S)src/tools/rustbook/main.rs
154157
TOOL_SOURCE_error_index_generator := $(S)src/tools/error_index_generator/main.rs
155158

159+
ONLY_RLIB_compiler_builtins := 1
156160
ONLY_RLIB_core := 1
157161
ONLY_RLIB_libc := 1
158162
ONLY_RLIB_alloc := 1

‎mk/main.mk

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -455,7 +455,10 @@ endif
455455
TSREQ$(1)_T_$(2)_H_$(3) = \
456456
$$(HSREQ$(1)_H_$(3)) \
457457
$$(foreach obj,$$(REQUIRED_OBJECTS_$(2)),\
458-
$$(TLIB$(1)_T_$(2)_H_$(3))/$$(obj))
458+
$$(TLIB$(1)_T_$(2)_H_$(3))/$$(obj)) \
459+
$$(TLIB0_T_$(2)_H_$(3))/$$(call CFG_STATIC_LIB_NAME_$(2),compiler-rt)
460+
# ^ This copies `libcompiler-rt.a` to the stage0 sysroot
461+
# ^ TODO(stage0) update this to not copy `libcompiler-rt.a` to stage0
459462

460463
# Prerequisites for a working stageN compiler and libraries, for a specific
461464
# target

‎mk/platform.mk

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -102,8 +102,6 @@ include $(wildcard $(CFG_SRC_DIR)mk/cfg/*.mk)
102102
define ADD_INSTALLED_OBJECTS
103103
INSTALLED_OBJECTS_$(1) += $$(CFG_INSTALLED_OBJECTS_$(1))
104104
REQUIRED_OBJECTS_$(1) += $$(CFG_THIRD_PARTY_OBJECTS_$(1))
105-
INSTALLED_OBJECTS_$(1) += $$(call CFG_STATIC_LIB_NAME_$(1),compiler-rt)
106-
REQUIRED_OBJECTS_$(1) += $$(call CFG_STATIC_LIB_NAME_$(1),compiler-rt)
107105
endef
108106

109107
$(foreach target,$(CFG_TARGET), \

‎mk/rt.mk

Lines changed: 177 additions & 161 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,16 @@
3737
################################################################################
3838
NATIVE_LIBS := hoedown miniz rust_test_helpers
3939

40+
# A macro to add a generic implementation of intrinsics iff a arch optimized implementation is not
41+
# already in the list.
42+
# $(1) is the target
43+
# $(2) is the intrinsic
44+
define ADD_INTRINSIC
45+
ifeq ($$(findstring X,$$(foreach intrinsic,$$(COMPRT_OBJS_$(1)),$$(if $$(findstring $(2),$$(intrinsic)),X,))),)
46+
COMPRT_OBJS_$(1) += $(2)
47+
endif
48+
endef
49+
4050
# $(1) is the target triple
4151
define NATIVE_LIBRARIES
4252

@@ -230,167 +240,15 @@ COMPRT_NAME_$(1) := $$(call CFG_STATIC_LIB_NAME_$(1),compiler-rt)
230240
COMPRT_LIB_$(1) := $$(RT_OUTPUT_DIR_$(1))/$$(COMPRT_NAME_$(1))
231241
COMPRT_BUILD_DIR_$(1) := $$(RT_OUTPUT_DIR_$(1))/compiler-rt
232242

233-
# GENERIC_SOURCES in CMakeLists.txt
234-
COMPRT_OBJS_$(1) := \
235-
absvdi2.o \
236-
absvsi2.o \
237-
adddf3.o \
238-
addsf3.o \
239-
addvdi3.o \
240-
addvsi3.o \
241-
apple_versioning.o \
242-
ashldi3.o \
243-
ashrdi3.o \
244-
clear_cache.o \
245-
clzdi2.o \
246-
clzsi2.o \
247-
cmpdi2.o \
248-
comparedf2.o \
249-
comparesf2.o \
250-
ctzdi2.o \
251-
ctzsi2.o \
252-
divdc3.o \
253-
divdf3.o \
254-
divdi3.o \
255-
divmoddi4.o \
256-
divmodsi4.o \
257-
divsc3.o \
258-
divsf3.o \
259-
divsi3.o \
260-
divxc3.o \
261-
extendsfdf2.o \
262-
extendhfsf2.o \
263-
ffsdi2.o \
264-
fixdfdi.o \
265-
fixdfsi.o \
266-
fixsfdi.o \
267-
fixsfsi.o \
268-
fixunsdfdi.o \
269-
fixunsdfsi.o \
270-
fixunssfdi.o \
271-
fixunssfsi.o \
272-
fixunsxfdi.o \
273-
fixunsxfsi.o \
274-
fixxfdi.o \
275-
floatdidf.o \
276-
floatdisf.o \
277-
floatdixf.o \
278-
floatsidf.o \
279-
floatsisf.o \
280-
floatundidf.o \
281-
floatundisf.o \
282-
floatundixf.o \
283-
floatunsidf.o \
284-
floatunsisf.o \
285-
int_util.o \
286-
lshrdi3.o \
287-
moddi3.o \
288-
modsi3.o \
289-
muldc3.o \
290-
muldf3.o \
291-
muldi3.o \
292-
mulodi4.o \
293-
mulosi4.o \
294-
muloti4.o \
295-
mulsc3.o \
296-
mulsf3.o \
297-
mulvdi3.o \
298-
mulvsi3.o \
299-
mulxc3.o \
300-
negdf2.o \
301-
negdi2.o \
302-
negsf2.o \
303-
negvdi2.o \
304-
negvsi2.o \
305-
paritydi2.o \
306-
paritysi2.o \
307-
popcountdi2.o \
308-
popcountsi2.o \
309-
powidf2.o \
310-
powisf2.o \
311-
powixf2.o \
312-
subdf3.o \
313-
subsf3.o \
314-
subvdi3.o \
315-
subvsi3.o \
316-
truncdfhf2.o \
317-
truncdfsf2.o \
318-
truncsfhf2.o \
319-
ucmpdi2.o \
320-
udivdi3.o \
321-
udivmoddi4.o \
322-
udivmodsi4.o \
323-
udivsi3.o \
324-
umoddi3.o \
325-
umodsi3.o
326-
327-
ifeq ($$(findstring ios,$(1)),)
328-
COMPRT_OBJS_$(1) += \
329-
absvti2.o \
330-
addtf3.o \
331-
addvti3.o \
332-
ashlti3.o \
333-
ashrti3.o \
334-
clzti2.o \
335-
cmpti2.o \
336-
ctzti2.o \
337-
divtf3.o \
338-
divti3.o \
339-
ffsti2.o \
340-
fixdfti.o \
341-
fixsfti.o \
342-
fixunsdfti.o \
343-
fixunssfti.o \
344-
fixunsxfti.o \
345-
fixxfti.o \
346-
floattidf.o \
347-
floattisf.o \
348-
floattixf.o \
349-
floatuntidf.o \
350-
floatuntisf.o \
351-
floatuntixf.o \
352-
lshrti3.o \
353-
modti3.o \
354-
multf3.o \
355-
multi3.o \
356-
mulvti3.o \
357-
negti2.o \
358-
negvti2.o \
359-
parityti2.o \
360-
popcountti2.o \
361-
powitf2.o \
362-
subtf3.o \
363-
subvti3.o \
364-
trampoline_setup.o \
365-
ucmpti2.o \
366-
udivmodti4.o \
367-
udivti3.o \
368-
umodti3.o
369-
endif
370-
371-
ifeq ($$(findstring apple,$(1)),apple)
372-
COMPRT_OBJS_$(1) += \
373-
atomic_flag_clear.o \
374-
atomic_flag_clear_explicit.o \
375-
atomic_flag_test_and_set.o \
376-
atomic_flag_test_and_set_explicit.o \
377-
atomic_signal_fence.o \
378-
atomic_thread_fence.o
379-
endif
380-
243+
# We must avoid compiling both a generic implementation (e.g. `floatdidf.c) and an arch optimized
244+
# implementation (e.g. `x86_64/floatdidf.S) of the same symbol (e.g. `floatdidf) because that causes
245+
# linker errors. To avoid that, we first add all the arch optimized implementations and then add the
246+
# generic implementations if and only if its arch optimized version is not already in the list. This
247+
# last part is handled by the ADD_INTRINSIC macro.
381248

382-
ifeq ($$(findstring windows,$(1)),)
383-
COMPRT_OBJS_$(1) += emutls.o
384-
endif
249+
COMPRT_OBJS_$(1) :=
385250

386251
ifeq ($$(findstring msvc,$(1)),)
387-
388-
ifeq ($$(findstring freebsd,$(1)),)
389-
COMPRT_OBJS_$(1) += gcc_personality_v0.o
390-
endif
391-
392-
COMPRT_OBJS_$(1) += emutls.o
393-
394252
ifeq ($$(findstring x86_64,$(1)),x86_64)
395253
COMPRT_OBJS_$(1) += \
396254
x86_64/chkstk.o \
@@ -540,9 +398,166 @@ COMPRT_OBJS_$(1) += \
540398
arm/unordsf2vfp.o
541399
endif
542400

401+
$(foreach intrinsic,absvdi2.o \
402+
absvsi2.o \
403+
adddf3.o \
404+
addsf3.o \
405+
addvdi3.o \
406+
addvsi3.o \
407+
apple_versioning.o \
408+
ashldi3.o \
409+
ashrdi3.o \
410+
clear_cache.o \
411+
clzdi2.o \
412+
clzsi2.o \
413+
cmpdi2.o \
414+
comparedf2.o \
415+
comparesf2.o \
416+
ctzdi2.o \
417+
ctzsi2.o \
418+
divdc3.o \
419+
divdf3.o \
420+
divdi3.o \
421+
divmoddi4.o \
422+
divmodsi4.o \
423+
divsc3.o \
424+
divsf3.o \
425+
divsi3.o \
426+
divxc3.o \
427+
extendsfdf2.o \
428+
extendhfsf2.o \
429+
ffsdi2.o \
430+
fixdfdi.o \
431+
fixdfsi.o \
432+
fixsfdi.o \
433+
fixsfsi.o \
434+
fixunsdfdi.o \
435+
fixunsdfsi.o \
436+
fixunssfdi.o \
437+
fixunssfsi.o \
438+
fixunsxfdi.o \
439+
fixunsxfsi.o \
440+
fixxfdi.o \
441+
floatdidf.o \
442+
floatdisf.o \
443+
floatdixf.o \
444+
floatsidf.o \
445+
floatsisf.o \
446+
floatundidf.o \
447+
floatundisf.o \
448+
floatundixf.o \
449+
floatunsidf.o \
450+
floatunsisf.o \
451+
int_util.o \
452+
lshrdi3.o \
453+
moddi3.o \
454+
modsi3.o \
455+
muldc3.o \
456+
muldf3.o \
457+
muldi3.o \
458+
mulodi4.o \
459+
mulosi4.o \
460+
muloti4.o \
461+
mulsc3.o \
462+
mulsf3.o \
463+
mulvdi3.o \
464+
mulvsi3.o \
465+
mulxc3.o \
466+
negdf2.o \
467+
negdi2.o \
468+
negsf2.o \
469+
negvdi2.o \
470+
negvsi2.o \
471+
paritydi2.o \
472+
paritysi2.o \
473+
popcountdi2.o \
474+
popcountsi2.o \
475+
powidf2.o \
476+
powisf2.o \
477+
powixf2.o \
478+
subdf3.o \
479+
subsf3.o \
480+
subvdi3.o \
481+
subvsi3.o \
482+
truncdfhf2.o \
483+
truncdfsf2.o \
484+
truncsfhf2.o \
485+
ucmpdi2.o \
486+
udivdi3.o \
487+
udivmoddi4.o \
488+
udivmodsi4.o \
489+
udivsi3.o \
490+
umoddi3.o \
491+
umodsi3.o,
492+
$(call ADD_INTRINSIC,$(1),$(intrinsic)))
493+
494+
ifeq ($$(findstring ios,$(1)),)
495+
$(foreach intrinsic,absvti2.o \
496+
addtf3.o \
497+
addvti3.o \
498+
ashlti3.o \
499+
ashrti3.o \
500+
clzti2.o \
501+
cmpti2.o \
502+
ctzti2.o \
503+
divtf3.o \
504+
divti3.o \
505+
ffsti2.o \
506+
fixdfti.o \
507+
fixsfti.o \
508+
fixunsdfti.o \
509+
fixunssfti.o \
510+
fixunsxfti.o \
511+
fixxfti.o \
512+
floattidf.o \
513+
floattisf.o \
514+
floattixf.o \
515+
floatuntidf.o \
516+
floatuntisf.o \
517+
floatuntixf.o \
518+
lshrti3.o \
519+
modti3.o \
520+
multf3.o \
521+
multi3.o \
522+
mulvti3.o \
523+
negti2.o \
524+
negvti2.o \
525+
parityti2.o \
526+
popcountti2.o \
527+
powitf2.o \
528+
subtf3.o \
529+
subvti3.o \
530+
trampoline_setup.o \
531+
ucmpti2.o \
532+
udivmodti4.o \
533+
udivti3.o \
534+
umodti3.o,
535+
$(call ADD_INTRINSIC,$(1),$(intrinsic)))
536+
endif
537+
538+
ifeq ($$(findstring apple,$(1)),apple)
539+
$(foreach intrinsic,atomic_flag_clear.o \
540+
atomic_flag_clear_explicit.o \
541+
atomic_flag_test_and_set.o \
542+
atomic_flag_test_and_set_explicit.o \
543+
atomic_signal_fence.o \
544+
atomic_thread_fence.o,
545+
$(call ADD_INTRINSIC,$(1),$(intrinsic)))
546+
endif
547+
548+
ifeq ($$(findstring windows,$(1)),)
549+
$(call ADD_INTRINSIC,$(1),emutls.o)
550+
endif
551+
552+
ifeq ($$(findstring msvc,$(1)),)
553+
554+
ifeq ($$(findstring freebsd,$(1)),)
555+
$(call ADD_INTRINSIC,$(1),gcc_personality_v0.o)
556+
endif
557+
endif
558+
543559
ifeq ($$(findstring aarch64,$(1)),aarch64)
544-
COMPRT_OBJS_$(1) += \
545-
comparetf2.o \
560+
$(foreach intrinsic,comparetf2.o \
546561
extenddftf2.o \
547562
extendsftf2.o \
548563
fixtfdi.o \
@@ -557,7 +572,8 @@ COMPRT_OBJS_$(1) += \
557572
floatunsitf.o \
558573
multc3.o \
559574
trunctfdf2.o \
560-
trunctfsf2.o
575+
trunctfsf2.o,
576+
$(call ADD_INTRINSIC,$(1),$(intrinsic)))
561577
endif
562578

563579
ifeq ($$(findstring msvc,$(1)),msvc)

‎src/bootstrap/clean.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@ pub fn clean(build: &Build) {
2828

2929
let out = build.out.join(host);
3030

31-
rm_rf(build, &out.join("compiler-rt"));
3231
rm_rf(build, &out.join("doc"));
3332

3433
for stage in 0..4 {

‎src/bootstrap/compile.rs

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -35,13 +35,23 @@ pub fn std<'a>(build: &'a Build, target: &str, compiler: &Compiler<'a>) {
3535
println!("Building stage{} std artifacts ({} -> {})", compiler.stage,
3636
compiler.host, target);
3737

38-
// Move compiler-rt into place as it'll be required by the compiler when
39-
// building the standard library to link the dylib of libstd
4038
let libdir = build.sysroot_libdir(compiler, target);
4139
let _ = fs::remove_dir_all(&libdir);
4240
t!(fs::create_dir_all(&libdir));
43-
copy(&build.compiler_rt_built.borrow()[target],
44-
&libdir.join(staticlib("compiler-rt", target)));
41+
// FIXME(stage0) remove this `if` after the next snapshot
42+
// The stage0 compiler still passes the `-lcompiler-rt` flag to the linker but now `bootstrap`
43+
// never builds a `libcopmiler-rt.a`! We'll fill the hole by simply copying stage0's
44+
// `libcompiler-rt.a` to where the stage1's one is expected (though we could as well just use
45+
// an empty `.a` archive). Note that the symbols of that stage0 `libcompiler-rt.a` won't make
46+
// it to the final binary because now `libcore.rlib` also contains the symbols that
47+
// `libcompiler-rt.a` provides. Since that rlib appears first in the linker arguments, its
48+
// symbols are used instead of `libcompiler-rt.a`'s.
49+
if compiler.stage == 0 {
50+
let rtlib = &staticlib("compiler-rt", target);
51+
let src = build.rustc.parent().unwrap().parent().unwrap().join("lib").join("rustlib")
52+
.join(target).join("lib").join(rtlib);
53+
copy(&src, &libdir.join(rtlib));
54+
}
4555

4656
// Some platforms have startup objects that may be required to produce the
4757
// libstd dynamic library, for example.
@@ -83,12 +93,10 @@ pub fn std_link(build: &Build,
8393

8494
// If we're linking one compiler host's output into another, then we weren't
8595
// called from the `std` method above. In that case we clean out what's
86-
// already there and then also link compiler-rt into place.
96+
// already there.
8797
if host != compiler.host {
8898
let _ = fs::remove_dir_all(&libdir);
8999
t!(fs::create_dir_all(&libdir));
90-
copy(&build.compiler_rt_built.borrow()[target],
91-
&libdir.join(staticlib("compiler-rt", target)));
92100
}
93101
add_to_sysroot(&out_dir, &libdir);
94102

‎src/bootstrap/lib.rs

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@ extern crate rustc_serialize;
2828
extern crate toml;
2929
extern crate regex;
3030

31-
use std::cell::RefCell;
3231
use std::collections::HashMap;
3332
use std::env;
3433
use std::fs::{self, File};
@@ -131,7 +130,6 @@ pub struct Build {
131130
// Runtime state filled in later on
132131
cc: HashMap<String, (gcc::Tool, Option<PathBuf>)>,
133132
cxx: HashMap<String, gcc::Tool>,
134-
compiler_rt_built: RefCell<HashMap<String, PathBuf>>,
135133
}
136134

137135
/// The various "modes" of invoking Cargo.
@@ -198,7 +196,6 @@ impl Build {
198196
package_vers: String::new(),
199197
cc: HashMap::new(),
200198
cxx: HashMap::new(),
201-
compiler_rt_built: RefCell::new(HashMap::new()),
202199
gdb_version: None,
203200
lldb_version: None,
204201
lldb_python_dir: None,
@@ -252,9 +249,6 @@ impl Build {
252249
Llvm { _dummy } => {
253250
native::llvm(self, target.target);
254251
}
255-
CompilerRt { _dummy } => {
256-
native::compiler_rt(self, target.target);
257-
}
258252
TestHelpers { _dummy } => {
259253
native::test_helpers(self, target.target);
260254
}
@@ -839,11 +833,6 @@ impl Build {
839833
}
840834
}
841835

842-
/// Root output directory for compiler-rt compiled for `target`
843-
fn compiler_rt_out(&self, target: &str) -> PathBuf {
844-
self.out.join(target).join("compiler-rt")
845-
}
846-
847836
/// Root output directory for rust_test_helpers library compiled for
848837
/// `target`
849838
fn test_helpers_out(&self, target: &str) -> PathBuf {

‎src/bootstrap/native.rs

Lines changed: 1 addition & 396 deletions
Large diffs are not rendered by default.

‎src/bootstrap/step.rs

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,6 @@ macro_rules! targets {
8282
// There aren't really any parameters to this, but empty structs
8383
// with braces are unstable so we just pick something that works.
8484
(llvm, Llvm { _dummy: () }),
85-
(compiler_rt, CompilerRt { _dummy: () }),
8685
(test_helpers, TestHelpers { _dummy: () }),
8786
(debugger_scripts, DebuggerScripts { stage: u32 }),
8887

@@ -334,8 +333,7 @@ impl<'a> Step<'a> {
334333
vec![self.libstd(compiler)]
335334
}
336335
Source::Libstd { compiler } => {
337-
vec![self.compiler_rt(()),
338-
self.rustc(compiler.stage).target(compiler.host)]
336+
vec![self.rustc(compiler.stage).target(compiler.host)]
339337
}
340338
Source::LibrustcLink { compiler, host } => {
341339
vec![self.librustc(compiler),
@@ -348,7 +346,6 @@ impl<'a> Step<'a> {
348346
vec![self.libstd(compiler),
349347
self.target(host).rustc(compiler.stage)]
350348
}
351-
Source::CompilerRt { _dummy } => Vec::new(),
352349
Source::Llvm { _dummy } => Vec::new(),
353350
Source::TestHelpers { _dummy } => Vec::new(),
354351
Source::DebuggerScripts { stage: _ } => Vec::new(),

‎src/bootstrap/util.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ use filetime::FileTime;
2323

2424
/// Returns the `name` as the filename of a static library for `target`.
2525
pub fn staticlib(name: &str, target: &str) -> String {
26-
if target.contains("windows-msvc") {
26+
if target.contains("windows") {
2727
format!("{}.lib", name)
2828
} else {
2929
format!("lib{}.a", name)

‎src/libcompiler_builtins/Cargo.toml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
[package]
2+
authors = ["The Rust Project Developers"]
3+
build = "build.rs"
4+
name = "compiler_builtins"
5+
version = "0.0.0"
6+
7+
[lib]
8+
name = "compiler_builtins"
9+
path = "lib.rs"
10+
11+
[dependencies]
12+
core = { path = "../libcore" }
13+
14+
[build-dependencies]
15+
gcc = "0.3.27"

‎src/libcompiler_builtins/build.rs

Lines changed: 404 additions & 0 deletions
Large diffs are not rendered by default.

‎src/libcompiler_builtins/lib.rs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
2+
// file at the top-level directory of this distribution and at
3+
// http://rust-lang.org/COPYRIGHT.
4+
//
5+
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6+
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7+
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8+
// option. This file may not be copied, modified, or distributed
9+
// except according to those terms.
10+
11+
#![cfg_attr(not(stage0), feature(compiler_builtins))]
12+
#![no_std]
13+
#![cfg_attr(not(stage0), compiler_builtins)]
14+
#![unstable(feature = "compiler_builtins_lib",
15+
reason = "internal implementation detail of rustc right now",
16+
issue = "0")]
17+
#![crate_name = "compiler_builtins"]
18+
#![crate_type = "rlib"]
19+
#![feature(staged_api)]

‎src/librustc/middle/cstore.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,7 @@ pub trait CrateStore<'tcx> {
210210
fn is_explicitly_linked(&self, cnum: ast::CrateNum) -> bool;
211211
fn is_allocator(&self, cnum: ast::CrateNum) -> bool;
212212
fn is_panic_runtime(&self, cnum: ast::CrateNum) -> bool;
213+
fn is_compiler_builtins(&self, cnum: ast::CrateNum) -> bool;
213214
fn panic_strategy(&self, cnum: ast::CrateNum) -> PanicStrategy;
214215
fn extern_crate(&self, cnum: ast::CrateNum) -> Option<ExternCrate>;
215216
fn crate_attrs(&self, cnum: ast::CrateNum) -> Vec<ast::Attribute>;
@@ -405,6 +406,7 @@ impl<'tcx> CrateStore<'tcx> for DummyCrateStore {
405406
fn is_explicitly_linked(&self, cnum: ast::CrateNum) -> bool { bug!("is_explicitly_linked") }
406407
fn is_allocator(&self, cnum: ast::CrateNum) -> bool { bug!("is_allocator") }
407408
fn is_panic_runtime(&self, cnum: ast::CrateNum) -> bool { bug!("is_panic_runtime") }
409+
fn is_compiler_builtins(&self, cnum: ast::CrateNum) -> bool { bug!("is_compiler_builtins") }
408410
fn panic_strategy(&self, cnum: ast::CrateNum) -> PanicStrategy {
409411
bug!("panic_strategy")
410412
}

‎src/librustc_back/target/asmjs_unknown_emscripten.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@ pub fn target() -> Result<Target, String> {
1818
dynamic_linking: false,
1919
executables: true,
2020
exe_suffix: ".js".to_string(),
21-
no_compiler_rt: true,
2221
linker_is_gnu: true,
2322
allow_asm: false,
2423
obj_is_bitcode: true,

‎src/librustc_back/target/le32_unknown_nacl.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ pub fn target() -> TargetResult {
2222
dynamic_linking: false,
2323
executables: true,
2424
exe_suffix: ".pexe".to_string(),
25-
no_compiler_rt: false,
2625
linker_is_gnu: true,
2726
allow_asm: false,
2827
max_atomic_width: 32,

‎src/librustc_back/target/mod.rs

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -306,9 +306,6 @@ pub struct TargetOptions {
306306
pub allows_weak_linkage: bool,
307307
/// Whether the linker support rpaths or not. Defaults to false.
308308
pub has_rpath: bool,
309-
/// Whether to disable linking to compiler-rt. Defaults to false, as LLVM
310-
/// will emit references to the functions that compiler-rt provides.
311-
pub no_compiler_rt: bool,
312309
/// Whether to disable linking to the default libraries, typically corresponds
313310
/// to `-nodefaultlibs`. Defaults to true.
314311
pub no_default_libraries: bool,
@@ -381,7 +378,6 @@ impl Default for TargetOptions {
381378
linker_is_gnu: false,
382379
allows_weak_linkage: true,
383380
has_rpath: false,
384-
no_compiler_rt: false,
385381
no_default_libraries: true,
386382
position_independent_executables: false,
387383
pre_link_objects_exe: Vec::new(),
@@ -524,7 +520,6 @@ impl Target {
524520
key!(linker_is_gnu, bool);
525521
key!(allows_weak_linkage, bool);
526522
key!(has_rpath, bool);
527-
key!(no_compiler_rt, bool);
528523
key!(no_default_libraries, bool);
529524
key!(position_independent_executables, bool);
530525
key!(archive_format);
@@ -667,7 +662,6 @@ impl ToJson for Target {
667662
target_option_val!(linker_is_gnu);
668663
target_option_val!(allows_weak_linkage);
669664
target_option_val!(has_rpath);
670-
target_option_val!(no_compiler_rt);
671665
target_option_val!(no_default_libraries);
672666
target_option_val!(position_independent_executables);
673667
target_option_val!(archive_format);

‎src/librustc_metadata/csearch.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -346,6 +346,10 @@ impl<'tcx> CrateStore<'tcx> for cstore::CStore {
346346
self.get_crate_data(cnum).is_panic_runtime()
347347
}
348348

349+
fn is_compiler_builtins(&self, cnum: ast::CrateNum) -> bool {
350+
self.get_crate_data(cnum).is_compiler_builtins()
351+
}
352+
349353
fn panic_strategy(&self, cnum: ast::CrateNum) -> PanicStrategy {
350354
self.get_crate_data(cnum).panic_strategy()
351355
}

‎src/librustc_metadata/cstore.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,11 @@ impl CrateMetadata {
340340
attr::contains_name(&attrs, "needs_panic_runtime")
341341
}
342342

343+
pub fn is_compiler_builtins(&self) -> bool {
344+
let attrs = decoder::get_crate_attributes(self.data());
345+
attr::contains_name(&attrs, "compiler_builtins")
346+
}
347+
343348
pub fn panic_strategy(&self) -> PanicStrategy {
344349
decoder::get_panic_strategy(self.data())
345350
}

‎src/librustc_trans/back/link.rs

Lines changed: 43 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -573,10 +573,6 @@ fn write_rlib_bytecode_object_v1(writer: &mut Write,
573573
fn link_staticlib(sess: &Session, objects: &[PathBuf], out_filename: &Path,
574574
tempdir: &Path) {
575575
let mut ab = link_rlib(sess, None, objects, out_filename, tempdir);
576-
if !sess.target.target.options.no_compiler_rt {
577-
ab.add_native_library("compiler-rt");
578-
}
579-
580576
let mut all_native_libs = vec![];
581577

582578
each_linked_rlib(sess, &mut |cnum, path| {
@@ -640,9 +636,6 @@ fn link_natively(sess: &Session,
640636
let mut linker = trans.linker_info.to_linker(&mut cmd, &sess);
641637
link_args(&mut *linker, sess, crate_type, tmpdir,
642638
objects, out_filename, outputs);
643-
if !sess.target.target.options.no_compiler_rt {
644-
linker.link_staticlib("compiler-rt");
645-
}
646639
}
647640
cmd.args(&sess.target.target.options.late_link_args);
648641
for obj in &sess.target.target.options.post_link_objects {
@@ -933,24 +926,38 @@ fn add_upstream_rust_crates(cmd: &mut Linker,
933926
// crates.
934927
let deps = sess.cstore.used_crates(LinkagePreference::RequireDynamic);
935928

929+
let mut compiler_builtins = None;
930+
936931
for &(cnum, _) in &deps {
937932
// We may not pass all crates through to the linker. Some crates may
938933
// appear statically in an existing dylib, meaning we'll pick up all the
939934
// symbols from the dylib.
940935
let src = sess.cstore.used_crate_source(cnum);
941936
match data[cnum as usize - 1] {
937+
// compiler-builtins are always placed last to ensure that they're
938+
// linked correctly.
939+
_ if sess.cstore.is_compiler_builtins(cnum) => {
940+
assert!(compiler_builtins.is_none());
941+
compiler_builtins = Some(cnum);
942+
}
942943
Linkage::NotLinked |
943944
Linkage::IncludedFromDylib => {}
944945
Linkage::Static => {
945-
add_static_crate(cmd, sess, tmpdir, crate_type,
946-
&src.rlib.unwrap().0, sess.cstore.is_no_builtins(cnum))
946+
add_static_crate(cmd, sess, tmpdir, crate_type, cnum);
947947
}
948948
Linkage::Dynamic => {
949949
add_dynamic_crate(cmd, sess, &src.dylib.unwrap().0)
950950
}
951951
}
952952
}
953953

954+
// We must always link the `compiler_builtins` crate statically. Even if it
955+
// was already "included" in a dylib (e.g. `libstd` when `-C prefer-dynamic`
956+
// is used)
957+
if let Some(cnum) = compiler_builtins {
958+
add_static_crate(cmd, sess, tmpdir, crate_type, cnum);
959+
}
960+
954961
// Converts a library file-stem into a cc -l argument
955962
fn unlib<'a>(config: &config::Config, stem: &'a str) -> &'a str {
956963
if stem.starts_with("lib") && !config.target.options.is_like_windows {
@@ -996,8 +1003,9 @@ fn add_upstream_rust_crates(cmd: &mut Linker,
9961003
sess: &Session,
9971004
tmpdir: &Path,
9981005
crate_type: config::CrateType,
999-
cratepath: &Path,
1000-
is_a_no_builtins_crate: bool) {
1006+
cnum: ast::CrateNum) {
1007+
let src = sess.cstore.used_crate_source(cnum);
1008+
let cratepath = &src.rlib.unwrap().0;
10011009
if !sess.lto() && crate_type != config::CrateTypeDylib {
10021010
cmd.link_rlib(&fix_windows_verbatim_for_gcc(cratepath));
10031011
return
@@ -1021,7 +1029,13 @@ fn add_upstream_rust_crates(cmd: &mut Linker,
10211029
}
10221030
let canonical = f.replace("-", "_");
10231031
let canonical_name = name.replace("-", "_");
1024-
if sess.lto() && !is_a_no_builtins_crate &&
1032+
1033+
// If we're performing LTO and this is a rust-generated object
1034+
// file, then we don't need the object file as it's part of the
1035+
// LTO module. Note that `#![no_builtins]` is excluded from LTO,
1036+
// though, so we let that object file slide.
1037+
if sess.lto() &&
1038+
!sess.cstore.is_no_builtins(cnum) &&
10251039
canonical.starts_with(&canonical_name) &&
10261040
canonical.ends_with(".o") {
10271041
let num = &f[name.len()..f.len() - 2];
@@ -1033,13 +1047,23 @@ fn add_upstream_rust_crates(cmd: &mut Linker,
10331047
any_objects = true;
10341048
}
10351049

1036-
if any_objects {
1037-
archive.build();
1038-
if crate_type == config::CrateTypeDylib {
1039-
cmd.link_whole_rlib(&fix_windows_verbatim_for_gcc(&dst));
1040-
} else {
1041-
cmd.link_rlib(&fix_windows_verbatim_for_gcc(&dst));
1042-
}
1050+
if !any_objects {
1051+
return
1052+
}
1053+
archive.build();
1054+
1055+
// If we're creating a dylib, then we need to include the
1056+
// whole of each object in our archive into that artifact. This is
1057+
// because a `dylib` can be reused as an intermediate artifact.
1058+
//
1059+
// Note, though, that we don't want to include the whole of a
1060+
// compiler-builtins crate (e.g. compiler-rt) because it'll get
1061+
// repeatedly linked anyway.
1062+
if crate_type == config::CrateTypeDylib &&
1063+
!sess.cstore.is_compiler_builtins(cnum) {
1064+
cmd.link_whole_rlib(&fix_windows_verbatim_for_gcc(&dst));
1065+
} else {
1066+
cmd.link_rlib(&fix_windows_verbatim_for_gcc(&dst));
10431067
}
10441068
});
10451069
}

‎src/libstd/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ collections = { path = "../libcollections" }
1919
core = { path = "../libcore" }
2020
libc = { path = "../rustc/libc_shim" }
2121
rand = { path = "../librand" }
22+
compiler_builtins = { path = "../libcompiler_builtins" }
2223
rustc_unicode = { path = "../librustc_unicode" }
2324
unwind = { path = "../libunwind" }
2425

‎src/libstd/lib.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -224,6 +224,7 @@
224224
#![feature(char_internals)]
225225
#![feature(collections)]
226226
#![feature(collections_bound)]
227+
#![feature(compiler_builtins_lib)]
227228
#![feature(const_fn)]
228229
#![feature(core_float)]
229230
#![feature(core_intrinsics)]
@@ -322,6 +323,9 @@ extern crate unwind;
322323
#[cfg(stage0)]
323324
extern crate alloc_system;
324325

326+
// compiler-rt intrinsics
327+
extern crate compiler_builtins;
328+
325329
// Make std testable by not duplicating lang items and other globals. See #2912
326330
#[cfg(test)] extern crate std as realstd;
327331

‎src/libsyntax/feature_gate.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -298,6 +298,10 @@ declare_features! (
298298

299299
// elide `'static` lifetimes in `static`s and `const`s
300300
(active, static_in_const, "1.13.0", Some(35897)),
301+
302+
// Used to identify the `compiler_builtins` crate
303+
// rustc internal
304+
(active, compiler_builtins, "1.13.0", None),
301305
);
302306

303307
declare_features! (
@@ -537,6 +541,12 @@ pub const KNOWN_ATTRIBUTES: &'static [(&'static str, AttributeType, AttributeGat
537541
libcore functions that are inlined \
538542
across crates and will never be stable",
539543
cfg_fn!(rustc_attrs))),
544+
("compiler_builtins", Whitelisted, Gated("compiler_builtins",
545+
"the `#[compiler_builtins]` attribute is used to \
546+
identify the `compiler_builtins` crate which \
547+
contains compiler-rt intrinsics and will never be \
548+
stable",
549+
cfg_fn!(compiler_builtins))),
540550

541551
("allow_internal_unstable", Normal, Gated("allow_internal_unstable",
542552
EXPLAIN_ALLOW_INTERNAL_UNSTABLE,

‎src/rustc/std_shim/Cargo.lock

Lines changed: 9 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
2+
// file at the top-level directory of this distribution and at
3+
// http://rust-lang.org/COPYRIGHT.
4+
//
5+
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6+
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7+
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8+
// option. This file may not be copied, modified, or distributed
9+
// except according to those terms.
10+
11+
#![compiler_builtins] //~ ERROR the `#[compiler_builtins]` attribute is
12+
13+
fn main() {}
14+

‎src/test/run-make/no-duplicate-libs/bar.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,12 @@
88
// option. This file may not be copied, modified, or distributed
99
// except according to those terms.
1010

11-
#![feature(lang_items, libc)]
11+
#![feature(lang_items, libc, compiler_builtins_lib)]
1212
#![crate_type = "dylib"]
1313
#![no_std]
1414

1515
extern crate libc;
16+
extern crate compiler_builtins;
1617

1718
#[no_mangle]
1819
pub extern fn bar() {}

‎src/test/run-make/no-duplicate-libs/foo.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,12 @@
88
// option. This file may not be copied, modified, or distributed
99
// except according to those terms.
1010

11-
#![feature(lang_items, libc)]
11+
#![feature(lang_items, libc, compiler_builtins_lib)]
1212
#![no_std]
1313
#![crate_type = "dylib"]
1414

1515
extern crate libc;
16+
extern crate compiler_builtins;
1617

1718
#[no_mangle]
1819
pub extern fn foo() {}

0 commit comments

Comments
 (0)
Please sign in to comment.