Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Provide Group::span_open and span_close #134

Merged
merged 1 commit into from
Sep 17, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
79 changes: 49 additions & 30 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -502,9 +502,7 @@ impl fmt::Debug for TokenTree {
/// `Delimiter`s.
#[derive(Clone)]
pub struct Group {
delimiter: Delimiter,
stream: TokenStream,
span: Span,
inner: imp::Group,
}

/// Describes how a sequence of token trees is delimited.
Expand All @@ -527,36 +525,73 @@ pub enum Delimiter {
}

impl Group {
fn _new(inner: imp::Group) -> Self {
Group {
inner: inner,
}
}

fn _new_stable(inner: stable::Group) -> Self {
Group {
inner: inner.into(),
}
}

/// Creates a new `Group` with the given delimiter and token stream.
///
/// This constructor will set the span for this group to
/// `Span::call_site()`. To change the span you can use the `set_span`
/// method below.
pub fn new(delimiter: Delimiter, stream: TokenStream) -> Group {
Group {
delimiter: delimiter,
stream: stream,
span: Span::call_site(),
inner: imp::Group::new(delimiter, stream.inner),
}
}

/// Returns the delimiter of this `Group`
pub fn delimiter(&self) -> Delimiter {
self.delimiter
self.inner.delimiter()
}

/// Returns the `TokenStream` of tokens that are delimited in this `Group`.
///
/// Note that the returned token stream does not include the delimiter
/// returned above.
pub fn stream(&self) -> TokenStream {
self.stream.clone()
TokenStream::_new(self.inner.stream())
}

/// Returns the span for the delimiters of this token stream, spanning the
/// entire `Group`.
///
/// ```text
/// pub fn span(&self) -> Span {
/// ^^^^^^^
/// ```
pub fn span(&self) -> Span {
self.span
Span::_new(self.inner.span())
}

/// Returns the span pointing to the opening delimiter of this group.
///
/// ```text
/// pub fn span_open(&self) -> Span {
/// ^
/// ```
#[cfg(procmacro2_semver_exempt)]
pub fn span_open(&self) -> Span {
Span::_new(self.inner.span_open())
}

/// Returns the span pointing to the closing delimiter of this group.
///
/// ```text
/// pub fn span_close(&self) -> Span {
/// ^
/// ```
#[cfg(procmacro2_semver_exempt)]
pub fn span_close(&self) -> Span {
Span::_new(self.inner.span_close())
}

/// Configures the span for this `Group`'s delimiters, but not its internal
Expand All @@ -566,38 +601,22 @@ impl Group {
/// by this group, but rather it will only set the span of the delimiter
/// tokens at the level of the `Group`.
pub fn set_span(&mut self, span: Span) {
self.span = span;
self.inner.set_span(span.inner)
}
}

/// Prints the group as a string that should be losslessly convertible back
/// into the same group (modulo spans), except for possibly `TokenTree::Group`s
/// with `Delimiter::None` delimiters.
impl fmt::Display for Group {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let (left, right) = match self.delimiter {
Delimiter::Parenthesis => ("(", ")"),
Delimiter::Brace => ("{", "}"),
Delimiter::Bracket => ("[", "]"),
Delimiter::None => ("", ""),
};

f.write_str(left)?;
self.stream.fmt(f)?;
f.write_str(right)?;

Ok(())
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
fmt::Display::fmt(&self.inner, formatter)
}
}

impl fmt::Debug for Group {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
let mut debug = fmt.debug_struct("Group");
debug.field("delimiter", &self.delimiter);
debug.field("stream", &self.stream);
#[cfg(procmacro2_semver_exempt)]
debug.field("span", &self.span);
debug.finish()
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
fmt::Debug::fmt(&self.inner, formatter)
}
}

Expand Down
82 changes: 76 additions & 6 deletions src/stable.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ use std::vec;
use strnom::{block_comment, skip_whitespace, whitespace, word_break, Cursor, PResult};
use unicode_xid::UnicodeXID;

use {Delimiter, Group, Punct, Spacing, TokenTree};
use {Delimiter, Punct, Spacing, TokenTree};

#[derive(Clone)]
pub struct TokenStream {
Expand Down Expand Up @@ -431,6 +431,75 @@ impl fmt::Debug for Span {
}
}

#[derive(Clone)]
pub struct Group {
delimiter: Delimiter,
stream: TokenStream,
span: Span,
}

impl Group {
pub fn new(delimiter: Delimiter, stream: TokenStream) -> Group {
Group {
delimiter: delimiter,
stream: stream,
span: Span::call_site(),
}
}

pub fn delimiter(&self) -> Delimiter {
self.delimiter
}

pub fn stream(&self) -> TokenStream {
self.stream.clone()
}

pub fn span(&self) -> Span {
self.span
}

pub fn span_open(&self) -> Span {
self.span
}

pub fn span_close(&self) -> Span {
self.span
}

pub fn set_span(&mut self, span: Span) {
self.span = span;
}
}

impl fmt::Display for Group {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let (left, right) = match self.delimiter {
Delimiter::Parenthesis => ("(", ")"),
Delimiter::Brace => ("{", "}"),
Delimiter::Bracket => ("[", "]"),
Delimiter::None => ("", ""),
};

f.write_str(left)?;
self.stream.fmt(f)?;
f.write_str(right)?;

Ok(())
}
}

impl fmt::Debug for Group {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
let mut debug = fmt.debug_struct("Group");
debug.field("delimiter", &self.delimiter);
debug.field("stream", &self.stream);
#[cfg(procmacro2_semver_exempt)]
debug.field("span", &self.span);
debug.finish()
}
}

#[derive(Clone)]
pub struct Ident {
sym: String,
Expand Down Expand Up @@ -747,7 +816,7 @@ fn token_tree(input: Cursor) -> PResult<TokenTree> {
}

named!(token_kind -> TokenTree, alt!(
map!(group, TokenTree::Group)
map!(group, |g| TokenTree::Group(::Group::_new_stable(g)))
|
map!(literal, |l| TokenTree::Literal(::Literal::_new_stable(l))) // must be before symbol
|
Expand All @@ -761,19 +830,19 @@ named!(group -> Group, alt!(
punct!("("),
token_stream,
punct!(")")
) => { |ts| Group::new(Delimiter::Parenthesis, ::TokenStream::_new_stable(ts)) }
) => { |ts| Group::new(Delimiter::Parenthesis, ts) }
|
delimited!(
punct!("["),
token_stream,
punct!("]")
) => { |ts| Group::new(Delimiter::Bracket, ::TokenStream::_new_stable(ts)) }
) => { |ts| Group::new(Delimiter::Bracket, ts) }
|
delimited!(
punct!("{"),
token_stream,
punct!("}")
) => { |ts| Group::new(Delimiter::Brace, ::TokenStream::_new_stable(ts)) }
) => { |ts| Group::new(Delimiter::Brace, ts) }
));

fn symbol_leading_ws(input: Cursor) -> PResult<TokenTree> {
Expand Down Expand Up @@ -1288,7 +1357,8 @@ fn doc_comment(input: Cursor) -> PResult<Vec<TokenTree>> {
for tt in stream.iter_mut() {
tt.set_span(span);
}
trees.push(Group::new(Delimiter::Bracket, stream.into_iter().collect()).into());
let group = Group::new(Delimiter::Bracket, stream.into_iter().collect());
trees.push(::Group::_new_stable(group).into());
for tt in trees.iter_mut() {
tt.set_span(span);
}
Expand Down
Loading