lower attr spans and inline some functions to hopefully mitigate perf regressions
This commit is contained in:
parent
2f0652745d
commit
4daa35ce33
5 changed files with 52 additions and 13 deletions
|
@ -870,7 +870,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
if attrs.is_empty() {
|
if attrs.is_empty() {
|
||||||
&[]
|
&[]
|
||||||
} else {
|
} else {
|
||||||
let lowered_attrs = self.lower_attrs_vec(attrs, target_span);
|
let lowered_attrs = self.lower_attrs_vec(attrs, self.lower_span(target_span));
|
||||||
|
|
||||||
debug_assert_eq!(id.owner, self.current_hir_id_owner);
|
debug_assert_eq!(id.owner, self.current_hir_id_owner);
|
||||||
let ret = self.arena.alloc_from_iter(lowered_attrs);
|
let ret = self.arena.alloc_from_iter(lowered_attrs);
|
||||||
|
@ -891,7 +891,8 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn lower_attrs_vec(&self, attrs: &[Attribute], target_span: Span) -> Vec<hir::Attribute> {
|
fn lower_attrs_vec(&self, attrs: &[Attribute], target_span: Span) -> Vec<hir::Attribute> {
|
||||||
self.attribute_parser.parse_attribute_list(attrs, target_span, OmitDoc::Lower)
|
self.attribute_parser
|
||||||
|
.parse_attribute_list(attrs, target_span, OmitDoc::Lower, |s| self.lower_span(s))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn alias_attrs(&mut self, id: HirId, target_id: HirId) {
|
fn alias_attrs(&mut self, id: HirId, target_id: HirId) {
|
||||||
|
|
|
@ -178,7 +178,7 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
parse_only: Some(sym),
|
parse_only: Some(sym),
|
||||||
limit_diagnostics,
|
limit_diagnostics,
|
||||||
}
|
}
|
||||||
.parse_attribute_list(attrs, target_span, OmitDoc::Skip);
|
.parse_attribute_list(attrs, target_span, OmitDoc::Skip, std::convert::identity);
|
||||||
|
|
||||||
assert!(parsed.len() <= 1);
|
assert!(parsed.len() <= 1);
|
||||||
|
|
||||||
|
@ -210,6 +210,8 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
attrs: &'a [ast::Attribute],
|
attrs: &'a [ast::Attribute],
|
||||||
target_span: Span,
|
target_span: Span,
|
||||||
omit_doc: OmitDoc,
|
omit_doc: OmitDoc,
|
||||||
|
|
||||||
|
lower_span: impl Copy + Fn(Span) -> Span,
|
||||||
) -> Vec<Attribute> {
|
) -> Vec<Attribute> {
|
||||||
let mut attributes = Vec::new();
|
let mut attributes = Vec::new();
|
||||||
|
|
||||||
|
@ -242,7 +244,7 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
attributes.push(Attribute::Parsed(AttributeKind::DocComment {
|
attributes.push(Attribute::Parsed(AttributeKind::DocComment {
|
||||||
style: attr.style,
|
style: attr.style,
|
||||||
kind: *comment_kind,
|
kind: *comment_kind,
|
||||||
span: attr.span,
|
span: lower_span(attr.span),
|
||||||
comment: *symbol,
|
comment: *symbol,
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
@ -264,7 +266,10 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
|
|
||||||
if let Some(accepts) = ATTRIBUTE_MAPPING.0.get(parts.as_slice()) {
|
if let Some(accepts) = ATTRIBUTE_MAPPING.0.get(parts.as_slice()) {
|
||||||
for f in accepts {
|
for f in accepts {
|
||||||
let cx = AcceptContext { group_cx: &group_cx, attr_span: attr.span };
|
let cx = AcceptContext {
|
||||||
|
group_cx: &group_cx,
|
||||||
|
attr_span: lower_span(attr.span),
|
||||||
|
};
|
||||||
|
|
||||||
f(&cx, &args)
|
f(&cx, &args)
|
||||||
}
|
}
|
||||||
|
@ -286,10 +291,10 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
|
|
||||||
attributes.push(Attribute::Unparsed(Box::new(AttrItem {
|
attributes.push(Attribute::Unparsed(Box::new(AttrItem {
|
||||||
path: AttrPath::from_ast(&n.item.path),
|
path: AttrPath::from_ast(&n.item.path),
|
||||||
args: self.lower_attr_args(&n.item.args),
|
args: self.lower_attr_args(&n.item.args, lower_span),
|
||||||
id: HashIgnoredAttrId { attr_id: attr.id },
|
id: HashIgnoredAttrId { attr_id: attr.id },
|
||||||
style: attr.style,
|
style: attr.style,
|
||||||
span: attr.span,
|
span: lower_span(attr.span),
|
||||||
})));
|
})));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -308,7 +313,7 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
attributes
|
attributes
|
||||||
}
|
}
|
||||||
|
|
||||||
fn lower_attr_args(&self, args: &ast::AttrArgs) -> AttrArgs {
|
fn lower_attr_args(&self, args: &ast::AttrArgs, lower_span: impl Fn(Span) -> Span) -> AttrArgs {
|
||||||
match args {
|
match args {
|
||||||
ast::AttrArgs::Empty => AttrArgs::Empty,
|
ast::AttrArgs::Empty => AttrArgs::Empty,
|
||||||
ast::AttrArgs::Delimited(args) => AttrArgs::Delimited(DelimArgs {
|
ast::AttrArgs::Delimited(args) => AttrArgs::Delimited(DelimArgs {
|
||||||
|
@ -323,7 +328,8 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
// In valid code the value always ends up as a single literal. Otherwise, a dummy
|
// In valid code the value always ends up as a single literal. Otherwise, a dummy
|
||||||
// literal suffices because the error is handled elsewhere.
|
// literal suffices because the error is handled elsewhere.
|
||||||
let lit = if let ast::ExprKind::Lit(token_lit) = expr.kind
|
let lit = if let ast::ExprKind::Lit(token_lit) = expr.kind
|
||||||
&& let Ok(lit) = ast::MetaItemLit::from_token_lit(token_lit, expr.span)
|
&& let Ok(lit) =
|
||||||
|
ast::MetaItemLit::from_token_lit(token_lit, lower_span(expr.span))
|
||||||
{
|
{
|
||||||
lit
|
lit
|
||||||
} else {
|
} else {
|
||||||
|
@ -335,7 +341,7 @@ impl<'sess> AttributeParser<'sess> {
|
||||||
span: DUMMY_SP,
|
span: DUMMY_SP,
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
AttrArgs::Eq { eq_span: *eq_span, expr: lit }
|
AttrArgs::Eq { eq_span: lower_span(*eq_span), expr: lit }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1093,6 +1093,7 @@ impl Attribute {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AttributeExt for Attribute {
|
impl AttributeExt for Attribute {
|
||||||
|
#[inline]
|
||||||
fn id(&self) -> AttrId {
|
fn id(&self) -> AttrId {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(u) => u.id.attr_id,
|
Attribute::Unparsed(u) => u.id.attr_id,
|
||||||
|
@ -1100,6 +1101,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn meta_item_list(&self) -> Option<ThinVec<ast::MetaItemInner>> {
|
fn meta_item_list(&self) -> Option<ThinVec<ast::MetaItemInner>> {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(n) => match n.as_ref() {
|
Attribute::Unparsed(n) => match n.as_ref() {
|
||||||
|
@ -1112,15 +1114,18 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn value_str(&self) -> Option<Symbol> {
|
fn value_str(&self) -> Option<Symbol> {
|
||||||
self.value_lit().and_then(|x| x.value_str())
|
self.value_lit().and_then(|x| x.value_str())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn value_span(&self) -> Option<Span> {
|
fn value_span(&self) -> Option<Span> {
|
||||||
self.value_lit().map(|i| i.span)
|
self.value_lit().map(|i| i.span)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// For a single-segment attribute, returns its name; otherwise, returns `None`.
|
/// For a single-segment attribute, returns its name; otherwise, returns `None`.
|
||||||
|
#[inline]
|
||||||
fn ident(&self) -> Option<Ident> {
|
fn ident(&self) -> Option<Ident> {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(n) => {
|
Attribute::Unparsed(n) => {
|
||||||
|
@ -1134,6 +1139,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn path_matches(&self, name: &[Symbol]) -> bool {
|
fn path_matches(&self, name: &[Symbol]) -> bool {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(n) => {
|
Attribute::Unparsed(n) => {
|
||||||
|
@ -1144,11 +1150,12 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn is_doc_comment(&self) -> bool {
|
fn is_doc_comment(&self) -> bool {
|
||||||
// FIXME(jdonszelmann): make the 2nd check unnecessary here
|
|
||||||
matches!(self, Attribute::Parsed(AttributeKind::DocComment { .. }))
|
matches!(self, Attribute::Parsed(AttributeKind::DocComment { .. }))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn span(&self) -> Span {
|
fn span(&self) -> Span {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(u) => u.span,
|
Attribute::Unparsed(u) => u.span,
|
||||||
|
@ -1159,6 +1166,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn is_word(&self) -> bool {
|
fn is_word(&self) -> bool {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(n) => {
|
Attribute::Unparsed(n) => {
|
||||||
|
@ -1168,6 +1176,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn ident_path(&self) -> Option<SmallVec<[Ident; 1]>> {
|
fn ident_path(&self) -> Option<SmallVec<[Ident; 1]>> {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(n) => Some(n.path.segments.iter().copied().collect()),
|
Attribute::Unparsed(n) => Some(n.path.segments.iter().copied().collect()),
|
||||||
|
@ -1175,6 +1184,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn doc_str(&self) -> Option<Symbol> {
|
fn doc_str(&self) -> Option<Symbol> {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Parsed(AttributeKind::DocComment { comment, .. }) => Some(*comment),
|
Attribute::Parsed(AttributeKind::DocComment { comment, .. }) => Some(*comment),
|
||||||
|
@ -1182,6 +1192,7 @@ impl AttributeExt for Attribute {
|
||||||
_ => None,
|
_ => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#[inline]
|
||||||
fn doc_str_and_comment_kind(&self) -> Option<(Symbol, CommentKind)> {
|
fn doc_str_and_comment_kind(&self) -> Option<(Symbol, CommentKind)> {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Parsed(AttributeKind::DocComment { kind, comment, .. }) => {
|
Attribute::Parsed(AttributeKind::DocComment { kind, comment, .. }) => {
|
||||||
|
@ -1194,6 +1205,7 @@ impl AttributeExt for Attribute {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
fn style(&self) -> AttrStyle {
|
fn style(&self) -> AttrStyle {
|
||||||
match &self {
|
match &self {
|
||||||
Attribute::Unparsed(u) => u.style,
|
Attribute::Unparsed(u) => u.style,
|
||||||
|
@ -1205,34 +1217,42 @@ impl AttributeExt for Attribute {
|
||||||
|
|
||||||
// FIXME(fn_delegation): use function delegation instead of manually forwarding
|
// FIXME(fn_delegation): use function delegation instead of manually forwarding
|
||||||
impl Attribute {
|
impl Attribute {
|
||||||
|
#[inline]
|
||||||
pub fn id(&self) -> AttrId {
|
pub fn id(&self) -> AttrId {
|
||||||
AttributeExt::id(self)
|
AttributeExt::id(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn name_or_empty(&self) -> Symbol {
|
pub fn name_or_empty(&self) -> Symbol {
|
||||||
AttributeExt::name_or_empty(self)
|
AttributeExt::name_or_empty(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn meta_item_list(&self) -> Option<ThinVec<MetaItemInner>> {
|
pub fn meta_item_list(&self) -> Option<ThinVec<MetaItemInner>> {
|
||||||
AttributeExt::meta_item_list(self)
|
AttributeExt::meta_item_list(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn value_str(&self) -> Option<Symbol> {
|
pub fn value_str(&self) -> Option<Symbol> {
|
||||||
AttributeExt::value_str(self)
|
AttributeExt::value_str(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn value_span(&self) -> Option<Span> {
|
pub fn value_span(&self) -> Option<Span> {
|
||||||
AttributeExt::value_span(self)
|
AttributeExt::value_span(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn ident(&self) -> Option<Ident> {
|
pub fn ident(&self) -> Option<Ident> {
|
||||||
AttributeExt::ident(self)
|
AttributeExt::ident(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn path_matches(&self, name: &[Symbol]) -> bool {
|
pub fn path_matches(&self, name: &[Symbol]) -> bool {
|
||||||
AttributeExt::path_matches(self, name)
|
AttributeExt::path_matches(self, name)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn is_doc_comment(&self) -> bool {
|
pub fn is_doc_comment(&self) -> bool {
|
||||||
AttributeExt::is_doc_comment(self)
|
AttributeExt::is_doc_comment(self)
|
||||||
}
|
}
|
||||||
|
@ -1242,34 +1262,42 @@ impl Attribute {
|
||||||
AttributeExt::has_name(self, name)
|
AttributeExt::has_name(self, name)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn span(&self) -> Span {
|
pub fn span(&self) -> Span {
|
||||||
AttributeExt::span(self)
|
AttributeExt::span(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn is_word(&self) -> bool {
|
pub fn is_word(&self) -> bool {
|
||||||
AttributeExt::is_word(self)
|
AttributeExt::is_word(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn path(&self) -> SmallVec<[Symbol; 1]> {
|
pub fn path(&self) -> SmallVec<[Symbol; 1]> {
|
||||||
AttributeExt::path(self)
|
AttributeExt::path(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn ident_path(&self) -> Option<SmallVec<[Ident; 1]>> {
|
pub fn ident_path(&self) -> Option<SmallVec<[Ident; 1]>> {
|
||||||
AttributeExt::ident_path(self)
|
AttributeExt::ident_path(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn doc_str(&self) -> Option<Symbol> {
|
pub fn doc_str(&self) -> Option<Symbol> {
|
||||||
AttributeExt::doc_str(self)
|
AttributeExt::doc_str(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn is_proc_macro_attr(&self) -> bool {
|
pub fn is_proc_macro_attr(&self) -> bool {
|
||||||
AttributeExt::is_proc_macro_attr(self)
|
AttributeExt::is_proc_macro_attr(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn doc_str_and_comment_kind(&self) -> Option<(Symbol, CommentKind)> {
|
pub fn doc_str_and_comment_kind(&self) -> Option<(Symbol, CommentKind)> {
|
||||||
AttributeExt::doc_str_and_comment_kind(self)
|
AttributeExt::doc_str_and_comment_kind(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
pub fn style(&self) -> AttrStyle {
|
pub fn style(&self) -> AttrStyle {
|
||||||
AttributeExt::style(self)
|
AttributeExt::style(self)
|
||||||
}
|
}
|
||||||
|
|
|
@ -2732,7 +2732,6 @@ fn check_invalid_crate_level_attr(tcx: TyCtxt<'_>, attrs: &[Attribute]) {
|
||||||
continue;
|
continue;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
let item = tcx
|
let item = tcx
|
||||||
.hir_free_items()
|
.hir_free_items()
|
||||||
.map(|id| tcx.hir_item(id))
|
.map(|id| tcx.hir_item(id))
|
||||||
|
|
|
@ -142,7 +142,12 @@ impl<'a, 'ra, 'tcx> visit::Visitor<'a> for DefCollector<'a, 'ra, 'tcx> {
|
||||||
self.resolver.tcx.features(),
|
self.resolver.tcx.features(),
|
||||||
Vec::new(),
|
Vec::new(),
|
||||||
);
|
);
|
||||||
let attrs = parser.parse_attribute_list(&i.attrs, i.span, OmitDoc::Skip);
|
let attrs = parser.parse_attribute_list(
|
||||||
|
&i.attrs,
|
||||||
|
i.span,
|
||||||
|
OmitDoc::Skip,
|
||||||
|
std::convert::identity,
|
||||||
|
);
|
||||||
|
|
||||||
let macro_data =
|
let macro_data =
|
||||||
self.resolver.compile_macro(def, i.ident, &attrs, i.span, i.id, edition);
|
self.resolver.compile_macro(def, i.ident, &attrs, i.span, i.id, edition);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue