]> git.lizzy.rs Git - rust.git/commitdiff
Implement empty_enum lint and add a test
authorOwen Sanchez <pengowen816@gmail.com>
Sun, 5 Feb 2017 04:52:44 +0000 (21:52 -0700)
committerOwen Sanchez <pengowen816@gmail.com>
Sun, 5 Feb 2017 04:52:44 +0000 (21:52 -0700)
clippy_lints/src/empty_enum.rs
tests/compile-fail/empty_enum.rs [new file with mode: 0644]

index 17be52d659aedc160088c64fd86608ba37aa596a..f930a8599e27d8495be9d5139af212d4932b892c 100644 (file)
@@ -2,10 +2,7 @@
 
 use rustc::lint::*;
 use rustc::hir::*;
-use utils::{span_lint_and_then, snippet_opt};
-use rustc::ty::layout::TargetDataLayout;
-use rustc::ty::TypeFoldable;
-use rustc::traits::Reveal;
+use utils::span_lint_and_then;
 
 /// **What it does:** Checks for `enum`s with no variants.
 ///
@@ -19,7 +16,7 @@
 /// ```
 declare_lint! {
     pub EMPTY_ENUM,
-    Warn,
+    Allow,
     "enum with no variants"
 }
 
@@ -35,46 +32,13 @@ fn get_lints(&self) -> LintArray {
 impl<'a, 'tcx> LateLintPass<'a, 'tcx> for EmptyEnum {
     fn check_item(&mut self, cx: &LateContext, item: &Item) {
         let did = cx.tcx.hir.local_def_id(item.id);
-        if let ItemEnum(ref def, _) = item.node {
+        if let ItemEnum(..) = item.node {
             let ty = cx.tcx.item_type(did);
             let adt = ty.ty_adt_def().expect("already checked whether this is an enum");
-            for (i, variant) in adt.variants.iter().enumerate() {
-                let data_layout = TargetDataLayout::parse(cx.sess());
-                cx.tcx.infer_ctxt((), Reveal::All).enter(|infcx| {
-                    let size: u64 = variant.fields
-                        .iter()
-                        .map(|f| {
-                            let ty = cx.tcx.item_type(f.did);
-                            if ty.needs_subst() {
-                                0 // we can't reason about generics, so we treat them as zero sized
-                            } else {
-                                ty.layout(&infcx)
-                                    .expect("layout should be computable for concrete type")
-                                    .size(&data_layout)
-                                    .bytes()
-                            }
-                        })
-                        .sum();
-                    if size > 0 {
-                        span_lint_and_then(cx, EMPTY_ENUM, def.variants[i].span, "large enum variant found", |db| {
-                            if variant.fields.len() == 1 {
-                                let span = match def.variants[i].node.data {
-                                    VariantData::Struct(ref fields, _) |
-                                    VariantData::Tuple(ref fields, _) => fields[0].ty.span,
-                                    VariantData::Unit(_) => unreachable!(),
-                                };
-                                if let Some(snip) = snippet_opt(cx, span) {
-                                    db.span_suggestion(span,
-                                                       "consider boxing the large fields to reduce the total size of \
-                                                        the enum",
-                                                       format!("Box<{}>", snip));
-                                    return;
-                                }
-                            }
-                            db.span_help(def.variants[i].span,
-                                         "consider boxing the large fields to reduce the total size of the enum");
-                        });
-                    }
+            if adt.variants.is_empty() {
+                span_lint_and_then(cx, EMPTY_ENUM, item.span, "enum with no variants", |db| {
+                    db.span_help(item.span,
+                                 "consider using the uninhabited type `!` or a wrapper around it");
                 });
             }
         }
diff --git a/tests/compile-fail/empty_enum.rs b/tests/compile-fail/empty_enum.rs
new file mode 100644 (file)
index 0000000..f6a9de3
--- /dev/null
@@ -0,0 +1,10 @@
+#![feature(plugin)]
+#![plugin(clippy)]
+
+#![deny(empty_enum)]
+
+enum Empty {} //~ ERROR enum with no variants
+    //~^ HELP consider using the uninhabited type `!` or a wrapper around it
+
+fn main() {
+}