1
1
//! Functions dealing with attributes and meta items.
2
2
3
3
use crate::ast;
4
- use crate::ast::{AttrArgs, AttrArgsEq, AttrId, AttrItem, AttrKind, AttrStyle, Attribute};
5
- use crate::ast::{DelimArgs, LitKind, MetaItemLit};
6
- use crate::ast::{MacDelimiter, MetaItem, MetaItemKind, NestedMetaItem};
7
- use crate::ast::{Path, PathSegment};
4
+ use crate::ast::{AttrArgs, AttrArgsEq, AttrId, AttrItem, AttrKind, AttrStyle, AttrVec, Attribute};
5
+ use crate::ast::{DelimArgs, Expr, ExprKind, LitKind, MetaItemLit};
6
+ use crate::ast::{MacDelimiter, MetaItem, MetaItemKind, NestedMetaItem, NormalAttr };
7
+ use crate::ast::{Path, PathSegment, StrStyle, DUMMY_NODE_ID };
8
8
use crate::ptr::P;
9
9
use crate::token::{self, CommentKind, Delimiter, Token};
10
10
use crate::tokenstream::{DelimSpan, Spacing, TokenTree};
11
11
use crate::tokenstream::{LazyAttrTokenStream, TokenStream};
12
12
use crate::util::comments;
13
13
use rustc_data_structures::sync::WorkerLocal;
14
14
use rustc_index::bit_set::GrowableBitSet;
15
- use rustc_span::source_map::BytePos;
16
15
use rustc_span::symbol::{sym, Ident, Symbol};
17
16
use rustc_span::Span;
18
17
use std::cell::Cell;
@@ -223,11 +222,7 @@ impl AttrItem {
223
222
}
224
223
225
224
pub fn meta(&self, span: Span) -> Option<MetaItem> {
226
- Some(MetaItem {
227
- path: self.path.clone(),
228
- kind: MetaItemKind::from_attr_args(&self.args)?,
229
- span,
230
- })
225
+ Some(MetaItem { path: self.path.clone(), kind: self.meta_kind()?, span })
231
226
}
232
227
233
228
pub fn meta_kind(&self) -> Option<MetaItemKind> {
@@ -329,26 +324,13 @@ impl Attribute {
329
324
/* Constructors */
330
325
331
326
pub fn mk_name_value_item_str(ident: Ident, str: Symbol, str_span: Span) -> MetaItem {
332
- let lit_kind = LitKind::Str(str, ast::StrStyle::Cooked);
333
- mk_name_value_item(ident, lit_kind, str_span)
327
+ mk_name_value_item(ident, LitKind::Str(str, ast::StrStyle::Cooked), str_span)
334
328
}
335
329
336
330
pub fn mk_name_value_item(ident: Ident, kind: LitKind, lit_span: Span) -> MetaItem {
337
331
let lit = MetaItemLit { token_lit: kind.to_token_lit(), kind, span: lit_span };
338
332
let span = ident.span.to(lit_span);
339
- MetaItem { path: Path::from_ident(ident), span, kind: MetaItemKind::NameValue(lit) }
340
- }
341
-
342
- pub fn mk_list_item(ident: Ident, items: Vec<NestedMetaItem>) -> MetaItem {
343
- MetaItem { path: Path::from_ident(ident), span: ident.span, kind: MetaItemKind::List(items) }
344
- }
345
-
346
- pub fn mk_word_item(ident: Ident) -> MetaItem {
347
- MetaItem { path: Path::from_ident(ident), span: ident.span, kind: MetaItemKind::Word }
348
- }
349
-
350
- pub fn mk_nested_word_item(ident: Ident) -> NestedMetaItem {
351
- NestedMetaItem::MetaItem(mk_word_item(ident))
333
+ MetaItem { path: Path::from_ident(ident), kind: MetaItemKind::NameValue(lit), span }
352
334
}
353
335
354
336
pub struct AttrIdGenerator(WorkerLocal<Cell<u32>>);
@@ -406,21 +388,58 @@ pub fn mk_attr_from_item(
406
388
span: Span,
407
389
) -> Attribute {
408
390
Attribute {
409
- kind: AttrKind::Normal(P(ast:: NormalAttr { item, tokens })),
391
+ kind: AttrKind::Normal(P(NormalAttr { item, tokens })),
410
392
id: g.mk_attr_id(),
411
393
style,
412
394
span,
413
395
}
414
396
}
415
397
416
- /// Returns an inner attribute with the given value and span.
417
- pub fn mk_attr_inner(g: &AttrIdGenerator, item: MetaItem) -> Attribute {
418
- mk_attr(g, AttrStyle::Inner, item.path, item.kind.attr_args(item.span), item.span)
398
+ pub fn mk_attr_word(g: &AttrIdGenerator, style: AttrStyle, name: Symbol, span: Span) -> Attribute {
399
+ let path = Path::from_ident(Ident::new(name, span));
400
+ let args = AttrArgs::Empty;
401
+ mk_attr(g, style, path, args, span)
402
+ }
403
+
404
+ pub fn mk_attr_name_value_str(
405
+ g: &AttrIdGenerator,
406
+ style: AttrStyle,
407
+ name: Symbol,
408
+ val: Symbol,
409
+ span: Span,
410
+ ) -> Attribute {
411
+ let lit = LitKind::Str(val, StrStyle::Cooked).to_token_lit();
412
+ let expr = P(Expr {
413
+ id: DUMMY_NODE_ID,
414
+ kind: ExprKind::Lit(lit),
415
+ span,
416
+ attrs: AttrVec::new(),
417
+ tokens: None,
418
+ });
419
+ let path = Path::from_ident(Ident::new(name, span));
420
+ let args = AttrArgs::Eq(span, AttrArgsEq::Ast(expr));
421
+ mk_attr(g, style, path, args, span)
419
422
}
420
423
421
- /// Returns an outer attribute with the given value and span.
422
- pub fn mk_attr_outer(g: &AttrIdGenerator, item: MetaItem) -> Attribute {
423
- mk_attr(g, AttrStyle::Outer, item.path, item.kind.attr_args(item.span), item.span)
424
+ pub fn mk_attr_nested_word(
425
+ g: &AttrIdGenerator,
426
+ style: AttrStyle,
427
+ outer: Symbol,
428
+ inner: Symbol,
429
+ span: Span,
430
+ ) -> Attribute {
431
+ let inner_tokens = TokenStream::new(vec![TokenTree::Token(
432
+ Token::from_ast_ident(Ident::new(inner, span)),
433
+ Spacing::Alone,
434
+ )]);
435
+ let outer_ident = Ident::new(outer, span);
436
+ let path = Path::from_ident(outer_ident);
437
+ let attr_args = AttrArgs::Delimited(DelimArgs {
438
+ dspan: DelimSpan::from_single(span),
439
+ delim: MacDelimiter::Parenthesis,
440
+ tokens: inner_tokens,
441
+ });
442
+ mk_attr(g, style, path, attr_args, span)
424
443
}
425
444
426
445
pub fn mk_doc_comment(
@@ -438,23 +457,6 @@ pub fn list_contains_name(items: &[NestedMetaItem], name: Symbol) -> bool {
438
457
}
439
458
440
459
impl MetaItem {
441
- fn token_trees(&self) -> Vec<TokenTree> {
442
- let mut idents = vec![];
443
- let mut last_pos = BytePos(0_u32);
444
- for (i, segment) in self.path.segments.iter().enumerate() {
445
- let is_first = i == 0;
446
- if !is_first {
447
- let mod_sep_span =
448
- Span::new(last_pos, segment.ident.span.lo(), segment.ident.span.ctxt(), None);
449
- idents.push(TokenTree::token_alone(token::ModSep, mod_sep_span));
450
- }
451
- idents.push(TokenTree::Token(Token::from_ast_ident(segment.ident), Spacing::Alone));
452
- last_pos = segment.ident.span.hi();
453
- }
454
- idents.extend(self.kind.token_trees(self.span));
455
- idents
456
- }
457
-
458
460
fn from_tokens<I>(tokens: &mut iter::Peekable<I>) -> Option<MetaItem>
459
461
where
460
462
I: Iterator<Item = TokenTree>,
@@ -526,62 +528,6 @@ impl MetaItemKind {
526
528
}
527
529
}
528
530
529
- pub fn attr_args(&self, span: Span) -> AttrArgs {
530
- match self {
531
- MetaItemKind::Word => AttrArgs::Empty,
532
- MetaItemKind::NameValue(lit) => {
533
- let expr = P(ast::Expr {
534
- id: ast::DUMMY_NODE_ID,
535
- kind: ast::ExprKind::Lit(lit.token_lit.clone()),
536
- span: lit.span,
537
- attrs: ast::AttrVec::new(),
538
- tokens: None,
539
- });
540
- AttrArgs::Eq(span, AttrArgsEq::Ast(expr))
541
- }
542
- MetaItemKind::List(list) => {
543
- let mut tts = Vec::new();
544
- for (i, item) in list.iter().enumerate() {
545
- if i > 0 {
546
- tts.push(TokenTree::token_alone(token::Comma, span));
547
- }
548
- tts.extend(item.token_trees())
549
- }
550
- AttrArgs::Delimited(DelimArgs {
551
- dspan: DelimSpan::from_single(span),
552
- delim: MacDelimiter::Parenthesis,
553
- tokens: TokenStream::new(tts),
554
- })
555
- }
556
- }
557
- }
558
-
559
- fn token_trees(&self, span: Span) -> Vec<TokenTree> {
560
- match self {
561
- MetaItemKind::Word => vec![],
562
- MetaItemKind::NameValue(lit) => {
563
- vec![
564
- TokenTree::token_alone(token::Eq, span),
565
- TokenTree::Token(lit.to_token(), Spacing::Alone),
566
- ]
567
- }
568
- MetaItemKind::List(list) => {
569
- let mut tokens = Vec::new();
570
- for (i, item) in list.iter().enumerate() {
571
- if i > 0 {
572
- tokens.push(TokenTree::token_alone(token::Comma, span));
573
- }
574
- tokens.extend(item.token_trees())
575
- }
576
- vec![TokenTree::Delimited(
577
- DelimSpan::from_single(span),
578
- Delimiter::Parenthesis,
579
- TokenStream::new(tokens),
580
- )]
581
- }
582
- }
583
- }
584
-
585
531
fn list_from_tokens(tokens: TokenStream) -> Option<MetaItemKind> {
586
532
let mut tokens = tokens.into_trees().peekable();
587
533
let mut result = Vec::new();
@@ -620,7 +566,7 @@ impl MetaItemKind {
620
566
}) => MetaItemKind::list_from_tokens(tokens.clone()),
621
567
AttrArgs::Delimited(..) => None,
622
568
AttrArgs::Eq(_, AttrArgsEq::Ast(expr)) => match expr.kind {
623
- ast:: ExprKind::Lit(token_lit) => {
569
+ ExprKind::Lit(token_lit) => {
624
570
// Turn failures to `None`, we'll get parse errors elsewhere.
625
571
MetaItemLit::from_token_lit(token_lit, expr.span)
626
572
.ok()
@@ -659,15 +605,6 @@ impl NestedMetaItem {
659
605
}
660
606
}
661
607
662
- fn token_trees(&self) -> Vec<TokenTree> {
663
- match self {
664
- NestedMetaItem::MetaItem(item) => item.token_trees(),
665
- NestedMetaItem::Lit(lit) => {
666
- vec![TokenTree::Token(lit.to_token(), Spacing::Alone)]
667
- }
668
- }
669
- }
670
-
671
608
fn from_tokens<I>(tokens: &mut iter::Peekable<I>) -> Option<NestedMetaItem>
672
609
where
673
610
I: Iterator<Item = TokenTree>,
0 commit comments