Skip to content

Commit

Permalink
Emit the lint level of the unused-crate-dependencies
Browse files Browse the repository at this point in the history
Also, turn off the lint when the unused dependencies json flag
is specified so that cargo doesn't have to supress the lint
  • Loading branch information
est31 committed Mar 8, 2021
1 parent 13371b5 commit 3a62eb7
Show file tree
Hide file tree
Showing 6 changed files with 66 additions and 19 deletions.
2 changes: 1 addition & 1 deletion compiler/rustc_errors/src/emitter.rs
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,7 @@ pub trait Emitter {
fn emit_future_breakage_report(&mut self, _diags: Vec<(FutureBreakage, Diagnostic)>) {}

/// Emit list of unused externs
fn emit_unused_externs(&mut self, _unused_externs: &[&str]) {}
fn emit_unused_externs(&mut self, _lint_level: &str, _unused_externs: &[&str]) {}

/// Checks if should show explanations about "rustc --explain"
fn should_show_explain(&self) -> bool {
Expand Down
10 changes: 6 additions & 4 deletions compiler/rustc_errors/src/json.rs
Original file line number Diff line number Diff line change
Expand Up @@ -159,8 +159,8 @@ impl Emitter for JsonEmitter {
}
}

fn emit_unused_externs(&mut self, unused_externs: &[&str]) {
let data = UnusedExterns { unused_extern_names: unused_externs };
fn emit_unused_externs(&mut self, lint_level: &str, unused_externs: &[&str]) {
let data = UnusedExterns { lint_level, unused_extern_names: unused_externs };
let result = if self.pretty {
writeln!(&mut self.dst, "{}", as_pretty_json(&data))
} else {
Expand Down Expand Up @@ -336,9 +336,11 @@ struct FutureIncompatReport {
}

#[derive(Encodable)]
struct UnusedExterns<'a, 'b> {
struct UnusedExterns<'a, 'b, 'c> {
/// The severity level of the unused dependencies lint
lint_level: &'a str,
/// List of unused externs by their names.
unused_extern_names: &'a [&'b str],
unused_extern_names: &'b [&'c str],
}

impl Diagnostic {
Expand Down
8 changes: 4 additions & 4 deletions compiler/rustc_errors/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -767,8 +767,8 @@ impl Handler {
self.inner.borrow_mut().emitter.emit_future_breakage_report(diags)
}

pub fn emit_unused_externs(&self, unused_externs: &[&str]) {
self.inner.borrow_mut().emit_unused_externs(unused_externs)
pub fn emit_unused_externs(&self, lint_level: &str, unused_externs: &[&str]) {
self.inner.borrow_mut().emit_unused_externs(lint_level, unused_externs)
}

pub fn delay_as_bug(&self, diagnostic: Diagnostic) {
Expand Down Expand Up @@ -845,8 +845,8 @@ impl HandlerInner {
self.emitter.emit_artifact_notification(path, artifact_type);
}

fn emit_unused_externs(&mut self, unused_externs: &[&str]) {
self.emitter.emit_unused_externs(unused_externs);
fn emit_unused_externs(&mut self, lint_level: &str, unused_externs: &[&str]) {
self.emitter.emit_unused_externs(lint_level, unused_externs);
}

fn treat_err_as_bug(&self) -> bool {
Expand Down
7 changes: 7 additions & 0 deletions compiler/rustc_interface/src/passes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ use rustc_hir::definitions::Definitions;
use rustc_hir::Crate;
use rustc_index::vec::IndexVec;
use rustc_lint::LintStore;
use rustc_metadata::creader::CStore;
use rustc_middle::arena::Arena;
use rustc_middle::dep_graph::DepGraph;
use rustc_middle::middle;
Expand Down Expand Up @@ -836,6 +837,12 @@ fn analysis(tcx: TyCtxt<'_>, cnum: CrateNum) -> Result<()> {
});

sess.time("looking_for_derive_registrar", || proc_macro_decls::find(tcx));

let cstore = tcx
.cstore_as_any()
.downcast_ref::<CStore>()
.expect("`tcx.cstore` is not a `CStore`");
cstore.report_unused_deps(tcx);
},
{
par_iter(&tcx.hir().krate().modules).for_each(|(&module, _)| {
Expand Down
36 changes: 28 additions & 8 deletions compiler/rustc_metadata/src/creader.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,9 @@ pub struct CStore {
/// This map is used to verify we get no hash conflicts between
/// `StableCrateId` values.
stable_crate_ids: FxHashMap<StableCrateId, CrateNum>,

/// Unused externs of the crate
unused_externs: Vec<Symbol>,
}

pub struct CrateLoader<'a> {
Expand Down Expand Up @@ -190,6 +193,21 @@ impl CStore {
crate fn has_global_allocator(&self) -> bool {
self.has_global_allocator
}

pub fn report_unused_deps(&self, tcx: TyCtxt<'_>) {
let level = tcx
.lint_level_at_node(lint::builtin::UNUSED_CRATE_DEPENDENCIES, rustc_hir::CRATE_HIR_ID)
.0;
if level != lint::Level::Allow && tcx.sess.opts.json_unused_externs {
let unused_externs =
self.unused_externs.iter().map(|ident| ident.to_ident_string()).collect::<Vec<_>>();
let unused_externs = unused_externs.iter().map(String::as_str).collect::<Vec<&str>>();
tcx.sess
.parse_sess
.span_diagnostic
.emit_unused_externs(level.as_str(), &unused_externs);
}
}
}

impl<'a> CrateLoader<'a> {
Expand Down Expand Up @@ -217,6 +235,7 @@ impl<'a> CrateLoader<'a> {
allocator_kind: None,
has_global_allocator: false,
stable_crate_ids,
unused_externs: Vec::new(),
},
used_extern_options: Default::default(),
}
Expand Down Expand Up @@ -893,18 +912,23 @@ impl<'a> CrateLoader<'a> {
fn report_unused_deps(&mut self, krate: &ast::Crate) {
// Make a point span rather than covering the whole file
let span = krate.span.shrink_to_lo();
let mut unused_externs = Vec::new();
// Complain about anything left over
for (name, entry) in self.sess.opts.externs.iter() {
if let ExternLocation::FoundInLibrarySearchDirectories = entry.location {
// Don't worry about pathless `--extern foo` sysroot references
continue;
}
if self.used_extern_options.contains(&Symbol::intern(name)) {
let name_interned = Symbol::intern(name);
if self.used_extern_options.contains(&name_interned) {
continue;
}

// Got a real unused --extern
if self.sess.opts.json_unused_externs {
self.cstore.unused_externs.push(name_interned);
continue;
}

let diag = match self.sess.opts.extern_dep_specs.get(name) {
Some(loc) => BuiltinLintDiagnostics::ExternDepSpec(name.clone(), loc.into()),
None => {
Expand All @@ -918,7 +942,6 @@ impl<'a> CrateLoader<'a> {
)
}
};
unused_externs.push(name as &str);
self.sess.parse_sess.buffer_lint_with_diagnostic(
lint::builtin::UNUSED_CRATE_DEPENDENCIES,
span,
Expand All @@ -931,19 +954,16 @@ impl<'a> CrateLoader<'a> {
diag,
);
}
if self.sess.opts.json_unused_externs {
self.sess.parse_sess.span_diagnostic.emit_unused_externs(&unused_externs);
}
}

pub fn postprocess(&mut self, krate: &ast::Crate) {
self.inject_profiler_runtime(krate);
self.inject_allocator_crate(krate);
self.inject_panic_runtime(krate);

info!("{:?}", CrateDump(&self.cstore));

self.report_unused_deps(krate);

info!("{:?}", CrateDump(&self.cstore));
}

pub fn process_extern_crate(
Expand Down
22 changes: 20 additions & 2 deletions src/librustdoc/doctest.rs
Original file line number Diff line number Diff line change
Expand Up @@ -188,8 +188,23 @@ crate fn run(options: Options) -> Result<(), ErrorReported> {
.map(|v| (*v).clone())
.collect::<Vec<String>>();
unused_extern_names.sort();
let unused_extern_json =
serde_json::to_string(&UnusedExterns { unused_extern_names }).unwrap();
// Take the most severe lint level
let lint_level = unused_extern_reports
.iter()
.map(|uexts| uexts.lint_level.as_str())
.max_by_key(|v| match *v {
"warn" => 1,
"deny" => 2,
"forbid" => 3,
// The allow lint level is not expected,
// as if allow is specified, no message
// is to be emitted.
v => unreachable!("Invalid lint level '{}'", v),
})
.unwrap_or("warn")
.to_string();
let uext = UnusedExterns { lint_level, unused_extern_names };
let unused_extern_json = serde_json::to_string(&uext).unwrap();
eprintln!("{}", unused_extern_json);
}
}
Expand Down Expand Up @@ -265,6 +280,8 @@ impl DirState {

#[derive(serde::Serialize, serde::Deserialize)]
struct UnusedExterns {
/// Lint level of the unused_crate_dependencies lint
lint_level: String,
/// List of unused externs by their names.
unused_extern_names: Vec<String>,
}
Expand Down Expand Up @@ -317,6 +334,7 @@ fn run_test(
compiler.arg("--error-format=json");
compiler.arg("--json").arg("unused-externs");
compiler.arg("-Z").arg("unstable-options");
compiler.arg("-W").arg("unused_crate_dependencies");
}
for lib_str in &options.lib_strs {
compiler.arg("-L").arg(&lib_str);
Expand Down

0 comments on commit 3a62eb7

Please sign in to comment.