///
/// This is registered as a set of expression syntax extension called quote!
/// that lifts its argument token-tree to an AST representing the
-/// construction of the same token tree, with token::SubstNt interpreted
+/// construction of the same token tree, with `token::SubstNt` interpreted
/// as antiquotes (splices).
pub mod rt {
use ast;
use codemap::Spanned;
use ext::base::ExtCtxt;
- use parse::{self, token, classify};
+ use parse::{self, classify};
+ use parse::token::{self, Token};
use ptr::P;
- use std::rc::Rc;
use symbol::Symbol;
use tokenstream::{self, TokenTree, TokenStream};
impl ToTokens for ast::Path {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtPath(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Ty {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtTy(P(self.clone()));
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Block {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtBlock(P(self.clone()));
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Generics {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtGenerics(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for ast::WhereClause {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtWhereClause(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for P<ast::Item> {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtItem(self.clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::ImplItem {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtImplItem(self.clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for P<ast::ImplItem> {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtImplItem((**self).clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::TraitItem {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtTraitItem(self.clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Stmt {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtStmt(self.clone());
- let mut tts = vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))];
+ let mut tts = vec![TokenTree::Token(self.span, Token::interpolated(nt))];
// Some statements require a trailing semicolon.
if classify::stmt_ends_with_semi(&self.node) {
impl ToTokens for P<ast::Expr> {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtExpr(self.clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for P<ast::Pat> {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtPat(self.clone());
- vec![TokenTree::Token(self.span, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(self.span, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Arm {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtArm(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for ast::Arg {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtArg(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for P<ast::Block> {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtBlock(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
impl ToTokens for ast::MetaItem {
fn to_tokens(&self, _cx: &ExtCtxt) -> Vec<TokenTree> {
let nt = token::NtMeta(self.clone());
- vec![TokenTree::Token(DUMMY_SP, token::Interpolated(Rc::new(nt)))]
+ vec![TokenTree::Token(DUMMY_SP, Token::interpolated(nt))]
}
}
fn parse_tts(&self, s: String) -> Vec<TokenTree> {
let source_name = "<quote expansion>".to_owned();
- parse::parse_stream_from_source_str(source_name, s, self.parse_sess())
+ parse::parse_stream_from_source_str(source_name, s, self.parse_sess(), None)
.into_trees().collect()
}
}
}
TokenTree::Token(span, token::CloseDelim(delim)) => {
let tree = TokenTree::Delimited(span, Delimited {
- delim: delim,
+ delim,
tts: result.into_iter().map(TokenStream::from).collect::<TokenStream>().into(),
});
result = results.pop().unwrap();
result.push(tree);
}
- tree @ _ => result.push(tree),
+ tree => result.push(tree),
}
}
result
}
pub fn parse_ty_panic(parser: &mut Parser) -> P<Ty> {
- panictry!(parser.parse_ty_no_plus())
+ panictry!(parser.parse_ty())
}
pub fn parse_stmt_panic(parser: &mut Parser) -> Option<Stmt> {
#[allow(non_upper_case_globals)]
fn expr_mk_token(cx: &ExtCtxt, sp: Span, tok: &token::Token) -> P<ast::Expr> {
macro_rules! mk_lit {
- ($name: expr, $suffix: expr, $($args: expr),*) => {{
- let inner = cx.expr_call(sp, mk_token_path(cx, sp, $name), vec![$($args),*]);
+ ($name: expr, $suffix: expr, $content: expr $(, $count: expr)*) => {{
+ let name = mk_name(cx, sp, ast::Ident::with_empty_ctxt($content));
+ let inner = cx.expr_call(sp, mk_token_path(cx, sp, $name), vec![
+ name $(, cx.expr_usize(sp, $count))*
+ ]);
let suffix = match $suffix {
Some(name) => cx.expr_some(sp, mk_name(cx, sp, ast::Ident::with_empty_ctxt(name))),
None => cx.expr_none(sp)
cx.expr_call(sp, mk_token_path(cx, sp, "Literal"), vec![inner, suffix])
}}
}
- match *tok {
+
+ let name = match *tok {
token::BinOp(binop) => {
return cx.expr_call(sp, mk_token_path(cx, sp, "BinOp"), vec![mk_binop(cx, sp, binop)]);
}
vec![mk_delim(cx, sp, delim)]);
}
- token::Literal(token::Byte(i), suf) => {
- let e_byte = mk_name(cx, sp, ast::Ident::with_empty_ctxt(i));
- return mk_lit!("Byte", suf, e_byte);
- }
-
- token::Literal(token::Char(i), suf) => {
- let e_char = mk_name(cx, sp, ast::Ident::with_empty_ctxt(i));
- return mk_lit!("Char", suf, e_char);
- }
-
- token::Literal(token::Integer(i), suf) => {
- let e_int = mk_name(cx, sp, ast::Ident::with_empty_ctxt(i));
- return mk_lit!("Integer", suf, e_int);
- }
-
- token::Literal(token::Float(fident), suf) => {
- let e_fident = mk_name(cx, sp, ast::Ident::with_empty_ctxt(fident));
- return mk_lit!("Float", suf, e_fident);
- }
-
- token::Literal(token::Str_(ident), suf) => {
- return mk_lit!("Str_", suf, mk_name(cx, sp, ast::Ident::with_empty_ctxt(ident)))
- }
-
- token::Literal(token::StrRaw(ident, n), suf) => {
- return mk_lit!("StrRaw", suf, mk_name(cx, sp, ast::Ident::with_empty_ctxt(ident)),
- cx.expr_usize(sp, n))
- }
+ token::Literal(token::Byte(i), suf) => return mk_lit!("Byte", suf, i),
+ token::Literal(token::Char(i), suf) => return mk_lit!("Char", suf, i),
+ token::Literal(token::Integer(i), suf) => return mk_lit!("Integer", suf, i),
+ token::Literal(token::Float(i), suf) => return mk_lit!("Float", suf, i),
+ token::Literal(token::Str_(i), suf) => return mk_lit!("Str_", suf, i),
+ token::Literal(token::StrRaw(i, n), suf) => return mk_lit!("StrRaw", suf, i, n),
+ token::Literal(token::ByteStr(i), suf) => return mk_lit!("ByteStr", suf, i),
+ token::Literal(token::ByteStrRaw(i, n), suf) => return mk_lit!("ByteStrRaw", suf, i, n),
token::Ident(ident) => {
return cx.expr_call(sp,
token::Interpolated(_) => panic!("quote! with interpolated token"),
- _ => ()
- }
-
- let name = match *tok {
token::Eq => "Eq",
token::Lt => "Lt",
token::Le => "Le",
token::At => "At",
token::Dot => "Dot",
token::DotDot => "DotDot",
+ token::DotDotDot => "DotDotDot",
token::Comma => "Comma",
token::Semi => "Semi",
token::Colon => "Colon",
token::Question => "Question",
token::Underscore => "Underscore",
token::Eof => "Eof",
- _ => panic!("unhandled token in quote!"),
+
+ token::Whitespace | token::Comment | token::Shebang(_) => {
+ panic!("unhandled token in quote!");
+ }
};
mk_token_path(cx, sp, name)
}