Skip to content

Commit

Permalink
auto merge of #13489 : JustAPerson/rust/crate-file-name, r=alexcrichton
Browse files Browse the repository at this point in the history
Before, the `--crate-file-name` flag only checked crate attributes for
possible crate types. Now, if any type is specified by one or more
`--crate-type` flags, only the filenames for those types will be
emitted, and any types specified by crate attributes will be ignored.
  • Loading branch information
bors committed Apr 15, 2014
2 parents 8a4ffbf + 0162f8e commit 189584e
Show file tree
Hide file tree
Showing 4 changed files with 74 additions and 35 deletions.
9 changes: 7 additions & 2 deletions src/doc/rust.md
Original file line number Diff line number Diff line change
Expand Up @@ -3920,7 +3920,9 @@ link Rust crates together, and more information about native libraries can be
found in the [ffi tutorial][ffi].

In one session of compilation, the compiler can generate multiple artifacts
through the usage of command line flags and the `crate_type` attribute.
through the usage of either command line flags or the `crate_type` attribute.
If one or more command line flag is specified, all `crate_type` attributes will
be ignored in favor of only building the artifacts specified by command line.

* `--crate-type=bin`, `#[crate_type = "bin"]` - A runnable executable will be
produced. This requires that there is a `main` function in the crate which
Expand Down Expand Up @@ -3963,7 +3965,10 @@ through the usage of command line flags and the `crate_type` attribute.

Note that these outputs are stackable in the sense that if multiple are
specified, then the compiler will produce each form of output at once without
having to recompile.
having to recompile. However, this only applies for outputs specified by the same
method. If only `crate_type` attributes are specified, then they will all be
built, but if one or more `--crate-type` command line flag is specified,
then only those outputs will be built.

With all these different kinds of outputs, if crate A depends on crate B, then
the compiler could find B in various different forms throughout the system. The
Expand Down
74 changes: 41 additions & 33 deletions src/librustc/driver/session.rs
Original file line number Diff line number Diff line change
Expand Up @@ -498,43 +498,51 @@ pub fn collect_crate_types(session: &Session,
if session.opts.test {
return vec!(CrateTypeExecutable)
}

// Only check command line flags if present. If no types are specified by
// command line, then reuse the empty `base` Vec to hold the types that
// will be found in crate attributes.
let mut base = session.opts.crate_types.clone();
let iter = attrs.iter().filter_map(|a| {
if a.name().equiv(&("crate_type")) {
match a.value_str() {
Some(ref n) if n.equiv(&("rlib")) => Some(CrateTypeRlib),
Some(ref n) if n.equiv(&("dylib")) => Some(CrateTypeDylib),
Some(ref n) if n.equiv(&("lib")) => {
Some(default_lib_output())
}
Some(ref n) if n.equiv(&("staticlib")) => {
Some(CrateTypeStaticlib)
}
Some(ref n) if n.equiv(&("bin")) => Some(CrateTypeExecutable),
Some(_) => {
session.add_lint(lint::UnknownCrateType,
ast::CRATE_NODE_ID,
a.span,
~"invalid `crate_type` value");
None
}
_ => {
session.add_lint(lint::UnknownCrateType, ast::CRATE_NODE_ID,
a.span, ~"`crate_type` requires a value");
None
if base.len() > 0 {
return base
} else {
let iter = attrs.iter().filter_map(|a| {
if a.name().equiv(&("crate_type")) {
match a.value_str() {
Some(ref n) if n.equiv(&("rlib")) => Some(CrateTypeRlib),
Some(ref n) if n.equiv(&("dylib")) => Some(CrateTypeDylib),
Some(ref n) if n.equiv(&("lib")) => {
Some(default_lib_output())
}
Some(ref n) if n.equiv(&("staticlib")) => {
Some(CrateTypeStaticlib)
}
Some(ref n) if n.equiv(&("bin")) => Some(CrateTypeExecutable),
Some(_) => {
session.add_lint(lint::UnknownCrateType,
ast::CRATE_NODE_ID,
a.span,
~"invalid `crate_type` value");
None
}
_ => {
session.add_lint(lint::UnknownCrateType, ast::CRATE_NODE_ID,
a.span, ~"`crate_type` requires a value");
None
}
}
} else {
None
}
} else {
None
});
base.extend(iter);
if base.len() == 0 {
base.push(CrateTypeExecutable);
}
});
base.extend(iter);
if base.len() == 0 {
base.push(CrateTypeExecutable);
}
base.as_mut_slice().sort();
base.dedup();
return base;
base.as_mut_slice().sort();
base.dedup();
return base;
}
}

pub fn sess_os_to_meta_os(os: abi::Os) -> metadata::loader::Os {
Expand Down
13 changes: 13 additions & 0 deletions src/test/run-make/obey-crate-type-flag/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
-include ../tools.mk

# check that rustc builds all crate_type attributes
# delete rlib
# delete whatever dylib is made for this system
# check that rustc only builds --crate-type flags, ignoring attributes
# fail if an rlib was built
all:
$(RUSTC) test.rs
rm $(TMPDIR)/libtest*.rlib
rm $(TMPDIR)/libtest*
$(RUSTC) --crate-type dylib test.rs
rm $(TMPDIR)/libtest*.rlib && exit 1 || exit 0
13 changes: 13 additions & 0 deletions src/test/run-make/obey-crate-type-flag/test.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

#![crate_type = "rlib"]
#![crate_type = "dylib"]

0 comments on commit 189584e

Please sign in to comment.