Pre-RFC: cfg - Aligning feature configuration between Cargo & rustc

Hi, The Cargo feature request ticket directs a Pre-RFC here in the first instance. Also a previous discussion "pre-rfc-crate-defined-cfg-attributes"1 suggests cfg related functionality might best be addressed in Cargo.

Feature: Add a constrained/defined subset of #[cfg(...)] functionality to Cargo, via [cfg.features] in Cargo.tom, that enables the same rust-lang features/behavior available via rustc --cfg. The rustc --cfg feature is quite prominent, so was a little surprising this language feature (?) is not available in any degree via Cargo:

Context: Something like the following is elegant and expressive, and is available to you if you build using rustc but not if you use cargo build|run:

#[cfg(debug)]
fn a() { }

A workaround is this:

#[cfg(feature = "debug")]
fn a() { }

Proposal: Cargo.toml might look like this:

[cfg.features]
debug = []
trace = ["traceable", "jaeger"]

[features]
traceable = ["opentelemetry", "tracing", "tracing-opentelemetry"]
jaeger = ["tracing-jaeger","opentelemetry-jaeger"]

Where Cargo debug=[] is equivalent to rustc --cfg debug and trace = ["traceable", "jaeger"] is equivalent to rustc --cfg trace --cfg 'feature="jaeger"' --cfg 'feature="traceable"'

Not sure how enthused people are by that? Whether a RFC is warranted or how best to proceed - i.e. how difficult to implement this might be?

Appreciate any thoughts.

That's not an omission, but a deliberate design decision. Cargo intentionally doesn't expose the full power of arbitrary cfg attributes. I don't remember off the top of my head the exact arguments for why the system works the way it does (that's probably explained in some issue/pr/rfc), but the overall idea is that unrestricted cfgs would break composition of independent cargo packages.

1 Like

It's worth noting that you can set arbitrary cfg flags for just your crate with build.rs, so while it's more difficult than if it were in the manifest, it's not something you can't do with cargo.

1 Like

If cfgs are going to be exposed in Cargo.toml, we should make sure that we can take advantage of the conditional compilation checking feature.

OK, thanks for the insight. IIUC, Cargo does not support conditional compilation via Cargo.toml, but rather through build.rs?

If that is correct then users can be put on the right path just with a documentation suggestion or two?

Thanks, I've not had reason to use build.rs, so it looks like that time has arrived.

Per @matklad's comment, unless there is a chorus of support I'm going to considered this solved by your suggestion to use build.rs.

#[cfg(feature= "...")] is supported using Cargo.toml. Why do you want it to not be namespaced? You can rewrite the #[cfg] from #[cfg(foo)] to #[cfg(feature = "foo")], right?

I addressed that in the OP: "Something like the following is elegant and expressive". Yes things can be rewritten, I gave that workaround in the OP. In the example I tried to convey that, in the example, trace is a particular configuration of features.

In case it mitigates the objections @matklad aluded to I've amended the proposal to be [cfg.features], because it is not more general than that.

Otherwise, I'll leave this as is - stalled.
If others have similar needs they'll likely find this thread.