2020-01-11 17:02:46 +01:00
|
|
|
use crate::pp::Breaks::{Consistent, Inconsistent};
|
|
|
|
use crate::pp::{self, Breaks};
|
2019-02-07 02:33:01 +09:00
|
|
|
|
2020-02-29 20:37:32 +03:00
|
|
|
use rustc_ast::attr;
|
|
|
|
use rustc_ast::ptr::P;
|
2020-07-21 22:16:19 +03:00
|
|
|
use rustc_ast::token::{self, BinOpToken, CommentKind, DelimToken, Nonterminal, Token, TokenKind};
|
2020-06-24 17:45:08 +03:00
|
|
|
use rustc_ast::tokenstream::{TokenStream, TokenTree};
|
2020-07-22 11:42:36 +03:00
|
|
|
use rustc_ast::util::classify;
|
|
|
|
use rustc_ast::util::comments::{gather_comments, Comment, CommentStyle};
|
2020-02-29 20:37:32 +03:00
|
|
|
use rustc_ast::util::parser::{self, AssocOp, Fixity};
|
2020-04-27 23:26:11 +05:30
|
|
|
use rustc_ast::{self as ast, BlockCheckMode, PatKind, RangeEnd, RangeSyntax};
|
|
|
|
use rustc_ast::{GenericArg, MacArgs};
|
|
|
|
use rustc_ast::{GenericBound, SelfKind, TraitBoundModifier};
|
|
|
|
use rustc_ast::{InlineAsmOperand, InlineAsmRegOrRegClass};
|
|
|
|
use rustc_ast::{InlineAsmOptions, InlineAsmTemplatePiece};
|
2020-01-11 10:33:18 +01:00
|
|
|
use rustc_span::edition::Edition;
|
2020-02-21 01:21:17 +01:00
|
|
|
use rustc_span::source_map::{SourceMap, Spanned};
|
2020-04-19 13:00:18 +02:00
|
|
|
use rustc_span::symbol::{kw, sym, Ident, IdentPrinter, Symbol};
|
2020-01-01 19:25:28 +01:00
|
|
|
use rustc_span::{BytePos, FileName, Span};
|
2012-12-23 17:41:37 -05:00
|
|
|
|
2018-11-29 11:36:58 +11:00
|
|
|
use std::borrow::Cow;
|
2013-05-24 19:35:29 -07:00
|
|
|
|
2019-07-14 16:09:39 +03:00
|
|
|
pub enum MacHeader<'a> {
|
|
|
|
Path(&'a ast::Path),
|
|
|
|
Keyword(&'static str),
|
|
|
|
}
|
|
|
|
|
2014-03-16 20:58:11 +02:00
|
|
|
pub enum AnnNode<'a> {
|
2020-04-19 13:00:18 +02:00
|
|
|
Ident(&'a Ident),
|
|
|
|
Name(&'a Symbol),
|
2018-08-22 22:05:19 +01:00
|
|
|
Block(&'a ast::Block),
|
|
|
|
Item(&'a ast::Item),
|
|
|
|
SubItem(ast::NodeId),
|
|
|
|
Expr(&'a ast::Expr),
|
|
|
|
Pat(&'a ast::Pat),
|
2019-07-14 21:17:37 +01:00
|
|
|
Crate(&'a ast::Crate),
|
2011-07-05 11:48:19 +02:00
|
|
|
}
|
2013-08-29 15:24:33 -07:00
|
|
|
|
2014-01-09 15:05:33 +02:00
|
|
|
pub trait PpAnn {
|
2019-12-22 17:42:04 -05:00
|
|
|
fn pre(&self, _state: &mut State<'_>, _node: AnnNode<'_>) {}
|
|
|
|
fn post(&self, _state: &mut State<'_>, _node: AnnNode<'_>) {}
|
2013-08-29 15:24:33 -07:00
|
|
|
}
|
|
|
|
|
2015-03-30 09:38:59 -04:00
|
|
|
#[derive(Copy, Clone)]
|
2014-01-09 15:05:33 +02:00
|
|
|
pub struct NoAnn;
|
2011-07-05 11:48:19 +02:00
|
|
|
|
2014-01-09 15:05:33 +02:00
|
|
|
impl PpAnn for NoAnn {}
|
2013-08-29 15:24:33 -07:00
|
|
|
|
2019-07-05 18:29:15 -04:00
|
|
|
pub struct Comments<'a> {
|
2020-02-22 16:07:05 +02:00
|
|
|
sm: &'a SourceMap,
|
2020-07-22 11:42:36 +03:00
|
|
|
comments: Vec<Comment>,
|
2019-07-05 18:29:15 -04:00
|
|
|
current: usize,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl<'a> Comments<'a> {
|
2020-02-22 16:07:05 +02:00
|
|
|
pub fn new(sm: &'a SourceMap, filename: FileName, input: String) -> Comments<'a> {
|
2020-07-22 11:42:36 +03:00
|
|
|
let comments = gather_comments(sm, filename, input);
|
2020-02-22 16:07:05 +02:00
|
|
|
Comments { sm, comments, current: 0 }
|
2019-07-05 18:29:15 -04:00
|
|
|
}
|
|
|
|
|
2020-07-22 11:42:36 +03:00
|
|
|
pub fn next(&self) -> Option<Comment> {
|
2019-07-05 18:29:15 -04:00
|
|
|
self.comments.get(self.current).cloned()
|
|
|
|
}
|
|
|
|
|
|
|
|
pub fn trailing_comment(
|
2020-10-13 01:39:47 +02:00
|
|
|
&self,
|
2019-12-31 20:15:40 +03:00
|
|
|
span: rustc_span::Span,
|
2019-07-05 18:29:15 -04:00
|
|
|
next_pos: Option<BytePos>,
|
2020-07-22 11:42:36 +03:00
|
|
|
) -> Option<Comment> {
|
2019-07-05 18:29:15 -04:00
|
|
|
if let Some(cmnt) = self.next() {
|
2020-07-22 11:42:36 +03:00
|
|
|
if cmnt.style != CommentStyle::Trailing {
|
2019-12-22 17:42:04 -05:00
|
|
|
return None;
|
|
|
|
}
|
2020-02-22 16:07:05 +02:00
|
|
|
let span_line = self.sm.lookup_char_pos(span.hi());
|
|
|
|
let comment_line = self.sm.lookup_char_pos(cmnt.pos);
|
2019-07-05 18:29:15 -04:00
|
|
|
let next = next_pos.unwrap_or_else(|| cmnt.pos + BytePos(1));
|
|
|
|
if span.hi() < cmnt.pos && cmnt.pos < next && span_line.line == comment_line.line {
|
|
|
|
return Some(cmnt);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
None
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-03-17 22:27:37 -07:00
|
|
|
pub struct State<'a> {
|
2019-07-05 19:10:18 -04:00
|
|
|
pub s: pp::Printer,
|
2019-07-05 18:29:15 -04:00
|
|
|
comments: Option<Comments<'a>>,
|
2019-12-22 17:42:04 -05:00
|
|
|
ann: &'a (dyn PpAnn + 'a),
|
|
|
|
is_expanded: bool,
|
2013-02-04 14:02:01 -08:00
|
|
|
}
|
2011-07-05 11:48:19 +02:00
|
|
|
|
2019-06-24 12:12:56 -04:00
|
|
|
crate const INDENT_UNIT: usize = 4;
|
2011-07-05 11:48:19 +02:00
|
|
|
|
2014-06-09 13:12:30 -07:00
|
|
|
/// Requires you to pass an input filename and reader so that
|
2019-05-09 19:04:04 +03:00
|
|
|
/// it can scan the input text for comments to copy forward.
|
2019-12-22 17:42:04 -05:00
|
|
|
pub fn print_crate<'a>(
|
2020-02-22 16:07:05 +02:00
|
|
|
sm: &'a SourceMap,
|
2019-12-22 17:42:04 -05:00
|
|
|
krate: &ast::Crate,
|
|
|
|
filename: FileName,
|
|
|
|
input: String,
|
|
|
|
ann: &'a dyn PpAnn,
|
|
|
|
is_expanded: bool,
|
2020-01-11 10:33:18 +01:00
|
|
|
edition: Edition,
|
2019-12-22 17:42:04 -05:00
|
|
|
) -> String {
|
2019-07-05 18:32:04 -04:00
|
|
|
let mut s = State {
|
2019-07-05 19:10:18 -04:00
|
|
|
s: pp::mk_printer(),
|
2020-02-22 16:07:05 +02:00
|
|
|
comments: Some(Comments::new(sm, filename, input)),
|
2019-07-05 18:32:04 -04:00
|
|
|
ann,
|
|
|
|
is_expanded,
|
|
|
|
};
|
2017-01-17 01:14:53 +00:00
|
|
|
|
2020-11-13 00:35:46 +03:00
|
|
|
if is_expanded && !krate.attrs.iter().any(|attr| attr.has_name(sym::no_core)) {
|
2015-02-05 17:04:11 -08:00
|
|
|
// We need to print `#![no_std]` (and its feature gate) so that
|
|
|
|
// compiling pretty-printed source won't inject libstd again.
|
2019-09-06 03:56:45 +01:00
|
|
|
// However, we don't want these attributes in the AST because
|
2015-02-05 17:04:11 -08:00
|
|
|
// of the feature gate, so we fake them up here.
|
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
// `#![feature(prelude_import)]`
|
2020-04-19 13:00:18 +02:00
|
|
|
let pi_nested = attr::mk_nested_word_item(Ident::with_dummy_span(sym::prelude_import));
|
|
|
|
let list = attr::mk_list_item(Ident::with_dummy_span(sym::feature), vec![pi_nested]);
|
2019-07-30 14:18:19 -04:00
|
|
|
let fake_attr = attr::mk_attr_inner(list);
|
2019-06-24 14:15:11 -04:00
|
|
|
s.print_attribute(&fake_attr);
|
2015-02-05 17:04:11 -08:00
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
// Currently, in Rust 2018 we don't have `extern crate std;` at the crate
|
2019-08-25 22:36:13 +01:00
|
|
|
// root, so this is not needed, and actually breaks things.
|
2020-01-11 10:33:18 +01:00
|
|
|
if edition == Edition::Edition2015 {
|
2019-09-06 03:56:45 +01:00
|
|
|
// `#![no_std]`
|
2020-04-19 13:00:18 +02:00
|
|
|
let no_std_meta = attr::mk_word_item(Ident::with_dummy_span(sym::no_std));
|
2019-08-25 22:36:13 +01:00
|
|
|
let fake_attr = attr::mk_attr_inner(no_std_meta);
|
|
|
|
s.print_attribute(&fake_attr);
|
|
|
|
}
|
2015-02-05 17:04:11 -08:00
|
|
|
}
|
|
|
|
|
2021-02-14 21:14:12 +03:00
|
|
|
s.print_inner_attributes(&krate.attrs);
|
|
|
|
for item in &krate.items {
|
|
|
|
s.print_item(item);
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
s.print_remaining_comments();
|
2019-07-14 21:17:37 +01:00
|
|
|
s.ann.post(&mut s, AnnNode::Crate(krate));
|
2019-07-05 19:10:18 -04:00
|
|
|
s.s.eof()
|
2012-02-21 15:34:26 -08:00
|
|
|
}
|
|
|
|
|
2020-06-14 14:30:42 +03:00
|
|
|
// This makes printed token streams look slightly nicer,
|
|
|
|
// and also addresses some specific regressions described in #63896 and #73345.
|
2020-03-17 15:08:11 +01:00
|
|
|
fn tt_prepend_space(tt: &TokenTree, prev: &TokenTree) -> bool {
|
2020-06-14 14:30:42 +03:00
|
|
|
if let TokenTree::Token(token) = prev {
|
2020-07-21 22:16:19 +03:00
|
|
|
if let token::DocComment(comment_kind, ..) = token.kind {
|
|
|
|
return comment_kind != CommentKind::Line;
|
2020-06-14 14:30:42 +03:00
|
|
|
}
|
|
|
|
}
|
2019-08-25 20:41:52 +03:00
|
|
|
match tt {
|
2020-10-12 23:51:35 +02:00
|
|
|
TokenTree::Token(token) => token.kind != token::Comma,
|
|
|
|
TokenTree::Delimited(_, DelimToken::Paren, _) => {
|
|
|
|
!matches!(prev, TokenTree::Token(Token { kind: token::Ident(..), .. }))
|
|
|
|
}
|
|
|
|
TokenTree::Delimited(_, DelimToken::Bracket, _) => {
|
|
|
|
!matches!(prev, TokenTree::Token(Token { kind: token::Pound, .. }))
|
|
|
|
}
|
2020-06-14 14:30:42 +03:00
|
|
|
TokenTree::Delimited(..) => true,
|
2019-08-25 20:41:52 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-06-25 07:51:55 -06:00
|
|
|
fn binop_to_string(op: BinOpToken) -> &'static str {
|
2014-10-28 11:05:28 +11:00
|
|
|
match op {
|
2019-12-22 17:42:04 -05:00
|
|
|
token::Plus => "+",
|
|
|
|
token::Minus => "-",
|
|
|
|
token::Star => "*",
|
|
|
|
token::Slash => "/",
|
|
|
|
token::Percent => "%",
|
|
|
|
token::Caret => "^",
|
|
|
|
token::And => "&",
|
|
|
|
token::Or => "|",
|
|
|
|
token::Shl => "<<",
|
|
|
|
token::Shr => ">>",
|
2014-10-28 11:05:28 +11:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-21 22:16:19 +03:00
|
|
|
fn doc_comment_to_string(
|
|
|
|
comment_kind: CommentKind,
|
|
|
|
attr_style: ast::AttrStyle,
|
|
|
|
data: Symbol,
|
|
|
|
) -> String {
|
|
|
|
match (comment_kind, attr_style) {
|
|
|
|
(CommentKind::Line, ast::AttrStyle::Outer) => format!("///{}", data),
|
|
|
|
(CommentKind::Line, ast::AttrStyle::Inner) => format!("//!{}", data),
|
|
|
|
(CommentKind::Block, ast::AttrStyle::Outer) => format!("/**{}*/", data),
|
|
|
|
(CommentKind::Block, ast::AttrStyle::Inner) => format!("/*!{}*/", data),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-05-19 19:56:45 +03:00
|
|
|
pub fn literal_to_string(lit: token::Lit) -> String {
|
|
|
|
let token::Lit { kind, symbol, suffix } = lit;
|
2019-05-19 01:04:26 +03:00
|
|
|
let mut out = match kind {
|
2019-12-22 17:42:04 -05:00
|
|
|
token::Byte => format!("b'{}'", symbol),
|
|
|
|
token::Char => format!("'{}'", symbol),
|
|
|
|
token::Str => format!("\"{}\"", symbol),
|
|
|
|
token::StrRaw(n) => {
|
|
|
|
format!("r{delim}\"{string}\"{delim}", delim = "#".repeat(n as usize), string = symbol)
|
|
|
|
}
|
|
|
|
token::ByteStr => format!("b\"{}\"", symbol),
|
|
|
|
token::ByteStrRaw(n) => {
|
|
|
|
format!("br{delim}\"{string}\"{delim}", delim = "#".repeat(n as usize), string = symbol)
|
|
|
|
}
|
|
|
|
token::Integer | token::Float | token::Bool | token::Err => symbol.to_string(),
|
2019-05-09 19:04:04 +03:00
|
|
|
};
|
|
|
|
|
|
|
|
if let Some(suffix) = suffix {
|
|
|
|
out.push_str(&suffix.as_str())
|
|
|
|
}
|
|
|
|
|
|
|
|
out
|
|
|
|
}
|
|
|
|
|
2019-07-05 16:00:38 -04:00
|
|
|
fn visibility_qualified(vis: &ast::Visibility, s: &str) -> String {
|
2020-09-26 12:51:00 -04:00
|
|
|
format!("{}{}", State::new().to_string(|s| s.print_visibility(vis)), s)
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2011-05-28 19:16:18 -07:00
|
|
|
|
2019-07-09 09:26:50 -04:00
|
|
|
impl std::ops::Deref for State<'_> {
|
|
|
|
type Target = pp::Printer;
|
|
|
|
fn deref(&self) -> &Self::Target {
|
|
|
|
&self.s
|
2012-11-04 20:41:00 -08:00
|
|
|
}
|
2019-07-09 09:26:50 -04:00
|
|
|
}
|
2011-05-28 19:16:18 -07:00
|
|
|
|
2019-07-09 09:26:50 -04:00
|
|
|
impl std::ops::DerefMut for State<'_> {
|
|
|
|
fn deref_mut(&mut self) -> &mut Self::Target {
|
|
|
|
&mut self.s
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-07-09 09:26:50 -04:00
|
|
|
}
|
2011-05-28 19:16:18 -07:00
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
pub trait PrintState<'a>: std::ops::Deref<Target = pp::Printer> + std::ops::DerefMut {
|
2019-07-09 09:26:50 -04:00
|
|
|
fn comments(&mut self) -> &mut Option<Comments<'a>>;
|
2020-04-19 13:00:18 +02:00
|
|
|
fn print_ident(&mut self, ident: Ident);
|
2019-07-13 19:11:07 +03:00
|
|
|
fn print_generic_args(&mut self, args: &ast::GenericArgs, colons_before_params: bool);
|
2011-05-28 19:16:18 -07:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn strsep<T, F>(
|
|
|
|
&mut self,
|
|
|
|
sep: &'static str,
|
|
|
|
space_before: bool,
|
|
|
|
b: Breaks,
|
|
|
|
elts: &[T],
|
|
|
|
mut op: F,
|
|
|
|
) where
|
|
|
|
F: FnMut(&mut Self, &T),
|
2015-09-14 21:58:20 +12:00
|
|
|
{
|
2019-06-24 14:15:11 -04:00
|
|
|
self.rbox(0, b);
|
2019-07-14 01:05:52 +00:00
|
|
|
if let Some((first, rest)) = elts.split_first() {
|
|
|
|
op(self, first);
|
|
|
|
for elt in rest {
|
|
|
|
if space_before {
|
|
|
|
self.space();
|
2018-10-19 15:40:07 +01:00
|
|
|
}
|
|
|
|
self.word_space(sep);
|
2019-07-14 01:05:52 +00:00
|
|
|
op(self, elt);
|
2018-10-19 15:40:07 +01:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2019-07-14 01:05:52 +00:00
|
|
|
fn commasep<T, F>(&mut self, b: Breaks, elts: &[T], op: F)
|
2019-12-22 17:42:04 -05:00
|
|
|
where
|
|
|
|
F: FnMut(&mut Self, &T),
|
2018-10-19 15:40:07 +01:00
|
|
|
{
|
2019-07-14 01:05:52 +00:00
|
|
|
self.strsep(",", false, b, elts, op)
|
2018-10-19 15:40:07 +01:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn maybe_print_comment(&mut self, pos: BytePos) {
|
2016-10-12 20:54:41 +03:00
|
|
|
while let Some(ref cmnt) = self.next_comment() {
|
|
|
|
if cmnt.pos < pos {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_comment(cmnt);
|
2016-10-12 20:54:41 +03:00
|
|
|
} else {
|
2019-12-22 17:42:04 -05:00
|
|
|
break;
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-22 11:42:36 +03:00
|
|
|
fn print_comment(&mut self, cmnt: &Comment) {
|
2019-06-24 14:15:11 -04:00
|
|
|
match cmnt.style {
|
2020-07-22 11:42:36 +03:00
|
|
|
CommentStyle::Mixed => {
|
2020-08-02 15:27:03 +01:00
|
|
|
if !self.is_beginning_of_line() {
|
|
|
|
self.zerobreak();
|
|
|
|
}
|
2020-07-12 18:22:09 +01:00
|
|
|
if let Some((last, lines)) = cmnt.lines.split_last() {
|
|
|
|
self.ibox(0);
|
|
|
|
|
|
|
|
for line in lines {
|
|
|
|
self.word(line.clone());
|
|
|
|
self.hardbreak()
|
|
|
|
}
|
|
|
|
|
|
|
|
self.word(last.clone());
|
|
|
|
self.space();
|
|
|
|
|
|
|
|
self.end();
|
|
|
|
}
|
2019-07-09 09:51:56 -04:00
|
|
|
self.zerobreak()
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2020-07-22 11:42:36 +03:00
|
|
|
CommentStyle::Isolated => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.hardbreak_if_not_bol();
|
2015-09-14 21:58:20 +12:00
|
|
|
for line in &cmnt.lines {
|
|
|
|
// Don't print empty lines because they will end up as trailing
|
2019-09-06 03:56:45 +01:00
|
|
|
// whitespace.
|
2015-09-14 21:58:20 +12:00
|
|
|
if !line.is_empty() {
|
2019-07-09 09:51:56 -04:00
|
|
|
self.word(line.clone());
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-07-09 09:51:56 -04:00
|
|
|
self.hardbreak();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
2020-07-22 11:42:36 +03:00
|
|
|
CommentStyle::Trailing => {
|
2019-07-09 09:51:56 -04:00
|
|
|
if !self.is_beginning_of_line() {
|
|
|
|
self.word(" ");
|
2016-10-12 20:54:41 +03:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
if cmnt.lines.len() == 1 {
|
2019-07-09 09:51:56 -04:00
|
|
|
self.word(cmnt.lines[0].clone());
|
|
|
|
self.hardbreak()
|
2015-09-14 21:58:20 +12:00
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(0);
|
2015-09-14 21:58:20 +12:00
|
|
|
for line in &cmnt.lines {
|
|
|
|
if !line.is_empty() {
|
2019-07-09 09:51:56 -04:00
|
|
|
self.word(line.clone());
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-07-09 09:51:56 -04:00
|
|
|
self.hardbreak();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
2020-07-22 11:42:36 +03:00
|
|
|
CommentStyle::BlankLine => {
|
2015-09-14 21:58:20 +12:00
|
|
|
// We need to do at least one, possibly two hardbreaks.
|
2019-07-09 09:51:56 -04:00
|
|
|
let twice = match self.last_token() {
|
2019-07-05 09:58:34 -04:00
|
|
|
pp::Token::String(s) => ";" == s,
|
2019-07-07 10:51:18 -04:00
|
|
|
pp::Token::Begin(_) => true,
|
|
|
|
pp::Token::End => true,
|
2019-12-22 17:42:04 -05:00
|
|
|
_ => false,
|
2015-09-14 21:58:20 +12:00
|
|
|
};
|
2019-07-07 10:51:18 -04:00
|
|
|
if twice {
|
2019-07-09 09:51:56 -04:00
|
|
|
self.hardbreak();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-07-09 09:51:56 -04:00
|
|
|
self.hardbreak();
|
2017-06-25 06:38:13 -06:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2020-02-22 16:07:05 +02:00
|
|
|
if let Some(cmnts) = self.comments() {
|
|
|
|
cmnts.current += 1;
|
2019-07-05 18:29:15 -04:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2020-07-22 11:42:36 +03:00
|
|
|
fn next_comment(&mut self) -> Option<Comment> {
|
2019-07-05 18:29:15 -04:00
|
|
|
self.comments().as_mut().and_then(|c| c.next())
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_literal(&mut self, lit: &ast::Lit) {
|
|
|
|
self.maybe_print_comment(lit.span.lo());
|
2019-07-09 09:51:56 -04:00
|
|
|
self.word(lit.token.to_string())
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_string(&mut self, st: &str, style: ast::StrStyle) {
|
2015-09-14 21:58:20 +12:00
|
|
|
let st = match style {
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::StrStyle::Cooked => (format!("\"{}\"", st.escape_debug())),
|
2016-02-09 18:01:08 +01:00
|
|
|
ast::StrStyle::Raw(n) => {
|
2020-01-23 00:42:35 -05:00
|
|
|
format!("r{delim}\"{string}\"{delim}", delim = "#".repeat(n as usize), string = st)
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
};
|
2019-07-09 09:51:56 -04:00
|
|
|
self.word(st)
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2020-07-08 20:03:37 +10:00
|
|
|
fn print_symbol(&mut self, sym: Symbol, style: ast::StrStyle) {
|
|
|
|
self.print_string(&sym.as_str(), style);
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_inner_attributes(&mut self, attrs: &[ast::Attribute]) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_either_attributes(attrs, ast::AttrStyle::Inner, false, true)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_inner_attributes_no_trailing_hardbreak(&mut self, attrs: &[ast::Attribute]) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_either_attributes(attrs, ast::AttrStyle::Inner, false, false)
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_outer_attributes(&mut self, attrs: &[ast::Attribute]) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_either_attributes(attrs, ast::AttrStyle::Outer, false, true)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_inner_attributes_inline(&mut self, attrs: &[ast::Attribute]) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_either_attributes(attrs, ast::AttrStyle::Inner, true, true)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_outer_attributes_inline(&mut self, attrs: &[ast::Attribute]) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_either_attributes(attrs, ast::AttrStyle::Outer, true, true)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_either_attributes(
|
|
|
|
&mut self,
|
|
|
|
attrs: &[ast::Attribute],
|
|
|
|
kind: ast::AttrStyle,
|
|
|
|
is_inline: bool,
|
|
|
|
trailing_hardbreak: bool,
|
|
|
|
) {
|
2015-09-14 21:58:20 +12:00
|
|
|
let mut count = 0;
|
|
|
|
for attr in attrs {
|
2016-11-14 12:00:25 +00:00
|
|
|
if attr.style == kind {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_attribute_inline(attr, is_inline);
|
2016-06-16 21:16:55 +01:00
|
|
|
if is_inline {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
2016-06-16 21:16:55 +01:00
|
|
|
}
|
|
|
|
count += 1;
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
2015-11-03 17:39:51 +01:00
|
|
|
if count > 0 && trailing_hardbreak && !is_inline {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.hardbreak_if_not_bol();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_attribute(&mut self, attr: &ast::Attribute) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_attribute_inline(attr, false)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_attribute_inline(&mut self, attr: &ast::Attribute, is_inline: bool) {
|
2015-11-03 17:39:51 +01:00
|
|
|
if !is_inline {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.hardbreak_if_not_bol();
|
2015-11-03 17:39:51 +01:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(attr.span.lo());
|
2019-10-24 06:33:12 +11:00
|
|
|
match attr.kind {
|
2020-11-05 20:27:48 +03:00
|
|
|
ast::AttrKind::Normal(ref item, _) => {
|
2019-10-24 06:33:12 +11:00
|
|
|
match attr.style {
|
|
|
|
ast::AttrStyle::Inner => self.word("#!["),
|
|
|
|
ast::AttrStyle::Outer => self.word("#["),
|
|
|
|
}
|
|
|
|
self.print_attr_item(&item, attr.span);
|
|
|
|
self.word("]");
|
|
|
|
}
|
2020-07-21 22:16:19 +03:00
|
|
|
ast::AttrKind::DocComment(comment_kind, data) => {
|
|
|
|
self.word(doc_comment_to_string(comment_kind, attr.style, data));
|
2019-10-24 06:33:12 +11:00
|
|
|
self.hardbreak()
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-08-18 01:10:56 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
fn print_attr_item(&mut self, item: &ast::AttrItem, span: Span) {
|
|
|
|
self.ibox(0);
|
2019-12-01 17:07:38 +03:00
|
|
|
match &item.args {
|
|
|
|
MacArgs::Delimited(_, delim, tokens) => self.print_mac_common(
|
|
|
|
Some(MacHeader::Path(&item.path)),
|
|
|
|
false,
|
|
|
|
None,
|
|
|
|
delim.to_token(),
|
2020-06-24 17:45:08 +03:00
|
|
|
tokens,
|
2019-12-01 17:07:38 +03:00
|
|
|
true,
|
|
|
|
span,
|
|
|
|
),
|
|
|
|
MacArgs::Empty | MacArgs::Eq(..) => {
|
2019-08-18 01:10:56 +03:00
|
|
|
self.print_path(&item.path, false, 0);
|
2020-12-19 23:38:22 +03:00
|
|
|
if let MacArgs::Eq(_, token) = &item.args {
|
2019-08-18 01:10:56 +03:00
|
|
|
self.space();
|
2019-12-01 17:07:38 +03:00
|
|
|
self.word_space("=");
|
2020-12-19 23:38:22 +03:00
|
|
|
let token_str = self.token_to_string_ext(token, true);
|
|
|
|
self.word(token_str);
|
2019-07-13 21:01:04 +03:00
|
|
|
}
|
2017-03-03 09:23:59 +00:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2019-08-18 01:10:56 +03:00
|
|
|
self.end();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_meta_list_item(&mut self, item: &ast::NestedMetaItem) {
|
2019-03-03 20:56:24 +03:00
|
|
|
match item {
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::NestedMetaItem::MetaItem(ref mi) => self.print_meta_item(mi),
|
|
|
|
ast::NestedMetaItem::Literal(ref lit) => self.print_literal(lit),
|
2016-08-19 18:58:14 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_meta_item(&mut self, item: &ast::MetaItem) {
|
|
|
|
self.ibox(INDENT_UNIT);
|
2019-09-26 18:04:05 +01:00
|
|
|
match item.kind {
|
2019-07-13 19:11:07 +03:00
|
|
|
ast::MetaItemKind::Word => self.print_path(&item.path, false, 0),
|
2016-11-15 07:37:10 +00:00
|
|
|
ast::MetaItemKind::NameValue(ref value) => {
|
2019-07-13 19:11:07 +03:00
|
|
|
self.print_path(&item.path, false, 0);
|
2019-07-09 09:51:56 -04:00
|
|
|
self.space();
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("=");
|
|
|
|
self.print_literal(value);
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2016-11-15 07:37:10 +00:00
|
|
|
ast::MetaItemKind::List(ref items) => {
|
2019-07-13 19:11:07 +03:00
|
|
|
self.print_path(&item.path, false, 0);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2019-12-22 17:42:04 -05:00
|
|
|
self.commasep(Consistent, &items[..], |s, i| s.print_meta_list_item(i));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2015-11-03 17:39:51 +01:00
|
|
|
|
2017-03-03 09:23:59 +00:00
|
|
|
/// This doesn't deserve to be called "pretty" printing, but it should be
|
|
|
|
/// meaning-preserving. A quick hack that might help would be to look at the
|
|
|
|
/// spans embedded in the TTs to decide where to put spaces and newlines.
|
|
|
|
/// But it'd be better to parse these according to the grammar of the
|
|
|
|
/// appropriate macro, transcribe back into the grammar we just parsed from,
|
|
|
|
/// and then pretty-print the resulting AST nodes (so, e.g., we print
|
|
|
|
/// expression arguments as expressions). It can be done! I think.
|
2020-06-24 17:45:08 +03:00
|
|
|
fn print_tt(&mut self, tt: &TokenTree, convert_dollar_crate: bool) {
|
2017-03-03 09:23:59 +00:00
|
|
|
match tt {
|
2020-06-24 17:45:08 +03:00
|
|
|
TokenTree::Token(token) => {
|
2020-09-26 12:41:53 -04:00
|
|
|
let token_str = self.token_to_string_ext(&token, convert_dollar_crate);
|
|
|
|
self.word(token_str);
|
2020-03-22 13:36:56 +01:00
|
|
|
if let token::DocComment(..) = token.kind {
|
|
|
|
self.hardbreak()
|
2017-03-03 09:23:59 +00:00
|
|
|
}
|
|
|
|
}
|
2019-07-13 23:08:29 +03:00
|
|
|
TokenTree::Delimited(dspan, delim, tts) => {
|
|
|
|
self.print_mac_common(
|
2019-12-22 17:42:04 -05:00
|
|
|
None,
|
|
|
|
false,
|
|
|
|
None,
|
2020-06-24 17:45:08 +03:00
|
|
|
*delim,
|
2019-12-22 17:42:04 -05:00
|
|
|
tts,
|
|
|
|
convert_dollar_crate,
|
|
|
|
dspan.entire(),
|
2019-07-13 23:08:29 +03:00
|
|
|
);
|
|
|
|
}
|
2017-03-03 09:23:59 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-06-24 17:45:08 +03:00
|
|
|
fn print_tts(&mut self, tts: &TokenStream, convert_dollar_crate: bool) {
|
|
|
|
let mut iter = tts.trees().peekable();
|
2020-03-17 15:08:11 +01:00
|
|
|
while let Some(tt) = iter.next() {
|
2020-06-24 17:45:08 +03:00
|
|
|
self.print_tt(&tt, convert_dollar_crate);
|
|
|
|
if let Some(next) = iter.peek() {
|
|
|
|
if tt_prepend_space(next, &tt) {
|
|
|
|
self.space();
|
|
|
|
}
|
2017-03-03 09:23:59 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
|
2019-07-13 19:11:07 +03:00
|
|
|
fn print_mac_common(
|
|
|
|
&mut self,
|
2019-07-14 16:09:39 +03:00
|
|
|
header: Option<MacHeader<'_>>,
|
2019-07-13 19:11:07 +03:00
|
|
|
has_bang: bool,
|
2020-04-19 13:00:18 +02:00
|
|
|
ident: Option<Ident>,
|
2019-07-13 23:08:29 +03:00
|
|
|
delim: DelimToken,
|
2020-06-24 17:45:08 +03:00
|
|
|
tts: &TokenStream,
|
2019-07-13 23:08:29 +03:00
|
|
|
convert_dollar_crate: bool,
|
2019-07-13 19:11:07 +03:00
|
|
|
span: Span,
|
|
|
|
) {
|
2019-07-14 00:11:59 +03:00
|
|
|
if delim == DelimToken::Brace {
|
|
|
|
self.cbox(INDENT_UNIT);
|
|
|
|
}
|
2019-07-14 16:09:39 +03:00
|
|
|
match header {
|
|
|
|
Some(MacHeader::Path(path)) => self.print_path(path, false, 0),
|
|
|
|
Some(MacHeader::Keyword(kw)) => self.word(kw),
|
|
|
|
None => {}
|
2019-07-13 23:08:29 +03:00
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
if has_bang {
|
|
|
|
self.word("!");
|
|
|
|
}
|
2019-07-13 20:35:46 +03:00
|
|
|
if let Some(ident) = ident {
|
2019-07-14 00:11:59 +03:00
|
|
|
self.nbsp();
|
2019-07-13 20:35:46 +03:00
|
|
|
self.print_ident(ident);
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
match delim {
|
2019-07-13 23:08:29 +03:00
|
|
|
DelimToken::Brace => {
|
2019-07-14 16:09:39 +03:00
|
|
|
if header.is_some() || has_bang || ident.is_some() {
|
2019-07-14 00:11:59 +03:00
|
|
|
self.nbsp();
|
|
|
|
}
|
|
|
|
self.word("{");
|
|
|
|
if !tts.is_empty() {
|
|
|
|
self.space();
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
}
|
2020-09-26 12:41:53 -04:00
|
|
|
_ => {
|
|
|
|
let token_str = self.token_kind_to_string(&token::OpenDelim(delim));
|
|
|
|
self.word(token_str)
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
}
|
2019-07-13 23:11:04 +03:00
|
|
|
self.ibox(0);
|
2019-07-13 23:08:29 +03:00
|
|
|
self.print_tts(tts, convert_dollar_crate);
|
2019-07-13 23:11:04 +03:00
|
|
|
self.end();
|
2019-07-13 19:11:07 +03:00
|
|
|
match delim {
|
2019-07-13 23:08:29 +03:00
|
|
|
DelimToken::Brace => self.bclose(span),
|
2020-09-26 12:41:53 -04:00
|
|
|
_ => {
|
|
|
|
let token_str = self.token_kind_to_string(&token::CloseDelim(delim));
|
|
|
|
self.word(token_str)
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
}
|
2015-09-14 21:58:20 +12:00
|
|
|
}
|
2011-08-02 15:25:06 -07:00
|
|
|
|
2019-07-13 19:11:07 +03:00
|
|
|
fn print_path(&mut self, path: &ast::Path, colons_before_params: bool, depth: usize) {
|
|
|
|
self.maybe_print_comment(path.span.lo());
|
|
|
|
|
|
|
|
for (i, segment) in path.segments[..path.segments.len() - depth].iter().enumerate() {
|
|
|
|
if i > 0 {
|
|
|
|
self.word("::")
|
|
|
|
}
|
|
|
|
self.print_path_segment(segment, colons_before_params);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
fn print_path_segment(&mut self, segment: &ast::PathSegment, colons_before_params: bool) {
|
|
|
|
if segment.ident.name != kw::PathRoot {
|
|
|
|
self.print_ident(segment.ident);
|
|
|
|
if let Some(ref args) = segment.args {
|
|
|
|
self.print_generic_args(args, colons_before_params);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
fn head<S: Into<Cow<'static, str>>>(&mut self, w: S) {
|
2018-11-29 11:36:58 +11:00
|
|
|
let w = w.into();
|
2019-09-06 03:56:45 +01:00
|
|
|
// Outer-box is consistent.
|
2019-06-24 14:15:11 -04:00
|
|
|
self.cbox(INDENT_UNIT);
|
2019-09-06 03:56:45 +01:00
|
|
|
// Head-box is inconsistent.
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(w.len() + 1);
|
2019-09-06 03:56:45 +01:00
|
|
|
// Keyword that starts the head.
|
2014-03-16 20:58:11 +02:00
|
|
|
if !w.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp(w);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2012-04-19 14:46:11 -07:00
|
|
|
|
2019-07-13 19:11:07 +03:00
|
|
|
fn bopen(&mut self) {
|
|
|
|
self.word("{");
|
2019-09-06 03:56:45 +01:00
|
|
|
self.end(); // Close the head-box.
|
2013-12-27 14:11:01 -08:00
|
|
|
}
|
2011-06-15 11:19:50 -07:00
|
|
|
|
2019-12-31 20:15:40 +03:00
|
|
|
fn bclose_maybe_open(&mut self, span: rustc_span::Span, close_box: bool) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(span.hi());
|
2019-07-09 09:30:08 -04:00
|
|
|
self.break_offset_if_not_bol(1, -(INDENT_UNIT as isize));
|
2019-07-13 19:11:07 +03:00
|
|
|
self.word("}");
|
2014-03-16 20:58:11 +02:00
|
|
|
if close_box {
|
2019-09-06 03:56:45 +01:00
|
|
|
self.end(); // Close the outer-box.
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
|
2019-12-31 20:15:40 +03:00
|
|
|
fn bclose(&mut self, span: rustc_span::Span) {
|
2019-07-09 09:30:08 -04:00
|
|
|
self.bclose_maybe_open(span, true)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2014-01-29 17:39:21 -08:00
|
|
|
|
2019-07-13 19:11:07 +03:00
|
|
|
fn break_offset_if_not_bol(&mut self, n: usize, off: isize) {
|
|
|
|
if !self.is_beginning_of_line() {
|
|
|
|
self.break_offset(n, off)
|
2020-10-26 21:02:48 -04:00
|
|
|
} else if off != 0 && self.last_token().is_hardbreak_tok() {
|
|
|
|
// We do something pretty sketchy here: tuck the nonzero
|
|
|
|
// offset-adjustment we were going to deposit along with the
|
|
|
|
// break into the previous hardbreak.
|
|
|
|
self.replace_last_token(pp::Printer::hardbreak_tok_offset(off));
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2020-09-26 12:41:53 -04:00
|
|
|
|
|
|
|
fn nonterminal_to_string(&self, nt: &Nonterminal) -> String {
|
|
|
|
match *nt {
|
|
|
|
token::NtExpr(ref e) => self.expr_to_string(e),
|
|
|
|
token::NtMeta(ref e) => self.attr_item_to_string(e),
|
|
|
|
token::NtTy(ref e) => self.ty_to_string(e),
|
|
|
|
token::NtPath(ref e) => self.path_to_string(e),
|
|
|
|
token::NtItem(ref e) => self.item_to_string(e),
|
|
|
|
token::NtBlock(ref e) => self.block_to_string(e),
|
|
|
|
token::NtStmt(ref e) => self.stmt_to_string(e),
|
|
|
|
token::NtPat(ref e) => self.pat_to_string(e),
|
|
|
|
token::NtIdent(e, is_raw) => IdentPrinter::for_ast_ident(e, is_raw).to_string(),
|
|
|
|
token::NtLifetime(e) => e.to_string(),
|
|
|
|
token::NtLiteral(ref e) => self.expr_to_string(e),
|
|
|
|
token::NtTT(ref tree) => self.tt_to_string(tree),
|
|
|
|
token::NtVis(ref e) => self.vis_to_string(e),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// Print the token kind precisely, without converting `$crate` into its respective crate name.
|
|
|
|
fn token_kind_to_string(&self, tok: &TokenKind) -> String {
|
|
|
|
self.token_kind_to_string_ext(tok, None)
|
|
|
|
}
|
|
|
|
|
|
|
|
fn token_kind_to_string_ext(
|
|
|
|
&self,
|
|
|
|
tok: &TokenKind,
|
|
|
|
convert_dollar_crate: Option<Span>,
|
|
|
|
) -> String {
|
|
|
|
match *tok {
|
|
|
|
token::Eq => "=".to_string(),
|
|
|
|
token::Lt => "<".to_string(),
|
|
|
|
token::Le => "<=".to_string(),
|
|
|
|
token::EqEq => "==".to_string(),
|
|
|
|
token::Ne => "!=".to_string(),
|
|
|
|
token::Ge => ">=".to_string(),
|
|
|
|
token::Gt => ">".to_string(),
|
|
|
|
token::Not => "!".to_string(),
|
|
|
|
token::Tilde => "~".to_string(),
|
|
|
|
token::OrOr => "||".to_string(),
|
|
|
|
token::AndAnd => "&&".to_string(),
|
|
|
|
token::BinOp(op) => binop_to_string(op).to_string(),
|
|
|
|
token::BinOpEq(op) => format!("{}=", binop_to_string(op)),
|
|
|
|
|
|
|
|
/* Structural symbols */
|
|
|
|
token::At => "@".to_string(),
|
|
|
|
token::Dot => ".".to_string(),
|
|
|
|
token::DotDot => "..".to_string(),
|
|
|
|
token::DotDotDot => "...".to_string(),
|
|
|
|
token::DotDotEq => "..=".to_string(),
|
|
|
|
token::Comma => ",".to_string(),
|
|
|
|
token::Semi => ";".to_string(),
|
|
|
|
token::Colon => ":".to_string(),
|
|
|
|
token::ModSep => "::".to_string(),
|
|
|
|
token::RArrow => "->".to_string(),
|
|
|
|
token::LArrow => "<-".to_string(),
|
|
|
|
token::FatArrow => "=>".to_string(),
|
|
|
|
token::OpenDelim(token::Paren) => "(".to_string(),
|
|
|
|
token::CloseDelim(token::Paren) => ")".to_string(),
|
|
|
|
token::OpenDelim(token::Bracket) => "[".to_string(),
|
|
|
|
token::CloseDelim(token::Bracket) => "]".to_string(),
|
|
|
|
token::OpenDelim(token::Brace) => "{".to_string(),
|
|
|
|
token::CloseDelim(token::Brace) => "}".to_string(),
|
|
|
|
token::OpenDelim(token::NoDelim) | token::CloseDelim(token::NoDelim) => "".to_string(),
|
|
|
|
token::Pound => "#".to_string(),
|
|
|
|
token::Dollar => "$".to_string(),
|
|
|
|
token::Question => "?".to_string(),
|
|
|
|
token::SingleQuote => "'".to_string(),
|
|
|
|
|
|
|
|
/* Literals */
|
|
|
|
token::Literal(lit) => literal_to_string(lit),
|
|
|
|
|
|
|
|
/* Name components */
|
|
|
|
token::Ident(s, is_raw) => {
|
|
|
|
IdentPrinter::new(s, is_raw, convert_dollar_crate).to_string()
|
|
|
|
}
|
|
|
|
token::Lifetime(s) => s.to_string(),
|
|
|
|
|
|
|
|
/* Other */
|
|
|
|
token::DocComment(comment_kind, attr_style, data) => {
|
|
|
|
doc_comment_to_string(comment_kind, attr_style, data)
|
|
|
|
}
|
|
|
|
token::Eof => "<eof>".to_string(),
|
|
|
|
|
|
|
|
token::Interpolated(ref nt) => self.nonterminal_to_string(nt),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// Print the token precisely, without converting `$crate` into its respective crate name.
|
|
|
|
fn token_to_string(&self, token: &Token) -> String {
|
|
|
|
self.token_to_string_ext(token, false)
|
|
|
|
}
|
|
|
|
|
|
|
|
fn token_to_string_ext(&self, token: &Token, convert_dollar_crate: bool) -> String {
|
|
|
|
let convert_dollar_crate = convert_dollar_crate.then_some(token.span);
|
|
|
|
self.token_kind_to_string_ext(&token.kind, convert_dollar_crate)
|
|
|
|
}
|
|
|
|
|
|
|
|
fn ty_to_string(&self, ty: &ast::Ty) -> String {
|
|
|
|
self.to_string(|s| s.print_type(ty))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn bounds_to_string(&self, bounds: &[ast::GenericBound]) -> String {
|
|
|
|
self.to_string(|s| s.print_type_bounds("", bounds))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn pat_to_string(&self, pat: &ast::Pat) -> String {
|
|
|
|
self.to_string(|s| s.print_pat(pat))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn expr_to_string(&self, e: &ast::Expr) -> String {
|
|
|
|
self.to_string(|s| s.print_expr(e))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn tt_to_string(&self, tt: &TokenTree) -> String {
|
|
|
|
self.to_string(|s| s.print_tt(tt, false))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn tts_to_string(&self, tokens: &TokenStream) -> String {
|
|
|
|
self.to_string(|s| s.print_tts(tokens, false))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn stmt_to_string(&self, stmt: &ast::Stmt) -> String {
|
|
|
|
self.to_string(|s| s.print_stmt(stmt))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn item_to_string(&self, i: &ast::Item) -> String {
|
|
|
|
self.to_string(|s| s.print_item(i))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn generic_params_to_string(&self, generic_params: &[ast::GenericParam]) -> String {
|
|
|
|
self.to_string(|s| s.print_generic_params(generic_params))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn path_to_string(&self, p: &ast::Path) -> String {
|
|
|
|
self.to_string(|s| s.print_path(p, false, 0))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn path_segment_to_string(&self, p: &ast::PathSegment) -> String {
|
|
|
|
self.to_string(|s| s.print_path_segment(p, false))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn vis_to_string(&self, v: &ast::Visibility) -> String {
|
|
|
|
self.to_string(|s| s.print_visibility(v))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn block_to_string(&self, blk: &ast::Block) -> String {
|
|
|
|
self.to_string(|s| {
|
|
|
|
// Containing cbox, will be closed by `print_block` at `}`.
|
|
|
|
s.cbox(INDENT_UNIT);
|
|
|
|
// Head-ibox, will be closed by `print_block` after `{`.
|
|
|
|
s.ibox(0);
|
|
|
|
s.print_block(blk)
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
|
|
|
fn meta_list_item_to_string(&self, li: &ast::NestedMetaItem) -> String {
|
|
|
|
self.to_string(|s| s.print_meta_list_item(li))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn attr_item_to_string(&self, ai: &ast::AttrItem) -> String {
|
|
|
|
self.to_string(|s| s.print_attr_item(ai, ai.path.span))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn attribute_to_string(&self, attr: &ast::Attribute) -> String {
|
|
|
|
self.to_string(|s| s.print_attribute(attr))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn param_to_string(&self, arg: &ast::Param) -> String {
|
|
|
|
self.to_string(|s| s.print_param(arg, false))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn to_string(&self, f: impl FnOnce(&mut State<'_>)) -> String {
|
|
|
|
let mut printer = State::new();
|
|
|
|
f(&mut printer);
|
|
|
|
printer.s.eof()
|
|
|
|
}
|
2019-07-13 19:11:07 +03:00
|
|
|
}
|
2011-03-17 17:39:47 -07:00
|
|
|
|
2019-07-13 19:11:07 +03:00
|
|
|
impl<'a> PrintState<'a> for State<'a> {
|
|
|
|
fn comments(&mut self) -> &mut Option<Comments<'a>> {
|
|
|
|
&mut self.comments
|
|
|
|
}
|
|
|
|
|
2020-04-19 13:00:18 +02:00
|
|
|
fn print_ident(&mut self, ident: Ident) {
|
2020-02-23 01:29:36 +03:00
|
|
|
self.s.word(IdentPrinter::for_ast_ident(ident, ident.is_raw_guess()).to_string());
|
2019-07-13 19:11:07 +03:00
|
|
|
self.ann.post(self, AnnNode::Ident(&ident))
|
|
|
|
}
|
|
|
|
|
|
|
|
fn print_generic_args(&mut self, args: &ast::GenericArgs, colons_before_params: bool) {
|
|
|
|
if colons_before_params {
|
|
|
|
self.s.word("::")
|
|
|
|
}
|
|
|
|
|
|
|
|
match *args {
|
|
|
|
ast::GenericArgs::AngleBracketed(ref data) => {
|
|
|
|
self.s.word("<");
|
2020-03-22 04:40:05 +01:00
|
|
|
self.commasep(Inconsistent, &data.args, |s, arg| match arg {
|
|
|
|
ast::AngleBracketedArg::Arg(a) => s.print_generic_arg(a),
|
|
|
|
ast::AngleBracketedArg::Constraint(c) => s.print_assoc_constraint(c),
|
2019-07-13 19:11:07 +03:00
|
|
|
});
|
|
|
|
self.s.word(">")
|
|
|
|
}
|
|
|
|
|
|
|
|
ast::GenericArgs::Parenthesized(ref data) => {
|
|
|
|
self.s.word("(");
|
2019-12-01 16:00:08 +01:00
|
|
|
self.commasep(Inconsistent, &data.inputs, |s, ty| s.print_type(ty));
|
2019-07-13 19:11:07 +03:00
|
|
|
self.s.word(")");
|
2019-12-01 16:00:08 +01:00
|
|
|
self.print_fn_ret_ty(&data.output);
|
2019-07-13 19:11:07 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
impl<'a> State<'a> {
|
2020-09-26 12:41:53 -04:00
|
|
|
pub fn new() -> State<'a> {
|
2021-01-07 17:58:05 +03:00
|
|
|
State { s: pp::mk_printer(), comments: None, ann: &NoAnn, is_expanded: false }
|
2020-09-26 12:51:00 -04:00
|
|
|
}
|
|
|
|
|
2014-03-16 20:58:11 +02:00
|
|
|
// Synthesizes a comment that was not textually present in the original source
|
|
|
|
// file.
|
2019-06-24 14:15:11 -04:00
|
|
|
pub fn synth_comment(&mut self, text: String) {
|
|
|
|
self.s.word("/*");
|
|
|
|
self.s.space();
|
|
|
|
self.s.word(text);
|
|
|
|
self.s.space();
|
2017-06-24 21:22:42 -06:00
|
|
|
self.s.word("*/")
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn commasep_cmnt<T, F, G>(&mut self, b: Breaks, elts: &[T], mut op: F, mut get_span: G)
|
|
|
|
where
|
2019-06-24 14:15:11 -04:00
|
|
|
F: FnMut(&mut State<'_>, &T),
|
2019-12-31 20:15:40 +03:00
|
|
|
G: FnMut(&T) -> rustc_span::Span,
|
2014-12-08 13:28:32 -05:00
|
|
|
{
|
2019-06-24 14:15:11 -04:00
|
|
|
self.rbox(0, b);
|
2014-03-16 20:58:11 +02:00
|
|
|
let len = elts.len();
|
2017-05-16 09:21:30 +02:00
|
|
|
let mut i = 0;
|
|
|
|
for elt in elts {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(get_span(elt).hi());
|
|
|
|
op(self, elt);
|
2017-05-16 09:21:30 +02:00
|
|
|
i += 1;
|
2014-03-16 20:58:11 +02:00
|
|
|
if i < len {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(",");
|
2019-12-22 17:42:04 -05:00
|
|
|
self.maybe_print_trailing_comment(get_span(elt), Some(get_span(&elts[i]).hi()));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.space_if_not_bol();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2011-07-26 15:37:36 -07:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn commasep_exprs(&mut self, b: Breaks, exprs: &[P<ast::Expr>]) {
|
2017-05-12 20:05:39 +02:00
|
|
|
self.commasep_cmnt(b, exprs, |s, e| s.print_expr(e), |e| e.span)
|
2012-03-08 18:10:07 -08:00
|
|
|
}
|
|
|
|
|
2020-04-27 23:26:11 +05:30
|
|
|
crate fn print_foreign_mod(&mut self, nmod: &ast::ForeignMod, attrs: &[ast::Attribute]) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_inner_attributes(attrs);
|
2015-01-31 12:20:46 -05:00
|
|
|
for item in &nmod.items {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_foreign_item(item);
|
2014-01-09 15:05:33 +02:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-10-15 22:48:13 +02:00
|
|
|
pub fn print_opt_lifetime(&mut self, lifetime: &Option<ast::Lifetime>) {
|
2018-05-30 16:49:39 +01:00
|
|
|
if let Some(lt) = *lifetime {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_lifetime(lt);
|
|
|
|
self.nbsp();
|
2013-02-18 17:45:56 -08:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
}
|
|
|
|
|
2020-03-29 11:31:58 -07:00
|
|
|
pub fn print_assoc_constraint(&mut self, constraint: &ast::AssocTyConstraint) {
|
2020-03-22 04:40:05 +01:00
|
|
|
self.print_ident(constraint.ident);
|
|
|
|
self.s.space();
|
|
|
|
match &constraint.kind {
|
|
|
|
ast::AssocTyConstraintKind::Equality { ty } => {
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_type(ty);
|
|
|
|
}
|
|
|
|
ast::AssocTyConstraintKind::Bound { bounds } => {
|
|
|
|
self.print_type_bounds(":", &*bounds);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-03-29 11:31:58 -07:00
|
|
|
pub fn print_generic_arg(&mut self, generic_arg: &GenericArg) {
|
2018-05-16 12:57:45 +01:00
|
|
|
match generic_arg {
|
2018-05-30 16:49:39 +01:00
|
|
|
GenericArg::Lifetime(lt) => self.print_lifetime(*lt),
|
2018-05-27 20:07:09 +01:00
|
|
|
GenericArg::Type(ty) => self.print_type(ty),
|
2019-02-05 16:50:16 +01:00
|
|
|
GenericArg::Const(ct) => self.print_expr(&ct.value),
|
2018-02-08 08:58:13 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-15 22:48:13 +02:00
|
|
|
pub fn print_type(&mut self, ty: &ast::Ty) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(ty.span.lo());
|
|
|
|
self.ibox(0);
|
2019-09-26 17:25:31 +01:00
|
|
|
match ty.kind {
|
2016-09-20 16:54:24 +02:00
|
|
|
ast::TyKind::Slice(ref ty) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("[");
|
|
|
|
self.print_type(ty);
|
|
|
|
self.s.word("]");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Ptr(ref mt) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("*");
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mt(mt, true);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Rptr(ref lifetime, ref mt) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("&");
|
|
|
|
self.print_opt_lifetime(lifetime);
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mt(mt, false);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-08-02 15:56:20 +08:00
|
|
|
ast::TyKind::Never => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("!");
|
2019-12-22 17:42:04 -05:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Tup(ref elts) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2019-12-22 17:42:04 -05:00
|
|
|
self.commasep(Inconsistent, &elts[..], |s, ty| s.print_type(ty));
|
2014-03-16 20:58:11 +02:00
|
|
|
if elts.len() == 1 {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(",");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Paren(ref typ) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.print_type(typ);
|
|
|
|
self.pclose();
|
2014-06-11 12:14:38 -07:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::BareFn(ref f) => {
|
2019-12-22 17:42:04 -05:00
|
|
|
self.print_ty_fn(f.ext, f.unsafety, &f.decl, None, &f.generic_params);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Path(None, ref path) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, false, 0);
|
2015-01-31 21:20:24 +02:00
|
|
|
}
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::TyKind::Path(Some(ref qself), ref path) => self.print_qpath(path, qself, false),
|
2017-10-10 17:33:19 +03:00
|
|
|
ast::TyKind::TraitObject(ref bounds, syntax) => {
|
2017-12-19 23:40:17 +03:00
|
|
|
let prefix = if syntax == ast::TraitObjectSyntax::Dyn { "dyn" } else { "" };
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_type_bounds(prefix, &bounds[..]);
|
2014-11-07 06:53:45 -05:00
|
|
|
}
|
2018-06-18 16:23:13 +02:00
|
|
|
ast::TyKind::ImplTrait(_, ref bounds) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_type_bounds("impl", &bounds[..]);
|
2016-08-01 04:25:32 +03:00
|
|
|
}
|
2018-05-17 21:28:50 +03:00
|
|
|
ast::TyKind::Array(ref ty, ref length) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("[");
|
|
|
|
self.print_type(ty);
|
|
|
|
self.s.word("; ");
|
|
|
|
self.print_expr(&length.value);
|
|
|
|
self.s.word("]");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Typeof(ref e) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("typeof(");
|
|
|
|
self.print_expr(&e.value);
|
|
|
|
self.s.word(")");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:53:21 +01:00
|
|
|
ast::TyKind::Infer => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("_");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-03-28 18:56:29 -07:00
|
|
|
ast::TyKind::Err => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.s.word("/*ERROR*/");
|
|
|
|
self.pclose();
|
2017-03-28 18:56:29 -07:00
|
|
|
}
|
2016-03-06 15:54:44 +03:00
|
|
|
ast::TyKind::ImplicitSelf => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("Self");
|
2016-03-06 15:54:44 +03:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::TyKind::MacCall(ref m) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_mac(m);
|
2015-07-25 21:30:35 -07:00
|
|
|
}
|
2018-11-30 15:53:44 +00:00
|
|
|
ast::TyKind::CVarArgs => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("...");
|
2018-11-30 15:53:44 +00:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-12-01 00:00:39 +02:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_foreign_item(&mut self, item: &ast::ForeignItem) {
|
2020-02-29 15:51:08 +03:00
|
|
|
let ast::Item { id, span, ident, ref attrs, ref kind, ref vis, tokens: _ } = *item;
|
2020-02-15 18:28:47 +01:00
|
|
|
self.ann.pre(self, AnnNode::SubItem(id));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.hardbreak_if_not_bol();
|
2020-02-15 18:28:47 +01:00
|
|
|
self.maybe_print_comment(span.lo());
|
|
|
|
self.print_outer_attributes(attrs);
|
|
|
|
match kind {
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ForeignItemKind::Fn(box ast::FnKind(def, sig, gen, body)) => {
|
2020-02-23 10:24:30 +01:00
|
|
|
self.print_fn_full(sig, ident, gen, vis, *def, body.as_deref(), attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-02-14 15:56:05 +01:00
|
|
|
ast::ForeignItemKind::Static(ty, mutbl, body) => {
|
2020-02-23 10:24:30 +01:00
|
|
|
let def = ast::Defaultness::Final;
|
2020-02-21 01:21:17 +01:00
|
|
|
self.print_item_const(ident, Some(*mutbl), ty, body.as_deref(), vis, def);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ForeignItemKind::TyAlias(box ast::TyAliasKind(def, generics, bounds, ty)) => {
|
2020-02-23 10:24:30 +01:00
|
|
|
self.print_associated_type(ident, generics, bounds, ty.as_deref(), vis, *def);
|
2017-09-03 19:53:58 +01:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::ForeignItemKind::MacCall(m) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_mac(m);
|
2019-12-01 02:25:32 +03:00
|
|
|
if m.args.need_semicolon() {
|
|
|
|
self.s.word(";");
|
2018-05-22 08:01:21 -07:00
|
|
|
}
|
2018-03-10 18:16:26 -08:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-02-15 18:28:47 +01:00
|
|
|
self.ann.post(self, AnnNode::SubItem(id))
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-02-10 23:15:45 -08:00
|
|
|
|
2020-02-14 15:56:05 +01:00
|
|
|
fn print_item_const(
|
2019-12-22 17:42:04 -05:00
|
|
|
&mut self,
|
2020-04-19 13:00:18 +02:00
|
|
|
ident: Ident,
|
2020-02-14 15:56:05 +01:00
|
|
|
mutbl: Option<ast::Mutability>,
|
2019-12-22 17:42:04 -05:00
|
|
|
ty: &ast::Ty,
|
2020-02-14 15:56:05 +01:00
|
|
|
body: Option<&ast::Expr>,
|
2019-12-22 17:42:04 -05:00
|
|
|
vis: &ast::Visibility,
|
2020-02-21 01:21:17 +01:00
|
|
|
defaultness: ast::Defaultness,
|
2019-12-22 17:42:04 -05:00
|
|
|
) {
|
2020-02-21 01:21:17 +01:00
|
|
|
self.head("");
|
|
|
|
self.print_visibility(vis);
|
|
|
|
self.print_defaultness(defaultness);
|
2020-02-14 15:56:05 +01:00
|
|
|
let leading = match mutbl {
|
2020-02-15 22:33:21 +01:00
|
|
|
None => "const",
|
|
|
|
Some(ast::Mutability::Not) => "static",
|
|
|
|
Some(ast::Mutability::Mut) => "static mut",
|
2020-02-14 15:56:05 +01:00
|
|
|
};
|
2020-02-21 01:21:17 +01:00
|
|
|
self.word_space(leading);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(ident);
|
|
|
|
self.word_space(":");
|
|
|
|
self.print_type(ty);
|
2020-02-14 15:56:05 +01:00
|
|
|
self.s.space();
|
|
|
|
self.end(); // end the head-ibox
|
|
|
|
if let Some(body) = body {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("=");
|
2020-02-14 15:56:05 +01:00
|
|
|
self.print_expr(body);
|
2015-03-15 19:35:25 -06:00
|
|
|
}
|
2020-02-14 15:56:05 +01:00
|
|
|
self.s.word(";");
|
|
|
|
self.end(); // end the outer cbox
|
2015-03-15 19:35:25 -06:00
|
|
|
}
|
|
|
|
|
2019-12-01 10:25:45 +01:00
|
|
|
fn print_associated_type(
|
|
|
|
&mut self,
|
2020-04-19 13:00:18 +02:00
|
|
|
ident: Ident,
|
2020-02-07 04:03:54 +03:00
|
|
|
generics: &ast::Generics,
|
2019-12-01 10:25:45 +01:00
|
|
|
bounds: &ast::GenericBounds,
|
|
|
|
ty: Option<&ast::Ty>,
|
2020-02-21 01:21:17 +01:00
|
|
|
vis: &ast::Visibility,
|
|
|
|
defaultness: ast::Defaultness,
|
2019-12-01 10:25:45 +01:00
|
|
|
) {
|
2020-02-21 01:21:17 +01:00
|
|
|
self.head("");
|
|
|
|
self.print_visibility(vis);
|
|
|
|
self.print_defaultness(defaultness);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("type");
|
|
|
|
self.print_ident(ident);
|
2020-02-07 04:03:54 +03:00
|
|
|
self.print_generic_params(&generics.params);
|
2019-12-01 10:25:45 +01:00
|
|
|
self.print_type_bounds(":", bounds);
|
2020-02-07 04:03:54 +03:00
|
|
|
self.print_where_clause(&generics.where_clause);
|
2015-03-10 12:28:44 +02:00
|
|
|
if let Some(ty) = ty {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_type(ty);
|
2015-03-10 12:28:44 +02:00
|
|
|
}
|
2020-02-21 01:21:17 +01:00
|
|
|
self.s.word(";");
|
|
|
|
self.end(); // end inner head-block
|
|
|
|
self.end(); // end outer head-block
|
2014-08-05 19:44:21 -07:00
|
|
|
}
|
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
/// Pretty-prints an item.
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_item(&mut self, item: &ast::Item) {
|
|
|
|
self.hardbreak_if_not_bol();
|
|
|
|
self.maybe_print_comment(item.span.lo());
|
|
|
|
self.print_outer_attributes(&item.attrs);
|
|
|
|
self.ann.pre(self, AnnNode::Item(item));
|
2019-09-26 17:51:36 +01:00
|
|
|
match item.kind {
|
2018-03-09 18:51:48 +03:00
|
|
|
ast::ItemKind::ExternCrate(orig_name) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(&item.vis, "extern crate"));
|
2018-03-09 18:51:48 +03:00
|
|
|
if let Some(orig_name) = orig_name {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_name(orig_name);
|
|
|
|
self.s.space();
|
|
|
|
self.s.word("as");
|
|
|
|
self.s.space();
|
2015-01-13 17:30:17 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(item.ident);
|
|
|
|
self.s.word(";");
|
|
|
|
self.end(); // end inner head-block
|
|
|
|
self.end(); // end outer head-block
|
2015-01-13 17:30:17 +02:00
|
|
|
}
|
2017-09-26 23:04:00 +02:00
|
|
|
ast::ItemKind::Use(ref tree) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(&item.vis, "use"));
|
|
|
|
self.print_use_tree(tree);
|
|
|
|
self.s.word(";");
|
|
|
|
self.end(); // end inner head-block
|
|
|
|
self.end(); // end outer head-block
|
2015-01-13 17:30:17 +02:00
|
|
|
}
|
2020-02-14 15:56:05 +01:00
|
|
|
ast::ItemKind::Static(ref ty, mutbl, ref body) => {
|
2020-02-21 01:21:17 +01:00
|
|
|
let def = ast::Defaultness::Final;
|
|
|
|
self.print_item_const(item.ident, Some(mutbl), ty, body.as_deref(), &item.vis, def);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-02-23 10:24:30 +01:00
|
|
|
ast::ItemKind::Const(def, ref ty, ref body) => {
|
2020-02-21 01:21:17 +01:00
|
|
|
self.print_item_const(item.ident, None, ty, body.as_deref(), &item.vis, def);
|
rustc: Add `const` globals to the language
This change is an implementation of [RFC 69][rfc] which adds a third kind of
global to the language, `const`. This global is most similar to what the old
`static` was, and if you're unsure about what to use then you should use a
`const`.
The semantics of these three kinds of globals are:
* A `const` does not represent a memory location, but only a value. Constants
are translated as rvalues, which means that their values are directly inlined
at usage location (similar to a #define in C/C++). Constant values are, well,
constant, and can not be modified. Any "modification" is actually a
modification to a local value on the stack rather than the actual constant
itself.
Almost all values are allowed inside constants, whether they have interior
mutability or not. There are a few minor restrictions listed in the RFC, but
they should in general not come up too often.
* A `static` now always represents a memory location (unconditionally). Any
references to the same `static` are actually a reference to the same memory
location. Only values whose types ascribe to `Sync` are allowed in a `static`.
This restriction is in place because many threads may access a `static`
concurrently. Lifting this restriction (and allowing unsafe access) is a
future extension not implemented at this time.
* A `static mut` continues to always represent a memory location. All references
to a `static mut` continue to be `unsafe`.
This is a large breaking change, and many programs will need to be updated
accordingly. A summary of the breaking changes is:
* Statics may no longer be used in patterns. Statics now always represent a
memory location, which can sometimes be modified. To fix code, repurpose the
matched-on-`static` to a `const`.
static FOO: uint = 4;
match n {
FOO => { /* ... */ }
_ => { /* ... */ }
}
change this code to:
const FOO: uint = 4;
match n {
FOO => { /* ... */ }
_ => { /* ... */ }
}
* Statics may no longer refer to other statics by value. Due to statics being
able to change at runtime, allowing them to reference one another could
possibly lead to confusing semantics. If you are in this situation, use a
constant initializer instead. Note, however, that statics may reference other
statics by address, however.
* Statics may no longer be used in constant expressions, such as array lengths.
This is due to the same restrictions as listed above. Use a `const` instead.
[breaking-change]
[rfc]: https://github.com/rust-lang/rfcs/pull/246
2014-10-06 08:17:01 -07:00
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ItemKind::Fn(box ast::FnKind(def, ref sig, ref gen, ref body)) => {
|
2020-02-21 01:21:17 +01:00
|
|
|
let body = body.as_deref();
|
|
|
|
self.print_fn_full(sig, item.ident, gen, &item.vis, def, body, &item.attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-09 11:36:51 +01:00
|
|
|
ast::ItemKind::Mod(ref _mod) => {
|
2020-09-26 12:41:53 -04:00
|
|
|
self.head(self.to_string(|s| {
|
2020-08-23 03:42:19 -07:00
|
|
|
s.print_visibility(&item.vis);
|
|
|
|
s.print_unsafety(_mod.unsafety);
|
|
|
|
s.word("mod");
|
|
|
|
}));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(item.ident);
|
2018-07-11 15:19:32 +02:00
|
|
|
|
2018-07-12 23:35:40 +02:00
|
|
|
if _mod.inline || self.is_expanded {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
|
|
|
self.bopen();
|
2021-02-14 21:14:12 +03:00
|
|
|
self.print_inner_attributes(&item.attrs);
|
|
|
|
for item in &_mod.items {
|
|
|
|
self.print_item(item);
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.bclose(item.span);
|
2018-07-11 15:19:32 +02:00
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(";");
|
|
|
|
self.end(); // end inner head-block
|
|
|
|
self.end(); // end outer head-block
|
2018-07-11 15:19:32 +02:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-09 11:36:51 +01:00
|
|
|
ast::ItemKind::ForeignMod(ref nmod) => {
|
2020-09-26 12:41:53 -04:00
|
|
|
self.head(self.to_string(|s| {
|
2020-08-23 03:42:19 -07:00
|
|
|
s.print_unsafety(nmod.unsafety);
|
|
|
|
s.word("extern");
|
|
|
|
}));
|
2019-11-09 22:05:20 +03:00
|
|
|
if let Some(abi) = nmod.abi {
|
2019-11-10 00:44:59 +03:00
|
|
|
self.print_literal(&abi.as_lit());
|
|
|
|
self.nbsp();
|
2019-11-09 22:05:20 +03:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.bopen();
|
|
|
|
self.print_foreign_mod(nmod, &item.attrs);
|
|
|
|
self.bclose(item.span);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-03-15 21:27:40 -05:00
|
|
|
ast::ItemKind::GlobalAsm(ref ga) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(&item.vis, "global_asm!"));
|
2019-10-22 08:31:37 +11:00
|
|
|
self.s.word(ga.asm.to_string());
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2017-03-15 21:27:40 -05:00
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ItemKind::TyAlias(box ast::TyAliasKind(def, ref generics, ref bounds, ref ty)) => {
|
2020-02-21 23:00:27 +01:00
|
|
|
let ty = ty.as_deref();
|
|
|
|
self.print_associated_type(item.ident, generics, bounds, ty, &item.vis, def);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-09 11:36:51 +01:00
|
|
|
ast::ItemKind::Enum(ref enum_definition, ref params) => {
|
2019-12-22 17:42:04 -05:00
|
|
|
self.print_enum_def(enum_definition, params, item.ident, item.span, &item.vis);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-09 11:36:51 +01:00
|
|
|
ast::ItemKind::Struct(ref struct_def, ref generics) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(&item.vis, "struct"));
|
|
|
|
self.print_struct(struct_def, generics, item.ident, item.span, true);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-08-29 05:04:31 +00:00
|
|
|
ast::ItemKind::Union(ref struct_def, ref generics) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(&item.vis, "union"));
|
|
|
|
self.print_struct(struct_def, generics, item.ident, item.span, true);
|
2016-08-29 05:04:31 +00:00
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ItemKind::Impl(box ast::ImplKind {
|
2019-12-22 17:42:04 -05:00
|
|
|
unsafety,
|
|
|
|
polarity,
|
|
|
|
defaultness,
|
2020-01-13 20:30:23 -08:00
|
|
|
constness,
|
2019-12-22 17:42:04 -05:00
|
|
|
ref generics,
|
2020-01-13 20:30:20 -08:00
|
|
|
ref of_trait,
|
|
|
|
ref self_ty,
|
|
|
|
ref items,
|
2021-01-29 08:31:08 +01:00
|
|
|
}) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("");
|
|
|
|
self.print_visibility(&item.vis);
|
|
|
|
self.print_defaultness(defaultness);
|
|
|
|
self.print_unsafety(unsafety);
|
|
|
|
self.word_nbsp("impl");
|
2020-01-13 20:30:23 -08:00
|
|
|
self.print_constness(constness);
|
2014-12-10 06:15:06 -05:00
|
|
|
|
2018-05-26 23:21:08 +01:00
|
|
|
if !generics.params.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_generic_params(&generics.params);
|
|
|
|
self.s.space();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-03-27 06:16:28 -04:00
|
|
|
|
2020-03-04 16:15:23 -08:00
|
|
|
if let ast::ImplPolarity::Negative(_) = polarity {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("!");
|
2014-12-28 23:33:18 +01:00
|
|
|
}
|
|
|
|
|
2020-01-13 20:30:20 -08:00
|
|
|
if let Some(ref t) = *of_trait {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_trait_ref(t);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("for");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2012-08-08 17:14:25 -07:00
|
|
|
|
2020-01-13 20:30:20 -08:00
|
|
|
self.print_type(self_ty);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_where_clause(&generics.where_clause);
|
2012-08-08 14:17:52 -07:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.bopen();
|
|
|
|
self.print_inner_attributes(&item.attrs);
|
2020-01-13 20:30:20 -08:00
|
|
|
for impl_item in items {
|
2019-12-01 16:15:10 +01:00
|
|
|
self.print_assoc_item(impl_item);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.bclose(item.span);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::ItemKind::Trait(box ast::TraitKind(
|
|
|
|
is_auto,
|
|
|
|
unsafety,
|
|
|
|
ref generics,
|
|
|
|
ref bounds,
|
|
|
|
ref trait_items,
|
|
|
|
)) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("");
|
|
|
|
self.print_visibility(&item.vis);
|
|
|
|
self.print_unsafety(unsafety);
|
|
|
|
self.print_is_auto(is_auto);
|
|
|
|
self.word_nbsp("trait");
|
|
|
|
self.print_ident(item.ident);
|
|
|
|
self.print_generic_params(&generics.params);
|
2014-12-24 22:34:57 +13:00
|
|
|
let mut real_bounds = Vec::with_capacity(bounds.len());
|
2015-02-13 07:33:44 +00:00
|
|
|
for b in bounds.iter() {
|
2018-06-14 12:23:46 +01:00
|
|
|
if let GenericBound::Trait(ref ptr, ast::TraitBoundModifier::Maybe) = *b {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("for ?");
|
|
|
|
self.print_trait_ref(&ptr.trait_ref);
|
2014-12-24 22:34:57 +13:00
|
|
|
} else {
|
2015-02-13 07:33:44 +00:00
|
|
|
real_bounds.push(b.clone());
|
2014-12-24 22:34:57 +13:00
|
|
|
}
|
2014-04-03 13:38:45 +13:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_type_bounds(":", &real_bounds[..]);
|
|
|
|
self.print_where_clause(&generics.where_clause);
|
|
|
|
self.s.word(" ");
|
|
|
|
self.bopen();
|
2020-01-31 06:43:33 +01:00
|
|
|
self.print_inner_attributes(&item.attrs);
|
2015-03-10 12:28:44 +02:00
|
|
|
for trait_item in trait_items {
|
2019-12-01 16:15:10 +01:00
|
|
|
self.print_assoc_item(trait_item);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.bclose(item.span);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-10-02 12:27:45 +00:00
|
|
|
ast::ItemKind::TraitAlias(ref generics, ref bounds) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("");
|
|
|
|
self.print_visibility(&item.vis);
|
|
|
|
self.word_nbsp("trait");
|
|
|
|
self.print_ident(item.ident);
|
|
|
|
self.print_generic_params(&generics.params);
|
2017-10-02 12:27:45 +00:00
|
|
|
let mut real_bounds = Vec::with_capacity(bounds.len());
|
|
|
|
// FIXME(durka) this seems to be some quite outdated syntax
|
|
|
|
for b in bounds.iter() {
|
2018-06-14 12:23:46 +01:00
|
|
|
if let GenericBound::Trait(ref ptr, ast::TraitBoundModifier::Maybe) = *b {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("for ?");
|
|
|
|
self.print_trait_ref(&ptr.trait_ref);
|
2017-10-02 12:27:45 +00:00
|
|
|
} else {
|
|
|
|
real_bounds.push(b.clone());
|
|
|
|
}
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
|
|
|
self.print_type_bounds("=", &real_bounds[..]);
|
|
|
|
self.print_where_clause(&generics.where_clause);
|
|
|
|
self.s.word(";");
|
2017-10-02 12:27:45 +00:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::ItemKind::MacCall(ref mac) => {
|
2019-07-13 20:35:46 +03:00
|
|
|
self.print_mac(mac);
|
2019-12-01 02:25:32 +03:00
|
|
|
if mac.args.need_semicolon() {
|
|
|
|
self.s.word(";");
|
2018-05-22 08:01:21 -07:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-07-13 20:35:46 +03:00
|
|
|
ast::ItemKind::MacroDef(ref macro_def) => {
|
2020-03-14 00:52:24 +03:00
|
|
|
let (kw, has_bang) = if macro_def.macro_rules {
|
2019-07-14 20:16:16 +01:00
|
|
|
("macro_rules", true)
|
|
|
|
} else {
|
|
|
|
self.print_visibility(&item.vis);
|
|
|
|
("macro", false)
|
|
|
|
};
|
2019-07-13 20:35:46 +03:00
|
|
|
self.print_mac_common(
|
2019-07-14 16:09:39 +03:00
|
|
|
Some(MacHeader::Keyword(kw)),
|
|
|
|
has_bang,
|
2019-07-13 23:08:29 +03:00
|
|
|
Some(item.ident),
|
2019-12-01 17:53:59 +03:00
|
|
|
macro_def.body.delim(),
|
2020-06-24 17:45:08 +03:00
|
|
|
¯o_def.body.inner_tokens(),
|
2019-07-13 23:08:29 +03:00
|
|
|
true,
|
|
|
|
item.span,
|
2019-07-13 20:35:46 +03:00
|
|
|
);
|
2021-02-08 10:03:57 -08:00
|
|
|
if macro_def.body.need_semicolon() {
|
|
|
|
self.word(";");
|
|
|
|
}
|
2017-03-05 05:15:58 +00:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-08-22 22:05:19 +01:00
|
|
|
self.ann.post(self, AnnNode::Item(item))
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_trait_ref(&mut self, t: &ast::TraitRef) {
|
2018-03-10 02:02:39 +03:00
|
|
|
self.print_path(&t.path, false, 0)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_formal_generic_params(&mut self, generic_params: &[ast::GenericParam]) {
|
2017-10-16 21:07:26 +02:00
|
|
|
if !generic_params.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("for");
|
|
|
|
self.print_generic_params(generic_params);
|
|
|
|
self.nbsp();
|
2014-11-07 06:53:45 -05:00
|
|
|
}
|
2015-02-09 16:49:27 +13:00
|
|
|
}
|
2014-11-07 06:53:45 -05:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_poly_trait_ref(&mut self, t: &ast::PolyTraitRef) {
|
|
|
|
self.print_formal_generic_params(&t.bound_generic_params);
|
2014-11-07 06:53:45 -05:00
|
|
|
self.print_trait_ref(&t.trait_ref)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_enum_def(
|
|
|
|
&mut self,
|
|
|
|
enum_definition: &ast::EnumDef,
|
|
|
|
generics: &ast::Generics,
|
2020-04-19 13:00:18 +02:00
|
|
|
ident: Ident,
|
2019-12-31 20:15:40 +03:00
|
|
|
span: rustc_span::Span,
|
2019-12-22 17:42:04 -05:00
|
|
|
visibility: &ast::Visibility,
|
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head(visibility_qualified(visibility, "enum"));
|
|
|
|
self.print_ident(ident);
|
|
|
|
self.print_generic_params(&generics.params);
|
|
|
|
self.print_where_clause(&generics.where_clause);
|
|
|
|
self.s.space();
|
2015-02-18 15:58:07 -08:00
|
|
|
self.print_variants(&enum_definition.variants, span)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-12-31 20:15:40 +03:00
|
|
|
crate fn print_variants(&mut self, variants: &[ast::Variant], span: rustc_span::Span) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.bopen();
|
2015-01-31 12:20:46 -05:00
|
|
|
for v in variants {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.space_if_not_bol();
|
|
|
|
self.maybe_print_comment(v.span.lo());
|
2019-08-13 21:40:21 -03:00
|
|
|
self.print_outer_attributes(&v.attrs);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.print_variant(v);
|
|
|
|
self.s.word(",");
|
|
|
|
self.end();
|
|
|
|
self.maybe_print_trailing_comment(v.span, None);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
self.bclose(span)
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_visibility(&mut self, vis: &ast::Visibility) {
|
2020-08-21 19:11:00 -04:00
|
|
|
match vis.kind {
|
2018-01-29 14:12:09 +09:00
|
|
|
ast::VisibilityKind::Public => self.word_nbsp("pub"),
|
|
|
|
ast::VisibilityKind::Crate(sugar) => match sugar {
|
2017-10-19 14:43:47 -07:00
|
|
|
ast::CrateSugar::PubCrate => self.word_nbsp("pub(crate)"),
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::CrateSugar::JustCrate => self.word_nbsp("crate"),
|
|
|
|
},
|
2018-01-29 14:12:09 +09:00
|
|
|
ast::VisibilityKind::Restricted { ref path, .. } => {
|
2020-09-26 12:41:53 -04:00
|
|
|
let path = self.to_string(|s| s.print_path(path, false, 0));
|
2017-04-02 04:46:33 +00:00
|
|
|
if path == "self" || path == "super" {
|
2018-11-29 11:36:58 +11:00
|
|
|
self.word_nbsp(format!("pub({})", path))
|
2017-04-02 04:46:33 +00:00
|
|
|
} else {
|
2018-11-29 11:36:58 +11:00
|
|
|
self.word_nbsp(format!("pub(in {})", path))
|
2017-04-02 04:46:33 +00:00
|
|
|
}
|
2016-12-05 03:51:11 +00:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
ast::VisibilityKind::Inherited => {}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_defaultness(&mut self, defaultness: ast::Defaultness) {
|
2020-02-22 02:01:53 +01:00
|
|
|
if let ast::Defaultness::Default(_) = defaultness {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("default");
|
2016-11-18 17:14:42 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_struct(
|
|
|
|
&mut self,
|
|
|
|
struct_def: &ast::VariantData,
|
|
|
|
generics: &ast::Generics,
|
2020-04-19 13:00:18 +02:00
|
|
|
ident: Ident,
|
2019-12-31 20:15:40 +03:00
|
|
|
span: rustc_span::Span,
|
2019-12-22 17:42:04 -05:00
|
|
|
print_finalizer: bool,
|
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(ident);
|
|
|
|
self.print_generic_params(&generics.params);
|
2019-03-24 00:06:58 +03:00
|
|
|
match struct_def {
|
|
|
|
ast::VariantData::Tuple(..) | ast::VariantData::Unit(..) => {
|
|
|
|
if let ast::VariantData::Tuple(..) = struct_def {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2019-12-22 17:42:04 -05:00
|
|
|
self.commasep(Inconsistent, struct_def.fields(), |s, field| {
|
|
|
|
s.maybe_print_comment(field.span.lo());
|
|
|
|
s.print_outer_attributes(&field.attrs);
|
|
|
|
s.print_visibility(&field.vis);
|
|
|
|
s.print_type(&field.ty)
|
|
|
|
});
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2019-03-24 00:06:58 +03:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_where_clause(&generics.where_clause);
|
2019-03-24 00:06:58 +03:00
|
|
|
if print_finalizer {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(";");
|
2019-03-24 00:06:58 +03:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2019-09-06 03:56:45 +01:00
|
|
|
self.end(); // Close the outer-box.
|
2015-10-01 18:47:27 +03:00
|
|
|
}
|
2019-03-24 00:06:58 +03:00
|
|
|
ast::VariantData::Struct(..) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_where_clause(&generics.where_clause);
|
|
|
|
self.nbsp();
|
|
|
|
self.bopen();
|
|
|
|
self.hardbreak_if_not_bol();
|
2012-09-21 18:10:45 -07:00
|
|
|
|
2019-03-24 00:06:58 +03:00
|
|
|
for field in struct_def.fields() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.hardbreak_if_not_bol();
|
|
|
|
self.maybe_print_comment(field.span.lo());
|
|
|
|
self.print_outer_attributes(&field.attrs);
|
|
|
|
self.print_visibility(&field.vis);
|
|
|
|
self.print_ident(field.ident.unwrap());
|
|
|
|
self.word_nbsp(":");
|
|
|
|
self.print_type(&field.ty);
|
|
|
|
self.s.word(",");
|
2019-03-24 00:06:58 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
self.bclose(span)
|
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2012-09-21 18:10:45 -07:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_variant(&mut self, v: &ast::Variant) {
|
|
|
|
self.head("");
|
2019-12-01 23:30:33 +01:00
|
|
|
self.print_visibility(&v.vis);
|
2015-11-28 19:02:07 +00:00
|
|
|
let generics = ast::Generics::default();
|
2019-08-13 21:40:21 -03:00
|
|
|
self.print_struct(&v.data, &generics, v.ident, v.span, false);
|
2020-03-22 13:36:56 +01:00
|
|
|
if let Some(ref d) = v.disr_expr {
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_expr(&d.value)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-12-01 16:15:10 +01:00
|
|
|
crate fn print_assoc_item(&mut self, item: &ast::AssocItem) {
|
2020-02-29 15:51:08 +03:00
|
|
|
let ast::Item { id, span, ident, ref attrs, ref kind, ref vis, tokens: _ } = *item;
|
|
|
|
self.ann.pre(self, AnnNode::SubItem(id));
|
|
|
|
self.hardbreak_if_not_bol();
|
|
|
|
self.maybe_print_comment(span.lo());
|
|
|
|
self.print_outer_attributes(attrs);
|
|
|
|
match kind {
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::AssocItemKind::Fn(box ast::FnKind(def, sig, gen, body)) => {
|
2020-02-29 15:51:08 +03:00
|
|
|
self.print_fn_full(sig, ident, gen, vis, *def, body.as_deref(), attrs);
|
|
|
|
}
|
|
|
|
ast::AssocItemKind::Const(def, ty, body) => {
|
|
|
|
self.print_item_const(ident, None, ty, body.as_deref(), vis, *def);
|
|
|
|
}
|
2021-01-29 08:31:08 +01:00
|
|
|
ast::AssocItemKind::TyAlias(box ast::TyAliasKind(def, generics, bounds, ty)) => {
|
2020-02-29 15:51:08 +03:00
|
|
|
self.print_associated_type(ident, generics, bounds, ty.as_deref(), vis, *def);
|
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::AssocItemKind::MacCall(m) => {
|
2020-02-29 15:51:08 +03:00
|
|
|
self.print_mac(m);
|
|
|
|
if m.args.need_semicolon() {
|
|
|
|
self.s.word(";");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
self.ann.post(self, AnnNode::SubItem(id))
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_stmt(&mut self, st: &ast::Stmt) {
|
|
|
|
self.maybe_print_comment(st.span.lo());
|
2019-09-26 17:34:50 +01:00
|
|
|
match st.kind {
|
2016-06-17 02:30:01 +00:00
|
|
|
ast::StmtKind::Local(ref loc) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_outer_attributes(&loc.attrs);
|
|
|
|
self.space_if_not_bol();
|
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.word_nbsp("let");
|
|
|
|
|
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.print_local_decl(loc);
|
|
|
|
self.end();
|
2016-06-17 02:30:01 +00:00
|
|
|
if let Some(ref init) = loc.init {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_expr(init);
|
2016-06-17 02:30:01 +00:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(";");
|
|
|
|
self.end();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
ast::StmtKind::Item(ref item) => self.print_item(item),
|
2016-06-17 02:30:01 +00:00
|
|
|
ast::StmtKind::Expr(ref expr) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.space_if_not_bol();
|
|
|
|
self.print_expr_outer_attr_style(expr, false);
|
2019-10-11 13:17:20 +02:00
|
|
|
if classify::expr_requires_semi_to_be_stmt(expr) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(";");
|
2016-06-24 11:39:18 +00:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-06-17 02:30:01 +00:00
|
|
|
ast::StmtKind::Semi(ref expr) => {
|
2020-02-27 04:10:42 +01:00
|
|
|
self.space_if_not_bol();
|
|
|
|
self.print_expr_outer_attr_style(expr, false);
|
|
|
|
self.s.word(";");
|
|
|
|
}
|
|
|
|
ast::StmtKind::Empty => {
|
|
|
|
self.space_if_not_bol();
|
|
|
|
self.s.word(";");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::StmtKind::MacCall(ref mac) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.space_if_not_bol();
|
2020-08-30 18:38:32 -04:00
|
|
|
self.print_outer_attributes(&mac.attrs);
|
|
|
|
self.print_mac(&mac.mac);
|
|
|
|
if mac.style == ast::MacStmtStyle::Semicolon {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(";");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2012-06-30 11:54:54 +01:00
|
|
|
}
|
2011-06-16 13:00:19 -07:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
self.maybe_print_trailing_comment(st.span, None)
|
2011-06-16 13:00:19 -07:00
|
|
|
}
|
2011-07-08 16:35:09 -07:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_block(&mut self, blk: &ast::Block) {
|
2014-03-16 20:58:11 +02:00
|
|
|
self.print_block_with_attrs(blk, &[])
|
|
|
|
}
|
2012-08-13 21:13:41 -04:00
|
|
|
|
2019-07-09 09:30:08 -04:00
|
|
|
crate fn print_block_unclosed_indent(&mut self, blk: &ast::Block) {
|
|
|
|
self.print_block_maybe_unclosed(blk, &[], false)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2011-08-15 14:42:33 -07:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_block_with_attrs(&mut self, blk: &ast::Block, attrs: &[ast::Attribute]) {
|
2019-07-09 09:30:08 -04:00
|
|
|
self.print_block_maybe_unclosed(blk, attrs, true)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2012-01-15 17:23:59 -08:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_block_maybe_unclosed(
|
|
|
|
&mut self,
|
|
|
|
blk: &ast::Block,
|
|
|
|
attrs: &[ast::Attribute],
|
|
|
|
close_box: bool,
|
|
|
|
) {
|
2014-03-16 20:58:11 +02:00
|
|
|
match blk.rules {
|
2019-06-24 14:15:11 -04:00
|
|
|
BlockCheckMode::Unsafe(..) => self.word_space("unsafe"),
|
2019-12-22 17:42:04 -05:00
|
|
|
BlockCheckMode::Default => (),
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(blk.span.lo());
|
|
|
|
self.ann.pre(self, AnnNode::Block(blk));
|
|
|
|
self.bopen();
|
2014-03-16 20:58:11 +02:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_inner_attributes(attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
|
2016-06-24 11:39:18 +00:00
|
|
|
for (i, st) in blk.stmts.iter().enumerate() {
|
2019-09-26 17:34:50 +01:00
|
|
|
match st.kind {
|
2016-06-26 02:19:34 +00:00
|
|
|
ast::StmtKind::Expr(ref expr) if i == blk.stmts.len() - 1 => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(st.span.lo());
|
|
|
|
self.space_if_not_bol();
|
|
|
|
self.print_expr_outer_attr_style(expr, false);
|
|
|
|
self.maybe_print_trailing_comment(expr.span, Some(blk.span.hi()));
|
2016-06-24 11:39:18 +00:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
_ => self.print_stmt(st),
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2016-06-24 11:39:18 +00:00
|
|
|
|
2019-07-09 09:30:08 -04:00
|
|
|
self.bclose_maybe_open(blk.span, close_box);
|
2018-08-22 22:05:19 +01:00
|
|
|
self.ann.post(self, AnnNode::Block(blk))
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
|
2019-08-28 01:15:33 +02:00
|
|
|
/// Print a `let pat = scrutinee` expression.
|
|
|
|
crate fn print_let(&mut self, pat: &ast::Pat, scrutinee: &ast::Expr) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("let ");
|
2019-05-15 16:05:58 +02:00
|
|
|
|
2019-08-28 01:15:33 +02:00
|
|
|
self.print_pat(pat);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
2019-05-15 16:05:58 +02:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("=");
|
2019-06-18 01:28:20 +02:00
|
|
|
self.print_expr_cond_paren(
|
|
|
|
scrutinee,
|
|
|
|
Self::cond_needs_par(scrutinee)
|
2019-12-22 17:42:04 -05:00
|
|
|
|| parser::needs_par_as_let_scrutinee(scrutinee.precedence().order()),
|
2019-06-18 01:28:20 +02:00
|
|
|
)
|
2019-05-15 16:05:58 +02:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_else(&mut self, els: Option<&ast::Expr>) {
|
2019-09-26 14:39:48 +01:00
|
|
|
if let Some(_else) = els {
|
|
|
|
match _else.kind {
|
|
|
|
// Another `else if` block.
|
|
|
|
ast::ExprKind::If(ref i, ref then, ref e) => {
|
|
|
|
self.cbox(INDENT_UNIT - 1);
|
|
|
|
self.ibox(0);
|
|
|
|
self.s.word(" else if ");
|
|
|
|
self.print_expr_as_cond(i);
|
|
|
|
self.s.space();
|
|
|
|
self.print_block(then);
|
2020-01-22 01:38:05 +01:00
|
|
|
self.print_else(e.as_deref())
|
2019-09-26 14:39:48 +01:00
|
|
|
}
|
|
|
|
// Final `else` block.
|
|
|
|
ast::ExprKind::Block(ref b, _) => {
|
|
|
|
self.cbox(INDENT_UNIT - 1);
|
|
|
|
self.ibox(0);
|
|
|
|
self.s.word(" else ");
|
|
|
|
self.print_block(b)
|
|
|
|
}
|
|
|
|
// Constraints would be great here!
|
|
|
|
_ => {
|
|
|
|
panic!("print_if saw if with weird alternative");
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2011-06-16 14:08:17 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_if(&mut self, test: &ast::Expr, blk: &ast::Block, elseopt: Option<&ast::Expr>) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("if");
|
2019-05-15 16:05:58 +02:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_as_cond(test);
|
|
|
|
self.s.space();
|
2011-07-08 16:35:09 -07:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_block(blk);
|
2014-08-24 18:04:29 -07:00
|
|
|
self.print_else(elseopt)
|
|
|
|
}
|
|
|
|
|
2020-02-29 19:32:20 +03:00
|
|
|
crate fn print_mac(&mut self, m: &ast::MacCall) {
|
2019-07-13 23:08:29 +03:00
|
|
|
self.print_mac_common(
|
2019-08-15 02:13:53 +03:00
|
|
|
Some(MacHeader::Path(&m.path)),
|
2019-07-14 16:09:39 +03:00
|
|
|
true,
|
|
|
|
None,
|
2019-12-01 02:25:32 +03:00
|
|
|
m.args.delim(),
|
2020-06-24 17:45:08 +03:00
|
|
|
&m.args.inner_tokens(),
|
2019-07-14 16:09:39 +03:00
|
|
|
true,
|
2019-12-01 15:55:32 +03:00
|
|
|
m.span(),
|
2019-07-13 23:08:29 +03:00
|
|
|
);
|
2012-09-11 21:25:01 -07:00
|
|
|
}
|
2012-11-30 11:18:25 -08:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_call_post(&mut self, args: &[P<ast::Expr>]) {
|
|
|
|
self.popen();
|
|
|
|
self.commasep_exprs(Inconsistent, args);
|
2014-03-16 20:58:11 +02:00
|
|
|
self.pclose()
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_expr_maybe_paren(&mut self, expr: &ast::Expr, prec: i8) {
|
2019-06-18 01:28:20 +02:00
|
|
|
self.print_expr_cond_paren(expr, expr.precedence().order() < prec)
|
2015-08-06 19:55:27 +12:00
|
|
|
}
|
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
/// Prints an expr using syntax that's acceptable in a condition position, such as the `cond` in
|
2017-07-20 16:53:56 -04:00
|
|
|
/// `if cond { ... }`.
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_expr_as_cond(&mut self, expr: &ast::Expr) {
|
2019-06-18 01:28:20 +02:00
|
|
|
self.print_expr_cond_paren(expr, Self::cond_needs_par(expr))
|
|
|
|
}
|
|
|
|
|
|
|
|
/// Does `expr` need parenthesis when printed in a condition position?
|
|
|
|
fn cond_needs_par(expr: &ast::Expr) -> bool {
|
2019-09-26 14:39:48 +01:00
|
|
|
match expr.kind {
|
2017-07-20 16:53:56 -04:00
|
|
|
// These cases need parens due to the parse error observed in #26461: `if return {}`
|
|
|
|
// parses as the erroneous construct `if (return {})`, not `if (return) {}`.
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::ExprKind::Closure(..) | ast::ExprKind::Ret(..) | ast::ExprKind::Break(..) => true,
|
2017-07-20 16:53:56 -04:00
|
|
|
|
|
|
|
_ => parser::contains_exterior_struct_lit(expr),
|
2019-06-18 01:28:20 +02:00
|
|
|
}
|
|
|
|
}
|
2017-07-20 16:53:56 -04:00
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
/// Prints `expr` or `(expr)` when `needs_par` holds.
|
2021-01-07 17:58:05 +03:00
|
|
|
fn print_expr_cond_paren(&mut self, expr: &ast::Expr, needs_par: bool) {
|
2014-04-17 05:33:58 +09:00
|
|
|
if needs_par {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2014-04-17 05:33:58 +09:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr(expr);
|
2014-04-17 05:33:58 +09:00
|
|
|
if needs_par {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2014-04-17 05:33:58 +09:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-04-27 23:26:11 +05:30
|
|
|
fn print_expr_vec(&mut self, exprs: &[P<ast::Expr>], attrs: &[ast::Attribute]) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.s.word("[");
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
2021-02-16 00:30:06 +01:00
|
|
|
self.commasep_exprs(Inconsistent, exprs);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("]");
|
|
|
|
self.end();
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2020-09-21 17:55:58 -03:00
|
|
|
fn print_expr_anon_const(&mut self, expr: &ast::AnonConst, attrs: &[ast::Attribute]) {
|
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.s.word("const");
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
|
|
|
self.print_expr(&expr.value);
|
|
|
|
self.end();
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_repeat(
|
|
|
|
&mut self,
|
|
|
|
element: &ast::Expr,
|
|
|
|
count: &ast::AnonConst,
|
2020-04-27 23:26:11 +05:30
|
|
|
attrs: &[ast::Attribute],
|
2019-12-22 17:42:04 -05:00
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.s.word("[");
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
|
|
|
self.print_expr(element);
|
|
|
|
self.word_space(";");
|
|
|
|
self.print_expr(&count.value);
|
|
|
|
self.s.word("]");
|
|
|
|
self.end();
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_struct(
|
|
|
|
&mut self,
|
|
|
|
path: &ast::Path,
|
|
|
|
fields: &[ast::Field],
|
2020-11-07 14:28:55 +00:00
|
|
|
rest: &ast::StructRest,
|
2020-04-27 23:26:11 +05:30
|
|
|
attrs: &[ast::Attribute],
|
2019-12-22 17:42:04 -05:00
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, true, 0);
|
|
|
|
self.s.word("{");
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
2016-12-29 13:57:01 -08:00
|
|
|
self.commasep_cmnt(
|
2015-09-10 22:46:52 +03:00
|
|
|
Consistent,
|
2021-02-16 00:30:06 +01:00
|
|
|
fields,
|
2015-09-10 22:46:52 +03:00
|
|
|
|s, field| {
|
2020-02-01 18:45:03 +01:00
|
|
|
s.print_outer_attributes(&field.attrs);
|
2019-06-24 14:15:11 -04:00
|
|
|
s.ibox(INDENT_UNIT);
|
2016-10-27 03:15:13 +03:00
|
|
|
if !field.is_shorthand {
|
2019-06-24 14:15:11 -04:00
|
|
|
s.print_ident(field.ident);
|
|
|
|
s.word_space(":");
|
2016-10-27 03:15:13 +03:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
s.print_expr(&field.expr);
|
|
|
|
s.end();
|
2015-09-10 22:46:52 +03:00
|
|
|
},
|
2019-12-22 17:42:04 -05:00
|
|
|
|f| f.span,
|
|
|
|
);
|
2020-11-07 14:28:55 +00:00
|
|
|
match rest {
|
|
|
|
ast::StructRest::Base(_) | ast::StructRest::Rest(_) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
2015-09-10 22:46:52 +03:00
|
|
|
if !fields.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(",");
|
|
|
|
self.s.space();
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("..");
|
2020-11-07 14:28:55 +00:00
|
|
|
if let ast::StructRest::Base(ref expr) = *rest {
|
|
|
|
self.print_expr(expr);
|
2019-12-22 17:42:04 -05:00
|
|
|
}
|
2020-11-07 14:28:55 +00:00
|
|
|
self.end();
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
2020-11-07 14:28:55 +00:00
|
|
|
ast::StructRest::None if !fields.is_empty() => self.s.word(","),
|
|
|
|
_ => {}
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("}");
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2020-04-27 23:26:11 +05:30
|
|
|
fn print_expr_tup(&mut self, exprs: &[P<ast::Expr>], attrs: &[ast::Attribute]) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
2021-02-16 00:30:06 +01:00
|
|
|
self.commasep_exprs(Inconsistent, exprs);
|
2015-01-13 21:16:56 -08:00
|
|
|
if exprs.len() == 1 {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(",");
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
self.pclose()
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_call(&mut self, func: &ast::Expr, args: &[P<ast::Expr>]) {
|
|
|
|
let prec = match func.kind {
|
|
|
|
ast::ExprKind::Field(..) => parser::PREC_FORCE_PAREN,
|
|
|
|
_ => parser::PREC_POSTFIX,
|
|
|
|
};
|
2017-07-20 16:53:56 -04:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(func, prec);
|
2015-01-13 21:16:56 -08:00
|
|
|
self.print_call_post(args)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_method_call(&mut self, segment: &ast::PathSegment, args: &[P<ast::Expr>]) {
|
2015-01-17 16:15:52 -08:00
|
|
|
let base_args = &args[1..];
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(&args[0], parser::PREC_POSTFIX);
|
|
|
|
self.s.word(".");
|
|
|
|
self.print_ident(segment.ident);
|
2018-02-23 17:48:54 +00:00
|
|
|
if let Some(ref args) = segment.args {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_generic_args(args, true);
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
self.print_call_post(base_args)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_binary(&mut self, op: ast::BinOp, lhs: &ast::Expr, rhs: &ast::Expr) {
|
2017-07-20 16:53:56 -04:00
|
|
|
let assoc_op = AssocOp::from_ast_binop(op.node);
|
|
|
|
let prec = assoc_op.precedence() as i8;
|
|
|
|
let fixity = assoc_op.fixity();
|
|
|
|
|
|
|
|
let (left_prec, right_prec) = match fixity {
|
|
|
|
Fixity::Left => (prec, prec + 1),
|
|
|
|
Fixity::Right => (prec + 1, prec),
|
|
|
|
Fixity::None => (prec + 1, prec + 1),
|
|
|
|
};
|
|
|
|
|
2019-09-26 14:39:48 +01:00
|
|
|
let left_prec = match (&lhs.kind, op.node) {
|
2017-11-05 09:28:00 -08:00
|
|
|
// These cases need parens: `x as i32 < y` has the parser thinking that `i32 < y` is
|
|
|
|
// the beginning of a path type. It starts trying to parse `x as (i32 < y ...` instead
|
|
|
|
// of `(x as i32) < ...`. We need to convince it _not_ to do that.
|
2020-04-16 17:38:52 -07:00
|
|
|
(&ast::ExprKind::Cast { .. }, ast::BinOpKind::Lt | ast::BinOpKind::Shl) => {
|
|
|
|
parser::PREC_FORCE_PAREN
|
|
|
|
}
|
2019-06-18 01:28:20 +02:00
|
|
|
// We are given `(let _ = a) OP b`.
|
|
|
|
//
|
|
|
|
// - When `OP <= LAnd` we should print `let _ = a OP b` to avoid redundant parens
|
|
|
|
// as the parser will interpret this as `(let _ = a) OP b`.
|
|
|
|
//
|
|
|
|
// - Otherwise, e.g. when we have `(let a = b) < c` in AST,
|
|
|
|
// parens are required since the parser would interpret `let a = b < c` as
|
|
|
|
// `let a = (b < c)`. To achieve this, we force parens.
|
|
|
|
(&ast::ExprKind::Let { .. }, _) if !parser::needs_par_as_let_scrutinee(prec) => {
|
|
|
|
parser::PREC_FORCE_PAREN
|
|
|
|
}
|
2017-11-05 09:28:00 -08:00
|
|
|
_ => left_prec,
|
|
|
|
};
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(lhs, left_prec);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space(op.node.to_string());
|
2017-07-20 16:53:56 -04:00
|
|
|
self.print_expr_maybe_paren(rhs, right_prec)
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_unary(&mut self, op: ast::UnOp, expr: &ast::Expr) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(ast::UnOp::to_string(op));
|
2017-07-20 16:53:56 -04:00
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_PREFIX)
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_addr_of(
|
|
|
|
&mut self,
|
|
|
|
kind: ast::BorrowKind,
|
|
|
|
mutability: ast::Mutability,
|
|
|
|
expr: &ast::Expr,
|
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("&");
|
2019-11-23 14:15:49 +00:00
|
|
|
match kind {
|
|
|
|
ast::BorrowKind::Ref => self.print_mutability(mutability, false),
|
|
|
|
ast::BorrowKind::Raw => {
|
|
|
|
self.word_nbsp("raw");
|
|
|
|
self.print_mutability(mutability, true);
|
|
|
|
}
|
|
|
|
}
|
2017-07-20 16:53:56 -04:00
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_PREFIX)
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
|
|
|
|
2019-10-15 22:48:13 +02:00
|
|
|
pub fn print_expr(&mut self, expr: &ast::Expr) {
|
2015-11-03 17:39:51 +01:00
|
|
|
self.print_expr_outer_attr_style(expr, true)
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_expr_outer_attr_style(&mut self, expr: &ast::Expr, is_inline: bool) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.maybe_print_comment(expr.span.lo());
|
2015-11-03 17:39:51 +01:00
|
|
|
|
2016-06-18 04:01:57 +00:00
|
|
|
let attrs = &expr.attrs;
|
2015-11-03 17:39:51 +01:00
|
|
|
if is_inline {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_outer_attributes_inline(attrs);
|
2015-11-03 17:39:51 +01:00
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_outer_attributes(attrs);
|
2015-11-03 17:39:51 +01:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.ann.pre(self, AnnNode::Expr(expr));
|
2019-09-26 14:39:48 +01:00
|
|
|
match expr.kind {
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Box(ref expr) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("box");
|
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_PREFIX);
|
2015-09-24 18:00:08 +03:00
|
|
|
}
|
2017-01-15 23:36:10 -08:00
|
|
|
ast::ExprKind::Array(ref exprs) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_vec(&exprs[..], attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-09-21 17:55:58 -03:00
|
|
|
ast::ExprKind::ConstBlock(ref anon_const) => {
|
|
|
|
self.print_expr_anon_const(anon_const, attrs);
|
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Repeat(ref element, ref count) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_repeat(element, count, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-11-07 14:28:55 +00:00
|
|
|
ast::ExprKind::Struct(ref path, ref fields, ref rest) => {
|
|
|
|
self.print_expr_struct(path, &fields[..], rest, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Tup(ref exprs) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_tup(&exprs[..], attrs);
|
2012-07-10 10:37:05 -07:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Call(ref func, ref args) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_call(func, &args[..]);
|
2012-08-09 19:31:47 -04:00
|
|
|
}
|
2020-06-09 15:34:23 -04:00
|
|
|
ast::ExprKind::MethodCall(ref segment, ref args, _) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_method_call(segment, &args[..]);
|
2013-10-28 15:22:49 -07:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Binary(op, ref lhs, ref rhs) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_binary(op, lhs, rhs);
|
2013-10-28 15:22:49 -07:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Unary(op, ref expr) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_unary(op, expr);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-11-23 14:15:49 +00:00
|
|
|
ast::ExprKind::AddrOf(k, m, ref expr) => {
|
|
|
|
self.print_expr_addr_of(k, m, expr);
|
2015-01-13 21:16:56 -08:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Lit(ref lit) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_literal(lit);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Cast(ref expr, ref ty) => {
|
2017-07-20 16:53:56 -04:00
|
|
|
let prec = AssocOp::As.precedence() as i8;
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(expr, prec);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("as");
|
|
|
|
self.print_type(ty);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Type(ref expr, ref ty) => {
|
2017-07-20 16:53:56 -04:00
|
|
|
let prec = AssocOp::Colon.precedence() as i8;
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(expr, prec);
|
|
|
|
self.word_space(":");
|
|
|
|
self.print_type(ty);
|
2015-02-01 09:59:46 +02:00
|
|
|
}
|
2019-08-28 01:15:33 +02:00
|
|
|
ast::ExprKind::Let(ref pat, ref scrutinee) => {
|
|
|
|
self.print_let(pat, scrutinee);
|
2019-05-15 16:05:58 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::If(ref test, ref blk, ref elseopt) => {
|
2020-01-22 01:38:05 +01:00
|
|
|
self.print_if(test, blk, elseopt.as_deref())
|
2014-08-24 18:04:29 -07:00
|
|
|
}
|
2018-01-16 01:44:32 +03:00
|
|
|
ast::ExprKind::While(ref test, ref blk, opt_label) => {
|
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.word_space(":");
|
2014-07-25 20:12:51 -04:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("while");
|
|
|
|
self.print_expr_as_cond(test);
|
|
|
|
self.s.space();
|
|
|
|
self.print_block_with_attrs(blk, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-01-16 01:44:32 +03:00
|
|
|
ast::ExprKind::ForLoop(ref pat, ref iter, ref blk, opt_label) => {
|
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.word_space(":");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("for");
|
|
|
|
self.print_pat(pat);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("in");
|
|
|
|
self.print_expr_as_cond(iter);
|
|
|
|
self.s.space();
|
|
|
|
self.print_block_with_attrs(blk, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-01-16 01:44:32 +03:00
|
|
|
ast::ExprKind::Loop(ref blk, opt_label) => {
|
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.word_space(":");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("loop");
|
|
|
|
self.s.space();
|
|
|
|
self.print_block_with_attrs(blk, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Match(ref expr, ref arms) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.cbox(INDENT_UNIT);
|
2019-07-09 09:49:37 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("match");
|
|
|
|
self.print_expr_as_cond(expr);
|
|
|
|
self.s.space();
|
|
|
|
self.bopen();
|
|
|
|
self.print_inner_attributes_no_trailing_hardbreak(attrs);
|
2015-01-31 12:20:46 -05:00
|
|
|
for arm in arms {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_arm(arm);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-07-09 07:38:31 -04:00
|
|
|
self.bclose(expr.span);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-06-06 15:50:59 -07:00
|
|
|
ast::ExprKind::Closure(
|
2019-12-22 17:42:04 -05:00
|
|
|
capture_clause,
|
|
|
|
asyncness,
|
|
|
|
movability,
|
|
|
|
ref decl,
|
|
|
|
ref body,
|
|
|
|
_,
|
|
|
|
) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_movability(movability);
|
|
|
|
self.print_asyncness(asyncness);
|
|
|
|
self.print_capture_clause(capture_clause);
|
2014-07-23 12:43:29 -07:00
|
|
|
|
2019-12-01 16:00:08 +01:00
|
|
|
self.print_fn_params_and_ret(decl, true);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.print_expr(body);
|
|
|
|
self.end(); // need to close a box
|
2016-06-23 09:51:18 +00:00
|
|
|
|
2014-03-16 20:58:11 +02:00
|
|
|
// a box will be closed by print_expr, but we didn't want an overall
|
|
|
|
// wrapper so we closed the corresponding opening. so create an
|
|
|
|
// empty box to satisfy the close.
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(0);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-04-16 05:44:39 +02:00
|
|
|
ast::ExprKind::Block(ref blk, opt_label) => {
|
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.word_space(":");
|
2018-04-16 05:44:39 +02:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
// containing cbox, will be closed by print-block at }
|
2019-06-24 14:15:11 -04:00
|
|
|
self.cbox(INDENT_UNIT);
|
2014-03-16 20:58:11 +02:00
|
|
|
// head-box, will be closed by print-block after {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(0);
|
|
|
|
self.print_block_with_attrs(blk, attrs);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-06-06 15:50:59 -07:00
|
|
|
ast::ExprKind::Async(capture_clause, _, ref blk) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("async");
|
|
|
|
self.print_capture_clause(capture_clause);
|
|
|
|
self.s.space();
|
2018-10-02 21:43:05 -07:00
|
|
|
// cbox/ibox in analogy to the `ExprKind::Block` arm above
|
2019-06-24 14:15:11 -04:00
|
|
|
self.cbox(INDENT_UNIT);
|
|
|
|
self.ibox(0);
|
|
|
|
self.print_block_with_attrs(blk, attrs);
|
2018-06-06 15:50:59 -07:00
|
|
|
}
|
2019-07-02 06:30:21 +02:00
|
|
|
ast::ExprKind::Await(ref expr) => {
|
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_POSTFIX);
|
|
|
|
self.s.word(".await");
|
2019-04-18 12:55:23 -07:00
|
|
|
}
|
2019-12-22 21:08:53 +00:00
|
|
|
ast::ExprKind::Assign(ref lhs, ref rhs, _) => {
|
2017-07-20 16:53:56 -04:00
|
|
|
let prec = AssocOp::Assign.precedence() as i8;
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(lhs, prec + 1);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_expr_maybe_paren(rhs, prec);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::AssignOp(op, ref lhs, ref rhs) => {
|
2017-07-20 16:53:56 -04:00
|
|
|
let prec = AssocOp::Assign.precedence() as i8;
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(lhs, prec + 1);
|
|
|
|
self.s.space();
|
|
|
|
self.s.word(op.node.to_string());
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_expr_maybe_paren(rhs, prec);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-03-18 16:47:09 +03:00
|
|
|
ast::ExprKind::Field(ref expr, ident) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_POSTFIX);
|
|
|
|
self.s.word(".");
|
|
|
|
self.print_ident(ident);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Index(ref expr, ref index) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_POSTFIX);
|
|
|
|
self.s.word("[");
|
|
|
|
self.print_expr(index);
|
|
|
|
self.s.word("]");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-11 12:52:39 -05:00
|
|
|
ast::ExprKind::Range(ref start, ref end, limits) => {
|
2017-07-20 16:53:56 -04:00
|
|
|
// Special case for `Range`. `AssocOp` claims that `Range` has higher precedence
|
|
|
|
// than `Assign`, but `x .. x = x` gives a parse error instead of `x .. (x = x)`.
|
|
|
|
// Here we use a fake precedence value so that any child with lower precedence than
|
|
|
|
// a "normal" binop gets parenthesized. (`LOr` is the lowest-precedence binop.)
|
|
|
|
let fake_prec = AssocOp::LOr.precedence() as i8;
|
2017-05-12 20:05:39 +02:00
|
|
|
if let Some(ref e) = *start {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(e, fake_prec);
|
2014-09-15 20:48:58 +12:00
|
|
|
}
|
2016-01-13 01:23:31 -05:00
|
|
|
if limits == ast::RangeLimits::HalfOpen {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("..");
|
2016-01-13 01:23:31 -05:00
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("..=");
|
2016-01-13 01:23:31 -05:00
|
|
|
}
|
2017-05-12 20:05:39 +02:00
|
|
|
if let Some(ref e) = *end {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(e, fake_prec);
|
2014-09-15 20:48:58 +12:00
|
|
|
}
|
2014-12-13 18:41:02 +13:00
|
|
|
}
|
2020-11-11 13:15:15 +00:00
|
|
|
ast::ExprKind::Underscore => self.s.word("_"),
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::ExprKind::Path(None, ref path) => self.print_path(path, true, 0),
|
|
|
|
ast::ExprKind::Path(Some(ref qself), ref path) => self.print_qpath(path, qself, true),
|
2018-01-16 01:44:32 +03:00
|
|
|
ast::ExprKind::Break(opt_label, ref opt_expr) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("break");
|
|
|
|
self.s.space();
|
2018-01-16 01:44:32 +03:00
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.s.space();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
Implement the `loop_break_value` feature.
This implements RFC 1624, tracking issue #37339.
- `FnCtxt` (in typeck) gets a stack of `LoopCtxt`s, which store the
currently deduced type of that loop, the desired type, and a list of
break expressions currently seen. `loop` loops get a fresh type
variable as their initial type (this logic is stolen from that for
arrays). `while` loops get `()`.
- `break {expr}` looks up the broken loop, and unifies the type of
`expr` with the type of the loop.
- `break` with no expr unifies the loop's type with `()`.
- When building MIR, `loop` loops no longer construct a `()` value at
termination of the loop; rather, the `break` expression assigns the
result of the loop. `while` loops are unchanged.
- `break` respects contexts in which expressions may not end with braced
blocks. That is, `while break { break-value } { while-body }` is
illegal; this preserves backwards compatibility.
- The RFC did not make it clear, but I chose to make `break ()` inside
of a `while` loop illegal, just in case we wanted to do anything with
that design space in the future.
This is my first time dealing with this part of rustc so I'm sure
there's plenty of problems to pick on here ^_^
2016-10-29 15:15:06 -07:00
|
|
|
if let Some(ref expr) = *opt_expr {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_JUMP);
|
|
|
|
self.s.space();
|
Implement the `loop_break_value` feature.
This implements RFC 1624, tracking issue #37339.
- `FnCtxt` (in typeck) gets a stack of `LoopCtxt`s, which store the
currently deduced type of that loop, the desired type, and a list of
break expressions currently seen. `loop` loops get a fresh type
variable as their initial type (this logic is stolen from that for
arrays). `while` loops get `()`.
- `break {expr}` looks up the broken loop, and unifies the type of
`expr` with the type of the loop.
- `break` with no expr unifies the loop's type with `()`.
- When building MIR, `loop` loops no longer construct a `()` value at
termination of the loop; rather, the `break` expression assigns the
result of the loop. `while` loops are unchanged.
- `break` respects contexts in which expressions may not end with braced
blocks. That is, `while break { break-value } { while-body }` is
illegal; this preserves backwards compatibility.
- The RFC did not make it clear, but I chose to make `break ()` inside
of a `while` loop illegal, just in case we wanted to do anything with
that design space in the future.
This is my first time dealing with this part of rustc so I'm sure
there's plenty of problems to pick on here ^_^
2016-10-29 15:15:06 -07:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-01-16 01:44:32 +03:00
|
|
|
ast::ExprKind::Continue(opt_label) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("continue");
|
|
|
|
self.s.space();
|
2018-01-16 01:44:32 +03:00
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.s.space()
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Ret(ref result) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("return");
|
2017-05-12 20:05:39 +02:00
|
|
|
if let Some(ref expr) = *result {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(" ");
|
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_JUMP);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2020-01-22 14:20:27 +00:00
|
|
|
ast::ExprKind::InlineAsm(ref a) => {
|
|
|
|
enum AsmArg<'a> {
|
|
|
|
Template(String),
|
|
|
|
Operand(&'a InlineAsmOperand),
|
|
|
|
Options(InlineAsmOptions),
|
|
|
|
}
|
|
|
|
|
|
|
|
let mut args = vec![];
|
|
|
|
args.push(AsmArg::Template(InlineAsmTemplatePiece::to_string(&a.template)));
|
|
|
|
args.extend(a.operands.iter().map(|(o, _)| AsmArg::Operand(o)));
|
|
|
|
if !a.options.is_empty() {
|
|
|
|
args.push(AsmArg::Options(a.options));
|
|
|
|
}
|
|
|
|
|
|
|
|
self.word("asm!");
|
|
|
|
self.popen();
|
|
|
|
self.commasep(Consistent, &args, |s, arg| match arg {
|
|
|
|
AsmArg::Template(template) => s.print_string(&template, ast::StrStyle::Cooked),
|
|
|
|
AsmArg::Operand(op) => {
|
|
|
|
let print_reg_or_class = |s: &mut Self, r: &InlineAsmRegOrRegClass| match r
|
|
|
|
{
|
|
|
|
InlineAsmRegOrRegClass::Reg(r) => {
|
2020-07-08 20:03:37 +10:00
|
|
|
s.print_symbol(*r, ast::StrStyle::Cooked)
|
2020-01-22 14:20:27 +00:00
|
|
|
}
|
|
|
|
InlineAsmRegOrRegClass::RegClass(r) => s.word(r.to_string()),
|
|
|
|
};
|
|
|
|
match op {
|
|
|
|
InlineAsmOperand::In { reg, expr } => {
|
|
|
|
s.word("in");
|
|
|
|
s.popen();
|
|
|
|
print_reg_or_class(s, reg);
|
|
|
|
s.pclose();
|
|
|
|
s.space();
|
|
|
|
s.print_expr(expr);
|
|
|
|
}
|
|
|
|
InlineAsmOperand::Out { reg, late, expr } => {
|
|
|
|
s.word(if *late { "lateout" } else { "out" });
|
|
|
|
s.popen();
|
|
|
|
print_reg_or_class(s, reg);
|
|
|
|
s.pclose();
|
|
|
|
s.space();
|
|
|
|
match expr {
|
|
|
|
Some(expr) => s.print_expr(expr),
|
|
|
|
None => s.word("_"),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
InlineAsmOperand::InOut { reg, late, expr } => {
|
|
|
|
s.word(if *late { "inlateout" } else { "inout" });
|
|
|
|
s.popen();
|
|
|
|
print_reg_or_class(s, reg);
|
|
|
|
s.pclose();
|
|
|
|
s.space();
|
|
|
|
s.print_expr(expr);
|
|
|
|
}
|
|
|
|
InlineAsmOperand::SplitInOut { reg, late, in_expr, out_expr } => {
|
|
|
|
s.word(if *late { "inlateout" } else { "inout" });
|
|
|
|
s.popen();
|
|
|
|
print_reg_or_class(s, reg);
|
|
|
|
s.pclose();
|
|
|
|
s.space();
|
|
|
|
s.print_expr(in_expr);
|
|
|
|
s.space();
|
|
|
|
s.word_space("=>");
|
|
|
|
match out_expr {
|
|
|
|
Some(out_expr) => s.print_expr(out_expr),
|
|
|
|
None => s.word("_"),
|
|
|
|
}
|
|
|
|
}
|
|
|
|
InlineAsmOperand::Const { expr } => {
|
|
|
|
s.word("const");
|
|
|
|
s.space();
|
|
|
|
s.print_expr(expr);
|
|
|
|
}
|
|
|
|
InlineAsmOperand::Sym { expr } => {
|
|
|
|
s.word("sym");
|
|
|
|
s.space();
|
|
|
|
s.print_expr(expr);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
AsmArg::Options(opts) => {
|
|
|
|
s.word("options");
|
|
|
|
s.popen();
|
|
|
|
let mut options = vec![];
|
|
|
|
if opts.contains(InlineAsmOptions::PURE) {
|
|
|
|
options.push("pure");
|
|
|
|
}
|
|
|
|
if opts.contains(InlineAsmOptions::NOMEM) {
|
|
|
|
options.push("nomem");
|
|
|
|
}
|
|
|
|
if opts.contains(InlineAsmOptions::READONLY) {
|
|
|
|
options.push("readonly");
|
|
|
|
}
|
|
|
|
if opts.contains(InlineAsmOptions::PRESERVES_FLAGS) {
|
|
|
|
options.push("preserves_flags");
|
|
|
|
}
|
|
|
|
if opts.contains(InlineAsmOptions::NORETURN) {
|
|
|
|
options.push("noreturn");
|
|
|
|
}
|
|
|
|
if opts.contains(InlineAsmOptions::NOSTACK) {
|
|
|
|
options.push("nostack");
|
|
|
|
}
|
2020-05-01 23:59:15 +01:00
|
|
|
if opts.contains(InlineAsmOptions::ATT_SYNTAX) {
|
|
|
|
options.push("att_syntax");
|
|
|
|
}
|
2020-01-22 14:20:27 +00:00
|
|
|
s.commasep(Inconsistent, &options, |s, &opt| {
|
|
|
|
s.word(opt);
|
|
|
|
});
|
|
|
|
s.pclose();
|
|
|
|
}
|
|
|
|
});
|
|
|
|
self.pclose();
|
|
|
|
}
|
2020-01-14 13:40:42 +00:00
|
|
|
ast::ExprKind::LlvmInlineAsm(ref a) => {
|
|
|
|
self.s.word("llvm_asm!");
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2020-07-08 20:03:37 +10:00
|
|
|
self.print_symbol(a.asm, a.asm_str_style);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space(":");
|
2014-04-17 17:35:40 +09:00
|
|
|
|
2016-12-29 13:57:01 -08:00
|
|
|
self.commasep(Inconsistent, &a.outputs, |s, out| {
|
2016-11-16 10:52:37 +00:00
|
|
|
let constraint = out.constraint.as_str();
|
|
|
|
let mut ch = constraint.chars();
|
2016-04-07 10:42:53 -07:00
|
|
|
match ch.next() {
|
|
|
|
Some('=') if out.is_rw => {
|
2019-12-22 17:42:04 -05:00
|
|
|
s.print_string(&format!("+{}", ch.as_str()), ast::StrStyle::Cooked)
|
2014-08-19 20:39:26 +01:00
|
|
|
}
|
2019-12-22 17:42:04 -05:00
|
|
|
_ => s.print_string(&constraint, ast::StrStyle::Cooked),
|
2014-08-19 20:39:26 +01:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
s.popen();
|
|
|
|
s.print_expr(&out.expr);
|
|
|
|
s.pclose();
|
|
|
|
});
|
|
|
|
self.s.space();
|
|
|
|
self.word_space(":");
|
2016-12-29 13:57:01 -08:00
|
|
|
|
|
|
|
self.commasep(Inconsistent, &a.inputs, |s, &(co, ref o)| {
|
2020-07-08 20:03:37 +10:00
|
|
|
s.print_symbol(co, ast::StrStyle::Cooked);
|
2019-06-24 14:15:11 -04:00
|
|
|
s.popen();
|
|
|
|
s.print_expr(o);
|
|
|
|
s.pclose();
|
|
|
|
});
|
|
|
|
self.s.space();
|
|
|
|
self.word_space(":");
|
2014-04-17 17:35:40 +09:00
|
|
|
|
2020-07-08 20:03:37 +10:00
|
|
|
self.commasep(Inconsistent, &a.clobbers, |s, &co| {
|
|
|
|
s.print_symbol(co, ast::StrStyle::Cooked);
|
2019-06-24 14:15:11 -04:00
|
|
|
});
|
2014-12-17 22:02:50 +09:00
|
|
|
|
2016-10-29 22:54:04 +01:00
|
|
|
let mut options = vec![];
|
2014-12-17 22:02:50 +09:00
|
|
|
if a.volatile {
|
|
|
|
options.push("volatile");
|
|
|
|
}
|
|
|
|
if a.alignstack {
|
|
|
|
options.push("alignstack");
|
|
|
|
}
|
2020-01-14 13:40:42 +00:00
|
|
|
if a.dialect == ast::LlvmAsmDialect::Intel {
|
2014-12-17 22:02:50 +09:00
|
|
|
options.push("intel");
|
|
|
|
}
|
|
|
|
|
2015-03-24 16:54:09 -07:00
|
|
|
if !options.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space(":");
|
2019-12-22 17:42:04 -05:00
|
|
|
self.commasep(Inconsistent, &options, |s, &co| {
|
|
|
|
s.print_string(co, ast::StrStyle::Cooked);
|
|
|
|
});
|
2014-12-17 22:02:50 +09:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
ast::ExprKind::MacCall(ref m) => self.print_mac(m),
|
2016-02-08 16:05:05 +01:00
|
|
|
ast::ExprKind::Paren(ref e) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.print_inner_attributes_inline(attrs);
|
|
|
|
self.print_expr(e);
|
|
|
|
self.pclose();
|
2019-12-22 17:42:04 -05:00
|
|
|
}
|
2016-12-26 14:34:03 +01:00
|
|
|
ast::ExprKind::Yield(ref e) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("yield");
|
2020-03-22 13:36:56 +01:00
|
|
|
|
|
|
|
if let Some(ref expr) = *e {
|
|
|
|
self.s.space();
|
|
|
|
self.print_expr_maybe_paren(expr, parser::PREC_JUMP);
|
2016-12-26 14:34:03 +01:00
|
|
|
}
|
|
|
|
}
|
2016-02-28 17:38:48 -05:00
|
|
|
ast::ExprKind::Try(ref e) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr_maybe_paren(e, parser::PREC_POSTFIX);
|
|
|
|
self.s.word("?")
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2018-07-21 18:47:02 -07:00
|
|
|
ast::ExprKind::TryBlock(ref blk) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.head("try");
|
|
|
|
self.s.space();
|
|
|
|
self.print_block_with_attrs(blk, attrs)
|
2017-02-17 15:12:47 -08:00
|
|
|
}
|
2018-12-17 04:57:32 +03:00
|
|
|
ast::ExprKind::Err => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.s.word("/*ERROR*/");
|
|
|
|
self.pclose()
|
2018-12-17 04:57:32 +03:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ann.post(self, AnnNode::Expr(expr));
|
|
|
|
self.end();
|
2011-08-10 12:51:50 -07:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_local_decl(&mut self, loc: &ast::Local) {
|
|
|
|
self.print_pat(&loc.pat);
|
2015-01-02 20:55:31 +09:00
|
|
|
if let Some(ref ty) = loc.ty {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space(":");
|
|
|
|
self.print_type(ty);
|
2011-03-04 07:22:43 +01:00
|
|
|
}
|
|
|
|
}
|
2011-03-24 16:33:20 +01:00
|
|
|
|
2019-10-15 22:48:13 +02:00
|
|
|
pub fn print_usize(&mut self, i: usize) {
|
2018-11-29 11:36:58 +11:00
|
|
|
self.s.word(i.to_string())
|
2014-08-10 15:54:33 +12:00
|
|
|
}
|
|
|
|
|
2020-04-19 13:00:18 +02:00
|
|
|
crate fn print_name(&mut self, name: Symbol) {
|
2019-10-22 08:31:37 +11:00
|
|
|
self.s.word(name.to_string());
|
2018-08-22 22:05:19 +01:00
|
|
|
self.ann.post(self, AnnNode::Name(&name))
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-08-07 09:47:28 -07:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
fn print_qpath(&mut self, path: &ast::Path, qself: &ast::QSelf, colons_before_params: bool) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("<");
|
|
|
|
self.print_type(&qself.ty);
|
2015-02-24 12:12:14 +02:00
|
|
|
if qself.position > 0 {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("as");
|
2015-02-24 12:12:14 +02:00
|
|
|
let depth = path.segments.len() - qself.position;
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, false, depth);
|
2015-02-24 12:12:14 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(">");
|
2020-11-12 12:41:19 +01:00
|
|
|
for item_segment in &path.segments[qself.position..] {
|
|
|
|
self.s.word("::");
|
|
|
|
self.print_ident(item_segment.ident);
|
|
|
|
if let Some(ref args) = item_segment.args {
|
|
|
|
self.print_generic_args(args, colons_before_params)
|
|
|
|
}
|
2016-12-10 06:45:58 +00:00
|
|
|
}
|
2015-01-13 06:02:56 +02:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_pat(&mut self, pat: &ast::Pat) {
|
|
|
|
self.maybe_print_comment(pat.span.lo());
|
|
|
|
self.ann.pre(self, AnnNode::Pat(pat));
|
2014-03-16 20:58:11 +02:00
|
|
|
/* Pat isn't normalized, but the beauty of it
|
2019-12-22 17:42:04 -05:00
|
|
|
is that it doesn't matter */
|
2019-09-26 16:18:31 +01:00
|
|
|
match pat.kind {
|
2019-06-24 14:15:11 -04:00
|
|
|
PatKind::Wild => self.s.word("_"),
|
2018-03-18 16:47:09 +03:00
|
|
|
PatKind::Ident(binding_mode, ident, ref sub) => {
|
2014-03-16 20:58:11 +02:00
|
|
|
match binding_mode {
|
2015-12-18 14:23:01 +01:00
|
|
|
ast::BindingMode::ByRef(mutbl) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("ref");
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mutability(mutbl, false);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-12-16 17:28:40 +01:00
|
|
|
ast::BindingMode::ByValue(ast::Mutability::Not) => {}
|
|
|
|
ast::BindingMode::ByValue(ast::Mutability::Mut) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("mut");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(ident);
|
2016-06-13 22:43:30 -07:00
|
|
|
if let Some(ref p) = *sub {
|
2019-10-14 18:12:04 +02:00
|
|
|
self.s.space();
|
|
|
|
self.s.word_space("@");
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_pat(p);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2019-07-09 09:12:14 +02:00
|
|
|
PatKind::TupleStruct(ref path, ref elts) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, true, 0);
|
|
|
|
self.popen();
|
2019-07-09 09:12:14 +02:00
|
|
|
self.commasep(Inconsistent, &elts[..], |s, p| s.print_pat(p));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2013-11-07 19:25:39 -08:00
|
|
|
}
|
2018-10-19 15:40:07 +01:00
|
|
|
PatKind::Or(ref pats) => {
|
2019-07-14 01:05:52 +00:00
|
|
|
self.strsep("|", true, Inconsistent, &pats[..], |s, p| s.print_pat(p));
|
2018-10-19 15:40:07 +01:00
|
|
|
}
|
2016-06-11 18:47:47 +03:00
|
|
|
PatKind::Path(None, ref path) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, true, 0);
|
2016-02-13 15:51:27 +03:00
|
|
|
}
|
2016-06-11 18:47:47 +03:00
|
|
|
PatKind::Path(Some(ref qself), ref path) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_qpath(path, qself, false);
|
2015-03-25 10:53:28 -06:00
|
|
|
}
|
2016-02-11 21:16:33 +03:00
|
|
|
PatKind::Struct(ref path, ref fields, etc) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(path, true, 0);
|
|
|
|
self.nbsp();
|
|
|
|
self.word_space("{");
|
2016-12-29 13:57:01 -08:00
|
|
|
self.commasep_cmnt(
|
2019-12-22 17:42:04 -05:00
|
|
|
Consistent,
|
|
|
|
&fields[..],
|
2014-03-16 20:58:11 +02:00
|
|
|
|s, f| {
|
2019-06-24 14:15:11 -04:00
|
|
|
s.cbox(INDENT_UNIT);
|
2019-08-15 02:35:36 +03:00
|
|
|
if !f.is_shorthand {
|
|
|
|
s.print_ident(f.ident);
|
2019-06-24 14:15:11 -04:00
|
|
|
s.word_nbsp(":");
|
2014-10-27 00:11:26 -07:00
|
|
|
}
|
2019-08-15 02:35:36 +03:00
|
|
|
s.print_pat(&f.pat);
|
2019-06-24 14:15:11 -04:00
|
|
|
s.end();
|
2014-03-16 20:58:11 +02:00
|
|
|
},
|
2019-12-22 17:42:04 -05:00
|
|
|
|f| f.pat.span,
|
|
|
|
);
|
2014-03-16 20:58:11 +02:00
|
|
|
if etc {
|
2019-12-22 17:42:04 -05:00
|
|
|
if !fields.is_empty() {
|
|
|
|
self.word_space(",");
|
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("..");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.s.word("}");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-07-09 09:12:14 +02:00
|
|
|
PatKind::Tuple(ref elts) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
2019-07-09 09:12:14 +02:00
|
|
|
self.commasep(Inconsistent, &elts[..], |s, p| s.print_pat(p));
|
|
|
|
if elts.len() == 1 {
|
|
|
|
self.s.word(",");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.pclose();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-11 21:16:33 +03:00
|
|
|
PatKind::Box(ref inner) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("box ");
|
|
|
|
self.print_pat(inner);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-02-11 21:16:33 +03:00
|
|
|
PatKind::Ref(ref inner, mutbl) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("&");
|
2019-12-16 17:28:40 +01:00
|
|
|
if mutbl == ast::Mutability::Mut {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("mut ");
|
2014-12-05 15:56:25 -08:00
|
|
|
}
|
2020-12-19 23:13:50 +01:00
|
|
|
if let PatKind::Ident(ast::BindingMode::ByValue(ast::Mutability::Mut), ..) =
|
|
|
|
inner.kind
|
|
|
|
{
|
|
|
|
self.popen();
|
|
|
|
self.print_pat(inner);
|
|
|
|
self.pclose();
|
|
|
|
} else {
|
|
|
|
self.print_pat(inner);
|
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
PatKind::Lit(ref e) => self.print_expr(&**e),
|
2018-05-28 19:32:03 -07:00
|
|
|
PatKind::Range(ref begin, ref end, Spanned { node: ref end_kind, .. }) => {
|
2019-12-11 10:04:34 +01:00
|
|
|
if let Some(e) = begin {
|
|
|
|
self.print_expr(e);
|
|
|
|
self.s.space();
|
|
|
|
}
|
2017-01-10 22:13:53 +01:00
|
|
|
match *end_kind {
|
2019-06-24 14:15:11 -04:00
|
|
|
RangeEnd::Included(RangeSyntax::DotDotDot) => self.s.word("..."),
|
|
|
|
RangeEnd::Included(RangeSyntax::DotDotEq) => self.s.word("..="),
|
|
|
|
RangeEnd::Excluded => self.s.word(".."),
|
2017-01-10 22:13:53 +01:00
|
|
|
}
|
2019-12-11 10:04:34 +01:00
|
|
|
if let Some(e) = end {
|
|
|
|
self.print_expr(e);
|
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-07-09 09:12:14 +02:00
|
|
|
PatKind::Slice(ref elts) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("[");
|
2019-07-09 09:12:14 +02:00
|
|
|
self.commasep(Inconsistent, &elts[..], |s, p| s.print_pat(p));
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("]");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-07-07 00:26:55 +02:00
|
|
|
PatKind::Rest => self.s.word(".."),
|
2018-02-24 15:27:06 +03:00
|
|
|
PatKind::Paren(ref inner) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.popen();
|
|
|
|
self.print_pat(inner);
|
|
|
|
self.pclose();
|
2018-02-24 15:27:06 +03:00
|
|
|
}
|
2020-02-29 19:32:20 +03:00
|
|
|
PatKind::MacCall(ref m) => self.print_mac(m),
|
2013-02-27 03:58:46 +09:00
|
|
|
}
|
2018-08-22 22:05:19 +01:00
|
|
|
self.ann.post(self, AnnNode::Pat(pat))
|
2013-12-27 14:11:01 -08:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_arm(&mut self, arm: &ast::Arm) {
|
2019-09-06 03:56:45 +01:00
|
|
|
// Note, I have no idea why this check is necessary, but here it is.
|
2014-07-27 18:05:07 -07:00
|
|
|
if arm.attrs.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
}
|
|
|
|
self.cbox(INDENT_UNIT);
|
|
|
|
self.ibox(0);
|
2019-08-28 01:15:33 +02:00
|
|
|
self.maybe_print_comment(arm.pat.span.lo());
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_outer_attributes(&arm.attrs);
|
2019-08-28 01:15:33 +02:00
|
|
|
self.print_pat(&arm.pat);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
2019-06-23 11:32:16 +02:00
|
|
|
if let Some(ref e) = arm.guard {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("if");
|
|
|
|
self.print_expr(e);
|
|
|
|
self.s.space();
|
2014-07-27 18:05:07 -07:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("=>");
|
2014-07-27 18:05:07 -07:00
|
|
|
|
2019-09-26 14:39:48 +01:00
|
|
|
match arm.body.kind {
|
2018-04-16 05:44:39 +02:00
|
|
|
ast::ExprKind::Block(ref blk, opt_label) => {
|
|
|
|
if let Some(label) = opt_label {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_ident(label.ident);
|
|
|
|
self.word_space(":");
|
2018-04-16 05:44:39 +02:00
|
|
|
}
|
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
// The block will close the pattern's ibox.
|
2019-07-09 09:30:08 -04:00
|
|
|
self.print_block_unclosed_indent(blk);
|
2014-11-22 16:24:58 +01:00
|
|
|
|
2019-09-06 03:56:45 +01:00
|
|
|
// If it is a user-provided unsafe block, print a comma after it.
|
2016-02-08 12:44:45 +01:00
|
|
|
if let BlockCheckMode::Unsafe(ast::UserProvided) = blk.rules {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(",");
|
2014-11-22 16:24:58 +01:00
|
|
|
}
|
2014-07-27 18:05:07 -07:00
|
|
|
}
|
|
|
|
_ => {
|
2019-09-06 03:56:45 +01:00
|
|
|
self.end(); // Close the ibox for the pattern.
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_expr(&arm.body);
|
|
|
|
self.s.word(",");
|
2014-07-27 18:05:07 -07:00
|
|
|
}
|
|
|
|
}
|
2019-09-06 03:56:45 +01:00
|
|
|
self.end(); // Close enclosing cbox.
|
2014-07-27 18:05:07 -07:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
fn print_explicit_self(&mut self, explicit_self: &ast::ExplicitSelf) {
|
2016-03-06 15:54:44 +03:00
|
|
|
match explicit_self.node {
|
|
|
|
SelfKind::Value(m) => {
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mutability(m, false);
|
2017-06-24 21:22:42 -06:00
|
|
|
self.s.word("self")
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-03-06 15:54:44 +03:00
|
|
|
SelfKind::Region(ref lt, m) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("&");
|
|
|
|
self.print_opt_lifetime(lt);
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mutability(m, false);
|
2017-06-24 21:22:42 -06:00
|
|
|
self.s.word("self")
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2016-03-06 15:54:44 +03:00
|
|
|
SelfKind::Explicit(ref typ, m) => {
|
2019-11-23 14:15:49 +00:00
|
|
|
self.print_mutability(m, false);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("self");
|
|
|
|
self.word_space(":");
|
2017-05-12 20:05:39 +02:00
|
|
|
self.print_type(typ)
|
2014-05-06 16:37:32 -07:00
|
|
|
}
|
2013-03-09 19:43:53 -05:00
|
|
|
}
|
2012-08-17 16:14:57 -07:00
|
|
|
}
|
|
|
|
|
2020-01-30 00:18:54 +01:00
|
|
|
fn print_fn_full(
|
|
|
|
&mut self,
|
|
|
|
sig: &ast::FnSig,
|
2020-04-19 13:00:18 +02:00
|
|
|
name: Ident,
|
2020-01-30 00:18:54 +01:00
|
|
|
generics: &ast::Generics,
|
|
|
|
vis: &ast::Visibility,
|
2020-02-21 01:21:17 +01:00
|
|
|
defaultness: ast::Defaultness,
|
2020-01-30 00:18:54 +01:00
|
|
|
body: Option<&ast::Block>,
|
|
|
|
attrs: &[ast::Attribute],
|
|
|
|
) {
|
|
|
|
if body.is_some() {
|
|
|
|
self.head("");
|
|
|
|
}
|
2020-02-21 01:21:17 +01:00
|
|
|
self.print_visibility(vis);
|
|
|
|
self.print_defaultness(defaultness);
|
|
|
|
self.print_fn(&sig.decl, sig.header, Some(name), generics);
|
2020-01-30 00:18:54 +01:00
|
|
|
if let Some(body) = body {
|
|
|
|
self.nbsp();
|
|
|
|
self.print_block_with_attrs(body, attrs);
|
|
|
|
} else {
|
|
|
|
self.s.word(";");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_fn(
|
|
|
|
&mut self,
|
|
|
|
decl: &ast::FnDecl,
|
|
|
|
header: ast::FnHeader,
|
2020-04-19 13:00:18 +02:00
|
|
|
name: Option<Ident>,
|
2019-12-22 17:42:04 -05:00
|
|
|
generics: &ast::Generics,
|
|
|
|
) {
|
2020-02-21 01:21:17 +01:00
|
|
|
self.print_fn_header_info(header);
|
2015-03-11 08:38:27 +02:00
|
|
|
if let Some(name) = name {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
|
|
|
self.print_ident(name);
|
2015-03-11 08:38:27 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_generic_params(&generics.params);
|
2019-12-01 16:00:08 +01:00
|
|
|
self.print_fn_params_and_ret(decl, false);
|
2015-03-13 21:54:29 -07:00
|
|
|
self.print_where_clause(&generics.where_clause)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2019-12-01 16:00:08 +01:00
|
|
|
crate fn print_fn_params_and_ret(&mut self, decl: &ast::FnDecl, is_closure: bool) {
|
|
|
|
let (open, close) = if is_closure { ("|", "|") } else { ("(", ")") };
|
|
|
|
self.word(open);
|
|
|
|
self.commasep(Inconsistent, &decl.inputs, |s, param| s.print_param(param, is_closure));
|
|
|
|
self.word(close);
|
|
|
|
self.print_fn_ret_ty(&decl.output)
|
2011-03-24 16:33:20 +01:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_movability(&mut self, movability: ast::Movability) {
|
2017-10-07 16:36:28 +02:00
|
|
|
match movability {
|
|
|
|
ast::Movability::Static => self.word_space("static"),
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::Movability::Movable => {}
|
2017-10-07 16:36:28 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-01-30 05:31:04 +01:00
|
|
|
crate fn print_asyncness(&mut self, asyncness: ast::Async) {
|
2018-06-06 15:50:59 -07:00
|
|
|
if asyncness.is_async() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_nbsp("async");
|
2018-06-06 15:50:59 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_capture_clause(&mut self, capture_clause: ast::CaptureBy) {
|
2014-07-23 12:43:29 -07:00
|
|
|
match capture_clause {
|
2016-02-08 15:27:08 +01:00
|
|
|
ast::CaptureBy::Value => self.word_space("move"),
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::CaptureBy::Ref => {}
|
2014-07-23 12:43:29 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-15 22:48:13 +02:00
|
|
|
pub fn print_type_bounds(&mut self, prefix: &'static str, bounds: &[ast::GenericBound]) {
|
2014-08-27 21:46:52 -04:00
|
|
|
if !bounds.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(prefix);
|
2014-03-16 20:58:11 +02:00
|
|
|
let mut first = true;
|
2015-01-31 12:20:46 -05:00
|
|
|
for bound in bounds {
|
2017-12-19 23:40:17 +03:00
|
|
|
if !(first && prefix.is_empty()) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.nbsp();
|
2017-12-19 23:40:17 +03:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
if first {
|
|
|
|
first = false;
|
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space("+");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-10-28 15:22:49 -07:00
|
|
|
|
2017-12-19 23:40:17 +03:00
|
|
|
match bound {
|
2018-06-14 12:23:46 +01:00
|
|
|
GenericBound::Trait(tref, modifier) => {
|
2017-12-19 23:40:17 +03:00
|
|
|
if modifier == &TraitBoundModifier::Maybe {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("?");
|
2017-12-19 23:40:17 +03:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_poly_trait_ref(tref);
|
2014-08-27 21:46:52 -04:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
GenericBound::Outlives(lt) => self.print_lifetime(*lt),
|
2017-12-19 23:40:17 +03:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-10-28 15:22:49 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_lifetime(&mut self, lifetime: ast::Lifetime) {
|
2017-03-25 21:14:18 +00:00
|
|
|
self.print_name(lifetime.ident.name)
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2013-10-28 15:22:49 -07:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_lifetime_bounds(
|
2019-12-22 17:42:04 -05:00
|
|
|
&mut self,
|
|
|
|
lifetime: ast::Lifetime,
|
|
|
|
bounds: &ast::GenericBounds,
|
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_lifetime(lifetime);
|
2016-06-29 21:53:01 +09:00
|
|
|
if !bounds.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(": ");
|
2016-06-29 21:53:01 +09:00
|
|
|
for (i, bound) in bounds.iter().enumerate() {
|
|
|
|
if i != 0 {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(" + ");
|
2016-06-29 21:53:01 +09:00
|
|
|
}
|
2018-05-28 15:23:16 +01:00
|
|
|
match bound {
|
2019-06-24 14:15:11 -04:00
|
|
|
ast::GenericBound::Outlives(lt) => self.print_lifetime(*lt),
|
2018-05-28 15:23:16 +01:00
|
|
|
_ => panic!(),
|
|
|
|
}
|
2016-06-29 21:53:01 +09:00
|
|
|
}
|
2014-08-05 22:59:24 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_generic_params(&mut self, generic_params: &[ast::GenericParam]) {
|
2017-10-16 21:07:26 +02:00
|
|
|
if generic_params.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
return;
|
2014-08-27 21:46:52 -04:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("<");
|
2014-08-27 21:46:52 -04:00
|
|
|
|
2017-10-16 21:07:26 +02:00
|
|
|
self.commasep(Inconsistent, &generic_params, |s, param| {
|
2019-08-02 08:36:08 +02:00
|
|
|
s.print_outer_attributes_inline(¶m.attrs);
|
|
|
|
|
2018-05-26 19:16:21 +01:00
|
|
|
match param.kind {
|
2018-05-30 16:49:39 +01:00
|
|
|
ast::GenericParamKind::Lifetime => {
|
|
|
|
let lt = ast::Lifetime { id: param.id, ident: param.ident };
|
|
|
|
s.print_lifetime_bounds(lt, ¶m.bounds)
|
2019-02-05 16:50:16 +01:00
|
|
|
}
|
2018-05-28 13:33:28 +01:00
|
|
|
ast::GenericParamKind::Type { ref default } => {
|
2019-06-24 14:15:11 -04:00
|
|
|
s.print_ident(param.ident);
|
|
|
|
s.print_type_bounds(":", ¶m.bounds);
|
2019-08-02 08:36:08 +02:00
|
|
|
if let Some(ref default) = default {
|
|
|
|
s.s.space();
|
|
|
|
s.word_space("=");
|
|
|
|
s.print_type(default)
|
2018-05-26 19:16:21 +01:00
|
|
|
}
|
|
|
|
}
|
2020-12-31 01:58:27 +01:00
|
|
|
ast::GenericParamKind::Const { ref ty, kw_span: _, ref default } => {
|
2019-06-24 14:15:11 -04:00
|
|
|
s.word_space("const");
|
|
|
|
s.print_ident(param.ident);
|
|
|
|
s.s.space();
|
|
|
|
s.word_space(":");
|
|
|
|
s.print_type(ty);
|
2020-12-31 01:58:27 +01:00
|
|
|
s.print_type_bounds(":", ¶m.bounds);
|
|
|
|
if let Some(ref _default) = default {
|
|
|
|
// FIXME(const_generics_defaults): print the `default` value here
|
|
|
|
}
|
2019-02-05 16:50:16 +01:00
|
|
|
}
|
2014-08-11 09:32:26 -07:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
});
|
2014-08-11 09:32:26 -07:00
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word(">");
|
2011-08-02 21:26:54 -07:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_where_clause(&mut self, where_clause: &ast::WhereClause) {
|
2020-06-08 21:09:54 -04:00
|
|
|
if where_clause.predicates.is_empty() && !where_clause.has_where_token {
|
2019-06-24 14:15:11 -04:00
|
|
|
return;
|
2014-08-11 09:32:26 -07:00
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("where");
|
2014-08-11 09:32:26 -07:00
|
|
|
|
2015-03-13 21:54:29 -07:00
|
|
|
for (i, predicate) in where_clause.predicates.iter().enumerate() {
|
2014-08-11 09:32:26 -07:00
|
|
|
if i != 0 {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.word_space(",");
|
2014-08-11 09:32:26 -07:00
|
|
|
}
|
|
|
|
|
2015-11-17 23:24:49 +09:00
|
|
|
match *predicate {
|
2017-10-16 21:07:26 +02:00
|
|
|
ast::WherePredicate::BoundPredicate(ast::WhereBoundPredicate {
|
|
|
|
ref bound_generic_params,
|
|
|
|
ref bounded_ty,
|
|
|
|
ref bounds,
|
|
|
|
..
|
|
|
|
}) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_formal_generic_params(bound_generic_params);
|
|
|
|
self.print_type(bounded_ty);
|
|
|
|
self.print_type_bounds(":", bounds);
|
2014-11-29 17:08:30 +13:00
|
|
|
}
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::WherePredicate::RegionPredicate(ast::WhereRegionPredicate {
|
|
|
|
ref lifetime,
|
|
|
|
ref bounds,
|
|
|
|
..
|
|
|
|
}) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_lifetime_bounds(*lifetime, bounds);
|
2014-12-20 02:29:19 -08:00
|
|
|
}
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::WherePredicate::EqPredicate(ast::WhereEqPredicate {
|
|
|
|
ref lhs_ty,
|
|
|
|
ref rhs_ty,
|
|
|
|
..
|
|
|
|
}) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_type(lhs_ty);
|
|
|
|
self.s.space();
|
|
|
|
self.word_space("=");
|
|
|
|
self.print_type(rhs_ty);
|
2014-11-29 17:08:30 +13:00
|
|
|
}
|
|
|
|
}
|
2014-08-11 09:32:26 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_use_tree(&mut self, tree: &ast::UseTree) {
|
2017-09-26 23:04:00 +02:00
|
|
|
match tree.kind {
|
2018-06-13 11:44:06 -05:00
|
|
|
ast::UseTreeKind::Simple(rename, ..) => {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(&tree.prefix, false, 0);
|
2018-03-09 18:58:44 +03:00
|
|
|
if let Some(rename) = rename {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.space();
|
|
|
|
self.word_space("as");
|
|
|
|
self.print_ident(rename);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
}
|
2017-09-26 23:04:00 +02:00
|
|
|
ast::UseTreeKind::Glob => {
|
|
|
|
if !tree.prefix.segments.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(&tree.prefix, false, 0);
|
|
|
|
self.s.word("::");
|
2017-09-26 23:04:00 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("*");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-09-26 23:04:00 +02:00
|
|
|
ast::UseTreeKind::Nested(ref items) => {
|
|
|
|
if tree.prefix.segments.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("{");
|
2014-03-16 20:58:11 +02:00
|
|
|
} else {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_path(&tree.prefix, false, 0);
|
|
|
|
self.s.word("::{");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-09-26 23:04:00 +02:00
|
|
|
self.commasep(Inconsistent, &items[..], |this, &(ref tree, _)| {
|
|
|
|
this.print_use_tree(tree)
|
2019-06-24 14:15:11 -04:00
|
|
|
});
|
|
|
|
self.s.word("}");
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2014-02-01 11:24:42 -08:00
|
|
|
}
|
2011-06-21 14:23:16 -07:00
|
|
|
}
|
2011-06-14 18:53:12 -07:00
|
|
|
|
2019-11-23 14:15:49 +00:00
|
|
|
pub fn print_mutability(&mut self, mutbl: ast::Mutability, print_const: bool) {
|
2014-03-16 20:58:11 +02:00
|
|
|
match mutbl {
|
2019-12-16 17:28:40 +01:00
|
|
|
ast::Mutability::Mut => self.word_nbsp("mut"),
|
2019-12-22 17:42:04 -05:00
|
|
|
ast::Mutability::Not => {
|
|
|
|
if print_const {
|
|
|
|
self.word_nbsp("const");
|
|
|
|
}
|
|
|
|
}
|
2013-01-30 17:20:02 -08:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
}
|
|
|
|
|
2019-11-23 14:15:49 +00:00
|
|
|
crate fn print_mt(&mut self, mt: &ast::MutTy, print_const: bool) {
|
|
|
|
self.print_mutability(mt.mutbl, print_const);
|
2016-02-08 23:55:55 +01:00
|
|
|
self.print_type(&mt.ty)
|
2011-03-24 16:33:20 +01:00
|
|
|
}
|
2011-03-04 07:22:43 +01:00
|
|
|
|
2019-08-27 13:24:32 +02:00
|
|
|
crate fn print_param(&mut self, input: &ast::Param, is_closure: bool) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
2019-08-02 09:34:49 +02:00
|
|
|
|
|
|
|
self.print_outer_attributes_inline(&input.attrs);
|
|
|
|
|
2019-09-26 17:25:31 +01:00
|
|
|
match input.ty.kind {
|
2019-06-24 14:15:11 -04:00
|
|
|
ast::TyKind::Infer if is_closure => self.print_pat(&input.pat),
|
2014-03-16 20:58:11 +02:00
|
|
|
_ => {
|
2016-05-08 21:18:21 +03:00
|
|
|
if let Some(eself) = input.to_self() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_explicit_self(&eself);
|
2016-05-08 21:18:21 +03:00
|
|
|
} else {
|
2019-09-26 16:18:31 +01:00
|
|
|
let invalid = if let PatKind::Ident(_, ident, _) = input.pat.kind {
|
2020-12-29 20:28:08 -05:00
|
|
|
ident.name == kw::Empty
|
2016-03-06 15:54:44 +03:00
|
|
|
} else {
|
|
|
|
false
|
|
|
|
};
|
2016-05-08 21:18:21 +03:00
|
|
|
if !invalid {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_pat(&input.pat);
|
|
|
|
self.s.word(":");
|
|
|
|
self.s.space();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_type(&input.ty);
|
2014-01-09 15:05:33 +02:00
|
|
|
}
|
2012-11-06 18:41:06 -08:00
|
|
|
}
|
2012-05-04 12:33:04 -07:00
|
|
|
}
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
|
|
|
|
2020-02-15 12:10:59 +09:00
|
|
|
crate fn print_fn_ret_ty(&mut self, fn_ret_ty: &ast::FnRetTy) {
|
|
|
|
if let ast::FnRetTy::Ty(ty) = fn_ret_ty {
|
2019-12-01 16:00:08 +01:00
|
|
|
self.space_if_not_bol();
|
|
|
|
self.ibox(INDENT_UNIT);
|
|
|
|
self.word_space("->");
|
|
|
|
self.print_type(ty);
|
|
|
|
self.end();
|
|
|
|
self.maybe_print_comment(ty.span.lo());
|
2014-11-09 16:14:15 +01:00
|
|
|
}
|
2014-09-05 21:27:47 -07:00
|
|
|
}
|
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn print_ty_fn(
|
|
|
|
&mut self,
|
|
|
|
ext: ast::Extern,
|
2020-01-30 02:42:33 +01:00
|
|
|
unsafety: ast::Unsafe,
|
2019-12-22 17:42:04 -05:00
|
|
|
decl: &ast::FnDecl,
|
2020-04-19 13:00:18 +02:00
|
|
|
name: Option<Ident>,
|
2019-12-22 17:42:04 -05:00
|
|
|
generic_params: &[ast::GenericParam],
|
|
|
|
) {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.ibox(INDENT_UNIT);
|
2017-10-16 21:07:26 +02:00
|
|
|
if !generic_params.is_empty() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.word("for");
|
|
|
|
self.print_generic_params(generic_params);
|
2015-03-18 11:54:06 -07:00
|
|
|
}
|
|
|
|
let generics = ast::Generics {
|
2017-10-16 21:07:26 +02:00
|
|
|
params: Vec::new(),
|
2020-06-08 21:09:54 -04:00
|
|
|
where_clause: ast::WhereClause {
|
|
|
|
has_where_token: false,
|
|
|
|
predicates: Vec::new(),
|
|
|
|
span: rustc_span::DUMMY_SP,
|
|
|
|
},
|
2019-12-31 20:15:40 +03:00
|
|
|
span: rustc_span::DUMMY_SP,
|
2015-03-18 11:54:06 -07:00
|
|
|
};
|
2020-01-30 00:18:54 +01:00
|
|
|
let header = ast::FnHeader { unsafety, ext, ..ast::FnHeader::default() };
|
2020-02-21 01:21:17 +01:00
|
|
|
self.print_fn(decl, header, name, &generics);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.end();
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2014-03-16 20:58:11 +02:00
|
|
|
|
2019-12-22 17:42:04 -05:00
|
|
|
crate fn maybe_print_trailing_comment(
|
|
|
|
&mut self,
|
2019-12-31 20:15:40 +03:00
|
|
|
span: rustc_span::Span,
|
2019-12-22 17:42:04 -05:00
|
|
|
next_pos: Option<BytePos>,
|
|
|
|
) {
|
2019-07-05 18:29:15 -04:00
|
|
|
if let Some(cmnts) = self.comments() {
|
|
|
|
if let Some(cmnt) = cmnts.trailing_comment(span, next_pos) {
|
|
|
|
self.print_comment(&cmnt);
|
2014-01-29 17:39:21 -08:00
|
|
|
}
|
2011-03-24 16:33:20 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_remaining_comments(&mut self) {
|
2014-03-16 20:58:11 +02:00
|
|
|
// If there aren't any remaining comments, then we need to manually
|
|
|
|
// make sure there is a line break at the end.
|
|
|
|
if self.next_comment().is_none() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.s.hardbreak();
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2017-05-12 20:05:39 +02:00
|
|
|
while let Some(ref cmnt) = self.next_comment() {
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_comment(cmnt);
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2011-07-05 11:48:19 +02:00
|
|
|
}
|
|
|
|
|
2020-02-21 01:21:17 +01:00
|
|
|
crate fn print_fn_header_info(&mut self, header: ast::FnHeader) {
|
2020-01-30 02:42:33 +01:00
|
|
|
self.print_constness(header.constness);
|
2020-01-30 05:31:04 +01:00
|
|
|
self.print_asyncness(header.asyncness);
|
2019-06-24 14:15:11 -04:00
|
|
|
self.print_unsafety(header.unsafety);
|
2015-10-24 16:52:07 +08:00
|
|
|
|
2019-11-09 22:05:20 +03:00
|
|
|
match header.ext {
|
|
|
|
ast::Extern::None => {}
|
|
|
|
ast::Extern::Implicit => {
|
|
|
|
self.word_nbsp("extern");
|
|
|
|
}
|
|
|
|
ast::Extern::Explicit(abi) => {
|
|
|
|
self.word_nbsp("extern");
|
2019-11-10 00:44:59 +03:00
|
|
|
self.print_literal(&abi.as_lit());
|
|
|
|
self.nbsp();
|
2019-11-09 22:05:20 +03:00
|
|
|
}
|
2013-03-13 22:25:28 -04:00
|
|
|
}
|
|
|
|
|
2017-06-24 21:22:42 -06:00
|
|
|
self.s.word("fn")
|
2012-05-24 23:44:58 -07:00
|
|
|
}
|
|
|
|
|
2020-01-30 02:42:33 +01:00
|
|
|
crate fn print_unsafety(&mut self, s: ast::Unsafe) {
|
2014-04-06 18:04:40 -07:00
|
|
|
match s {
|
2020-01-30 02:42:33 +01:00
|
|
|
ast::Unsafe::No => {}
|
|
|
|
ast::Unsafe::Yes(_) => self.word_nbsp("unsafe"),
|
2014-03-16 20:58:11 +02:00
|
|
|
}
|
2012-05-24 23:44:58 -07:00
|
|
|
}
|
2017-10-12 09:51:31 -03:00
|
|
|
|
2020-01-30 02:42:33 +01:00
|
|
|
crate fn print_constness(&mut self, s: ast::Const) {
|
2020-01-13 20:30:23 -08:00
|
|
|
match s {
|
2020-01-30 02:42:33 +01:00
|
|
|
ast::Const::No => {}
|
|
|
|
ast::Const::Yes(_) => self.word_nbsp("const"),
|
2020-01-13 20:30:23 -08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-24 14:15:11 -04:00
|
|
|
crate fn print_is_auto(&mut self, s: ast::IsAuto) {
|
2017-10-12 09:51:31 -03:00
|
|
|
match s {
|
|
|
|
ast::IsAuto::Yes => self.word_nbsp("auto"),
|
2019-06-24 14:15:11 -04:00
|
|
|
ast::IsAuto::No => {}
|
2017-10-12 09:51:31 -03:00
|
|
|
}
|
|
|
|
}
|
2012-11-04 20:41:00 -08:00
|
|
|
}
|