Skip to content

Commit 00b9d9f

Browse files
committed
Auto merge of rust-lang#15071 - matklad:no-regex, r=matklad
internal: remove spurious regex dependency - replace tokio's env-filter with a smaller&simpler targets filter - reshuffle logging infra a bit to make sure there's only a single place where we read environmental variables - use anyhow::Result in rust-analyzer binary
2 parents cd3bf9f + 424ef77 commit 00b9d9f

File tree

14 files changed

+197
-242
lines changed

14 files changed

+197
-242
lines changed

Cargo.lock

-37
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

crates/hir-ty/Cargo.toml

-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,6 @@ limit.workspace = true
4747
expect-test = "1.4.0"
4848
tracing = "0.1.35"
4949
tracing-subscriber = { version = "0.3.16", default-features = false, features = [
50-
"env-filter",
5150
"registry",
5251
] }
5352
tracing-tree = "0.2.1"

crates/hir-ty/src/tests.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ use syntax::{
3030
ast::{self, AstNode, HasName},
3131
SyntaxNode,
3232
};
33-
use tracing_subscriber::{layer::SubscriberExt, EnvFilter, Registry};
33+
use tracing_subscriber::{layer::SubscriberExt, Registry};
3434
use tracing_tree::HierarchicalLayer;
3535
use triomphe::Arc;
3636

@@ -52,7 +52,8 @@ fn setup_tracing() -> Option<tracing::subscriber::DefaultGuard> {
5252
return None;
5353
}
5454

55-
let filter = EnvFilter::from_env("CHALK_DEBUG");
55+
let filter: tracing_subscriber::filter::Targets =
56+
env::var("CHALK_DEBUG").ok().and_then(|it| it.parse().ok()).unwrap_or_default();
5657
let layer = HierarchicalLayer::default()
5758
.with_indent_lines(true)
5859
.with_ansi(false)

crates/rust-analyzer/Cargo.toml

-1
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,6 @@ mimalloc = { version = "0.1.30", default-features = false, optional = true }
3737
lsp-server = { version = "0.7.0", path = "../../lib/lsp-server" }
3838
tracing = "0.1.35"
3939
tracing-subscriber = { version = "0.3.16", default-features = false, features = [
40-
"env-filter",
4140
"registry",
4241
"fmt",
4342
"tracing-log",

crates/rust-analyzer/src/bin/logger.rs

+36-54
Original file line numberDiff line numberDiff line change
@@ -8,24 +8,26 @@ use std::{
88
sync::Arc,
99
};
1010

11-
use rust_analyzer::Result;
11+
use anyhow::Context;
1212
use tracing::{level_filters::LevelFilter, Event, Subscriber};
1313
use tracing_log::NormalizeEvent;
1414
use tracing_subscriber::{
15+
filter::Targets,
1516
fmt::{
1617
format::Writer, writer::BoxMakeWriter, FmtContext, FormatEvent, FormatFields,
1718
FormattedFields, MakeWriter,
1819
},
1920
layer::SubscriberExt,
2021
registry::LookupSpan,
2122
util::SubscriberInitExt,
22-
EnvFilter, Registry,
23+
Registry,
2324
};
2425
use tracing_tree::HierarchicalLayer;
2526

26-
pub(crate) struct Logger {
27-
filter: EnvFilter,
28-
file: Option<File>,
27+
pub(crate) struct LoggerConfig {
28+
pub(crate) log_file: Option<File>,
29+
pub(crate) filter: String,
30+
pub(crate) chalk_filter: Option<String>,
2931
}
3032

3133
struct MakeWriterStderr;
@@ -38,62 +40,42 @@ impl<'a> MakeWriter<'a> for MakeWriterStderr {
3840
}
3941
}
4042

41-
impl Logger {
42-
pub(crate) fn new(file: Option<File>, filter: Option<&str>) -> Logger {
43-
let filter = filter.map_or(EnvFilter::default(), EnvFilter::new);
44-
45-
Logger { filter, file }
46-
}
43+
impl LoggerConfig {
44+
pub(crate) fn init(self) -> anyhow::Result<()> {
45+
let mut filter: Targets = self
46+
.filter
47+
.parse()
48+
.with_context(|| format!("invalid log filter: `{}`", self.filter))?;
49+
50+
let mut chalk_layer = None;
51+
if let Some(chalk_filter) = self.chalk_filter {
52+
let level: LevelFilter =
53+
chalk_filter.parse().with_context(|| "invalid chalk log filter")?;
54+
chalk_layer = Some(
55+
HierarchicalLayer::default()
56+
.with_indent_lines(true)
57+
.with_ansi(false)
58+
.with_indent_amount(2)
59+
.with_writer(io::stderr),
60+
);
61+
filter = filter
62+
.with_target("chalk_solve", level)
63+
.with_target("chalk_ir", level)
64+
.with_target("chalk_recursive", level);
65+
};
4766

48-
pub(crate) fn install(self) -> Result<()> {
49-
// The meaning of CHALK_DEBUG I suspected is to tell chalk crates
50-
// (i.e. chalk-solve, chalk-ir, chalk-recursive) how to filter tracing
51-
// logs. But now we can only have just one filter, which means we have to
52-
// merge chalk filter to our main filter (from RA_LOG env).
53-
//
54-
// The acceptable syntax of CHALK_DEBUG is `target[span{field=value}]=level`.
55-
// As the value should only affect chalk crates, we'd better manually
56-
// specify the target. And for simplicity, CHALK_DEBUG only accept the value
57-
// that specify level.
58-
let chalk_level_dir = std::env::var("CHALK_DEBUG")
59-
.map(|val| {
60-
val.parse::<LevelFilter>().expect(
61-
"invalid CHALK_DEBUG value, expect right log level (like debug or trace)",
62-
)
63-
})
64-
.ok();
65-
66-
let chalk_layer = HierarchicalLayer::default()
67-
.with_indent_lines(true)
68-
.with_ansi(false)
69-
.with_indent_amount(2)
70-
.with_writer(io::stderr);
71-
72-
let writer = match self.file {
67+
let writer = match self.log_file {
7368
Some(file) => BoxMakeWriter::new(Arc::new(file)),
7469
None => BoxMakeWriter::new(io::stderr),
7570
};
7671
let ra_fmt_layer =
7772
tracing_subscriber::fmt::layer().event_format(LoggerFormatter).with_writer(writer);
7873

79-
match chalk_level_dir {
80-
Some(val) => {
81-
Registry::default()
82-
.with(
83-
self.filter
84-
.add_directive(format!("chalk_solve={val}").parse()?)
85-
.add_directive(format!("chalk_ir={val}").parse()?)
86-
.add_directive(format!("chalk_recursive={val}").parse()?),
87-
)
88-
.with(ra_fmt_layer)
89-
.with(chalk_layer)
90-
.init();
91-
}
92-
None => {
93-
Registry::default().with(self.filter).with(ra_fmt_layer).init();
94-
}
95-
};
96-
74+
let registry = Registry::default().with(filter).with(ra_fmt_layer);
75+
match chalk_layer {
76+
Some(chalk_layer) => registry.with(chalk_layer).init(),
77+
None => registry.init(),
78+
}
9779
Ok(())
9880
}
9981
}

crates/rust-analyzer/src/bin/main.rs

+33-30
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,11 @@
77
mod logger;
88
mod rustc_wrapper;
99

10-
use std::{
11-
env, fs,
12-
path::{Path, PathBuf},
13-
process,
14-
};
10+
use std::{env, fs, path::PathBuf, process};
1511

12+
use anyhow::Context;
1613
use lsp_server::Connection;
17-
use rust_analyzer::{cli::flags, config::Config, from_json, Result};
14+
use rust_analyzer::{cli::flags, config::Config, from_json};
1815
use vfs::AbsPathBuf;
1916

2017
#[cfg(all(feature = "mimalloc"))]
@@ -25,7 +22,7 @@ static ALLOC: mimalloc::MiMalloc = mimalloc::MiMalloc;
2522
#[global_allocator]
2623
static ALLOC: jemallocator::Jemalloc = jemallocator::Jemalloc;
2724

28-
fn main() {
25+
fn main() -> anyhow::Result<()> {
2926
if std::env::var("RA_RUSTC_WRAPPER").is_ok() {
3027
let mut args = std::env::args_os();
3128
let _me = args.next().unwrap();
@@ -41,14 +38,7 @@ fn main() {
4138
}
4239

4340
let flags = flags::RustAnalyzer::from_env_or_exit();
44-
if let Err(err) = try_main(flags) {
45-
tracing::error!("Unexpected error: {}", err);
46-
eprintln!("{err}");
47-
process::exit(101);
48-
}
49-
}
5041

51-
fn try_main(flags: flags::RustAnalyzer) -> Result<()> {
5242
#[cfg(debug_assertions)]
5343
if flags.wait_dbg || env::var("RA_WAIT_DBG").is_ok() {
5444
#[allow(unused_mut)]
@@ -58,14 +48,8 @@ fn try_main(flags: flags::RustAnalyzer) -> Result<()> {
5848
}
5949
}
6050

61-
let mut log_file = flags.log_file.as_deref();
62-
63-
let env_log_file = env::var("RA_LOG_FILE").ok();
64-
if let Some(env_log_file) = env_log_file.as_deref() {
65-
log_file = Some(Path::new(env_log_file));
66-
}
51+
setup_logging(flags.log_file.clone())?;
6752

68-
setup_logging(log_file)?;
6953
let verbosity = flags.verbosity();
7054

7155
match flags.subcommand {
@@ -102,7 +86,7 @@ fn try_main(flags: flags::RustAnalyzer) -> Result<()> {
10286
Ok(())
10387
}
10488

105-
fn setup_logging(log_file: Option<&Path>) -> Result<()> {
89+
fn setup_logging(log_file_flag: Option<PathBuf>) -> anyhow::Result<()> {
10690
if cfg!(windows) {
10791
// This is required so that windows finds our pdb that is placed right beside the exe.
10892
// By default it doesn't look at the folder the exe resides in, only in the current working
@@ -115,23 +99,42 @@ fn setup_logging(log_file: Option<&Path>) -> Result<()> {
11599
}
116100
}
117101
}
102+
118103
if env::var("RUST_BACKTRACE").is_err() {
119104
env::set_var("RUST_BACKTRACE", "short");
120105
}
121106

107+
let log_file = env::var("RA_LOG_FILE").ok().map(PathBuf::from).or(log_file_flag);
122108
let log_file = match log_file {
123109
Some(path) => {
124110
if let Some(parent) = path.parent() {
125111
let _ = fs::create_dir_all(parent);
126112
}
127-
Some(fs::File::create(path)?)
113+
Some(
114+
fs::File::create(&path)
115+
.with_context(|| format!("can't create log file at {}", path.display()))?,
116+
)
128117
}
129118
None => None,
130119
};
131-
let filter = env::var("RA_LOG").ok();
132-
// deliberately enable all `error` logs if the user has not set RA_LOG, as there is usually useful
133-
// information in there for debugging
134-
logger::Logger::new(log_file, filter.as_deref().or(Some("error"))).install()?;
120+
121+
logger::LoggerConfig {
122+
log_file,
123+
// Deliberately enable all `error` logs if the user has not set RA_LOG, as there is usually
124+
// useful information in there for debugging.
125+
filter: env::var("RA_LOG").ok().unwrap_or_else(|| "error".to_string()),
126+
// The meaning of CHALK_DEBUG I suspected is to tell chalk crates
127+
// (i.e. chalk-solve, chalk-ir, chalk-recursive) how to filter tracing
128+
// logs. But now we can only have just one filter, which means we have to
129+
// merge chalk filter to our main filter (from RA_LOG env).
130+
//
131+
// The acceptable syntax of CHALK_DEBUG is `target[span{field=value}]=level`.
132+
// As the value should only affect chalk crates, we'd better manually
133+
// specify the target. And for simplicity, CHALK_DEBUG only accept the value
134+
// that specify level.
135+
chalk_filter: env::var("CHALK_DEBUG").ok(),
136+
}
137+
.init()?;
135138

136139
profile::init();
137140

@@ -146,8 +149,8 @@ const STACK_SIZE: usize = 1024 * 1024 * 8;
146149
fn with_extra_thread(
147150
thread_name: impl Into<String>,
148151
thread_intent: stdx::thread::ThreadIntent,
149-
f: impl FnOnce() -> Result<()> + Send + 'static,
150-
) -> Result<()> {
152+
f: impl FnOnce() -> anyhow::Result<()> + Send + 'static,
153+
) -> anyhow::Result<()> {
151154
let handle = stdx::thread::Builder::new(thread_intent)
152155
.name(thread_name.into())
153156
.stack_size(STACK_SIZE)
@@ -158,7 +161,7 @@ fn with_extra_thread(
158161
Ok(())
159162
}
160163

161-
fn run_server() -> Result<()> {
164+
fn run_server() -> anyhow::Result<()> {
162165
tracing::info!("server version {} will start", rust_analyzer::version());
163166

164167
let (connection, io_threads) = Connection::stdio();

0 commit comments

Comments
 (0)