auto merge of #14000 : pnkfelix/rust/fsk-fix-issue13732, r=alexcrichton

Fix #13732.

This is a revised, much less hacky form of PR #13753

The changes here:

 * add instrumentation to aid debugging of linkage errors,
 * fine tune some things in the Makefile where we are telling binaries to use a host-oriented path for finding dynamic libraries, when it should be feeding the binaries a target-oriented path for dynamic libraries.
 * pass along the current stage number to run-make tests, and
 * skip certain tests when running atop stage1.

Fix #13746 as well.
This commit is contained in:
bors 2014-05-18 14:41:35 -07:00
commit e1403e1d83
30 changed files with 279 additions and 120 deletions

View File

@ -349,17 +349,44 @@ CFGFLAG$(1)_T_$(2)_H_$(3) = stage$(1)
endef
# Same macro/variables as above, but defined in a separate loop so it can use
# all the varibles above for all archs. The RPATH_VAR setup sometimes needs to
# all the variables above for all archs. The RPATH_VAR setup sometimes needs to
# reach across triples to get things in order.
#
# Defines (with the standard $(1)_T_$(2)_H_$(3) suffix):
# * `LD_LIBRARY_PATH_ENV_NAME`: the name for the key to use in the OS
# environment to access or extend the lookup path for dynamic
# libraries. Note on Windows, that key is `$PATH`, and thus not
# only conflates programs with dynamic libraries, but also often
# contains spaces which confuse make.
# * `LD_LIBRARY_PATH_ENV_HOSTDIR`: the entry to add to lookup path for the host
# * `LD_LIBRARY_PATH_ENV_TARGETDIR`: the entry to add to lookup path for target
#
# Below that, HOST_RPATH_VAR and TARGET_RPATH_VAR are defined in terms of the
# above settings.
#
define SREQ_CMDS
ifeq ($$(OSTYPE_$(3)),apple-darwin)
RPATH_VAR$(1)_T_$(2)_H_$(3) := \
DYLD_LIBRARY_PATH="$$$$DYLD_LIBRARY_PATH:$$(CURDIR)/$$(HLIB$(1)_H_$(3))"
LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3) := DYLD_LIBRARY_PATH
else
RPATH_VAR$(1)_T_$(2)_H_$(3) := \
LD_LIBRARY_PATH="$$$$LD_LIBRARY_PATH:$$(CURDIR)/$$(HLIB$(1)_H_$(3))"
ifeq ($$(CFG_WINDOWSY_$(2)),1)
LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3) := PATH
else
LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3) := LD_LIBRARY_PATH
endif
endif
LD_LIBRARY_PATH_ENV_HOSTDIR$(1)_T_$(2)_H_$(3) := \
$$(CURDIR)/$$(HLIB$(1)_H_$(3))
LD_LIBRARY_PATH_ENV_TARGETDIR$(1)_T_$(2)_H_$(3) := \
$$(CURDIR)/$$(TLIB1_T_$(2)_H_$(CFG_BUILD))
HOST_RPATH_VAR$(1)_T_$(2)_H_$(3) := \
$$(LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3))=$$$$$$(LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3)):$$(LD_LIBRARY_PATH_ENV_HOSTDIR$(1)_T_$(2)_H_$(3))
TARGET_RPATH_VAR$(1)_T_$(2)_H_$(3) := \
$$(LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3))=$$$$$$(LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3)):$$(LD_LIBRARY_PATH_ENV_TARGETDIR$(1)_T_$(2)_H_$(3))
RPATH_VAR$(1)_T_$(2)_H_$(3) := $$(HOST_RPATH_VAR$(1)_T_$(2)_H_$(3))
# Pass --cfg stage0 only for the build->host part of stage0;
# if you're building a cross config, the host->* parts are
@ -376,13 +403,7 @@ ifeq ($(1),0)
ifneq ($(strip $(CFG_BUILD)),$(strip $(3)))
CFGFLAG$(1)_T_$(2)_H_$(3) = stage1
ifeq ($$(OSTYPE_$(3)),apple-darwin)
RPATH_VAR$(1)_T_$(2)_H_$(3) := \
DYLD_LIBRARY_PATH="$$$$DYLD_LIBRARY_PATH:$$(CURDIR)/$$(TLIB1_T_$(2)_H_$(CFG_BUILD))"
else
RPATH_VAR$(1)_T_$(2)_H_$(3) := \
LD_LIBRARY_PATH="$$$$LD_LIBRARY_PATH:$$(CURDIR)/$$(TLIB1_T_$(2)_H_$(CFG_BUILD))"
endif
RPATH_VAR$(1)_T_$(2)_H_$(3) := $$(TARGET_RPATH_VAR$(1)_T_$(2)_H_$(3))
endif
endif

View File

@ -793,8 +793,27 @@ else
CRATEDOCTESTDEP_$(1)_$(2)_$(3)_$(4) = $$(RSINPUTS_$(4))
endif
# (Issues #13732, #13983, #14000) The doc for the regex crate includes
# uses of the `regex!` macro from the regex_macros crate. There is
# normally a dependence injected that makes the target's regex depend
# upon the host's regex_macros (see #13845), but that dependency
# injection is currently skipped for stage1 as a special case.
#
# Therefore, as a further special case, this conditional skips
# attempting to run the doc tests for the regex crate atop stage1,
# (since there is no regex_macros crate for the stage1 rustc to load).
#
# (Another approach for solving this would be to inject the desired
# dependence for stage1 as well, by setting things up to generate a
# regex_macros crate that was compatible with the stage1 rustc and
# thus re-enable our ability to run this test.)
ifeq (stage$(1)-crate-$(4),stage1-crate-regex)
check-stage$(1)-T-$(2)-H-$(3)-doc-crate-$(4)-exec:
@$$(call E, skipping doc-crate-$(4) as it uses macros and cannot run at stage$(1))
else
check-stage$(1)-T-$(2)-H-$(3)-doc-crate-$(4)-exec: \
$$(call TEST_OK_FILE,$(1),$(2),$(3),doc-crate-$(4))
endif
ifeq ($(2),$$(CFG_BUILD))
$$(call TEST_OK_FILE,$(1),$(2),$(3),doc-crate-$(4)): $$(CRATEDOCTESTDEP_$(1)_$(2)_$(3)_$(4))
@ -951,7 +970,10 @@ $(3)/test/run-make/%-$(1)-T-$(2)-H-$(3).ok: \
"$$(CC_$(3)) $$(CFG_GCCISH_CFLAGS_$(3))" \
$$(HBIN$(1)_H_$(3))/rustdoc$$(X_$(3)) \
"$$(TESTNAME)" \
"$$(RPATH_VAR$(1)_T_$(2)_H_$(3))"
$$(LD_LIBRARY_PATH_ENV_NAME$(1)_T_$(2)_H_$(3)) \
"$$(LD_LIBRARY_PATH_ENV_HOSTDIR$(1)_T_$(2)_H_$(3))" \
"$$(LD_LIBRARY_PATH_ENV_TARGETDIR$(1)_T_$(2)_H_$(3))" \
$(1)
@touch $$@
else
# FIXME #11094 - The above rule doesn't work right for multiple targets

View File

@ -11,54 +11,31 @@
use std::os;
use std::str;
use std::io::process::{ProcessExit, Command, Process, ProcessOutput};
use std::unstable::dynamic_lib::DynamicLibrary;
#[cfg(target_os = "win32")]
fn target_env(lib_path: &str, prog: &str) -> Vec<(StrBuf, StrBuf)> {
let env = os::env();
// Make sure we include the aux directory in the path
assert!(prog.ends_with(".exe"));
let aux_path = prog.slice(0u, prog.len() - 4u).to_owned() + ".libaux";
let mut new_env: Vec<_> = env.move_iter().map(|(k, v)| {
let new_v = if "PATH" == k {
format_strbuf!("{};{};{}", v, lib_path, aux_path)
} else {
v.to_strbuf()
};
(k.to_strbuf(), new_v)
}).collect();
if prog.ends_with("rustc.exe") {
new_env.push(("RUST_THREADS".to_strbuf(), "1".to_strbuf()));
}
return new_env;
}
#[cfg(target_os = "linux")]
#[cfg(target_os = "macos")]
#[cfg(target_os = "freebsd")]
fn target_env(lib_path: &str, prog: &str) -> Vec<(StrBuf,StrBuf)> {
// Make sure we include the aux directory in the path
let prog = if cfg!(windows) {prog.slice_to(prog.len() - 4)} else {prog};
let aux_path = prog + ".libaux";
// Need to be sure to put both the lib_path and the aux path in the dylib
// search path for the child.
let mut path = DynamicLibrary::search_path();
path.insert(0, Path::new(aux_path));
path.insert(0, Path::new(lib_path));
// Remove the previous dylib search path var
let var = DynamicLibrary::envvar();
let mut env: Vec<(StrBuf,StrBuf)> =
os::env().move_iter()
.map(|(ref k, ref v)| (k.to_strbuf(), v.to_strbuf()))
.collect();
let var = if cfg!(target_os = "macos") {
"DYLD_LIBRARY_PATH"
} else {
"LD_LIBRARY_PATH"
};
let prev = match env.iter().position(|&(ref k, _)| k.as_slice() == var) {
Some(i) => env.remove(i).unwrap().val1(),
None => "".to_strbuf(),
};
env.push((var.to_strbuf(), if prev.is_empty() {
format_strbuf!("{}:{}", lib_path, aux_path)
} else {
format_strbuf!("{}:{}:{}", lib_path, aux_path, prev)
}));
os::env().move_iter().map(|(a,b)|(a.to_strbuf(), b.to_strbuf())).collect();
match env.iter().position(|&(ref k, _)| k.as_slice() == var) {
Some(i) => { env.remove(i); }
None => {}
}
// Add the new dylib search path var
let newpath = DynamicLibrary::create_path(path.as_slice());
env.push((var.to_strbuf(),
str::from_utf8(newpath.as_slice()).unwrap().to_strbuf()));
return env;
}

View File

@ -30,6 +30,10 @@ def putenv(name, value):
value = normalize_path(value)
os.putenv(name, value)
def convert_path_spec(name, value):
if os.name == 'nt' and name != 'PATH':
value = ":".join(normalize_path(v) for v in value.split(";"))
return value
make = sys.argv[2]
putenv('RUSTC', os.path.abspath(sys.argv[3]))
@ -37,13 +41,10 @@ putenv('TMPDIR', os.path.abspath(sys.argv[4]))
putenv('CC', sys.argv[5])
putenv('RUSTDOC', os.path.abspath(sys.argv[6]))
filt = sys.argv[7]
ldpath = sys.argv[8]
if ldpath != '':
name = ldpath.split('=')[0]
value = ldpath.split('=')[1]
if os.name == 'nt' and name != 'PATH':
value = ":".join(normalize_path(v) for v in value.split(";"))
os.putenv(name, value)
putenv('LD_LIB_PATH_ENVVAR', sys.argv[8]);
putenv('HOST_RPATH_DIR', os.path.abspath(sys.argv[9]));
putenv('TARGET_RPATH_DIR', os.path.abspath(sys.argv[10]));
putenv('RUST_BUILD_STAGE', sys.argv[11])
if not filt in sys.argv[1]:
sys.exit(0)

View File

@ -17,7 +17,7 @@ use back::svh::Svh;
use driver::session::Session;
use driver::{driver, config};
use metadata::cstore;
use metadata::cstore::CStore;
use metadata::cstore::{CStore, CrateSource};
use metadata::decoder;
use metadata::loader;
use metadata::loader::CratePaths;
@ -68,10 +68,15 @@ impl<'a> visit::Visitor<()> for Env<'a> {
fn dump_crates(cstore: &CStore) {
debug!("resolved crates:");
cstore.iter_crate_data(|_, data| {
cstore.iter_crate_data_origins(|_, data, opt_source| {
debug!("crate_id: {}", data.crate_id());
debug!(" cnum: {}", data.cnum);
debug!(" hash: {}", data.hash());
opt_source.map(|cs| {
let CrateSource { dylib, rlib, cnum: _ } = cs;
dylib.map(|dl| debug!(" dylib: {}", dl.display()));
rlib.map(|rl| debug!(" rlib: {}", rl.display()));
});
})
}

View File

@ -114,6 +114,17 @@ impl CStore {
}
}
/// Like `iter_crate_data`, but passes source paths (if available) as well.
pub fn iter_crate_data_origins(&self, i: |ast::CrateNum,
&crate_metadata,
Option<CrateSource>|) {
for (&k, v) in self.metas.borrow().iter() {
let origin = self.get_used_crate_source(k);
origin.as_ref().map(|cs| { assert!(k == cs.cnum); });
i(k, &**v, origin);
}
}
pub fn add_used_crate_source(&self, src: CrateSource) {
let mut used_crate_sources = self.used_crate_sources.borrow_mut();
if !used_crate_sources.contains(&src) {

View File

@ -136,7 +136,7 @@ impl<'a> FileSearch<'a> {
pub fn add_dylib_search_paths(&self) {
self.for_each_lib_search_path(|lib_search_path| {
DynamicLibrary::add_search_path(lib_search_path);
DynamicLibrary::prepend_search_path(lib_search_path);
FileDoesntMatch
})
}

View File

@ -284,7 +284,7 @@ fn rust_input(cratefile: &str, matches: &getopts::Matches) -> Output {
core::run_core(libs.move_iter().map(|x| x.clone()).collect(),
cfgs.move_iter().map(|x| x.to_strbuf()).collect(),
&cr)
}).unwrap();
}).map_err(|boxed_any|format!("{:?}", boxed_any)).unwrap();
info!("finished with rustc");
analysiskey.replace(Some(analysis));

View File

@ -15,6 +15,7 @@ use std::io::{Command, TempDir};
use std::os;
use std::str;
use std::strbuf::StrBuf;
use std::unstable::dynamic_lib::DynamicLibrary;
use collections::{HashSet, HashMap};
use testing;
@ -150,12 +151,37 @@ fn runtest(test: &str, cratename: &str, libs: HashSet<Path>, should_fail: bool,
let outdir = TempDir::new("rustdoctest").expect("rustdoc needs a tempdir");
let out = Some(outdir.path().clone());
let cfg = config::build_configuration(&sess);
let libdir = sess.target_filesearch().get_lib_path();
driver::compile_input(sess, cfg, &input, &out, &None);
if no_run { return }
// Run the code!
match Command::new(outdir.path().join("rust_out")).output() {
//
// We're careful to prepend the *target* dylib search path to the child's
// environment to ensure that the target loads the right libraries at
// runtime. It would be a sad day if the *host* libraries were loaded as a
// mistake.
let exe = outdir.path().join("rust_out");
let env = {
let mut path = DynamicLibrary::search_path();
path.insert(0, libdir.clone());
// Remove the previous dylib search path var
let var = DynamicLibrary::envvar();
let mut env: Vec<(~str,~str)> = os::env().move_iter().collect();
match env.iter().position(|&(ref k, _)| k.as_slice() == var) {
Some(i) => { env.remove(i); }
None => {}
};
// Add the new dylib search path var
let newpath = DynamicLibrary::create_path(path.as_slice());
env.push((var.to_owned(),
str::from_utf8(newpath.as_slice()).unwrap().to_owned()));
env
};
match Command::new(exe).env(env.as_slice()).output() {
Err(e) => fail!("couldn't run the test: {}{}", e,
if e.kind == io::PermissionDenied {
" - maybe your tempdir is mounted with noexec?"

View File

@ -16,16 +16,16 @@ A simple wrapper over the platform's dynamic library facilities
*/
use clone::Clone;
use c_str::ToCStr;
use iter::Iterator;
use mem;
use ops::*;
use option::*;
use os;
use path::GenericPath;
use path;
use path::{Path,GenericPath};
use result::*;
use slice::Vector;
use slice::{Vector,ImmutableVector};
use str;
use vec::Vec;
@ -76,22 +76,55 @@ impl DynamicLibrary {
}
}
/// Appends a path to the system search path for dynamic libraries
pub fn add_search_path(path: &path::Path) {
let (envvar, sep) = if cfg!(windows) {
("PATH", ';' as u8)
/// Prepends a path to this process's search path for dynamic libraries
pub fn prepend_search_path(path: &Path) {
let mut search_path = DynamicLibrary::search_path();
search_path.insert(0, path.clone());
let newval = DynamicLibrary::create_path(search_path.as_slice());
os::setenv(DynamicLibrary::envvar(),
str::from_utf8(newval.as_slice()).unwrap());
}
/// From a slice of paths, create a new vector which is suitable to be an
/// environment variable for this platforms dylib search path.
pub fn create_path(path: &[Path]) -> Vec<u8> {
let mut newvar = Vec::new();
for (i, path) in path.iter().enumerate() {
if i > 0 { newvar.push(DynamicLibrary::separator()); }
newvar.push_all(path.as_vec());
}
return newvar;
}
/// Returns the environment variable for this process's dynamic library
/// search path
pub fn envvar() -> &'static str {
if cfg!(windows) {
"PATH"
} else if cfg!(target_os = "macos") {
("DYLD_LIBRARY_PATH", ':' as u8)
"DYLD_LIBRARY_PATH"
} else {
("LD_LIBRARY_PATH", ':' as u8)
};
let mut newenv = Vec::from_slice(path.as_vec());
newenv.push(sep);
match os::getenv_as_bytes(envvar) {
Some(bytes) => newenv.push_all(bytes),
"LD_LIBRARY_PATH"
}
}
fn separator() -> u8 {
if cfg!(windows) {';' as u8} else {':' as u8}
}
/// Returns the current search path for dynamic libraries being used by this
/// process
pub fn search_path() -> Vec<Path> {
let mut ret = Vec::new();
match os::getenv_as_bytes(DynamicLibrary::envvar()) {
Some(env) => {
for portion in env.split(|a| *a == DynamicLibrary::separator()) {
ret.push(Path::new(portion));
}
}
None => {}
}
os::setenv(envvar, str::from_utf8(newenv.as_slice()).unwrap());
return ret;
}
/// Access the value at the symbol of the dynamic library
@ -168,11 +201,12 @@ mod test {
#[cfg(target_os = "macos")]
#[cfg(target_os = "freebsd")]
pub mod dl {
use prelude::*;
use c_str::ToCStr;
use libc;
use ptr;
use str;
use result::*;
pub unsafe fn open_external<T: ToCStr>(filename: T) -> *u8 {
filename.with_c_str(|raw_name| {

View File

@ -524,6 +524,9 @@ fn load_extern_macros(krate: &ast::ViewItem, fld: &mut MacroExpander) {
None => return
};
debug!("load_extern_macros: mapped crate {} to path {} and registrar {:s}",
crate_name, path.display(), registrar);
let lib = match DynamicLibrary::open(Some(&path)) {
Ok(lib) => lib,
// this is fatal: there are almost certainly macros we need

View File

@ -1,9 +1,13 @@
-include ../tools.mk
HOST_LIB_DIR=$(TMPDIR)/../../../stage$(RUST_BUILD_STAGE)/lib
# This overrides the LD_LIBRARY_PATH for RUN
TARGET_RPATH_DIR:=$(TARGET_RPATH_DIR):$(TMPDIR)
all:
$(RUSTC) lib.rs
ln -nsf $(call DYLIB,boot-*) $(call DYLIB,boot)
$(CC) main.c -o $(call RUN,main) -lboot
$(CC) main.c -o $(call RUN_BINFILE,main) $(call RPATH_LINK_SEARCH,$(HOST_LIB_DIR)) -lboot
$(call RUN,main)
rm $(call DYLIB,boot)
$(call REMOVE_DYLIBS,boot)
$(call FAIL,main)

View File

@ -1,9 +1,13 @@
-include ../tools.mk
HOST_LIB_DIR=$(TMPDIR)/../../../stage$(RUST_BUILD_STAGE)/lib
# This overrides the LD_LIBRARY_PATH for RUN
TARGET_RPATH_DIR:=$(TARGET_RPATH_DIR):$(TMPDIR)
all:
$(RUSTC) lib.rs
ln -nsf $(call DYLIB,boot-*) $(call DYLIB,boot)
$(CC) main.c -o $(call RUN,main) -lboot
$(CC) main.c -o $(call RUN_BINFILE,main) $(call RPATH_LINK_SEARCH,$(HOST_LIB_DIR)) -lboot
$(call RUN,main)
rm $(call DYLIB,boot)
$(call REMOVE_DYLIBS,boot)
$(call FAIL,main)

View File

@ -9,6 +9,6 @@ all: $(call DYLIB,cfoo)
$(RUSTC) foo.rs
$(RUSTC) bar.rs
$(call RUN,bar)
rm $(TMPDIR)/$(call DYLIB_GLOB,cfoo)
$(call REMOVE_DYLIBS,cfoo)
$(call FAIL,bar)
endif

View File

@ -1,5 +1,8 @@
-include ../tools.mk
# This overrides the LD_LIBRARY_PATH for RUN
TARGET_RPATH_DIR:=$(TARGET_RPATH_DIR):$(TMPDIR)
# This hits an assertion in the linker on older versions of osx apparently
ifeq ($(shell uname),Darwin)
all:
@ -8,7 +11,7 @@ else
all: $(call DYLIB,cfoo)
$(RUSTC) foo.rs
$(RUSTC) bar.rs
LD_LIBRARY_PATH=$(TMPDIR) $(call RUN,bar)
rm $(TMPDIR)/$(call DYLIB_GLOB,cfoo)
$(call RUN,bar)
$(call REMOVE_DYLIBS,cfoo)
$(call FAIL,bar)
endif

View File

@ -1,9 +1,11 @@
-include ../tools.mk
HOST_LIB_DIR=$(TMPDIR)/../../../stage$(RUST_BUILD_STAGE)/lib
all:
$(RUSTC) foo.rs
ln -s $(call DYLIB,foo-*) $(call DYLIB,foo)
$(CC) bar.c -lfoo -o $(call RUN,bar) -Wl,-rpath,$(TMPDIR)
$(CC) bar.c -lfoo -o $(call RUN_BINFILE,bar) $(call RPATH_LINK_SEARCH,$(HOST_LIB_DIR)) -Wl,-rpath,$(TMPDIR)
$(call RUN,bar)
rm $(call DYLIB,foo)
$(call REMOVE_DYLIBS,foo)
$(call FAIL,bar)

View File

@ -11,7 +11,7 @@ ifneq ($(shell uname),FreeBSD)
all:
$(RUSTC) foo.rs
ln -s $(call STATICLIB,foo-*) $(call STATICLIB,foo)
$(CC) bar.c -lfoo -o $(call RUN,bar) $(EXTRAFLAGS) -lstdc++
$(CC) bar.c -lfoo -o $(call RUN_BINFILE,bar) $(EXTRAFLAGS) -lstdc++
$(call RUN,bar)
rm $(call STATICLIB,foo*)
$(call RUN,bar)

View File

@ -5,5 +5,5 @@ all: $(call STATICLIB,cfoo)
$(RUSTC) bar.rs
rm $(TMPDIR)/$(call STATICLIB_GLOB,cfoo)
$(call RUN,bar)
rm $(TMPDIR)/$(call DYLIB_GLOB,foo)
$(call REMOVE_DYLIBS,foo)
$(call FAIL,bar)

View File

@ -3,6 +3,6 @@
all: $(call STATICLIB,cfoo)
$(RUSTC) foo.rs
$(RUSTC) bar.rs
rm $(TMPDIR)/$(call RLIB_GLOB,foo)
$(call REMOVE_RLIBS,foo)
rm $(TMPDIR)/$(call STATICLIB_GLOB,cfoo)
$(call RUN,bar)

View File

@ -6,7 +6,7 @@ all:
$(RUSTC) m3.rs
$(RUSTC) m4.rs
$(call RUN,m4)
rm $(TMPDIR)/$(call DYLIB_GLOB,m1)
rm $(TMPDIR)/$(call DYLIB_GLOB,m2)
rm $(TMPDIR)/$(call DYLIB_GLOB,m3)
$(call REMOVE_DYLIBS,m1)
$(call REMOVE_DYLIBS,m2)
$(call REMOVE_DYLIBS,m3)
$(call FAIL,m4)

View File

@ -1,5 +1,8 @@
-include ../tools.mk
# This overrides the LD_LIBRARY_PATH for RUN
TARGET_RPATH_DIR:=$(TARGET_RPATH_DIR):$(TMPDIR)
all:
$(RUSTC) dylib.rs -o $(TMPDIR)/libdylib.so
$(RUSTC) main.rs

View File

@ -19,5 +19,5 @@ CC := $(CC:-g=)
all:
$(RUSTC) foo.rs -Z lto
ln -s $(call STATICLIB,foo-*) $(call STATICLIB,foo)
$(CC) bar.c -lfoo -o $(call RUN,bar) $(EXTRAFLAGS) -lstdc++
$(CC) bar.c -lfoo -o $(call RUN_BINFILE,bar) $(EXTRAFLAGS) -lstdc++
$(call RUN,bar)

View File

@ -1,6 +1,18 @@
-include ../tools.mk
all:
# This test attempts to use syntax extensions, which are known to be
# incompatible with stage1 at the moment.
ifeq ($(RUST_BUILD_STAGE),1)
DOTEST=
else
DOTEST=dotest
endif
all: $(DOTEST)
dotest:
env
$(RUSTC) lib.rs
$(RUSTC) main.rs -Z lto
$(call RUN,main)

View File

@ -3,7 +3,7 @@
all:
$(RUSTC) --crate-type=rlib crateA.rs
$(RUSTC) --crate-type=rlib crateB.rs
rm $(TMPDIR)/$(call RLIB_GLOB,crateA)
$(call REMOVE_RLIBS,crateA)
# Ensure crateC fails to compile since dependency crateA is missing
$(RUSTC) crateC.rs 2>&1 | \
grep "error: can't find crate for \`crateA\` which \`crateB\` depends on"

View File

@ -5,5 +5,5 @@ all:
$(RUSTC) dylib.rs
$(RUSTC) rlib.rs --crate-type=dylib
$(RUSTC) dylib.rs
rm $(call DYLIB,rlib-*)
$(call REMOVE_DYLIBS,rlib)
$(RUSTC) prog.rs && exit 1 || exit 0

View File

@ -7,7 +7,7 @@
# fail if an rlib was built
all:
$(RUSTC) test.rs
rm $(TMPDIR)/$(call RLIB_GLOB,test)
rm $(TMPDIR)/$(call DYLIB_GLOB,test)
$(call REMOVE_RLIBS,test)
$(call REMOVE_DYLIBS,test)
$(RUSTC) --crate-type dylib test.rs
rm $(TMPDIR)/$(call RLIB_GLOB,test) && exit 1 || exit 0
$(call REMOVE_RLIBS,test) && exit 1 || exit 0

View File

@ -2,8 +2,8 @@
all:
$(RUSTC) foo.rs --crate-type=rlib,dylib,staticlib
rm $(TMPDIR)/$(call RLIB_GLOB,bar)
rm $(TMPDIR)/$(call DYLIB_GLOB,bar)
$(call REMOVE_RLIBS,bar)
$(call REMOVE_DYLIBS,bar)
rm $(TMPDIR)/$(call STATICLIB_GLOB,bar)
$(RUSTC) foo.rs --crate-type=bin
rm $(TMPDIR)/$(call BIN,bar)
@ -41,4 +41,4 @@ all:
cmp $(TMPDIR)/foo.bc $(TMPDIR)/bar.bc
rm $(TMPDIR)/bar.bc
rm $(TMPDIR)/foo.bc
rm $(TMPDIR)/$(call RLIB_GLOB,bar)
$(call REMOVE_RLIBS,bar)

View File

@ -5,4 +5,4 @@ all:
$(RUSTC) foo.rs -C prefer-dynamic
$(call RUN,foo)
rm $(TMPDIR)/*bar*
$(call FAILS,foo)
$(call FAIL,foo)

View File

@ -4,8 +4,20 @@ export DYLD_LIBRARY_PATH:=$(TMPDIR):$(DYLD_LIBRARY_PATH)
RUSTC := $(RUSTC) --out-dir $(TMPDIR) -L $(TMPDIR)
CC := $(CC) -L $(TMPDIR)
RUN = $(TMPDIR)/$(1)
FAILS = $(TMPDIR)/$(1) && exit 1 || exit 0
# These deliberately use `=` and not `:=` so that client makefiles can
# augment HOST_RPATH_DIR / TARGET_RPATH_DIR.
HOST_RPATH_ENV = \
$(LD_LIB_PATH_ENVVAR)=$$$(LD_LIB_PATH_ENVVAR):$(HOST_RPATH_DIR)
TARGET_RPATH_ENV = \
$(LD_LIB_PATH_ENVVAR)=$$$(LD_LIB_PATH_ENVVAR):$(TARGET_RPATH_DIR)
# This is the name of the binary we will generate and run; use this
# e.g. for `$(CC) -o $(RUN_BINFILE)`.
RUN_BINFILE = $(TMPDIR)/$(1)
# RUN and FAIL are basic way we will invoke the generated binary. On
# non-windows platforms, they set the LD_LIBRARY_PATH environment
# variable before running the binary.
RLIB_GLOB = lib$(1)*.rlib
STATICLIB = $(TMPDIR)/lib$(1).a
@ -18,20 +30,32 @@ IS_WINDOWS=1
endif
ifeq ($(UNAME),Darwin)
RUN = $(TARGET_RPATH_ENV) $(RUN_BINFILE)
FAIL = $(TARGET_RPATH_ENV) $(RUN_BINFILE) && exit 1 || exit 0
DYLIB_GLOB = lib$(1)*.dylib
DYLIB = $(TMPDIR)/lib$(1).dylib
RPATH_LINK_SEARCH =
else
ifdef IS_WINDOWS
RUN = PATH="$(PATH):$(TARGET_RPATH_DIR)" $(RUN_BINFILE)
FAIL = PATH="$(PATH):$(TARGET_RPATH_DIR)" $(RUN_BINFILE) && exit 1 || exit 0
DYLIB_GLOB = $(1)*.dll
DYLIB = $(TMPDIR)/$(1).dll
BIN = $(1).exe
export PATH := $(PATH):$(LD_LIBRARY_PATH)
RPATH_LINK_SEARCH =
RUSTC := PATH="$(PATH):$(LD_LIBRARY_PATH)" $(RUSTC)
else
RUN = $(TARGET_RPATH_ENV) $(RUN_BINFILE)
FAIL = $(TARGET_RPATH_ENV) $(RUN_BINFILE) && exit 1 || exit 0
DYLIB_GLOB = lib$(1)*.so
DYLIB = $(TMPDIR)/lib$(1).so
RPATH_LINK_SEARCH = -Wl,-rpath-link=$(1)
endif
endif
REMOVE_DYLIBS = rm $(TMPDIR)/$(call DYLIB_GLOB,$(1))
REMOVE_RLIBS = rm $(TMPDIR)/$(call RLIB_GLOB,$(1))
%.a: %.o
ar crus $@ $<
%.dylib: %.o

View File

@ -1,9 +1,21 @@
-include ../tools.mk
# This test attempts to run rustc itself from the compiled binary; but
# that means that you need to set the LD_LIBRARY_PATH for rustc itself
# while running multiple_files, and that won't work for stage1.
# FIXME ignore windows
ifndef IS_WINDOWS
ifeq ($(RUST_BUILD_STAGE),1)
DOTEST=
else
DOTEST=dotest
endif
endif
all:
all: $(DOTEST)
dotest:
# check that we don't ICE on unicode input, issue #11178
$(RUSTC) multiple_files.rs
$(call RUN,multiple_files) "$(RUSTC)" "$(TMPDIR)"
@ -12,8 +24,3 @@ all:
# correct length. issue #8706
$(RUSTC) span_length.rs
$(call RUN,span_length) "$(RUSTC)" "$(TMPDIR)"
else
all:
endif