Remove MappedSubtree

This commit is contained in:
Lukas Wirth 2021-08-21 18:19:18 +02:00
parent 177c70128c
commit 5fb8c0ddfd
7 changed files with 21 additions and 41 deletions

View File

@ -14,7 +14,7 @@ use either::Either;
use hir_expand::{hygiene::Hygiene, name::AsName, AstId, InFile};
use itertools::Itertools;
use la_arena::ArenaMap;
use mbe::{syntax_node_to_token_tree, DelimiterKind, MappedSubTree};
use mbe::{syntax_node_to_token_tree, DelimiterKind};
use smallvec::{smallvec, SmallVec};
use syntax::{
ast::{self, AstNode, AttrsOwner},
@ -160,18 +160,18 @@ impl RawAttrs {
}
let subtree = match attr.input.as_deref() {
Some(AttrInput::TokenTree(it)) => it,
Some(AttrInput::TokenTree(it, _)) => it,
_ => return smallvec![attr.clone()],
};
// Input subtree is: `(cfg, $(attr),+)`
// Split it up into a `cfg` subtree and the `attr` subtrees.
// FIXME: There should be a common API for this.
let mut parts = subtree.tree.token_trees.split(
let mut parts = subtree.token_trees.split(
|tt| matches!(tt, tt::TokenTree::Leaf(tt::Leaf::Punct(p)) if p.char == ','),
);
let cfg = parts.next().unwrap();
let cfg = Subtree { delimiter: subtree.tree.delimiter, token_trees: cfg.to_vec() };
let cfg = Subtree { delimiter: subtree.delimiter, token_trees: cfg.to_vec() };
let cfg = CfgExpr::parse(&cfg);
let index = attr.id;
let attrs = parts.filter(|a| !a.is_empty()).filter_map(|attr| {
@ -260,7 +260,7 @@ impl Attrs {
pub fn docs(&self) -> Option<Documentation> {
let docs = self.by_key("doc").attrs().flat_map(|attr| match attr.input.as_deref()? {
AttrInput::Literal(s) => Some(s),
AttrInput::TokenTree(_) => None,
AttrInput::TokenTree(..) => None,
});
let indent = docs
.clone()
@ -465,7 +465,7 @@ impl AttrsWithOwner {
// FIXME: code duplication in `docs` above
let docs = self.by_key("doc").attrs().flat_map(|attr| match attr.input.as_deref()? {
AttrInput::Literal(s) => Some((s, attr.id)),
AttrInput::TokenTree(_) => None,
AttrInput::TokenTree(..) => None,
});
let indent = docs
.clone()
@ -654,14 +654,14 @@ pub enum AttrInput {
/// `#[attr = "string"]`
Literal(SmolStr),
/// `#[attr(subtree)]`
TokenTree(mbe::MappedSubTree),
TokenTree(tt::Subtree, mbe::TokenMap),
}
impl fmt::Display for AttrInput {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match self {
AttrInput::Literal(lit) => write!(f, " = \"{}\"", lit.escape_debug()),
AttrInput::TokenTree(subtree) => subtree.tree.fmt(f),
AttrInput::TokenTree(subtree, _) => subtree.fmt(f),
}
}
}
@ -682,7 +682,7 @@ impl Attr {
Some(Interned::new(AttrInput::Literal(value)))
} else if let Some(tt) = ast.token_tree() {
let (tree, map) = syntax_node_to_token_tree(tt.syntax());
Some(Interned::new(AttrInput::TokenTree(MappedSubTree { tree, map })))
Some(Interned::new(AttrInput::TokenTree(tree, map)))
} else {
None
};
@ -712,10 +712,9 @@ impl Attr {
}
match self.input.as_deref() {
Some(AttrInput::TokenTree(args)) => {
Some(AttrInput::TokenTree(args, _)) => {
let mut counter = 0;
let paths = args
.tree
.token_trees
.iter()
.group_by(move |tt| {
@ -760,7 +759,7 @@ pub struct AttrQuery<'a> {
impl<'a> AttrQuery<'a> {
pub fn tt_values(self) -> impl Iterator<Item = &'a Subtree> {
self.attrs().filter_map(|attr| match attr.input.as_deref()? {
AttrInput::TokenTree(it) => Some(&it.tree),
AttrInput::TokenTree(it, _) => Some(it),
_ => None,
})
}

View File

@ -787,12 +787,12 @@ fn attr_macro_as_call_id(
let mut arg = match &macro_attr.input {
Some(input) => match &**input {
attr::AttrInput::Literal(_) => Default::default(),
attr::AttrInput::TokenTree(tt) => tt.clone(),
attr::AttrInput::TokenTree(tt, map) => (tt.clone(), map.clone()),
},
None => Default::default(),
};
// The parentheses are always disposed here.
arg.tree.delimiter = None;
arg.0.delimiter = None;
let res = def.as_lazy_macro(
db.upcast(),

View File

@ -289,7 +289,7 @@ impl DefCollector<'_> {
|| *attr_name == hir_expand::name![register_tool]
{
match attr.input.as_deref() {
Some(AttrInput::TokenTree(subtree)) => match &*subtree.tree.token_trees {
Some(AttrInput::TokenTree(subtree, _)) => match &*subtree.token_trees {
[tt::TokenTree::Leaf(tt::Leaf::Ident(name))] => name.as_name(),
_ => continue,
},

View File

@ -387,7 +387,7 @@ fn expand_proc_macro(db: &dyn AstDatabase, id: MacroCallId) -> ExpandResult<tt::
let attr_arg = match &loc.kind {
MacroCallKind::Attr { attr_args, .. } => {
let mut attr_args = attr_args.tree.clone();
let mut attr_args = attr_args.0.clone();
mbe::Shift::new(&macro_arg.0).shift_all(&mut attr_args);
Some(attr_args)
}

View File

@ -283,7 +283,7 @@ pub enum MacroCallKind {
Attr {
ast_id: AstId<ast::Item>,
attr_name: String,
attr_args: mbe::MappedSubTree,
attr_args: (tt::Subtree, mbe::TokenMap),
/// Syntactical index of the invoking `#[attribute]`.
///
/// Outer attributes are counted first, then inner attributes. This does not support
@ -390,7 +390,7 @@ impl ExpansionInfo {
token_tree.left_delimiter_token()?.text_range().start();
let range = token.value.text_range().checked_sub(attr_input_start)?;
let token_id =
self.macro_arg_shift.shift(attr_args.map.token_by_range(range)?);
self.macro_arg_shift.shift(attr_args.1.token_by_range(range)?);
Some(token_id)
}
_ => None,
@ -437,7 +437,7 @@ impl ExpansionInfo {
MacroCallKind::Attr { attr_args, .. } => match self.macro_arg_shift.unshift(token_id) {
Some(unshifted) => {
token_id = unshifted;
(&attr_args.map, self.attr_input_or_mac_def.clone()?.syntax().cloned())
(&attr_args.1, self.attr_input_or_mac_def.clone()?.syntax().cloned())
}
None => (&self.macro_arg.1, self.arg.clone()),
},

View File

@ -69,7 +69,7 @@ pub use crate::{
parse_exprs_with_sep, parse_to_token_tree, syntax_node_to_token_tree,
token_tree_to_syntax_node,
},
token_map::{MappedSubTree, TokenMap},
token_map::TokenMap,
};
/// This struct contains AST for a single `macro_rules` definition. What might

View File

@ -5,7 +5,7 @@ use std::hash::Hash;
use parser::{SyntaxKind, T};
use syntax::{TextRange, TextSize};
#[derive(Debug, PartialEq, Eq, Clone, Copy)]
#[derive(Debug, PartialEq, Eq, Clone, Copy, Hash)]
enum TokenTextRange {
Token(TextRange),
Delimiter(TextRange),
@ -26,27 +26,8 @@ impl TokenTextRange {
}
}
#[derive(Debug, Clone, Default)]
pub struct MappedSubTree {
pub tree: tt::Subtree,
pub map: TokenMap,
}
impl Eq for MappedSubTree {}
impl PartialEq for MappedSubTree {
fn eq(&self, other: &Self) -> bool {
self.tree == other.tree && self.map == other.map
}
}
impl Hash for MappedSubTree {
fn hash<H: std::hash::Hasher>(&self, state: &mut H) {
self.tree.hash(state);
}
}
/// Maps `tt::TokenId` to the relative range of the original token.
#[derive(Debug, PartialEq, Eq, Clone, Default)]
#[derive(Debug, PartialEq, Eq, Clone, Default, Hash)]
pub struct TokenMap {
/// Maps `tt::TokenId` to the *relative* source range.
entries: Vec<(tt::TokenId, TokenTextRange)>,