Skip to content

Commit 07c0784

Browse files
committed
Auto merge of #5487 - matklad:mixed-deps, r=alexcrhiton
FIx false positive warning We warn if a feature was specified corresponding to a dependency which is not optional. However, a dependency can be both optional and required, and we shouldn't warn in that case. cc #5480 r? @alexcrichton
2 parents a24e8c6 + 739cc20 commit 07c0784

File tree

2 files changed

+86
-1
lines changed

2 files changed

+86
-1
lines changed

src/cargo/core/resolver/context.rs

+5-1
Original file line numberDiff line numberDiff line change
@@ -204,7 +204,11 @@ impl Context {
204204
// name.
205205
let base = reqs.deps.get(&*dep.name()).unwrap_or(&default_dep);
206206
used_features.insert(dep.name().as_str());
207-
if !dep.is_optional() && base.0 {
207+
let always_required = !dep.is_optional()
208+
&& !s.dependencies()
209+
.iter()
210+
.any(|d| d.is_optional() && d.name() == dep.name());
211+
if always_required && base.0 {
208212
self.warnings.push(format!(
209213
"Package `{}` does not have feature `{}`. It has a required dependency \
210214
with that name, but only optional dependencies can be used as features. \

tests/testsuite/build_script.rs

+81
Original file line numberDiff line numberDiff line change
@@ -3897,3 +3897,84 @@ fn optional_build_script_dep() {
38973897
execs().with_status(0).with_stdout("1\n"),
38983898
);
38993899
}
3900+
3901+
3902+
#[test]
3903+
fn optional_build_dep_and_required_normal_dep() {
3904+
let p = project("foo")
3905+
.file(
3906+
"Cargo.toml",
3907+
r#"
3908+
[package]
3909+
name = "foo"
3910+
version = "0.1.0"
3911+
authors = []
3912+
3913+
[dependencies]
3914+
bar = { path = "./bar", optional = true }
3915+
3916+
[build-dependencies]
3917+
bar = { path = "./bar" }
3918+
"#,
3919+
)
3920+
.file(
3921+
"build.rs",
3922+
r#"
3923+
extern crate bar;
3924+
fn main() { bar::bar(); }
3925+
"#,
3926+
)
3927+
.file(
3928+
"src/main.rs",
3929+
r#"
3930+
#[cfg(feature = "bar")]
3931+
extern crate bar;
3932+
3933+
fn main() {
3934+
#[cfg(feature = "bar")] {
3935+
println!("{}", bar::bar());
3936+
}
3937+
#[cfg(not(feature = "bar"))] {
3938+
println!("0");
3939+
}
3940+
}
3941+
"#,
3942+
)
3943+
.file(
3944+
"bar/Cargo.toml",
3945+
r#"
3946+
[project]
3947+
name = "bar"
3948+
version = "0.5.0"
3949+
authors = []
3950+
"#,
3951+
)
3952+
.file(
3953+
"bar/src/lib.rs",
3954+
r#"
3955+
pub fn bar() -> u32 { 1 }
3956+
"#,
3957+
);
3958+
let p = p.build();
3959+
3960+
assert_that(
3961+
p.cargo("run"),
3962+
execs().with_status(0).with_stdout("0").with_stderr(
3963+
"\
3964+
[COMPILING] bar v0.5.0 ([..])
3965+
[COMPILING] foo v0.1.0 ([..])
3966+
[FINISHED] dev [unoptimized + debuginfo] target(s) in [..]
3967+
[RUNNING] `[..]foo[EXE]`",
3968+
),
3969+
);
3970+
3971+
assert_that(
3972+
p.cargo("run --all-features"),
3973+
execs().with_status(0).with_stdout("1").with_stderr(
3974+
"\
3975+
[COMPILING] foo v0.1.0 ([..])
3976+
[FINISHED] dev [unoptimized + debuginfo] target(s) in [..]
3977+
[RUNNING] `[..]foo[EXE]`",
3978+
),
3979+
);
3980+
}

0 commit comments

Comments
 (0)