diff --git a/src/librustdoc/clean/inline.rs b/src/librustdoc/clean/inline.rs index e13b2688788..36eb1a1301c 100644 --- a/src/librustdoc/clean/inline.rs +++ b/src/librustdoc/clean/inline.rs @@ -20,6 +20,7 @@ use rustc::hir; use rustc::middle::cstore::{self, CrateStore}; use rustc::hir::def::Def; use rustc::hir::def_id::DefId; +use rustc::hir::print as pprust; use rustc::ty::{self, TyCtxt}; use rustc::ty::subst; use rustc::middle::stability; @@ -30,7 +31,7 @@ use core::{DocContext, DocAccessLevels}; use doctree; use clean::{self, GetDefId}; -use super::{Clean, ToSource}; +use super::Clean; /// Attempt to inline the definition of a local node id into this AST. /// @@ -333,8 +334,8 @@ pub fn build_impl(cx: &DocContext, let did = assoc_const.def_id; let type_scheme = tcx.lookup_item_type(did); let default = if assoc_const.has_value { - Some(lookup_const_by_id(tcx, did, None) - .unwrap().0.span.to_src(cx)) + Some(pprust::expr_to_string( + lookup_const_by_id(tcx, did, None).unwrap().0)) } else { None }; @@ -479,8 +480,6 @@ fn build_module(cx: &DocContext, tcx: &TyCtxt, fn build_const(cx: &DocContext, tcx: &TyCtxt, did: DefId) -> clean::Constant { - use rustc::hir::print as pprust; - let (expr, ty) = lookup_const_by_id(tcx, did, None).unwrap_or_else(|| { panic!("expected lookup_const_by_id to succeed for {:?}", did); }); diff --git a/src/librustdoc/clean/mod.rs b/src/librustdoc/clean/mod.rs index 35922c477cc..0a606e1425c 100644 --- a/src/librustdoc/clean/mod.rs +++ b/src/librustdoc/clean/mod.rs @@ -39,6 +39,7 @@ use rustc::middle::cstore::{self, CrateStore}; use rustc::middle::privacy::AccessLevels; use rustc::hir::def::Def; use rustc::hir::def_id::{DefId, DefIndex, CRATE_DEF_INDEX}; +use rustc::hir::print as pprust; use rustc::ty::subst::{self, ParamSpace, VecPerParamSpace}; use rustc::ty; use rustc::middle::stability; @@ -1285,8 +1286,7 @@ impl Clean for hir::TraitItem { let inner = match self.node { hir::ConstTraitItem(ref ty, ref default) => { AssociatedConstItem(ty.clean(cx), - default.as_ref().map(|expr| - expr.span.to_src(cx))) + default.as_ref().map(|e| pprust::expr_to_string(&e))) } hir::MethodTraitItem(ref sig, Some(_)) => { MethodItem(sig.clean(cx)) @@ -1316,7 +1316,7 @@ impl Clean for hir::ImplItem { let inner = match self.node { hir::ImplItemKind::Const(ref ty, ref expr) => { AssociatedConstItem(ty.clean(cx), - Some(expr.span.to_src(cx))) + Some(pprust::expr_to_string(expr))) } hir::ImplItemKind::Method(ref sig, _) => { MethodItem(sig.clean(cx)) @@ -1635,8 +1635,8 @@ impl Clean for hir::Ty { BorrowedRef {lifetime: l.clean(cx), mutability: m.mutbl.clean(cx), type_: box m.ty.clean(cx)}, TyVec(ref ty) => Vector(box ty.clean(cx)), - TyFixedLengthVec(ref ty, ref e) => FixedVector(box ty.clean(cx), - e.span.to_src(cx)), + TyFixedLengthVec(ref ty, ref e) => + FixedVector(box ty.clean(cx), pprust::expr_to_string(e)), TyTup(ref tys) => Tuple(tys.clean(cx)), TyPath(None, ref p) => { resolve_type(cx, p.clean(cx), self.id) @@ -2185,7 +2185,7 @@ impl Clean for doctree::Static { inner: StaticItem(Static { type_: self.type_.clean(cx), mutability: self.mutability.clean(cx), - expr: self.expr.span.to_src(cx), + expr: pprust::expr_to_string(&self.expr), }), } } @@ -2209,7 +2209,7 @@ impl Clean for doctree::Constant { deprecation: self.depr.clean(cx), inner: ConstantItem(Constant { type_: self.type_.clean(cx), - expr: self.expr.span.to_src(cx), + expr: pprust::expr_to_string(&self.expr), }), } } diff --git a/src/test/rustdoc/issue-33302.rs b/src/test/rustdoc/issue-33302.rs new file mode 100644 index 00000000000..b9188e8a4e9 --- /dev/null +++ b/src/test/rustdoc/issue-33302.rs @@ -0,0 +1,46 @@ +// Copyright 2016 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. + +// Ensure constant and array length values are not taken from source +// code, which wreaks havoc with macros. + +#![feature(associated_consts)] + +macro_rules! make { + ($n:expr) => { + pub struct S; + + // @has issue_33302/constant.CST.html \ + // '//pre[@class="rust const"]' 'pub const CST: i32 = 4 * 4' + pub const CST: i32 = ($n * $n); + // @has issue_33302/static.ST.html \ + // '//pre[@class="rust static"]' 'pub static ST: i32 = 4 * 4' + pub static ST: i32 = ($n * $n); + + pub trait T { + fn ignore(_: &X) {} + const C: X; + // @has issue_33302/trait.T.html \ + // '//*[@class="rust trait"]' 'const D: i32 = 4 * 4;' + // @has - '//*[@id="associatedconstant.D"]' 'const D: i32 = 4 * 4' + const D: i32 = ($n * $n); + } + + // @has issue_33302/struct.S.html \ + // '//h3[@class="impl"]' 'impl T<[i32; 4 * 4]> for S' + // @has - '//*[@id="associatedconstant.C"]' 'const C: [i32; 4 * 4] = [0; 4 * 4]' + // @has - '//*[@id="associatedconstant.D"]' 'const D: i32 = 4 * 4' + impl T<[i32; ($n * $n)]> for S { + const C: [i32; ($n * $n)] = [0; ($n * $n)]; + } + } +} + +make!(4);