mirror of
https://github.com/rust-lang/rust-analyzer
synced 2025-01-13 13:48:50 +00:00
Merge #4296
4296: Support cargo:rustc-cfg in build.rs r=matklad a=robojumper Fixes #4238. Co-authored-by: robojumper <robojumper@gmail.com>
This commit is contained in:
commit
1b136aae0b
4 changed files with 130 additions and 5 deletions
|
@ -53,4 +53,13 @@ impl CfgOptions {
|
||||||
pub fn insert_features(&mut self, iter: impl IntoIterator<Item = SmolStr>) {
|
pub fn insert_features(&mut self, iter: impl IntoIterator<Item = SmolStr>) {
|
||||||
iter.into_iter().for_each(|feat| self.insert_key_value("feature".into(), feat));
|
iter.into_iter().for_each(|feat| self.insert_key_value("feature".into(), feat));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Shortcut to set cfgs
|
||||||
|
pub fn insert_cfgs(&mut self, iter: impl IntoIterator<Item = SmolStr>) {
|
||||||
|
iter.into_iter().for_each(|cfg| match cfg.find('=') {
|
||||||
|
Some(split) => self
|
||||||
|
.insert_key_value(cfg[0..split].into(), cfg[split + 1..].trim_matches('"').into()),
|
||||||
|
None => self.insert_atom(cfg),
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -87,6 +87,7 @@ pub struct PackageData {
|
||||||
pub dependencies: Vec<PackageDependency>,
|
pub dependencies: Vec<PackageDependency>,
|
||||||
pub edition: Edition,
|
pub edition: Edition,
|
||||||
pub features: Vec<String>,
|
pub features: Vec<String>,
|
||||||
|
pub cfgs: Vec<String>,
|
||||||
pub out_dir: Option<PathBuf>,
|
pub out_dir: Option<PathBuf>,
|
||||||
pub proc_macro_dylib_path: Option<PathBuf>,
|
pub proc_macro_dylib_path: Option<PathBuf>,
|
||||||
}
|
}
|
||||||
|
@ -172,10 +173,12 @@ impl CargoWorkspace {
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
let mut out_dir_by_id = FxHashMap::default();
|
let mut out_dir_by_id = FxHashMap::default();
|
||||||
|
let mut cfgs = FxHashMap::default();
|
||||||
let mut proc_macro_dylib_paths = FxHashMap::default();
|
let mut proc_macro_dylib_paths = FxHashMap::default();
|
||||||
if cargo_features.load_out_dirs_from_check {
|
if cargo_features.load_out_dirs_from_check {
|
||||||
let resources = load_extern_resources(cargo_toml, cargo_features)?;
|
let resources = load_extern_resources(cargo_toml, cargo_features)?;
|
||||||
out_dir_by_id = resources.out_dirs;
|
out_dir_by_id = resources.out_dirs;
|
||||||
|
cfgs = resources.cfgs;
|
||||||
proc_macro_dylib_paths = resources.proc_dylib_paths;
|
proc_macro_dylib_paths = resources.proc_dylib_paths;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -201,6 +204,7 @@ impl CargoWorkspace {
|
||||||
edition,
|
edition,
|
||||||
dependencies: Vec::new(),
|
dependencies: Vec::new(),
|
||||||
features: Vec::new(),
|
features: Vec::new(),
|
||||||
|
cfgs: cfgs.get(&id).cloned().unwrap_or_default(),
|
||||||
out_dir: out_dir_by_id.get(&id).cloned(),
|
out_dir: out_dir_by_id.get(&id).cloned(),
|
||||||
proc_macro_dylib_path: proc_macro_dylib_paths.get(&id).cloned(),
|
proc_macro_dylib_path: proc_macro_dylib_paths.get(&id).cloned(),
|
||||||
});
|
});
|
||||||
|
@ -282,6 +286,7 @@ impl CargoWorkspace {
|
||||||
pub struct ExternResources {
|
pub struct ExternResources {
|
||||||
out_dirs: FxHashMap<PackageId, PathBuf>,
|
out_dirs: FxHashMap<PackageId, PathBuf>,
|
||||||
proc_dylib_paths: FxHashMap<PackageId, PathBuf>,
|
proc_dylib_paths: FxHashMap<PackageId, PathBuf>,
|
||||||
|
cfgs: FxHashMap<PackageId, Vec<String>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn load_extern_resources(
|
pub fn load_extern_resources(
|
||||||
|
@ -307,8 +312,14 @@ pub fn load_extern_resources(
|
||||||
for message in cargo_metadata::parse_messages(output.stdout.as_slice()) {
|
for message in cargo_metadata::parse_messages(output.stdout.as_slice()) {
|
||||||
if let Ok(message) = message {
|
if let Ok(message) = message {
|
||||||
match message {
|
match message {
|
||||||
Message::BuildScriptExecuted(BuildScript { package_id, out_dir, .. }) => {
|
Message::BuildScriptExecuted(BuildScript { package_id, out_dir, cfgs, .. }) => {
|
||||||
res.out_dirs.insert(package_id, out_dir);
|
res.out_dirs.insert(package_id.clone(), out_dir);
|
||||||
|
res.cfgs.insert(
|
||||||
|
package_id,
|
||||||
|
// FIXME: Current `cargo_metadata` uses `PathBuf` instead of `String`,
|
||||||
|
// change when https://github.com/oli-obk/cargo_metadata/pulls/112 reaches crates.io
|
||||||
|
cfgs.iter().filter_map(|c| c.to_str().map(|s| s.to_owned())).collect(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
Message::CompilerArtifact(message) => {
|
Message::CompilerArtifact(message) => {
|
||||||
|
|
|
@ -399,6 +399,7 @@ impl ProjectWorkspace {
|
||||||
let cfg_options = {
|
let cfg_options = {
|
||||||
let mut opts = default_cfg_options.clone();
|
let mut opts = default_cfg_options.clone();
|
||||||
opts.insert_features(cargo[pkg].features.iter().map(Into::into));
|
opts.insert_features(cargo[pkg].features.iter().map(Into::into));
|
||||||
|
opts.insert_cfgs(cargo[pkg].cfgs.iter().map(Into::into));
|
||||||
opts
|
opts
|
||||||
};
|
};
|
||||||
let mut env = Env::default();
|
let mut env = Env::default();
|
||||||
|
|
|
@ -9,7 +9,8 @@ use lsp_types::{
|
||||||
};
|
};
|
||||||
use rust_analyzer::req::{
|
use rust_analyzer::req::{
|
||||||
CodeActionParams, CodeActionRequest, Completion, CompletionParams, DidOpenTextDocument,
|
CodeActionParams, CodeActionRequest, Completion, CompletionParams, DidOpenTextDocument,
|
||||||
Formatting, GotoDefinition, HoverRequest, OnEnter, Runnables, RunnablesParams,
|
Formatting, GotoDefinition, GotoTypeDefinition, HoverRequest, OnEnter, Runnables,
|
||||||
|
RunnablesParams,
|
||||||
};
|
};
|
||||||
use serde_json::json;
|
use serde_json::json;
|
||||||
use tempfile::TempDir;
|
use tempfile::TempDir;
|
||||||
|
@ -574,7 +575,7 @@ version = \"0.0.0\"
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn resolve_include_concat_env() {
|
fn out_dirs_check() {
|
||||||
if skip_slow_tests() {
|
if skip_slow_tests() {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -597,11 +598,28 @@ fn main() {
|
||||||
r#"pub fn message() -> &'static str { "Hello, World!" }"#,
|
r#"pub fn message() -> &'static str { "Hello, World!" }"#,
|
||||||
)
|
)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
println!("cargo:rustc-cfg=atom_cfg");
|
||||||
|
println!("cargo:rustc-cfg=featlike=\"set\"");
|
||||||
println!("cargo:rerun-if-changed=build.rs");
|
println!("cargo:rerun-if-changed=build.rs");
|
||||||
}
|
}
|
||||||
//- src/main.rs
|
//- src/main.rs
|
||||||
include!(concat!(env!("OUT_DIR"), "/hello.rs"));
|
include!(concat!(env!("OUT_DIR"), "/hello.rs"));
|
||||||
|
|
||||||
|
#[cfg(atom_cfg)]
|
||||||
|
struct A;
|
||||||
|
#[cfg(bad_atom_cfg)]
|
||||||
|
struct A;
|
||||||
|
#[cfg(featlike = "set")]
|
||||||
|
struct B;
|
||||||
|
#[cfg(featlike = "not_set")]
|
||||||
|
struct B;
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let va = A;
|
||||||
|
let vb = B;
|
||||||
|
message();
|
||||||
|
}
|
||||||
|
|
||||||
fn main() { message(); }
|
fn main() { message(); }
|
||||||
"###,
|
"###,
|
||||||
)
|
)
|
||||||
|
@ -613,12 +631,98 @@ fn main() { message(); }
|
||||||
let res = server.send_request::<GotoDefinition>(GotoDefinitionParams {
|
let res = server.send_request::<GotoDefinition>(GotoDefinitionParams {
|
||||||
text_document_position_params: TextDocumentPositionParams::new(
|
text_document_position_params: TextDocumentPositionParams::new(
|
||||||
server.doc_id("src/main.rs"),
|
server.doc_id("src/main.rs"),
|
||||||
Position::new(2, 15),
|
Position::new(14, 8),
|
||||||
),
|
),
|
||||||
work_done_progress_params: Default::default(),
|
work_done_progress_params: Default::default(),
|
||||||
partial_result_params: Default::default(),
|
partial_result_params: Default::default(),
|
||||||
});
|
});
|
||||||
assert!(format!("{}", res).contains("hello.rs"));
|
assert!(format!("{}", res).contains("hello.rs"));
|
||||||
|
server.request::<GotoTypeDefinition>(
|
||||||
|
GotoDefinitionParams {
|
||||||
|
text_document_position_params: TextDocumentPositionParams::new(
|
||||||
|
server.doc_id("src/main.rs"),
|
||||||
|
Position::new(12, 9),
|
||||||
|
),
|
||||||
|
work_done_progress_params: Default::default(),
|
||||||
|
partial_result_params: Default::default(),
|
||||||
|
},
|
||||||
|
json!([{
|
||||||
|
"originSelectionRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 10,
|
||||||
|
"line": 12
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 8,
|
||||||
|
"line": 12
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 9,
|
||||||
|
"line": 3
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 0,
|
||||||
|
"line": 2
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetSelectionRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 8,
|
||||||
|
"line": 3
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 7,
|
||||||
|
"line": 3
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetUri": "file:///[..]src/main.rs"
|
||||||
|
}]),
|
||||||
|
);
|
||||||
|
server.request::<GotoTypeDefinition>(
|
||||||
|
GotoDefinitionParams {
|
||||||
|
text_document_position_params: TextDocumentPositionParams::new(
|
||||||
|
server.doc_id("src/main.rs"),
|
||||||
|
Position::new(13, 9),
|
||||||
|
),
|
||||||
|
work_done_progress_params: Default::default(),
|
||||||
|
partial_result_params: Default::default(),
|
||||||
|
},
|
||||||
|
json!([{
|
||||||
|
"originSelectionRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 10,
|
||||||
|
"line": 13
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 8,
|
||||||
|
"line":13
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 9,
|
||||||
|
"line": 7
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 0,
|
||||||
|
"line":6
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetSelectionRange": {
|
||||||
|
"end": {
|
||||||
|
"character": 8,
|
||||||
|
"line": 7
|
||||||
|
},
|
||||||
|
"start": {
|
||||||
|
"character": 7,
|
||||||
|
"line": 7
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"targetUri": "file:///[..]src/main.rs"
|
||||||
|
}]),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
|
Loading…
Reference in a new issue