From 0271224bdae26260ab498f47323997f9edb5879e Mon Sep 17 00:00:00 2001 From: Jakub Wieczorek Date: Fri, 6 Jun 2014 00:00:29 +0200 Subject: [PATCH 1/4] Add detection of dead struct fields --- src/librustc/middle/dead.rs | 81 ++++++++++++++++++++++- src/libsyntax/ast.rs | 9 +++ src/test/compile-fail/lint-dead-code-4.rs | 67 +++++++++++++++++++ 3 files changed, 155 insertions(+), 2 deletions(-) create mode 100644 src/test/compile-fail/lint-dead-code-4.rs diff --git a/src/librustc/middle/dead.rs b/src/librustc/middle/dead.rs index fb19fbd70c6..46899ae19ca 100644 --- a/src/librustc/middle/dead.rs +++ b/src/librustc/middle/dead.rs @@ -124,6 +124,32 @@ impl<'a> MarkSymbolVisitor<'a> { } } + fn handle_field_access(&mut self, lhs: &ast::Expr, name: &ast::Ident) { + match ty::get(ty::expr_ty_adjusted(self.tcx, lhs)).sty { + ty::ty_struct(id, _) => { + let fields = ty::lookup_struct_fields(self.tcx, id); + let field_id = fields.iter() + .find(|field| field.name == name.name).unwrap().id; + self.live_symbols.insert(field_id.node); + }, + _ => () + } + } + + fn handle_field_pattern_match(&mut self, lhs: &ast::Pat, pats: &[ast::FieldPat]) { + match self.tcx.def_map.borrow().get(&lhs.id) { + &def::DefStruct(id) | &def::DefVariant(_, id, _) => { + let fields = ty::lookup_struct_fields(self.tcx, id); + for pat in pats.iter() { + let field_id = fields.iter() + .find(|field| field.name == pat.ident.name).unwrap().id; + self.live_symbols.insert(field_id.node); + } + } + _ => () + } + } + fn mark_live_symbols(&mut self) { let mut scanned = HashSet::new(); while self.worklist.len() > 0 { @@ -147,10 +173,22 @@ impl<'a> MarkSymbolVisitor<'a> { match *node { ast_map::NodeItem(item) => { match item.node { + ast::ItemStruct(struct_def, _) => { + let has_extern_repr = item.attrs.iter().fold(attr::ReprAny, |acc, attr| { + attr::find_repr_attr(self.tcx.sess.diagnostic(), attr, acc) + }) == attr::ReprExtern; + let live_fields = struct_def.fields.iter().filter(|f| { + has_extern_repr || match f.node.kind { + ast::NamedField(_, ast::Public) => true, + _ => false + } + }); + self.live_symbols.extend(live_fields.map(|f| f.node.id)); + visit::walk_item(self, item, ()); + } ast::ItemFn(..) | ast::ItemTy(..) | ast::ItemEnum(..) - | ast::ItemStruct(..) | ast::ItemStatic(..) => { visit::walk_item(self, item, ()); } @@ -178,18 +216,32 @@ impl<'a> Visitor<()> for MarkSymbolVisitor<'a> { ast::ExprMethodCall(..) => { self.lookup_and_handle_method(expr.id, expr.span); } + ast::ExprField(ref lhs, ref ident, _) => { + self.handle_field_access(*lhs, ident); + } _ => () } visit::walk_expr(self, expr, ()) } + fn visit_pat(&mut self, pat: &ast::Pat, _: ()) { + match pat.node { + ast::PatStruct(_, ref fields, _) => { + self.handle_field_pattern_match(pat, fields.as_slice()); + } + _ => () + } + + visit::walk_pat(self, pat, ()) + } + fn visit_path(&mut self, path: &ast::Path, id: ast::NodeId, _: ()) { self.lookup_and_handle_definition(&id); visit::walk_path(self, path, ()); } - fn visit_item(&mut self, _item: &ast::Item, _: ()) { + fn visit_item(&mut self, _: &ast::Item, _: ()) { // Do not recurse into items. These items will be added to the // worklist and recursed into manually if necessary. } @@ -317,6 +369,23 @@ struct DeadVisitor<'a> { } impl<'a> DeadVisitor<'a> { + fn should_warn_about_field(&mut self, node: &ast::StructField_) -> bool { + let (is_named, has_leading_underscore) = match node.ident() { + Some(ref ident) => (true, token::get_ident(*ident).get()[0] == ('_' as u8)), + _ => (false, false) + }; + let field_type = ty::node_id_to_type(self.tcx, node.id); + let is_marker_field = match ty::ty_to_def_id(field_type) { + Some(def_id) => self.tcx.lang_items.items().any(|(_, item)| *item == Some(def_id)), + _ => false + }; + is_named + && !self.symbol_is_live(node.id, None) + && !has_leading_underscore + && !is_marker_field + && !has_allow_dead_code_or_lang_attr(node.attrs.as_slice()) + } + // id := node id of an item's definition. // ctor_id := `Some` if the item is a struct_ctor (tuple struct), // `None` otherwise. @@ -399,6 +468,14 @@ impl<'a> Visitor<()> for DeadVisitor<'a> { visit::walk_block(self, block, ()); } + fn visit_struct_field(&mut self, field: &ast::StructField, _: ()) { + if self.should_warn_about_field(&field.node) { + self.warn_dead_code(field.node.id, field.span, field.node.ident().unwrap()); + } + + visit::walk_struct_field(self, field, ()); + } + // Overwrite so that we don't warn the trait method itself. fn visit_trait_method(&mut self, trait_method: &ast::TraitMethod, _: ()) { match *trait_method { diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index 2bc24fd1eb3..e18484a68f3 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -1046,6 +1046,15 @@ pub struct StructField_ { pub attrs: Vec, } +impl StructField_ { + pub fn ident(&self) -> Option { + match self.kind { + NamedField(ref ident, _) => Some(ident.clone()), + UnnamedField(_) => None + } + } +} + pub type StructField = Spanned; #[deriving(Clone, PartialEq, Eq, Encodable, Decodable, Hash)] diff --git a/src/test/compile-fail/lint-dead-code-4.rs b/src/test/compile-fail/lint-dead-code-4.rs new file mode 100644 index 00000000000..718af1841b6 --- /dev/null +++ b/src/test/compile-fail/lint-dead-code-4.rs @@ -0,0 +1,67 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#![feature(struct_variant)] +#![allow(unused_variable)] +#![allow(non_camel_case_types)] +#![deny(dead_code)] + +extern crate libc; + +use std::num; + +struct Foo { + x: uint, + b: bool, //~ ERROR: code is never used + marker: std::kinds::marker::NoCopy +} + +fn field_read(f: Foo) -> uint { + num::pow(f.x, 2) +} + +enum XYZ { + X, + Y { + a: String, + b: int //~ ERROR: code is never used + }, + Z +} + +fn field_match_in_patterns(b: XYZ) -> String { + match b { + Y { a: a, .. } => a, + _ => "".to_string() + } +} + +struct Bar { + x: uint, //~ ERROR: code is never used + b: bool, + _guard: () +} + +#[repr(C)] +struct Baz { + x: libc::c_uint +} + +fn field_match_in_let(f: Bar) -> bool { + let Bar { b, .. } = f; + b +} + +fn main() { + field_read(Foo { x: 1, b: false, marker: std::kinds::marker::NoCopy }); + field_match_in_patterns(Z); + field_match_in_let(Bar { x: 42u, b: true, _guard: () }); + let _ = Baz { x: 0 }; +} From f7d86b2f4ace416a65e84603082c756b8b5dc43e Mon Sep 17 00:00:00 2001 From: Jakub Wieczorek Date: Fri, 6 Jun 2014 15:51:42 +0200 Subject: [PATCH 2/4] Remove the dead code identified by the new lint --- src/libglob/lib.rs | 3 -- src/libnative/io/mod.rs | 4 +- src/libnative/io/net.rs | 5 +- src/libnative/io/pipe_unix.rs | 5 +- src/librand/distributions/gamma.rs | 2 - src/librustc/front/std_inject.rs | 10 ++-- src/librustc/metadata/loader.rs | 4 +- src/librustc/metadata/tyencode.rs | 4 -- .../middle/borrowck/gather_loans/lifetime.rs | 4 +- .../middle/borrowck/gather_loans/mod.rs | 7 +-- .../borrowck/gather_loans/restrictions.rs | 2 - src/librustc/middle/borrowck/mod.rs | 1 - src/librustc/middle/liveness.rs | 48 ++----------------- src/librustc/middle/privacy.rs | 2 - src/librustc/middle/resolve.rs | 13 ++--- src/librustc/middle/trans/base.rs | 6 ++- src/librustc/middle/trans/foreign.rs | 6 +-- src/librustc/middle/typeck/coherence.rs | 8 +--- src/librustc/middle/typeck/variance.rs | 2 - src/librustc/util/common.rs | 16 ++----- src/librustdoc/html/markdown.rs | 1 + src/librustrt/mutex.rs | 2 + src/librustuv/idle.rs | 2 - src/librustuv/net.rs | 2 - src/librustuv/uvll.rs | 1 + src/libstd/collections/hashmap.rs | 5 +- src/libstd/rt/backtrace.rs | 1 + src/libstd/task.rs | 4 +- src/libsync/raw.rs | 8 ++-- src/libsyntax/ext/build.rs | 15 ++---- src/libsyntax/print/pprust.rs | 5 -- src/test/compile-fail/lint-dead-code-1.rs | 6 ++- .../compile-fail/lint-managed-heap-memory.rs | 1 + .../compile-fail/lint-owned-heap-memory.rs | 1 + .../compile-fail/lint-uppercase-variables.rs | 1 + 35 files changed, 61 insertions(+), 146 deletions(-) diff --git a/src/libglob/lib.rs b/src/libglob/lib.rs index f3e1da77ce5..6d39a332ad9 100644 --- a/src/libglob/lib.rs +++ b/src/libglob/lib.rs @@ -44,7 +44,6 @@ use std::string::String; * pattern - see the `glob` function for more details. */ pub struct Paths { - root: Path, dir_patterns: Vec, require_dir: bool, options: MatchOptions, @@ -108,7 +107,6 @@ pub fn glob_with(pattern: &str, options: MatchOptions) -> Paths { // FIXME: How do we want to handle verbatim paths? I'm inclined to return nothing, // since we can't very well find all UNC shares with a 1-letter server name. return Paths { - root: root, dir_patterns: Vec::new(), require_dir: false, options: options, @@ -134,7 +132,6 @@ pub fn glob_with(pattern: &str, options: MatchOptions) -> Paths { } Paths { - root: root, dir_patterns: dir_patterns, require_dir: require_dir, options: options, diff --git a/src/libnative/io/mod.rs b/src/libnative/io/mod.rs index 3b0dbe2d0dc..1ecf7e57023 100644 --- a/src/libnative/io/mod.rs +++ b/src/libnative/io/mod.rs @@ -152,13 +152,13 @@ fn keep_going(data: &[u8], f: |*u8, uint| -> i64) -> i64 { /// Implementation of rt::rtio's IoFactory trait to generate handles to the /// native I/O functionality. pub struct IoFactory { - cannot_construct_outside_of_this_module: () + _cannot_construct_outside_of_this_module: () } impl IoFactory { pub fn new() -> IoFactory { net::init(); - IoFactory { cannot_construct_outside_of_this_module: () } + IoFactory { _cannot_construct_outside_of_this_module: () } } } diff --git a/src/libnative/io/net.rs b/src/libnative/io/net.rs index 24956e514ec..e7effbd6bdb 100644 --- a/src/libnative/io/net.rs +++ b/src/libnative/io/net.rs @@ -254,7 +254,10 @@ pub struct TcpStream { struct Inner { fd: sock_t, - lock: mutex::NativeMutex, + + // Unused on Linux, where this lock is not necessary. + #[allow(dead_code)] + lock: mutex::NativeMutex } pub struct Guard<'a> { diff --git a/src/libnative/io/pipe_unix.rs b/src/libnative/io/pipe_unix.rs index 7a1134fbe59..1458b475ae9 100644 --- a/src/libnative/io/pipe_unix.rs +++ b/src/libnative/io/pipe_unix.rs @@ -58,7 +58,10 @@ fn addr_to_sockaddr_un(addr: &CString) -> IoResult<(libc::sockaddr_storage, uint struct Inner { fd: fd_t, - lock: mutex::NativeMutex, + + // Unused on Linux, where this lock is not necessary. + #[allow(dead_code)] + lock: mutex::NativeMutex } impl Inner { diff --git a/src/librand/distributions/gamma.rs b/src/librand/distributions/gamma.rs index cfabf2b08e2..b1a95149830 100644 --- a/src/librand/distributions/gamma.rs +++ b/src/librand/distributions/gamma.rs @@ -81,7 +81,6 @@ struct GammaSmallShape { /// See `Gamma` for sampling from a Gamma distribution with general /// shape parameters. struct GammaLargeShape { - shape: f64, scale: f64, c: f64, d: f64 @@ -118,7 +117,6 @@ impl GammaLargeShape { fn new_raw(shape: f64, scale: f64) -> GammaLargeShape { let d = shape - 1. / 3.; GammaLargeShape { - shape: shape, scale: scale, c: 1. / (9. * d).sqrt(), d: d diff --git a/src/librustc/front/std_inject.rs b/src/librustc/front/std_inject.rs index fe636f7b686..cf23a34d08c 100644 --- a/src/librustc/front/std_inject.rs +++ b/src/librustc/front/std_inject.rs @@ -130,9 +130,7 @@ fn inject_crates_ref(sess: &Session, krate: ast::Crate) -> ast::Crate { fold.fold_crate(krate) } -struct PreludeInjector<'a> { - sess: &'a Session, -} +struct PreludeInjector<'a>; impl<'a> fold::Folder for PreludeInjector<'a> { @@ -223,9 +221,7 @@ impl<'a> fold::Folder for PreludeInjector<'a> { } } -fn inject_prelude(sess: &Session, krate: ast::Crate) -> ast::Crate { - let mut fold = PreludeInjector { - sess: sess, - }; +fn inject_prelude(_: &Session, krate: ast::Crate) -> ast::Crate { + let mut fold = PreludeInjector; fold.fold_crate(krate) } diff --git a/src/librustc/metadata/loader.rs b/src/librustc/metadata/loader.rs index acd96b94f31..cfda97ad26f 100644 --- a/src/librustc/metadata/loader.rs +++ b/src/librustc/metadata/loader.rs @@ -86,7 +86,7 @@ pub struct Library { } pub struct ArchiveMetadata { - archive: ArchiveRO, + _archive: ArchiveRO, // See comments in ArchiveMetadata::new for why this is static data: &'static [u8], } @@ -487,7 +487,7 @@ impl ArchiveMetadata { unsafe { mem::transmute(data) } }; Some(ArchiveMetadata { - archive: ar, + _archive: ar, data: data, }) } diff --git a/src/librustc/metadata/tyencode.rs b/src/librustc/metadata/tyencode.rs index f48dbecc530..363fcf79eb5 100644 --- a/src/librustc/metadata/tyencode.rs +++ b/src/librustc/metadata/tyencode.rs @@ -42,8 +42,6 @@ pub struct ctxt<'a> { // Extra parameters are for converting to/from def_ids in the string rep. // Whatever format you choose should not contain pipe characters. pub struct ty_abbrev { - pos: uint, - len: uint, s: String } @@ -68,8 +66,6 @@ pub fn enc_ty(w: &mut MemWriter, cx: &ctxt, t: ty::t) { if abbrev_len < len { // I.e. it's actually an abbreviation. cx.abbrevs.borrow_mut().insert(t, ty_abbrev { - pos: pos as uint, - len: len as uint, s: format!("\\#{:x}:{:x}\\#", pos, len) }); } diff --git a/src/librustc/middle/borrowck/gather_loans/lifetime.rs b/src/librustc/middle/borrowck/gather_loans/lifetime.rs index 3337a56edf0..dc8567af9ed 100644 --- a/src/librustc/middle/borrowck/gather_loans/lifetime.rs +++ b/src/librustc/middle/borrowck/gather_loans/lifetime.rs @@ -29,7 +29,7 @@ pub fn guarantee_lifetime(bccx: &BorrowckCtxt, cause: euv::LoanCause, cmt: mc::cmt, loan_region: ty::Region, - loan_kind: ty::BorrowKind) + _: ty::BorrowKind) -> Result<(),()> { debug!("guarantee_lifetime(cmt={}, loan_region={})", cmt.repr(bccx.tcx), loan_region.repr(bccx.tcx)); @@ -38,7 +38,6 @@ pub fn guarantee_lifetime(bccx: &BorrowckCtxt, span: span, cause: cause, loan_region: loan_region, - loan_kind: loan_kind, cmt_original: cmt.clone()}; ctxt.check(&cmt, None) } @@ -55,7 +54,6 @@ struct GuaranteeLifetimeContext<'a> { span: Span, cause: euv::LoanCause, loan_region: ty::Region, - loan_kind: ty::BorrowKind, cmt_original: mc::cmt } diff --git a/src/librustc/middle/borrowck/gather_loans/mod.rs b/src/librustc/middle/borrowck/gather_loans/mod.rs index 003687e7b63..ec362f92441 100644 --- a/src/librustc/middle/borrowck/gather_loans/mod.rs +++ b/src/librustc/middle/borrowck/gather_loans/mod.rs @@ -310,7 +310,6 @@ impl<'a> GatherLoanCtxt<'a> { Loan { index: self.all_loans.len(), loan_path: loan_path, - cmt: cmt, kind: req_kind, gen_scope: gen_scope, kill_scope: kill_scope, @@ -481,8 +480,7 @@ impl<'a> GatherLoanCtxt<'a> { /// This visitor walks static initializer's expressions and makes /// sure the loans being taken are sound. struct StaticInitializerCtxt<'a> { - bccx: &'a BorrowckCtxt<'a>, - item_ub: ast::NodeId, + bccx: &'a BorrowckCtxt<'a> } impl<'a> visit::Visitor<()> for StaticInitializerCtxt<'a> { @@ -509,8 +507,7 @@ pub fn gather_loans_in_static_initializer(bccx: &mut BorrowckCtxt, expr: &ast::E debug!("gather_loans_in_static_initializer(expr={})", expr.repr(bccx.tcx)); let mut sicx = StaticInitializerCtxt { - bccx: bccx, - item_ub: expr.id, + bccx: bccx }; sicx.visit_expr(expr, ()); diff --git a/src/librustc/middle/borrowck/gather_loans/restrictions.rs b/src/librustc/middle/borrowck/gather_loans/restrictions.rs index 552381e4216..7c1f5937472 100644 --- a/src/librustc/middle/borrowck/gather_loans/restrictions.rs +++ b/src/librustc/middle/borrowck/gather_loans/restrictions.rs @@ -36,7 +36,6 @@ pub fn compute_restrictions(bccx: &BorrowckCtxt, bccx: bccx, span: span, cause: cause, - cmt_original: cmt.clone(), loan_region: loan_region, }; @@ -49,7 +48,6 @@ pub fn compute_restrictions(bccx: &BorrowckCtxt, struct RestrictionsContext<'a> { bccx: &'a BorrowckCtxt<'a>, span: Span, - cmt_original: mc::cmt, loan_region: ty::Region, cause: euv::LoanCause, } diff --git a/src/librustc/middle/borrowck/mod.rs b/src/librustc/middle/borrowck/mod.rs index 5706d249c46..7aaba22dd84 100644 --- a/src/librustc/middle/borrowck/mod.rs +++ b/src/librustc/middle/borrowck/mod.rs @@ -180,7 +180,6 @@ pub enum PartialTotal { pub struct Loan { index: uint, loan_path: Rc, - cmt: mc::cmt, kind: ty::BorrowKind, restrictions: Vec, gen_scope: ast::NodeId, diff --git a/src/librustc/middle/liveness.rs b/src/librustc/middle/liveness.rs index 8b1de130053..cf3d6983dfb 100644 --- a/src/librustc/middle/liveness.rs +++ b/src/librustc/middle/liveness.rs @@ -225,21 +225,12 @@ fn invalid_node() -> LiveNode { LiveNode(uint::MAX) } struct CaptureInfo { ln: LiveNode, - is_move: bool, var_nid: NodeId } -enum LocalKind { - FromMatch(BindingMode), - FromLetWithInitializer, - FromLetNoInitializer -} - struct LocalInfo { id: NodeId, - ident: Ident, - is_mutbl: bool, - kind: LocalKind, + ident: Ident } enum VarKind { @@ -405,23 +396,13 @@ fn visit_fn(ir: &mut IrMaps, } fn visit_local(ir: &mut IrMaps, local: &Local) { - pat_util::pat_bindings(&ir.tcx.def_map, local.pat, |bm, p_id, sp, path| { + pat_util::pat_bindings(&ir.tcx.def_map, local.pat, |_, p_id, sp, path| { debug!("adding local variable {}", p_id); let name = ast_util::path_to_ident(path); ir.add_live_node_for_node(p_id, VarDefNode(sp)); - let kind = match local.init { - Some(_) => FromLetWithInitializer, - None => FromLetNoInitializer - }; - let mutbl = match bm { - BindByValue(MutMutable) => true, - _ => false - }; ir.add_variable(Local(LocalInfo { id: p_id, - ident: name, - is_mutbl: mutbl, - kind: kind + ident: name })); }); visit::walk_local(ir, local, ()); @@ -433,16 +414,10 @@ fn visit_arm(ir: &mut IrMaps, arm: &Arm) { debug!("adding local variable {} from match with bm {:?}", p_id, bm); let name = ast_util::path_to_ident(path); - let mutbl = match bm { - BindByValue(MutMutable) => true, - _ => false - }; ir.add_live_node_for_node(p_id, VarDefNode(sp)); ir.add_variable(Local(LocalInfo { id: p_id, - ident: name, - is_mutbl: mutbl, - kind: FromMatch(bm) + ident: name })); }) } @@ -480,27 +455,12 @@ fn visit_expr(ir: &mut IrMaps, expr: &Expr) { // in better error messages than just pointing at the closure // construction site. let mut call_caps = Vec::new(); - let fv_mode = freevars::get_capture_mode(ir.tcx, expr.id); freevars::with_freevars(ir.tcx, expr.id, |freevars| { for fv in freevars.iter() { match moved_variable_node_id_from_def(fv.def) { Some(rv) => { let fv_ln = ir.add_live_node(FreeVarNode(fv.span)); - let fv_id = fv.def.def_id().node; - let fv_ty = ty::node_id_to_type(ir.tcx, fv_id); - let is_move = match fv_mode { - // var must be dead afterwards - freevars::CaptureByValue => { - ty::type_moves_by_default(ir.tcx, fv_ty) - } - - // var can still be used - freevars::CaptureByRef => { - false - } - }; call_caps.push(CaptureInfo {ln: fv_ln, - is_move: is_move, var_nid: rv}); } None => {} diff --git a/src/librustc/middle/privacy.rs b/src/librustc/middle/privacy.rs index fcd6d424659..50cbf6bbaf0 100644 --- a/src/librustc/middle/privacy.rs +++ b/src/librustc/middle/privacy.rs @@ -353,7 +353,6 @@ impl<'a> Visitor<()> for EmbargoVisitor<'a> { struct PrivacyVisitor<'a> { tcx: &'a ty::ctxt, curitem: ast::NodeId, - in_fn: bool, in_foreign: bool, parents: NodeMap, external_exports: resolve::ExternalExports, @@ -1445,7 +1444,6 @@ pub fn check_crate(tcx: &ty::ctxt, // Use the parent map to check the privacy of everything let mut visitor = PrivacyVisitor { curitem: ast::DUMMY_NODE_ID, - in_fn: false, in_foreign: false, tcx: tcx, parents: visitor.parents, diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 9bfa0e10aed..a700c3a0902 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -806,7 +806,6 @@ fn namespace_error_to_str(ns: NamespaceError) -> &'static str { /// The main resolver class. struct Resolver<'a> { session: &'a Session, - lang_items: &'a LanguageItems, graph_root: NameBindings, @@ -843,9 +842,6 @@ struct Resolver<'a> { // The idents for the primitive types. primitive_type_table: PrimitiveTypeTable, - // The four namespaces. - namespaces: Vec , - def_map: DefMap, export_map2: ExportMap2, trait_map: TraitMap, @@ -902,7 +898,7 @@ impl<'a, 'b> Visitor<()> for UnusedImportCheckVisitor<'a, 'b> { } impl<'a> Resolver<'a> { - fn new(session: &'a Session, lang_items: &'a LanguageItems, crate_span: Span) -> Resolver<'a> { + fn new(session: &'a Session, crate_span: Span) -> Resolver<'a> { let graph_root = NameBindings::new(); graph_root.define_module(NoParentLink, @@ -916,7 +912,6 @@ impl<'a> Resolver<'a> { Resolver { session: session, - lang_items: lang_items, // The outermost module has def ID 0; this is not reflected in the // AST. @@ -941,8 +936,6 @@ impl<'a> Resolver<'a> { primitive_type_table: PrimitiveTypeTable::new(), - namespaces: vec!(TypeNS, ValueNS), - def_map: RefCell::new(NodeMap::new()), export_map2: RefCell::new(NodeMap::new()), trait_map: NodeMap::new(), @@ -5576,10 +5569,10 @@ pub struct CrateMap { /// Entry point to crate resolution. pub fn resolve_crate(session: &Session, - lang_items: &LanguageItems, + _: &LanguageItems, krate: &Crate) -> CrateMap { - let mut resolver = Resolver::new(session, lang_items, krate.span); + let mut resolver = Resolver::new(session, krate.span); resolver.resolve(krate); let Resolver { def_map, export_map2, trait_map, last_private, external_exports, .. } = resolver; diff --git a/src/librustc/middle/trans/base.rs b/src/librustc/middle/trans/base.rs index 09f5d2a3507..1cc490bf8f8 100644 --- a/src/librustc/middle/trans/base.rs +++ b/src/librustc/middle/trans/base.rs @@ -106,7 +106,9 @@ pub fn init_insn_ctxt() { task_local_insn_key.replace(Some(RefCell::new(Vec::new()))); } -pub struct _InsnCtxt { _x: () } +pub struct _InsnCtxt { + _cannot_construct_outside_of_this_module: () +} #[unsafe_destructor] impl Drop for _InsnCtxt { @@ -124,7 +126,7 @@ pub fn push_ctxt(s: &'static str) -> _InsnCtxt { Some(ctx) => ctx.borrow_mut().push(s), None => {} } - _InsnCtxt { _x: () } + _InsnCtxt { _cannot_construct_outside_of_this_module: () } } pub struct StatRecorder<'a> { diff --git a/src/librustc/middle/trans/foreign.rs b/src/librustc/middle/trans/foreign.rs index 6f217d83a62..565fa88bf43 100644 --- a/src/librustc/middle/trans/foreign.rs +++ b/src/librustc/middle/trans/foreign.rs @@ -64,9 +64,6 @@ struct LlvmSignature { // function, because the foreign function may opt to return via an // out pointer. llret_ty: Type, - - // True if *Rust* would use an outpointer for this function. - sret: bool, } @@ -847,8 +844,7 @@ fn foreign_signature(ccx: &CrateContext, fn_sig: &ty::FnSig, arg_tys: &[ty::t]) let llret_ty = type_of::type_of(ccx, fn_sig.output); LlvmSignature { llarg_tys: llarg_tys, - llret_ty: llret_ty, - sret: type_of::return_uses_outptr(ccx, fn_sig.output), + llret_ty: llret_ty } } diff --git a/src/librustc/middle/typeck/coherence.rs b/src/librustc/middle/typeck/coherence.rs index 99a6aad715c..2c059318478 100644 --- a/src/librustc/middle/typeck/coherence.rs +++ b/src/librustc/middle/typeck/coherence.rs @@ -52,9 +52,7 @@ use std::cell::RefCell; use std::rc::Rc; struct UniversalQuantificationResult { - monotype: t, - type_variables: Vec , - type_param_defs: Rc > + monotype: t } fn get_base_type(inference_context: &InferCtxt, @@ -515,9 +513,7 @@ impl<'a> CoherenceChecker<'a> { let monotype = polytype.ty.subst(self.crate_context.tcx, &substitutions); UniversalQuantificationResult { - monotype: monotype, - type_variables: substitutions.tps, - type_param_defs: polytype.generics.type_param_defs.clone() + monotype: monotype } } diff --git a/src/librustc/middle/typeck/variance.rs b/src/librustc/middle/typeck/variance.rs index 04244ff31a8..92ebf42c7af 100644 --- a/src/librustc/middle/typeck/variance.rs +++ b/src/librustc/middle/typeck/variance.rs @@ -271,7 +271,6 @@ enum ParamKind { TypeParam, RegionParam, SelfParam } struct InferredInfo<'a> { item_id: ast::NodeId, kind: ParamKind, - index: uint, param_id: ast::NodeId, term: VarianceTermPtr<'a>, } @@ -310,7 +309,6 @@ impl<'a> TermsContext<'a> { let term = self.arena.alloc(|| InferredTerm(inf_index)); self.inferred_infos.push(InferredInfo { item_id: item_id, kind: kind, - index: index, param_id: param_id, term: term }); let newly_added = self.inferred_map.insert(param_id, inf_index); diff --git a/src/librustc/util/common.rs b/src/librustc/util/common.rs index 5ddae0c1bfe..08052c03de4 100644 --- a/src/librustc/util/common.rs +++ b/src/librustc/util/common.rs @@ -42,23 +42,17 @@ pub fn indent(op: || -> R) -> R { r } -pub struct _indenter { - _i: (), +pub struct Indenter { + _cannot_construct_outside_of_this_module: () } -impl Drop for _indenter { +impl Drop for Indenter { fn drop(&mut self) { debug!("<<"); } } -pub fn _indenter(_i: ()) -> _indenter { - _indenter { - _i: () - } -} - -pub fn indenter() -> _indenter { +pub fn indenter() -> Indenter { debug!(">>"); - _indenter(()) + Indenter { _cannot_construct_outside_of_this_module: () } } struct LoopQueryVisitor<'a> { diff --git a/src/librustdoc/html/markdown.rs b/src/librustdoc/html/markdown.rs index 260d26c5437..061c05058ae 100644 --- a/src/librustdoc/html/markdown.rs +++ b/src/librustdoc/html/markdown.rs @@ -24,6 +24,7 @@ //! // ... something using html //! ``` +#![allow(dead_code)] #![allow(non_camel_case_types)] use libc; diff --git a/src/librustrt/mutex.rs b/src/librustrt/mutex.rs index fccbe4a15e9..c2bf04917d2 100644 --- a/src/librustrt/mutex.rs +++ b/src/librustrt/mutex.rs @@ -339,10 +339,12 @@ mod imp { #[cfg(target_arch = "mips")] static __SIZEOF_PTHREAD_COND_T: uint = 48 - 8; + #[repr(C)] pub struct pthread_mutex_t { __align: libc::c_longlong, size: [u8, ..__SIZEOF_PTHREAD_MUTEX_T], } + #[repr(C)] pub struct pthread_cond_t { __align: libc::c_longlong, size: [u8, ..__SIZEOF_PTHREAD_COND_T], diff --git a/src/librustuv/idle.rs b/src/librustuv/idle.rs index f5cde39bc83..fe8935db2ec 100644 --- a/src/librustuv/idle.rs +++ b/src/librustuv/idle.rs @@ -18,7 +18,6 @@ use std::rt::rtio::{Callback, PausableIdleCallback}; pub struct IdleWatcher { handle: *uvll::uv_idle_t, idle_flag: bool, - closed: bool, callback: Box, } @@ -31,7 +30,6 @@ impl IdleWatcher { let me = box IdleWatcher { handle: handle, idle_flag: false, - closed: false, callback: cb, }; return me.install(); diff --git a/src/librustuv/net.rs b/src/librustuv/net.rs index e7bdc25a1fd..47b321b068b 100644 --- a/src/librustuv/net.rs +++ b/src/librustuv/net.rs @@ -165,7 +165,6 @@ pub struct TcpWatcher { pub struct TcpListener { home: HomeHandle, handle: *uvll::uv_pipe_t, - closing_task: Option, outgoing: Sender, IoError>>, incoming: Receiver, IoError>>, } @@ -358,7 +357,6 @@ impl TcpListener { let l = box TcpListener { home: io.make_handle(), handle: handle, - closing_task: None, outgoing: tx, incoming: rx, }; diff --git a/src/librustuv/uvll.rs b/src/librustuv/uvll.rs index f6c6d6c9068..a6193dd9379 100644 --- a/src/librustuv/uvll.rs +++ b/src/librustuv/uvll.rs @@ -136,6 +136,7 @@ pub struct uv_process_options_t { // These fields are private because they must be interfaced with through the // functions below. +#[repr(C)] pub struct uv_stdio_container_t { flags: libc::c_int, stream: *uv_stream_t, diff --git a/src/libstd/collections/hashmap.rs b/src/libstd/collections/hashmap.rs index 571c5794704..99544f2ff3b 100644 --- a/src/libstd/collections/hashmap.rs +++ b/src/libstd/collections/hashmap.rs @@ -393,7 +393,7 @@ mod table { } pub fn move_iter(self) -> MoveEntries { - MoveEntries { table: self, idx: 0, elems_seen: 0 } + MoveEntries { table: self, idx: 0 } } } @@ -428,8 +428,7 @@ mod table { /// Iterator over the entries in a table, consuming the table. pub struct MoveEntries { table: RawTable, - idx: uint, - elems_seen: uint, + idx: uint } impl<'a, K, V> Iterator<(&'a K, &'a V)> for Entries<'a, K, V> { diff --git a/src/libstd/rt/backtrace.rs b/src/libstd/rt/backtrace.rs index 766901fa04f..f1717c3a2ba 100644 --- a/src/libstd/rt/backtrace.rs +++ b/src/libstd/rt/backtrace.rs @@ -325,6 +325,7 @@ mod imp { #[cfg(target_os = "macos")] fn print(w: &mut Writer, idx: int, addr: *libc::c_void) -> IoResult<()> { use intrinsics; + #[repr(C)] struct Dl_info { dli_fname: *libc::c_char, dli_fbase: *libc::c_void, diff --git a/src/libstd/task.rs b/src/libstd/task.rs index 9ee62ee3d81..a4e1ad84252 100644 --- a/src/libstd/task.rs +++ b/src/libstd/task.rs @@ -84,7 +84,7 @@ pub struct TaskBuilder { /// Options to spawn the new task with pub opts: TaskOpts, gen_body: Option proc():Send>, - nocopy: Option, + nocopy: marker::NoCopy, } impl TaskBuilder { @@ -94,7 +94,7 @@ impl TaskBuilder { TaskBuilder { opts: TaskOpts::new(), gen_body: None, - nocopy: None, + nocopy: marker::NoCopy, } } diff --git a/src/libsync/raw.rs b/src/libsync/raw.rs index 8fd10cdfa8b..821afeaa1f2 100644 --- a/src/libsync/raw.rs +++ b/src/libsync/raw.rs @@ -355,7 +355,7 @@ pub struct Semaphore { /// dropped, this value will release the resource back to the semaphore. #[must_use] pub struct SemaphoreGuard<'a> { - guard: SemGuard<'a, ()>, + _guard: SemGuard<'a, ()>, } impl Semaphore { @@ -375,7 +375,7 @@ impl Semaphore { /// Acquire a resource of this semaphore, returning an RAII guard which will /// release the resource when dropped. pub fn access<'a>(&'a self) -> SemaphoreGuard<'a> { - SemaphoreGuard { guard: self.sem.access() } + SemaphoreGuard { _guard: self.sem.access() } } } @@ -398,7 +398,7 @@ pub struct Mutex { /// corresponding mutex is also unlocked. #[must_use] pub struct MutexGuard<'a> { - guard: SemGuard<'a, Vec>, + _guard: SemGuard<'a, Vec>, /// Inner condition variable which is connected to the outer mutex, and can /// be used for atomic-unlock-and-deschedule. pub cond: Condvar<'a>, @@ -421,7 +421,7 @@ impl Mutex { /// also be accessed through the returned guard. pub fn lock<'a>(&'a self) -> MutexGuard<'a> { let SemCondGuard { guard, cvar } = self.sem.access_cond(); - MutexGuard { guard: guard, cond: cvar } + MutexGuard { _guard: guard, cond: cvar } } } diff --git a/src/libsyntax/ext/build.rs b/src/libsyntax/ext/build.rs index 7b25f4db980..14769e3e510 100644 --- a/src/libsyntax/ext/build.rs +++ b/src/libsyntax/ext/build.rs @@ -21,11 +21,6 @@ use parse::token::special_idents; use parse::token::InternedString; use parse::token; -pub struct Field { - ident: ast::Ident, - ex: @ast::Expr -} - // Transitional reexports so qquote can find the paths it is looking for mod syntax { pub use ext; @@ -1000,9 +995,7 @@ impl<'a> AstBuilder for ExtCtxt<'a> { } } -struct Duplicator<'a> { - cx: &'a ExtCtxt<'a>, -} +struct Duplicator<'a>; impl<'a> Folder for Duplicator<'a> { fn new_id(&mut self, _: NodeId) -> NodeId { @@ -1021,10 +1014,8 @@ pub trait Duplicate { } impl Duplicate for @ast::Expr { - fn duplicate(&self, cx: &ExtCtxt) -> @ast::Expr { - let mut folder = Duplicator { - cx: cx, - }; + fn duplicate(&self, _: &ExtCtxt) -> @ast::Expr { + let mut folder = Duplicator; folder.fold_expr(*self) } } diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index 05c2558da48..a4518617d3d 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -19,7 +19,6 @@ use codemap::{CodeMap, BytePos}; use codemap; use diagnostic; use parse::classify::expr_is_simple_block; -use parse::token::IdentInterner; use parse::token; use parse::lexer::comments; use parse; @@ -30,7 +29,6 @@ use print::pp; use std::io::{IoResult, MemWriter}; use std::io; use std::mem; -use std::rc::Rc; use std::str; use std::string::String; @@ -58,7 +56,6 @@ pub struct CurrentCommentAndLiteral { pub struct State<'a> { pub s: pp::Printer, cm: Option<&'a CodeMap>, - intr: Rc, comments: Option >, literals: Option >, cur_cmnt_and_lit: CurrentCommentAndLiteral, @@ -76,7 +73,6 @@ pub fn rust_printer_annotated<'a>(writer: Box, State { s: pp::mk_printer(writer, default_columns), cm: None, - intr: token::get_ident_interner(), comments: None, literals: None, cur_cmnt_and_lit: CurrentCommentAndLiteral { @@ -111,7 +107,6 @@ pub fn print_crate<'a>(cm: &'a CodeMap, let mut s = State { s: pp::mk_printer(out, default_columns), cm: Some(cm), - intr: token::get_ident_interner(), comments: Some(cmnts), // If the code is post expansion, don't use the table of // literals, since it doesn't correspond with the literals diff --git a/src/test/compile-fail/lint-dead-code-1.rs b/src/test/compile-fail/lint-dead-code-1.rs index 10734f1f243..bca2a5d7edc 100644 --- a/src/test/compile-fail/lint-dead-code-1.rs +++ b/src/test/compile-fail/lint-dead-code-1.rs @@ -39,7 +39,10 @@ static STATIC_USED_IN_ENUM_DISCRIMINANT: uint = 10; pub type typ = *UsedStruct4; pub struct PubStruct(); struct PrivStruct; //~ ERROR: code is never used -struct UsedStruct1 { x: int } +struct UsedStruct1 { + #[allow(dead_code)] + x: int +} struct UsedStruct2(int); struct UsedStruct3; struct UsedStruct4; @@ -53,6 +56,7 @@ struct StructUsedAsField; struct StructUsedInEnum; struct StructUsedInGeneric; pub struct PubStruct2 { + #[allow(dead_code)] struct_used_as_field: *StructUsedAsField } diff --git a/src/test/compile-fail/lint-managed-heap-memory.rs b/src/test/compile-fail/lint-managed-heap-memory.rs index d9a79d75975..ff382cb46c7 100644 --- a/src/test/compile-fail/lint-managed-heap-memory.rs +++ b/src/test/compile-fail/lint-managed-heap-memory.rs @@ -8,6 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. +#![allow(dead_code)] #![feature(managed_boxes)] #![forbid(managed_heap_memory)] diff --git a/src/test/compile-fail/lint-owned-heap-memory.rs b/src/test/compile-fail/lint-owned-heap-memory.rs index c9688ad49d7..8f20999a56c 100644 --- a/src/test/compile-fail/lint-owned-heap-memory.rs +++ b/src/test/compile-fail/lint-owned-heap-memory.rs @@ -8,6 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. +#![allow(dead_code)] #![forbid(owned_heap_memory)] diff --git a/src/test/compile-fail/lint-uppercase-variables.rs b/src/test/compile-fail/lint-uppercase-variables.rs index 386b4019485..f1b36d719e9 100644 --- a/src/test/compile-fail/lint-uppercase-variables.rs +++ b/src/test/compile-fail/lint-uppercase-variables.rs @@ -8,6 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. +#![allow(dead_code)] #![deny(uppercase_variables)] use std::io::File; From 135625df96733dae77544de7abb2eae71f4946fc Mon Sep 17 00:00:00 2001 From: Jakub Wieczorek Date: Sun, 8 Jun 2014 21:55:17 +0200 Subject: [PATCH 3/4] Mark relevant structs with repr(C) --- src/libgreen/context.rs | 1 + src/libnative/io/c_win32.rs | 2 ++ 2 files changed, 3 insertions(+) diff --git a/src/libgreen/context.rs b/src/libgreen/context.rs index 5b1a4a8b80e..e377c203e30 100644 --- a/src/libgreen/context.rs +++ b/src/libgreen/context.rs @@ -143,6 +143,7 @@ extern { // stacks are disabled. #[cfg(target_arch = "x86")] +#[repr(C)] struct Registers { eax: u32, ebx: u32, ecx: u32, edx: u32, ebp: u32, esi: u32, edi: u32, esp: u32, diff --git a/src/libnative/io/c_win32.rs b/src/libnative/io/c_win32.rs index 93b3ec7ccef..a783a9b1243 100644 --- a/src/libnative/io/c_win32.rs +++ b/src/libnative/io/c_win32.rs @@ -20,6 +20,7 @@ pub static FIONBIO: libc::c_long = 0x8004667e; static FD_SETSIZE: uint = 64; pub static MSG_DONTWAIT: libc::c_int = 0; +#[repr(C)] pub struct WSADATA { pub wVersion: libc::WORD, pub wHighVersion: libc::WORD, @@ -32,6 +33,7 @@ pub struct WSADATA { pub type LPWSADATA = *mut WSADATA; +#[repr(C)] pub struct fd_set { fd_count: libc::c_uint, fd_array: [libc::SOCKET, ..FD_SETSIZE], From 8e34f647ee5db795e1ea46715de61cee63f4f4a7 Mon Sep 17 00:00:00 2001 From: Jakub Wieczorek Date: Mon, 9 Jun 2014 22:14:51 +0200 Subject: [PATCH 4/4] Add missing repr(C) annotations to mutex.rs --- src/librustrt/mutex.rs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/librustrt/mutex.rs b/src/librustrt/mutex.rs index c2bf04917d2..eec19e9d5db 100644 --- a/src/librustrt/mutex.rs +++ b/src/librustrt/mutex.rs @@ -298,10 +298,12 @@ mod imp { static _PTHREAD_MUTEX_SIG_init: libc::c_long = 0x32AAABA7; static _PTHREAD_COND_SIG_init: libc::c_long = 0x3CB0B1BB; + #[repr(C)] pub struct pthread_mutex_t { __sig: libc::c_long, __opaque: [u8, ..__PTHREAD_MUTEX_SIZE__], } + #[repr(C)] pub struct pthread_cond_t { __sig: libc::c_long, __opaque: [u8, ..__PTHREAD_COND_SIZE__], @@ -363,7 +365,9 @@ mod imp { mod os { use libc; + #[repr(C)] pub struct pthread_mutex_t { value: libc::c_int } + #[repr(C)] pub struct pthread_cond_t { value: libc::c_int } pub static PTHREAD_MUTEX_INITIALIZER: pthread_mutex_t = pthread_mutex_t {