-
Notifications
You must be signed in to change notification settings - Fork 13.3k
Mark allowed dead code and lang items as live #11471
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
@@ -293,7 +294,7 @@ static lint_table: &'static [(&'static str, LintSpec)] = &[ | |||
default: warn | |||
}), | |||
|
|||
("dead_code", | |||
(dead_code_lint_str, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm sorry about doing this...
nice work! |
// Check from a list of attributes if it contains the appropriate | ||
// `#[level(lintname)]` attribute (e.g. `#[allow(dead_code)]). | ||
pub fn contains_lint(attrs: &[ast::Attribute], | ||
level: level, lintname: &'static str) -> bool { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
each_lint
seems to be more like an all(..)
function whereas what I want to do is more along the line of an any(..)
function, so I decided that it's more straightforward to write a separate contains_lint
function.
Here's the diff of this commit from when you last reviewed it: http://ix.io/9Oy/diff diff --git a/src/librustc/middle/dead.rs b/src/librustc/middle/dead.rs
index ba810e5..52595d5 100644
--- a/src/librustc/middle/dead.rs
+++ b/src/librustc/middle/dead.rs
@@ -12,16 +12,16 @@
// closely. The idea is that all reachable symbols are live, codes called
// from live codes are live, and everything else is dead.
+use middle::lint::{allow, contains_lint, DeadCode};
+use middle::privacy;
use middle::ty;
use middle::typeck;
-use middle::privacy;
-use middle::lint::DeadCode;
use std::hashmap::HashSet;
use syntax::ast;
use syntax::ast_map;
use syntax::ast_util::{local_def, def_id_of_def, is_local};
-use syntax::attr::AttrMetaMethods;
+use syntax::attr;
use syntax::codemap;
use syntax::parse::token;
use syntax::visit::Visitor;
@@ -200,30 +200,22 @@ impl Visitor<()> for MarkSymbolVisitor {
}
fn has_allow_dead_code_or_lang_attr(attrs: &[ast::Attribute]) -> bool {
- for attr in attrs.iter() {
- if "allow" == attr.name() {
- if attr.meta_item_list().is_none() {
- continue
- }
- let list = attr.meta_item_list().unwrap();
- for meta_item in list.iter() {
- if dead_code_lint_str == meta_item.name() {
- return true;
- }
- }
- } else if "lang" == attr.name() {
- return true;
- }
- }
- false
+ contains_lint(attrs, allow, dead_code_lint_str)
+ || attr::contains_name(attrs, "lang")
}
// This visitor seeds items that
-// 1) we want to explicitly consider as live:
+// 1) We want to explicitly consider as live:
// * Item annotated with #[allow(dead_code)]
+// - This is done so that if we want to suppress warnings for a
+// group of dead functions, we only have to annotate the "root".
+// For example, if both `f` and `g` are dead and `f` calls `g`,
+// then annotating `f` with `#[allow(dead_code)]` will suppress
+// warning for both `f` and `g`.
// * Item annotated with #[lang=".."]
+// - This is because lang items are always callable from elsewhere.
// or
-// 2) we are not sure to be live or not
+// 2) We are not sure to be live or not
// * Implementation of a trait method
struct LifeSeeder {
worklist: ~[ast::NodeId],
diff --git a/src/librustc/middle/lint.rs b/src/librustc/middle/lint.rs
index b468f35..59536c6 100644
--- a/src/librustc/middle/lint.rs
+++ b/src/librustc/middle/lint.rs
@@ -532,6 +532,8 @@ impl<'a> Context<'a> {
}
}
+// Check that every lint from the list of attributes satisfies `f`.
+// Return true if that's the case. Otherwise return false.
pub fn each_lint(sess: session::Session,
attrs: &[ast::Attribute],
f: |@ast::MetaItem, level, @str| -> bool)
@@ -565,6 +567,25 @@ pub fn each_lint(sess: session::Session,
true
}
+// Check from a list of attributes if it contains the appropriate
+// `#[level(lintname)]` attribute (e.g. `#[allow(dead_code)]).
+pub fn contains_lint(attrs: &[ast::Attribute],
+ level: level, lintname: &'static str) -> bool {
+ let level_name = level_to_str(level);
+ for attr in attrs.iter().filter(|m| level_name == m.name()) {
+ if attr.meta_item_list().is_none() {
+ continue
+ }
+ let list = attr.meta_item_list().unwrap();
+ for meta_item in list.iter() {
+ if lintname == meta_item.name() {
+ return true;
+ }
+ }
+ }
+ false
+}
+
fn check_while_true_expr(cx: &Context, e: &ast::Expr) {
match e.node {
ast::ExprWhile(cond, _) => {
diff --git a/src/test/compile-fail/lint-dead-code-3.rs b/src/test/compile-fail/lint-dead-code-3.rs
index a24b3ae..50c9d50 100644
--- a/src/test/compile-fail/lint-dead-code-3.rs
+++ b/src/test/compile-fail/lint-dead-code-3.rs
@@ -87,6 +87,6 @@ pub fn foo() {
fn f() { g(); }
fn g() {}
-// Similarly, lang items are live
-#[lang="fail_"]
+// Similarly, lang items are live (we use a dummy name here)
+#[lang="blah"]
fn fail(_: *u8, _: *u8, _: uint) -> ! { loop {} } |
use syntax::codemap; | ||
use syntax::parse::token; | ||
use syntax::visit::Visitor; | ||
use syntax::visit; | ||
|
||
pub static dead_code_lint_str: &'static str = "dead_code"; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should be DEAD_CODE_LINT_STR
.
Dead code pass now explicitly checks for `#[allow(dead_code)]` and `#[lang=".."]` attributes on items and marks them as live if they have those attributes. The former is done so that if we want to suppress warnings for a group of dead functions, we only have to annotate the "root" of the call chain.
@alexcrichton: r+? I didn't check for duplicate function name when I moved the tests over from |
Dead code pass now explicitly checks for `#[allow(dead_code)]` and `#[lang=".."]` attributes on items and marks them as live if they have those attributes. The former is done so that if we want to suppress warnings for a group of dead functions, we only have to annotate the "root" of the call chain. Close #11380 and #11440.
Dead code pass now explicitly checks for
#[allow(dead_code)]
and#[lang=".."]
attributes on items and marks them as live if they havethose attributes. The former is done so that if we want to suppress
warnings for a group of dead functions, we only have to annotate the
"root" of the call chain.
Close #11380 and #11440.