save-analysis: add parent info to api dumps
The parent id is used for constructing rustdoc URLs by clients
This commit is contained in:
parent
4e4306c6df
commit
4dc7b585a2
7 changed files with 113 additions and 70 deletions
|
@ -248,7 +248,8 @@ fn keep_hygiene_data(sess: &Session) -> bool {
|
|||
fn keep_ast(sess: &Session) -> bool {
|
||||
sess.opts.debugging_opts.keep_ast ||
|
||||
sess.opts.debugging_opts.save_analysis ||
|
||||
sess.opts.debugging_opts.save_analysis_csv
|
||||
sess.opts.debugging_opts.save_analysis_csv ||
|
||||
sess.opts.debugging_opts.save_analysis_api
|
||||
}
|
||||
|
||||
/// The name used for source code that doesn't originate in a file
|
||||
|
|
|
@ -166,6 +166,7 @@ pub struct FunctionData {
|
|||
pub scope: NodeId,
|
||||
pub value: String,
|
||||
pub visibility: Visibility,
|
||||
pub parent: Option<NodeId>,
|
||||
}
|
||||
|
||||
/// Data about a function call.
|
||||
|
@ -292,7 +293,8 @@ pub struct StructVariantData {
|
|||
pub qualname: String,
|
||||
pub type_value: String,
|
||||
pub value: String,
|
||||
pub scope: NodeId
|
||||
pub scope: NodeId,
|
||||
pub parent: Option<NodeId>,
|
||||
}
|
||||
|
||||
#[derive(Debug, RustcEncodable)]
|
||||
|
@ -315,7 +317,8 @@ pub struct TupleVariantData {
|
|||
pub qualname: String,
|
||||
pub type_value: String,
|
||||
pub value: String,
|
||||
pub scope: NodeId
|
||||
pub scope: NodeId,
|
||||
pub parent: Option<NodeId>,
|
||||
}
|
||||
|
||||
/// Data for a typedef.
|
||||
|
@ -327,6 +330,7 @@ pub struct TypeDefData {
|
|||
pub qualname: String,
|
||||
pub value: String,
|
||||
pub visibility: Visibility,
|
||||
pub parent: Option<NodeId>,
|
||||
}
|
||||
|
||||
/// Data for a reference to a type or trait.
|
||||
|
@ -366,6 +370,7 @@ pub struct VariableData {
|
|||
pub qualname: String,
|
||||
pub span: Span,
|
||||
pub scope: NodeId,
|
||||
pub parent: Option<NodeId>,
|
||||
pub value: String,
|
||||
pub type_value: String,
|
||||
pub visibility: Visibility,
|
||||
|
|
|
@ -365,6 +365,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
type_value: typ,
|
||||
value: String::new(),
|
||||
scope: 0,
|
||||
parent: None,
|
||||
visibility: Visibility::Inherited,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
|
@ -488,6 +489,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
qualname: qualname,
|
||||
value: String::new(),
|
||||
visibility: Visibility::Inherited,
|
||||
parent: None,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
}
|
||||
|
@ -531,13 +533,14 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
self.visit_expr(expr);
|
||||
}
|
||||
|
||||
fn process_const(&mut self,
|
||||
id: ast::NodeId,
|
||||
name: ast::Name,
|
||||
span: Span,
|
||||
typ: &ast::Ty,
|
||||
expr: &ast::Expr,
|
||||
vis: Visibility) {
|
||||
fn process_assoc_const(&mut self,
|
||||
id: ast::NodeId,
|
||||
name: ast::Name,
|
||||
span: Span,
|
||||
typ: &ast::Ty,
|
||||
expr: &ast::Expr,
|
||||
parent_id: NodeId,
|
||||
vis: Visibility) {
|
||||
let qualname = format!("::{}", self.tcx.node_path_str(id));
|
||||
|
||||
let sub_span = self.span.sub_span_after_keyword(span, keywords::Const);
|
||||
|
@ -552,6 +555,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
value: self.span.snippet(expr.span),
|
||||
type_value: ty_to_string(&typ),
|
||||
scope: self.cur_scope,
|
||||
parent: Some(parent_id),
|
||||
visibility: vis,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
|
@ -646,7 +650,8 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
qualname: qualname,
|
||||
type_value: enum_data.qualname.clone(),
|
||||
value: val,
|
||||
scope: enum_data.scope
|
||||
scope: enum_data.scope,
|
||||
parent: Some(item.id),
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
}
|
||||
|
@ -669,7 +674,8 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
qualname: qualname,
|
||||
type_value: enum_data.qualname.clone(),
|
||||
value: val,
|
||||
scope: enum_data.scope
|
||||
scope: enum_data.scope,
|
||||
parent: Some(item.id),
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
}
|
||||
|
@ -722,7 +728,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
}
|
||||
self.process_generic_params(type_parameters, item.span, "", item.id);
|
||||
for impl_item in impl_items {
|
||||
self.visit_impl_item(impl_item);
|
||||
self.process_impl_item(impl_item, item.id);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -792,7 +798,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
// walk generics and methods
|
||||
self.process_generic_params(generics, item.span, &qualname, item.id);
|
||||
for method in methods {
|
||||
self.visit_trait_item(method)
|
||||
self.process_trait_item(method, item.id)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -998,6 +1004,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
value: value,
|
||||
type_value: typ,
|
||||
scope: 0,
|
||||
parent: None,
|
||||
visibility: Visibility::Inherited,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
|
@ -1046,6 +1053,57 @@ impl<'l, 'tcx: 'l, 'll, D: Dump + 'll> DumpVisitor<'l, 'tcx, 'll, D> {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn process_trait_item(&mut self, trait_item: &ast::TraitItem, trait_id: NodeId) {
|
||||
self.process_macro_use(trait_item.span, trait_item.id);
|
||||
match trait_item.node {
|
||||
ast::TraitItemKind::Const(ref ty, Some(ref expr)) => {
|
||||
self.process_assoc_const(trait_item.id,
|
||||
trait_item.ident.name,
|
||||
trait_item.span,
|
||||
&ty,
|
||||
&expr,
|
||||
trait_id,
|
||||
Visibility::Public);
|
||||
}
|
||||
ast::TraitItemKind::Method(ref sig, ref body) => {
|
||||
self.process_method(sig,
|
||||
body.as_ref().map(|x| &**x),
|
||||
trait_item.id,
|
||||
trait_item.ident.name,
|
||||
Visibility::Public,
|
||||
trait_item.span);
|
||||
}
|
||||
ast::TraitItemKind::Const(_, None) |
|
||||
ast::TraitItemKind::Type(..) |
|
||||
ast::TraitItemKind::Macro(_) => {}
|
||||
}
|
||||
}
|
||||
|
||||
fn process_impl_item(&mut self, impl_item: &ast::ImplItem, impl_id: NodeId) {
|
||||
self.process_macro_use(impl_item.span, impl_item.id);
|
||||
match impl_item.node {
|
||||
ast::ImplItemKind::Const(ref ty, ref expr) => {
|
||||
self.process_assoc_const(impl_item.id,
|
||||
impl_item.ident.name,
|
||||
impl_item.span,
|
||||
&ty,
|
||||
&expr,
|
||||
impl_id,
|
||||
From::from(&impl_item.vis));
|
||||
}
|
||||
ast::ImplItemKind::Method(ref sig, ref body) => {
|
||||
self.process_method(sig,
|
||||
Some(body),
|
||||
impl_item.id,
|
||||
impl_item.ident.name,
|
||||
From::from(&impl_item.vis),
|
||||
impl_item.span);
|
||||
}
|
||||
ast::ImplItemKind::Type(_) |
|
||||
ast::ImplItemKind::Macro(_) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'l, 'tcx: 'l, 'll, D: Dump +'ll> Visitor for DumpVisitor<'l, 'tcx, 'll, D> {
|
||||
|
@ -1180,6 +1238,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump +'ll> Visitor for DumpVisitor<'l, 'tcx, 'll, D>
|
|||
qualname: qualname.clone(),
|
||||
value: value,
|
||||
visibility: From::from(&item.vis),
|
||||
parent: None,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
|
||||
|
@ -1204,55 +1263,6 @@ impl<'l, 'tcx: 'l, 'll, D: Dump +'ll> Visitor for DumpVisitor<'l, 'tcx, 'll, D>
|
|||
}
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, trait_item: &ast::TraitItem) {
|
||||
self.process_macro_use(trait_item.span, trait_item.id);
|
||||
match trait_item.node {
|
||||
ast::TraitItemKind::Const(ref ty, Some(ref expr)) => {
|
||||
self.process_const(trait_item.id,
|
||||
trait_item.ident.name,
|
||||
trait_item.span,
|
||||
&ty,
|
||||
&expr,
|
||||
Visibility::Public);
|
||||
}
|
||||
ast::TraitItemKind::Method(ref sig, ref body) => {
|
||||
self.process_method(sig,
|
||||
body.as_ref().map(|x| &**x),
|
||||
trait_item.id,
|
||||
trait_item.ident.name,
|
||||
Visibility::Public,
|
||||
trait_item.span);
|
||||
}
|
||||
ast::TraitItemKind::Const(_, None) |
|
||||
ast::TraitItemKind::Type(..) |
|
||||
ast::TraitItemKind::Macro(_) => {}
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, impl_item: &ast::ImplItem) {
|
||||
self.process_macro_use(impl_item.span, impl_item.id);
|
||||
match impl_item.node {
|
||||
ast::ImplItemKind::Const(ref ty, ref expr) => {
|
||||
self.process_const(impl_item.id,
|
||||
impl_item.ident.name,
|
||||
impl_item.span,
|
||||
&ty,
|
||||
&expr,
|
||||
From::from(&impl_item.vis));
|
||||
}
|
||||
ast::ImplItemKind::Method(ref sig, ref body) => {
|
||||
self.process_method(sig,
|
||||
Some(body),
|
||||
impl_item.id,
|
||||
impl_item.ident.name,
|
||||
From::from(&impl_item.vis),
|
||||
impl_item.span);
|
||||
}
|
||||
ast::ImplItemKind::Type(_) |
|
||||
ast::ImplItemKind::Macro(_) => {}
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_ty(&mut self, t: &ast::Ty) {
|
||||
self.process_macro_use(t.span, t.id);
|
||||
match t.node {
|
||||
|
@ -1416,6 +1426,7 @@ impl<'l, 'tcx: 'l, 'll, D: Dump +'ll> Visitor for DumpVisitor<'l, 'tcx, 'll, D>
|
|||
value: value,
|
||||
type_value: String::new(),
|
||||
scope: 0,
|
||||
parent: None,
|
||||
visibility: Visibility::Inherited,
|
||||
}.lower(self.tcx));
|
||||
}
|
||||
|
|
|
@ -169,6 +169,7 @@ pub struct FunctionData {
|
|||
pub scope: DefId,
|
||||
pub value: String,
|
||||
pub visibility: Visibility,
|
||||
pub parent: Option<DefId>,
|
||||
}
|
||||
|
||||
impl Lower for data::FunctionData {
|
||||
|
@ -184,6 +185,7 @@ impl Lower for data::FunctionData {
|
|||
scope: make_def_id(self.scope, &tcx.map),
|
||||
value: self.value,
|
||||
visibility: self.visibility,
|
||||
parent: self.parent.map(|id| make_def_id(id, &tcx.map)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -328,6 +330,7 @@ pub struct MethodData {
|
|||
pub value: String,
|
||||
pub decl_id: Option<DefId>,
|
||||
pub visibility: Visibility,
|
||||
pub parent: Option<DefId>
|
||||
}
|
||||
|
||||
impl Lower for data::MethodData {
|
||||
|
@ -343,6 +346,7 @@ impl Lower for data::MethodData {
|
|||
value: self.value,
|
||||
decl_id: self.decl_id,
|
||||
visibility: self.visibility,
|
||||
parent: Some(make_def_id(self.scope, &tcx.map)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -438,7 +442,8 @@ pub struct StructVariantData {
|
|||
pub qualname: String,
|
||||
pub type_value: String,
|
||||
pub value: String,
|
||||
pub scope: DefId
|
||||
pub scope: DefId,
|
||||
pub parent: Option<DefId>,
|
||||
}
|
||||
|
||||
impl Lower for data::StructVariantData {
|
||||
|
@ -453,6 +458,7 @@ impl Lower for data::StructVariantData {
|
|||
type_value: self.type_value,
|
||||
value: self.value,
|
||||
scope: make_def_id(self.scope, &tcx.map),
|
||||
parent: self.parent.map(|id| make_def_id(id, &tcx.map)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -495,6 +501,7 @@ pub struct TupleVariantData {
|
|||
pub type_value: String,
|
||||
pub value: String,
|
||||
pub scope: DefId,
|
||||
pub parent: Option<DefId>,
|
||||
}
|
||||
|
||||
impl Lower for data::TupleVariantData {
|
||||
|
@ -509,6 +516,7 @@ impl Lower for data::TupleVariantData {
|
|||
type_value: self.type_value,
|
||||
value: self.value,
|
||||
scope: make_def_id(self.scope, &tcx.map),
|
||||
parent: self.parent.map(|id| make_def_id(id, &tcx.map)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -522,6 +530,7 @@ pub struct TypeDefData {
|
|||
pub qualname: String,
|
||||
pub value: String,
|
||||
pub visibility: Visibility,
|
||||
pub parent: Option<DefId>,
|
||||
}
|
||||
|
||||
impl Lower for data::TypeDefData {
|
||||
|
@ -535,6 +544,7 @@ impl Lower for data::TypeDefData {
|
|||
qualname: self.qualname,
|
||||
value: self.value,
|
||||
visibility: self.visibility,
|
||||
parent: self.parent.map(|id| make_def_id(id, &tcx.map)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -620,6 +630,7 @@ pub struct VariableData {
|
|||
pub scope: DefId,
|
||||
pub value: String,
|
||||
pub type_value: String,
|
||||
pub parent: Option<DefId>,
|
||||
pub visibility: Visibility,
|
||||
}
|
||||
|
||||
|
@ -636,6 +647,7 @@ impl Lower for data::VariableData {
|
|||
scope: make_def_id(self.scope, &tcx.map),
|
||||
value: self.value,
|
||||
type_value: self.type_value,
|
||||
parent: self.parent.map(|id| make_def_id(id, &tcx.map)),
|
||||
visibility: self.visibility,
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,6 +17,13 @@ use external_data::*;
|
|||
use data::{VariableKind, Visibility};
|
||||
use dump::Dump;
|
||||
|
||||
// A dumper to dump a restricted set of JSON information, designed for use with
|
||||
// libraries distributed without their source. Clients are likely to use type
|
||||
// information here, and (for example) generate Rustdoc URLs, but don't need
|
||||
// information for navigating the source of the crate.
|
||||
// Relative to the regular JSON save-analysis info, this form is filtered to
|
||||
// remove non-visible items, but includes some extra info for items (e.g., the
|
||||
// parent field for finding the struct to which a field belongs).
|
||||
pub struct JsonApiDumper<'b, W: Write + 'b> {
|
||||
output: &'b mut W,
|
||||
result: Analysis,
|
||||
|
@ -217,7 +224,7 @@ impl From<TupleVariantData> for Option<Def> {
|
|||
name: data.name,
|
||||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
children: vec![],
|
||||
decl_id: None,
|
||||
})
|
||||
|
@ -232,7 +239,7 @@ impl From<StructVariantData> for Option<Def> {
|
|||
name: data.name,
|
||||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
children: vec![],
|
||||
decl_id: None,
|
||||
})
|
||||
|
@ -285,7 +292,7 @@ impl From<FunctionData> for Option<Def> {
|
|||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
children: vec![],
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
decl_id: None,
|
||||
}),
|
||||
_ => None,
|
||||
|
@ -303,7 +310,7 @@ impl From<MethodData> for Option<Def> {
|
|||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
children: vec![],
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
decl_id: data.decl_id.map(|id| From::from(id)),
|
||||
}),
|
||||
_ => None,
|
||||
|
@ -354,7 +361,7 @@ impl From<TypeDefData> for Option<Def> {
|
|||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
children: vec![],
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
decl_id: None,
|
||||
}),
|
||||
_ => None,
|
||||
|
@ -377,7 +384,7 @@ impl From<VariableData> for Option<Def> {
|
|||
qualname: data.qualname,
|
||||
value: data.value,
|
||||
children: vec![],
|
||||
parent: None,
|
||||
parent: data.parent.map(|id| From::from(id)),
|
||||
decl_id: None,
|
||||
}),
|
||||
_ => None,
|
||||
|
|
|
@ -141,6 +141,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
scope: self.enclosing_scope(item.id),
|
||||
value: make_signature(decl, generics),
|
||||
visibility: From::from(&item.vis),
|
||||
parent: None,
|
||||
}))
|
||||
}
|
||||
ast::ItemKind::Static(ref typ, mt, ref expr) => {
|
||||
|
@ -163,6 +164,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
qualname: qualname,
|
||||
span: sub_span.unwrap(),
|
||||
scope: self.enclosing_scope(item.id),
|
||||
parent: None,
|
||||
value: value,
|
||||
type_value: ty_to_string(&typ),
|
||||
visibility: From::from(&item.vis),
|
||||
|
@ -179,6 +181,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
qualname: qualname,
|
||||
span: sub_span.unwrap(),
|
||||
scope: self.enclosing_scope(item.id),
|
||||
parent: None,
|
||||
value: self.span_utils.snippet(expr.span),
|
||||
type_value: ty_to_string(&typ),
|
||||
visibility: From::from(&item.vis),
|
||||
|
@ -284,6 +287,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
qualname: qualname,
|
||||
span: sub_span.unwrap(),
|
||||
scope: scope,
|
||||
parent: Some(scope),
|
||||
value: "".to_owned(),
|
||||
type_value: typ,
|
||||
visibility: From::from(&field.vis),
|
||||
|
@ -366,6 +370,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
|
||||
let sub_span = self.span_utils.sub_span_after_keyword(span, keywords::Fn);
|
||||
filter!(self.span_utils, sub_span, span, None);
|
||||
let parent_scope = self.enclosing_scope(id);
|
||||
Some(FunctionData {
|
||||
id: id,
|
||||
name: name.to_string(),
|
||||
|
@ -376,6 +381,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
|||
// FIXME you get better data here by using the visitor.
|
||||
value: String::new(),
|
||||
visibility: vis,
|
||||
parent: Some(parent_scope),
|
||||
})
|
||||
}
|
||||
|
||||
|
|
|
@ -5,3 +5,4 @@ krate2: krate2.rs
|
|||
code: foo.rs krate2
|
||||
$(RUSTC) foo.rs -Zsave-analysis-csv
|
||||
$(RUSTC) foo.rs -Zsave-analysis
|
||||
$(RUSTC) foo.rs -Zsave-analysis-api
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue