rollup merge of #21713: alexcrichton/second-pass-fmt
This commit is contained in:
commit
f6dd25bb38
@ -12,20 +12,22 @@
|
||||
|
||||
//! Threadsafe reference-counted boxes (the `Arc<T>` type).
|
||||
//!
|
||||
//! The `Arc<T>` type provides shared ownership of an immutable value. Destruction is
|
||||
//! deterministic, and will occur as soon as the last owner is gone. It is marked as `Send` because
|
||||
//! it uses atomic reference counting.
|
||||
//! The `Arc<T>` type provides shared ownership of an immutable value.
|
||||
//! Destruction is deterministic, and will occur as soon as the last owner is
|
||||
//! gone. It is marked as `Send` because it uses atomic reference counting.
|
||||
//!
|
||||
//! If you do not need thread-safety, and just need shared ownership, consider the [`Rc<T>`
|
||||
//! type](../rc/struct.Rc.html). It is the same as `Arc<T>`, but does not use atomics, making it
|
||||
//! both thread-unsafe as well as significantly faster when updating the reference count.
|
||||
//! If you do not need thread-safety, and just need shared ownership, consider
|
||||
//! the [`Rc<T>` type](../rc/struct.Rc.html). It is the same as `Arc<T>`, but
|
||||
//! does not use atomics, making it both thread-unsafe as well as significantly
|
||||
//! faster when updating the reference count.
|
||||
//!
|
||||
//! The `downgrade` method can be used to create a non-owning `Weak<T>` pointer to the box. A
|
||||
//! `Weak<T>` pointer can be upgraded to an `Arc<T>` pointer, but will return `None` if the value
|
||||
//! has already been dropped.
|
||||
//! The `downgrade` method can be used to create a non-owning `Weak<T>` pointer
|
||||
//! to the box. A `Weak<T>` pointer can be upgraded to an `Arc<T>` pointer, but
|
||||
//! will return `None` if the value has already been dropped.
|
||||
//!
|
||||
//! For example, a tree with parent pointers can be represented by putting the nodes behind strong
|
||||
//! `Arc<T>` pointers, and then storing the parent pointers as `Weak<T>` pointers.
|
||||
//! For example, a tree with parent pointers can be represented by putting the
|
||||
//! nodes behind strong `Arc<T>` pointers, and then storing the parent pointers
|
||||
//! as `Weak<T>` pointers.
|
||||
//!
|
||||
//! # Examples
|
||||
//!
|
||||
@ -87,8 +89,9 @@
|
||||
///
|
||||
/// # Example
|
||||
///
|
||||
/// In this example, a large vector of floats is shared between several tasks. With simple pipes,
|
||||
/// without `Arc`, a copy would have to be made for each task.
|
||||
/// In this example, a large vector of floats is shared between several tasks.
|
||||
/// With simple pipes, without `Arc`, a copy would have to be made for each
|
||||
/// task.
|
||||
///
|
||||
/// ```rust
|
||||
/// use std::sync::Arc;
|
||||
|
@ -1738,6 +1738,7 @@ pub fn remove(&mut self, value: &uint) -> bool {
|
||||
}
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl fmt::Debug for BitvSet {
|
||||
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
|
||||
try!(write!(fmt, "BitvSet {{"));
|
||||
|
@ -31,6 +31,7 @@ pub struct EnumSet<E> {
|
||||
|
||||
impl<E> Copy for EnumSet<E> {}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<E:CLike + fmt::Debug> fmt::Debug for EnumSet<E> {
|
||||
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
|
||||
try!(write!(fmt, "EnumSet {{"));
|
||||
|
@ -950,11 +950,14 @@ fn from_str(s: &str) -> Result<String, ()> {
|
||||
}
|
||||
|
||||
/// A generic trait for converting a value to a string
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait ToString {
|
||||
/// Converts the value of `self` to an owned string
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn to_string(&self) -> String;
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T: fmt::Display + ?Sized> ToString for T {
|
||||
#[inline]
|
||||
fn to_string(&self) -> String {
|
||||
@ -991,6 +994,7 @@ fn as_slice<'b>(&'b self) -> &'b str {
|
||||
}
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl fmt::Writer for String {
|
||||
#[inline]
|
||||
fn write_str(&mut self, s: &str) -> fmt::Result {
|
||||
|
@ -1591,13 +1591,6 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> fmt::Writer for Vec<u8> {
|
||||
fn write_str(&mut self, s: &str) -> fmt::Result {
|
||||
self.push_all(s.as_bytes());
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// Clone-on-write
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -10,7 +10,6 @@
|
||||
|
||||
//! Utilities for formatting and printing strings
|
||||
|
||||
#![allow(unused_variables)]
|
||||
#![stable(feature = "rust1", since = "1.0.0")]
|
||||
|
||||
use any;
|
||||
@ -27,6 +26,7 @@
|
||||
use slice::SliceExt;
|
||||
use slice;
|
||||
use str::{self, StrExt};
|
||||
use self::rt::v1::Alignment;
|
||||
|
||||
pub use self::num::radix;
|
||||
pub use self::num::Radix;
|
||||
@ -34,10 +34,15 @@
|
||||
|
||||
mod num;
|
||||
mod float;
|
||||
pub mod rt;
|
||||
|
||||
#[unstable(feature = "core",
|
||||
reason = "core and I/O reconciliation may alter this definition")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[doc(hidden)]
|
||||
pub mod rt {
|
||||
#[cfg(stage0)] pub use self::v1::*;
|
||||
pub mod v1;
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
/// The type returned by formatter methods.
|
||||
pub type Result = result::Result<(), Error>;
|
||||
|
||||
@ -46,8 +51,7 @@
|
||||
/// This type does not support transmission of an error other than that an error
|
||||
/// occurred. Any extra information must be arranged to be transmitted through
|
||||
/// some other means.
|
||||
#[unstable(feature = "core",
|
||||
reason = "core and I/O reconciliation may alter this definition")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[derive(Copy, Debug)]
|
||||
pub struct Error;
|
||||
|
||||
@ -60,8 +64,7 @@
|
||||
/// This trait should generally not be implemented by consumers of the standard
|
||||
/// library. The `write!` macro accepts an instance of `io::Writer`, and the
|
||||
/// `io::Writer` trait is favored over implementing this trait.
|
||||
#[unstable(feature = "core",
|
||||
reason = "waiting for core and I/O reconciliation")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait Writer {
|
||||
/// Writes a slice of bytes into this writer, returning whether the write
|
||||
/// succeeded.
|
||||
@ -73,12 +76,14 @@ pub trait Writer {
|
||||
/// # Errors
|
||||
///
|
||||
/// This function will return an instance of `FormatError` on error.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn write_str(&mut self, s: &str) -> Result;
|
||||
|
||||
/// Glue for usage of the `write!` macro with implementers of this trait.
|
||||
///
|
||||
/// This method should generally not be invoked manually, but rather through
|
||||
/// the `write!` macro itself.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn write_fmt(&mut self, args: Arguments) -> Result {
|
||||
// This Adapter is needed to allow `self` (of type `&mut
|
||||
// Self`) to be cast to a FormatWriter (below) without
|
||||
@ -104,18 +109,17 @@ fn write_fmt(&mut self, args: Arguments) -> Result {
|
||||
/// A struct to represent both where to emit formatting strings to and how they
|
||||
/// should be formatted. A mutable version of this is passed to all formatting
|
||||
/// traits.
|
||||
#[unstable(feature = "core",
|
||||
reason = "name may change and implemented traits are also unstable")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub struct Formatter<'a> {
|
||||
flags: uint,
|
||||
fill: char,
|
||||
align: rt::Alignment,
|
||||
align: rt::v1::Alignment,
|
||||
width: Option<uint>,
|
||||
precision: Option<uint>,
|
||||
|
||||
buf: &'a mut (Writer+'a),
|
||||
curarg: slice::Iter<'a, Argument<'a>>,
|
||||
args: &'a [Argument<'a>],
|
||||
curarg: slice::Iter<'a, ArgumentV1<'a>>,
|
||||
args: &'a [ArgumentV1<'a>],
|
||||
}
|
||||
|
||||
// NB. Argument is essentially an optimized partially applied formatting function,
|
||||
@ -127,35 +131,40 @@ enum Void {}
|
||||
/// family of functions. It contains a function to format the given value. At
|
||||
/// compile time it is ensured that the function and the value have the correct
|
||||
/// types, and then this struct is used to canonicalize arguments to one type.
|
||||
#[unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
#[derive(Copy)]
|
||||
pub struct Argument<'a> {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[doc(hidden)]
|
||||
pub struct ArgumentV1<'a> {
|
||||
value: &'a Void,
|
||||
formatter: fn(&Void, &mut Formatter) -> Result,
|
||||
}
|
||||
|
||||
impl<'a> Argument<'a> {
|
||||
impl<'a> ArgumentV1<'a> {
|
||||
#[inline(never)]
|
||||
fn show_uint(x: &uint, f: &mut Formatter) -> Result {
|
||||
Display::fmt(x, f)
|
||||
}
|
||||
|
||||
fn new<'b, T>(x: &'b T, f: fn(&T, &mut Formatter) -> Result) -> Argument<'b> {
|
||||
#[doc(hidden)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn new<'b, T>(x: &'b T,
|
||||
f: fn(&T, &mut Formatter) -> Result) -> ArgumentV1<'b> {
|
||||
unsafe {
|
||||
Argument {
|
||||
ArgumentV1 {
|
||||
formatter: mem::transmute(f),
|
||||
value: mem::transmute(x)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn from_uint(x: &uint) -> Argument {
|
||||
Argument::new(x, Argument::show_uint)
|
||||
#[doc(hidden)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn from_uint(x: &uint) -> ArgumentV1 {
|
||||
ArgumentV1::new(x, ArgumentV1::show_uint)
|
||||
}
|
||||
|
||||
fn as_uint(&self) -> Option<uint> {
|
||||
if self.formatter as uint == Argument::show_uint as uint {
|
||||
if self.formatter as uint == ArgumentV1::show_uint as uint {
|
||||
Some(unsafe { *(self.value as *const _ as *const uint) })
|
||||
} else {
|
||||
None
|
||||
@ -163,14 +172,32 @@ fn as_uint(&self) -> Option<uint> {
|
||||
}
|
||||
}
|
||||
|
||||
// flags available in the v1 format of format_args
|
||||
#[derive(Copy)]
|
||||
#[allow(dead_code)] // SignMinus isn't currently used
|
||||
enum FlagV1 { SignPlus, SignMinus, Alternate, SignAwareZeroPad, }
|
||||
|
||||
impl<'a> Arguments<'a> {
|
||||
/// When using the format_args!() macro, this function is used to generate the
|
||||
/// Arguments structure.
|
||||
#[doc(hidden)] #[inline]
|
||||
#[unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn new_v1(pieces: &'a [&'a str],
|
||||
args: &'a [ArgumentV1<'a>]) -> Arguments<'a> {
|
||||
Arguments {
|
||||
pieces: pieces,
|
||||
fmt: None,
|
||||
args: args
|
||||
}
|
||||
}
|
||||
|
||||
/// When using the format_args!() macro, this function is used to generate the
|
||||
/// Arguments structure.
|
||||
#[doc(hidden)] #[inline]
|
||||
#[cfg(stage0)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn new(pieces: &'a [&'a str],
|
||||
args: &'a [Argument<'a>]) -> Arguments<'a> {
|
||||
args: &'a [ArgumentV1<'a>]) -> Arguments<'a> {
|
||||
Arguments {
|
||||
pieces: pieces,
|
||||
fmt: None,
|
||||
@ -185,11 +212,28 @@ pub fn new(pieces: &'a [&'a str],
|
||||
/// created with `argumentuint`. However, failing to do so doesn't cause
|
||||
/// unsafety, but will ignore invalid .
|
||||
#[doc(hidden)] #[inline]
|
||||
#[unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
#[cfg(stage0)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn with_placeholders(pieces: &'a [&'a str],
|
||||
fmt: &'a [rt::Argument],
|
||||
args: &'a [Argument<'a>]) -> Arguments<'a> {
|
||||
fmt: &'a [rt::v1::Argument],
|
||||
args: &'a [ArgumentV1<'a>]) -> Arguments<'a> {
|
||||
Arguments {
|
||||
pieces: pieces,
|
||||
fmt: Some(fmt),
|
||||
args: args
|
||||
}
|
||||
}
|
||||
/// This function is used to specify nonstandard formatting parameters.
|
||||
/// The `pieces` array must be at least as long as `fmt` to construct
|
||||
/// a valid Arguments structure. Also, any `Count` within `fmt` that is
|
||||
/// `CountIsParam` or `CountIsNextParam` has to point to an argument
|
||||
/// created with `argumentuint`. However, failing to do so doesn't cause
|
||||
/// unsafety, but will ignore invalid .
|
||||
#[doc(hidden)] #[inline]
|
||||
#[cfg(not(stage0))]
|
||||
pub fn new_v1_formatted(pieces: &'a [&'a str],
|
||||
args: &'a [ArgumentV1<'a>],
|
||||
fmt: &'a [rt::v1::Argument]) -> Arguments<'a> {
|
||||
Arguments {
|
||||
pieces: pieces,
|
||||
fmt: Some(fmt),
|
||||
@ -214,11 +258,11 @@ pub struct Arguments<'a> {
|
||||
pieces: &'a [&'a str],
|
||||
|
||||
// Placeholder specs, or `None` if all specs are default (as in "{}{}").
|
||||
fmt: Option<&'a [rt::Argument]>,
|
||||
fmt: Option<&'a [rt::v1::Argument]>,
|
||||
|
||||
// Dynamic arguments for interpolation, to be interleaved with string
|
||||
// pieces. (Every argument is preceded by a string piece.)
|
||||
args: &'a [Argument<'a>],
|
||||
args: &'a [ArgumentV1<'a>],
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
@ -237,20 +281,20 @@ fn fmt(&self, fmt: &mut Formatter) -> Result {
|
||||
|
||||
/// Format trait for the `:?` format. Useful for debugging, all types
|
||||
/// should implement this.
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[deprecated(since = "1.0.0", reason = "renamed to Debug")]
|
||||
#[unstable(feature = "old_fmt")]
|
||||
pub trait Show {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `:?` format. Useful for debugging, all types
|
||||
/// should implement this.
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[rustc_on_unimplemented = "`{Self}` cannot be formatted using `:?`; if it is defined in your \
|
||||
crate, add `#[derive(Debug)]` or manually implement it"]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[rustc_on_unimplemented = "`{Self}` cannot be formatted using `:?`; if it is \
|
||||
defined in your crate, add `#[derive(Debug)]` or \
|
||||
manually implement it"]
|
||||
#[lang = "debug_trait"]
|
||||
pub trait Debug {
|
||||
/// Formats the value using the given formatter.
|
||||
@ -264,19 +308,20 @@ fn fmt(&self, f: &mut Formatter) -> Result { Show::fmt(self, f) }
|
||||
|
||||
/// When a value can be semantically expressed as a String, this trait may be
|
||||
/// used. It corresponds to the default format, `{}`.
|
||||
#[unstable(feature = "core")]
|
||||
#[deprecated(since = "1.0.0", reason = "renamed to Display")]
|
||||
#[unstable(feature = "old_fmt")]
|
||||
pub trait String {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// When a value can be semantically expressed as a String, this trait may be
|
||||
/// used. It corresponds to the default format, `{}`.
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[rustc_on_unimplemented = "`{Self}` cannot be formatted with the default formatter; try using \
|
||||
`:?` instead if you are using a format string"]
|
||||
#[rustc_on_unimplemented = "`{Self}` cannot be formatted with the default \
|
||||
formatter; try using `:?` instead if you are using \
|
||||
a format string"]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait Display {
|
||||
/// Formats the value using the given formatter.
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
@ -288,58 +333,58 @@ fn fmt(&self, f: &mut Formatter) -> Result { String::fmt(self, f) }
|
||||
}
|
||||
|
||||
/// Format trait for the `o` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait Octal {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `b` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait Binary {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `x` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait LowerHex {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `X` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait UpperHex {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `p` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait Pointer {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `e` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait LowerExp {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
/// Format trait for the `E` character
|
||||
#[unstable(feature = "core",
|
||||
reason = "I/O and core have yet to be reconciled")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub trait UpperExp {
|
||||
/// Formats the value using the given formatter.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
fn fmt(&self, &mut Formatter) -> Result;
|
||||
}
|
||||
|
||||
@ -351,16 +396,14 @@ pub trait UpperExp {
|
||||
///
|
||||
/// * output - the buffer to write output to
|
||||
/// * args - the precompiled arguments generated by `format_args!`
|
||||
#[unstable(feature = "core",
|
||||
reason = "libcore and I/O have yet to be reconciled, and this is an \
|
||||
implementation detail which should not otherwise be exported")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn write(output: &mut Writer, args: Arguments) -> Result {
|
||||
let mut formatter = Formatter {
|
||||
flags: 0,
|
||||
width: None,
|
||||
precision: None,
|
||||
buf: output,
|
||||
align: rt::AlignUnknown,
|
||||
align: Alignment::Unknown,
|
||||
fill: ' ',
|
||||
args: args.args,
|
||||
curarg: args.args.iter(),
|
||||
@ -402,7 +445,7 @@ impl<'a> Formatter<'a> {
|
||||
// First up is the collection of functions used to execute a format string
|
||||
// at runtime. This consumes all of the compile-time statics generated by
|
||||
// the format! syntax extension.
|
||||
fn run(&mut self, arg: &rt::Argument) -> Result {
|
||||
fn run(&mut self, arg: &rt::v1::Argument) -> Result {
|
||||
// Fill in the format parameters into the formatter
|
||||
self.fill = arg.format.fill;
|
||||
self.align = arg.format.align;
|
||||
@ -412,22 +455,22 @@ fn run(&mut self, arg: &rt::Argument) -> Result {
|
||||
|
||||
// Extract the correct argument
|
||||
let value = match arg.position {
|
||||
rt::ArgumentNext => { *self.curarg.next().unwrap() }
|
||||
rt::ArgumentIs(i) => self.args[i],
|
||||
rt::v1::Position::Next => { *self.curarg.next().unwrap() }
|
||||
rt::v1::Position::At(i) => self.args[i],
|
||||
};
|
||||
|
||||
// Then actually do some printing
|
||||
(value.formatter)(value.value, self)
|
||||
}
|
||||
|
||||
fn getcount(&mut self, cnt: &rt::Count) -> Option<uint> {
|
||||
fn getcount(&mut self, cnt: &rt::v1::Count) -> Option<uint> {
|
||||
match *cnt {
|
||||
rt::CountIs(n) => Some(n),
|
||||
rt::CountImplied => None,
|
||||
rt::CountIsParam(i) => {
|
||||
rt::v1::Count::Is(n) => Some(n),
|
||||
rt::v1::Count::Implied => None,
|
||||
rt::v1::Count::Param(i) => {
|
||||
self.args[i].as_uint()
|
||||
}
|
||||
rt::CountIsNextParam => {
|
||||
rt::v1::Count::NextParam => {
|
||||
self.curarg.next().and_then(|arg| arg.as_uint())
|
||||
}
|
||||
}
|
||||
@ -437,8 +480,8 @@ fn getcount(&mut self, cnt: &rt::Count) -> Option<uint> {
|
||||
// all formatting traits can use.
|
||||
|
||||
/// Performs the correct padding for an integer which has already been
|
||||
/// emitted into a byte-array. The byte-array should *not* contain the sign
|
||||
/// for the integer, that will be added by this method.
|
||||
/// emitted into a str. The str should *not* contain the sign for the
|
||||
/// integer, that will be added by this method.
|
||||
///
|
||||
/// # Arguments
|
||||
///
|
||||
@ -449,27 +492,25 @@ fn getcount(&mut self, cnt: &rt::Count) -> Option<uint> {
|
||||
///
|
||||
/// This function will correctly account for the flags provided as well as
|
||||
/// the minimum width. It will not take precision into account.
|
||||
#[unstable(feature = "core",
|
||||
reason = "definition may change slightly over time")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn pad_integral(&mut self,
|
||||
is_positive: bool,
|
||||
prefix: &str,
|
||||
buf: &str)
|
||||
-> Result {
|
||||
use char::CharExt;
|
||||
use fmt::rt::{FlagAlternate, FlagSignPlus, FlagSignAwareZeroPad};
|
||||
|
||||
let mut width = buf.len();
|
||||
|
||||
let mut sign = None;
|
||||
if !is_positive {
|
||||
sign = Some('-'); width += 1;
|
||||
} else if self.flags & (1 << (FlagSignPlus as uint)) != 0 {
|
||||
} else if self.flags & (1 << (FlagV1::SignPlus as uint)) != 0 {
|
||||
sign = Some('+'); width += 1;
|
||||
}
|
||||
|
||||
let mut prefixed = false;
|
||||
if self.flags & (1 << (FlagAlternate as uint)) != 0 {
|
||||
if self.flags & (1 << (FlagV1::Alternate as uint)) != 0 {
|
||||
prefixed = true; width += prefix.char_len();
|
||||
}
|
||||
|
||||
@ -499,16 +540,16 @@ pub fn pad_integral(&mut self,
|
||||
}
|
||||
// The sign and prefix goes before the padding if the fill character
|
||||
// is zero
|
||||
Some(min) if self.flags & (1 << (FlagSignAwareZeroPad as uint)) != 0 => {
|
||||
Some(min) if self.flags & (1 << (FlagV1::SignAwareZeroPad as uint)) != 0 => {
|
||||
self.fill = '0';
|
||||
try!(write_prefix(self));
|
||||
self.with_padding(min - width, rt::AlignRight, |f| {
|
||||
self.with_padding(min - width, Alignment::Right, |f| {
|
||||
f.buf.write_str(buf)
|
||||
})
|
||||
}
|
||||
// Otherwise, the sign and prefix goes after the padding
|
||||
Some(min) => {
|
||||
self.with_padding(min - width, rt::AlignRight, |f| {
|
||||
self.with_padding(min - width, Alignment::Right, |f| {
|
||||
try!(write_prefix(f)); f.buf.write_str(buf)
|
||||
})
|
||||
}
|
||||
@ -526,8 +567,7 @@ pub fn pad_integral(&mut self,
|
||||
/// is longer than this length
|
||||
///
|
||||
/// Notably this function ignored the `flag` parameters
|
||||
#[unstable(feature = "core",
|
||||
reason = "definition may change slightly over time")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn pad(&mut self, s: &str) -> Result {
|
||||
// Make sure there's a fast path up front
|
||||
if self.width.is_none() && self.precision.is_none() {
|
||||
@ -561,7 +601,7 @@ pub fn pad(&mut self, s: &str) -> Result {
|
||||
// If we're under both the maximum and the minimum width, then fill
|
||||
// up the minimum width with the specified string + some alignment.
|
||||
Some(width) => {
|
||||
self.with_padding(width - s.char_len(), rt::AlignLeft, |me| {
|
||||
self.with_padding(width - s.char_len(), Alignment::Left, |me| {
|
||||
me.buf.write_str(s)
|
||||
})
|
||||
}
|
||||
@ -570,19 +610,20 @@ pub fn pad(&mut self, s: &str) -> Result {
|
||||
|
||||
/// Runs a callback, emitting the correct padding either before or
|
||||
/// afterwards depending on whether right or left alignment is requested.
|
||||
fn with_padding<F>(&mut self, padding: uint, default: rt::Alignment, f: F) -> Result where
|
||||
F: FnOnce(&mut Formatter) -> Result,
|
||||
fn with_padding<F>(&mut self, padding: uint, default: Alignment,
|
||||
f: F) -> Result
|
||||
where F: FnOnce(&mut Formatter) -> Result,
|
||||
{
|
||||
use char::CharExt;
|
||||
let align = match self.align {
|
||||
rt::AlignUnknown => default,
|
||||
Alignment::Unknown => default,
|
||||
_ => self.align
|
||||
};
|
||||
|
||||
let (pre_pad, post_pad) = match align {
|
||||
rt::AlignLeft => (0, padding),
|
||||
rt::AlignRight | rt::AlignUnknown => (padding, 0),
|
||||
rt::AlignCenter => (padding / 2, (padding + 1) / 2),
|
||||
Alignment::Left => (0, padding),
|
||||
Alignment::Right | Alignment::Unknown => (padding, 0),
|
||||
Alignment::Center => (padding / 2, (padding + 1) / 2),
|
||||
};
|
||||
|
||||
let mut fill = [0u8; 4];
|
||||
@ -604,23 +645,20 @@ fn with_padding<F>(&mut self, padding: uint, default: rt::Alignment, f: F) -> Re
|
||||
|
||||
/// Writes some data to the underlying buffer contained within this
|
||||
/// formatter.
|
||||
#[unstable(feature = "core",
|
||||
reason = "reconciling core and I/O may alter this definition")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn write_str(&mut self, data: &str) -> Result {
|
||||
self.buf.write_str(data)
|
||||
}
|
||||
|
||||
/// Writes some formatted information into this instance
|
||||
#[unstable(feature = "core",
|
||||
reason = "reconciling core and I/O may alter this definition")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn write_fmt(&mut self, fmt: Arguments) -> Result {
|
||||
write(self.buf, fmt)
|
||||
}
|
||||
|
||||
/// Flags for formatting (packed version of rt::Flag)
|
||||
#[unstable(feature = "core",
|
||||
reason = "return type may change and method was just created")]
|
||||
pub fn flags(&self) -> uint { self.flags }
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn flags(&self) -> usize { self.flags }
|
||||
|
||||
/// Character used as 'fill' whenever there is alignment
|
||||
#[unstable(feature = "core", reason = "method was just created")]
|
||||
@ -628,7 +666,7 @@ pub fn fill(&self) -> char { self.fill }
|
||||
|
||||
/// Flag indicating what form of alignment was requested
|
||||
#[unstable(feature = "core", reason = "method was just created")]
|
||||
pub fn align(&self) -> rt::Alignment { self.align }
|
||||
pub fn align(&self) -> Alignment { self.align }
|
||||
|
||||
/// Optionally specified integer width that the output should be
|
||||
#[unstable(feature = "core", reason = "method was just created")]
|
||||
@ -649,20 +687,20 @@ fn fmt(&self, f: &mut Formatter) -> Result {
|
||||
/// This is a function which calls are emitted to by the compiler itself to
|
||||
/// create the Argument structures that are passed into the `format` function.
|
||||
#[doc(hidden)] #[inline]
|
||||
#[unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
#[cfg(stage0)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn argument<'a, T>(f: fn(&T, &mut Formatter) -> Result,
|
||||
t: &'a T) -> Argument<'a> {
|
||||
Argument::new(t, f)
|
||||
t: &'a T) -> ArgumentV1<'a> {
|
||||
ArgumentV1::new(t, f)
|
||||
}
|
||||
|
||||
/// When the compiler determines that the type of an argument *must* be a uint
|
||||
/// (such as for width and precision), then it invokes this method.
|
||||
#[doc(hidden)] #[inline]
|
||||
#[unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
pub fn argumentuint<'a>(s: &'a uint) -> Argument<'a> {
|
||||
Argument::from_uint(s)
|
||||
#[cfg(stage0)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn argumentuint<'a>(s: &'a uint) -> ArgumentV1<'a> {
|
||||
ArgumentV1::from_uint(s)
|
||||
}
|
||||
|
||||
// Implementations of the core formatting traits
|
||||
@ -741,9 +779,9 @@ fn fmt(&self, f: &mut Formatter) -> Result {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T> Pointer for *const T {
|
||||
fn fmt(&self, f: &mut Formatter) -> Result {
|
||||
f.flags |= 1 << (rt::FlagAlternate as uint);
|
||||
f.flags |= 1 << (FlagV1::Alternate as uint);
|
||||
let ret = LowerHex::fmt(&(*self as uint), f);
|
||||
f.flags &= !(1 << (rt::FlagAlternate as uint));
|
||||
f.flags &= !(1 << (FlagV1::Alternate as uint));
|
||||
ret
|
||||
}
|
||||
}
|
||||
@ -899,7 +937,7 @@ fn fmt(&self, f: &mut Formatter) -> Result { f.pad("&Any") }
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T: Debug> Debug for [T] {
|
||||
fn fmt(&self, f: &mut Formatter) -> Result {
|
||||
if f.flags & (1 << (rt::FlagAlternate as uint)) == 0 {
|
||||
if f.flags & (1 << (FlagV1::Alternate as uint)) == 0 {
|
||||
try!(write!(f, "["));
|
||||
}
|
||||
let mut is_first = true;
|
||||
@ -911,7 +949,7 @@ fn fmt(&self, f: &mut Formatter) -> Result {
|
||||
}
|
||||
try!(write!(f, "{:?}", *x))
|
||||
}
|
||||
if f.flags & (1 << (rt::FlagAlternate as uint)) == 0 {
|
||||
if f.flags & (1 << (FlagV1::Alternate as uint)) == 0 {
|
||||
try!(write!(f, "]"));
|
||||
}
|
||||
Ok(())
|
||||
|
@ -1,86 +0,0 @@
|
||||
// Copyright 2013 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
//! This is an internal module used by the ifmt! runtime. These structures are
|
||||
//! emitted to static arrays to precompile format strings ahead of time.
|
||||
//!
|
||||
//! These definitions are similar to their `ct` equivalents, but differ in that
|
||||
//! these can be statically allocated and are slightly optimized for the runtime
|
||||
|
||||
#![unstable(feature = "core",
|
||||
reason = "implementation detail of the `format_args!` macro")]
|
||||
|
||||
pub use self::Alignment::*;
|
||||
pub use self::Count::*;
|
||||
pub use self::Position::*;
|
||||
pub use self::Flag::*;
|
||||
|
||||
#[doc(hidden)]
|
||||
#[derive(Copy)]
|
||||
pub struct Argument {
|
||||
pub position: Position,
|
||||
pub format: FormatSpec,
|
||||
}
|
||||
|
||||
#[doc(hidden)]
|
||||
#[derive(Copy)]
|
||||
pub struct FormatSpec {
|
||||
pub fill: char,
|
||||
pub align: Alignment,
|
||||
pub flags: uint,
|
||||
pub precision: Count,
|
||||
pub width: Count,
|
||||
}
|
||||
|
||||
/// Possible alignments that can be requested as part of a formatting directive.
|
||||
#[derive(Copy, PartialEq)]
|
||||
pub enum Alignment {
|
||||
/// Indication that contents should be left-aligned.
|
||||
AlignLeft,
|
||||
/// Indication that contents should be right-aligned.
|
||||
AlignRight,
|
||||
/// Indication that contents should be center-aligned.
|
||||
AlignCenter,
|
||||
/// No alignment was requested.
|
||||
AlignUnknown,
|
||||
}
|
||||
|
||||
#[doc(hidden)]
|
||||
#[derive(Copy)]
|
||||
pub enum Count {
|
||||
CountIs(uint), CountIsParam(uint), CountIsNextParam, CountImplied,
|
||||
}
|
||||
|
||||
#[doc(hidden)]
|
||||
#[derive(Copy)]
|
||||
pub enum Position {
|
||||
ArgumentNext, ArgumentIs(uint)
|
||||
}
|
||||
|
||||
/// Flags which can be passed to formatting via a directive.
|
||||
///
|
||||
/// These flags are discovered through the `flags` field of the `Formatter`
|
||||
/// structure. The flag in that structure is a union of these flags into a
|
||||
/// `uint` where each flag's discriminant is the corresponding bit.
|
||||
#[derive(Copy)]
|
||||
pub enum Flag {
|
||||
/// A flag which enables number formatting to always print the sign of a
|
||||
/// number.
|
||||
FlagSignPlus,
|
||||
/// Currently not a used flag
|
||||
FlagSignMinus,
|
||||
/// Indicates that the "alternate formatting" for a type should be used.
|
||||
///
|
||||
/// The meaning of this flag is type-specific.
|
||||
FlagAlternate,
|
||||
/// Indicates that padding should be done with a `0` character as well as
|
||||
/// being aware of the sign to be printed.
|
||||
FlagSignAwareZeroPad,
|
||||
}
|
94
src/libcore/fmt/rt/v1.rs
Normal file
94
src/libcore/fmt/rt/v1.rs
Normal file
@ -0,0 +1,94 @@
|
||||
// Copyright 2013 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
//! This is an internal module used by the ifmt! runtime. These structures are
|
||||
//! emitted to static arrays to precompile format strings ahead of time.
|
||||
//!
|
||||
//! These definitions are similar to their `ct` equivalents, but differ in that
|
||||
//! these can be statically allocated and are slightly optimized for the runtime
|
||||
|
||||
#![stable(feature = "rust1", since = "1.0.0")]
|
||||
|
||||
#[cfg(stage0)] pub use self::Position::*;
|
||||
|
||||
#[cfg(stage0)] pub use self::Alignment::Left as AlignLeft;
|
||||
#[cfg(stage0)] pub use self::Alignment::Right as AlignRight;
|
||||
#[cfg(stage0)] pub use self::Alignment::Center as AlignCenter;
|
||||
#[cfg(stage0)] pub use self::Alignment::Unknown as AlignUnknown;
|
||||
#[cfg(stage0)] pub use self::Count::Is as CountIs;
|
||||
#[cfg(stage0)] pub use self::Count::Implied as CountImplied;
|
||||
#[cfg(stage0)] pub use self::Count::Param as CountIsParam;
|
||||
#[cfg(stage0)] pub use self::Count::NextParam as CountIsNextParam;
|
||||
#[cfg(stage0)] pub use self::Position::Next as ArgumentNext;
|
||||
#[cfg(stage0)] pub use self::Position::At as ArgumentIs;
|
||||
|
||||
#[derive(Copy)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub struct Argument {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub position: Position,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub format: FormatSpec,
|
||||
}
|
||||
|
||||
#[derive(Copy)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub struct FormatSpec {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fill: char,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub align: Alignment,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub flags: uint,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub precision: Count,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub width: Count,
|
||||
}
|
||||
|
||||
/// Possible alignments that can be requested as part of a formatting directive.
|
||||
#[derive(Copy, PartialEq)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub enum Alignment {
|
||||
/// Indication that contents should be left-aligned.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Left,
|
||||
/// Indication that contents should be right-aligned.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Right,
|
||||
/// Indication that contents should be center-aligned.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Center,
|
||||
/// No alignment was requested.
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Unknown,
|
||||
}
|
||||
|
||||
#[derive(Copy)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub enum Count {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Is(usize),
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Param(usize),
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
NextParam,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Implied,
|
||||
}
|
||||
|
||||
#[derive(Copy)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub enum Position {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
Next,
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
At(usize)
|
||||
}
|
@ -229,7 +229,7 @@
|
||||
use self::Result::{Ok, Err};
|
||||
|
||||
use clone::Clone;
|
||||
use fmt::Debug;
|
||||
use fmt;
|
||||
use iter::{Iterator, IteratorExt, DoubleEndedIterator, FromIterator, ExactSizeIterator};
|
||||
use ops::{FnMut, FnOnce};
|
||||
use option::Option::{self, None, Some};
|
||||
@ -715,7 +715,7 @@ pub fn unwrap_or_else<F: FnOnce(E) -> T>(self, op: F) -> T {
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T, E: Debug> Result<T, E> {
|
||||
impl<T, E: fmt::Debug> Result<T, E> {
|
||||
/// Unwraps a result, yielding the content of an `Ok`.
|
||||
///
|
||||
/// # Panics
|
||||
@ -746,7 +746,7 @@ pub fn unwrap(self) -> T {
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T: Debug, E> Result<T, E> {
|
||||
impl<T: fmt::Debug, E> Result<T, E> {
|
||||
/// Unwraps a result, yielding the content of an `Err`.
|
||||
///
|
||||
/// # Panics
|
||||
|
@ -362,19 +362,19 @@ impl<'a> Id<'a> {
|
||||
///
|
||||
/// Passing an invalid string (containing spaces, brackets,
|
||||
/// quotes, ...) will return an empty `Err` value.
|
||||
pub fn new<Name: IntoCow<'a, String, str>>(name: Name) -> Option<Id<'a>> {
|
||||
pub fn new<Name: IntoCow<'a, String, str>>(name: Name) -> Result<Id<'a>, ()> {
|
||||
let name = name.into_cow();
|
||||
{
|
||||
let mut chars = name.chars();
|
||||
match chars.next() {
|
||||
Some(c) if is_letter_or_underscore(c) => { ; },
|
||||
_ => return None
|
||||
_ => return Err(())
|
||||
}
|
||||
if !chars.all(is_constituent) {
|
||||
return None
|
||||
return Err(())
|
||||
}
|
||||
}
|
||||
return Some(Id{ name: name });
|
||||
return Ok(Id{ name: name });
|
||||
|
||||
fn is_letter_or_underscore(c: char) -> bool {
|
||||
in_range('a', c, 'z') || in_range('A', c, 'Z') || c == '_'
|
||||
@ -878,8 +878,8 @@ fn left_aligned_text() {
|
||||
fn simple_id_construction() {
|
||||
let id1 = Id::new("hello");
|
||||
match id1 {
|
||||
Some(_) => {;},
|
||||
None => panic!("'hello' is not a valid value for id anymore")
|
||||
Ok(_) => {;},
|
||||
Err(..) => panic!("'hello' is not a valid value for id anymore")
|
||||
}
|
||||
}
|
||||
|
||||
@ -887,8 +887,8 @@ fn simple_id_construction() {
|
||||
fn badly_formatted_id() {
|
||||
let id2 = Id::new("Weird { struct : ure } !!!");
|
||||
match id2 {
|
||||
Some(_) => panic!("graphviz id suddenly allows spaces, brackets and stuff"),
|
||||
None => {;}
|
||||
Ok(_) => panic!("graphviz id suddenly allows spaces, brackets and stuff"),
|
||||
Err(..) => {;}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -54,10 +54,10 @@ fn replace_newline_with_backslash_l(s: String) -> String {
|
||||
}
|
||||
|
||||
impl<'a, 'ast> dot::Labeller<'a, Node<'a>, Edge<'a>> for LabelledCFG<'a, 'ast> {
|
||||
fn graph_id(&'a self) -> dot::Id<'a> { dot::Id::new(&self.name[]).unwrap() }
|
||||
fn graph_id(&'a self) -> dot::Id<'a> { dot::Id::new(&self.name[]).ok().unwrap() }
|
||||
|
||||
fn node_id(&'a self, &(i,_): &Node<'a>) -> dot::Id<'a> {
|
||||
dot::Id::new(format!("N{}", i.node_id())).unwrap()
|
||||
dot::Id::new(format!("N{}", i.node_id())).ok().unwrap()
|
||||
}
|
||||
|
||||
fn node_label(&'a self, &(i, n): &Node<'a>) -> dot::LabelText<'a> {
|
||||
|
@ -157,10 +157,10 @@ fn new(tcx: &'a ty::ctxt<'tcx>,
|
||||
|
||||
impl<'a, 'tcx> dot::Labeller<'a, Node, Edge> for ConstraintGraph<'a, 'tcx> {
|
||||
fn graph_id(&self) -> dot::Id {
|
||||
dot::Id::new(self.graph_name.as_slice()).unwrap()
|
||||
dot::Id::new(self.graph_name.as_slice()).ok().unwrap()
|
||||
}
|
||||
fn node_id(&self, n: &Node) -> dot::Id {
|
||||
dot::Id::new(format!("node_{}", self.node_ids.get(n).unwrap())).unwrap()
|
||||
dot::Id::new(format!("node_{}", self.node_ids.get(n).unwrap())).ok().unwrap()
|
||||
}
|
||||
fn node_label(&self, n: &Node) -> dot::LabelText {
|
||||
match *n {
|
||||
|
@ -3952,8 +3952,8 @@ fn test_encode_hashmap_with_arbitrary_key() {
|
||||
struct ArbitraryType(uint);
|
||||
let mut hm: HashMap<ArbitraryType, bool> = HashMap::new();
|
||||
hm.insert(ArbitraryType(1), true);
|
||||
let mut mem_buf = Vec::new();
|
||||
let mut encoder = Encoder::new(&mut mem_buf as &mut fmt::Writer);
|
||||
let mut mem_buf = string::String::new();
|
||||
let mut encoder = Encoder::new(&mut mem_buf);
|
||||
let result = hm.encode(&mut encoder);
|
||||
match result.err().unwrap() {
|
||||
EncoderError::BadHashmapKey => (),
|
||||
|
@ -122,7 +122,7 @@ fn deref(&self) -> &[libc::c_char] {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl fmt::Debug for CString {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
String::from_utf8_lossy(self.as_bytes()).fmt(f)
|
||||
fmt::Debug::fmt(&String::from_utf8_lossy(self.as_bytes()), f)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -411,9 +411,10 @@
|
||||
pub use core::fmt::{LowerHex, UpperHex, Pointer};
|
||||
pub use core::fmt::{LowerExp, UpperExp};
|
||||
pub use core::fmt::Error;
|
||||
pub use core::fmt::{Argument, Arguments, write, radix, Radix, RadixFmt};
|
||||
pub use core::fmt::{ArgumentV1, Arguments, write, radix, Radix, RadixFmt};
|
||||
|
||||
#[doc(hidden)]
|
||||
#[cfg(stage0)]
|
||||
pub use core::fmt::{argument, argumentuint};
|
||||
|
||||
/// The format function takes a precompiled format string and a list of
|
||||
@ -431,9 +432,7 @@
|
||||
/// let s = fmt::format(format_args!("Hello, {}!", "world"));
|
||||
/// assert_eq!(s, "Hello, world!".to_string());
|
||||
/// ```
|
||||
#[unstable(feature = "std_misc",
|
||||
reason = "this is an implementation detail of format! and should not \
|
||||
be called directly")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub fn format(args: Arguments) -> string::String {
|
||||
let mut output = string::String::new();
|
||||
let _ = write!(&mut output, "{}", args);
|
||||
|
@ -393,14 +393,15 @@ pub fn status(&self) -> IoResult<ProcessExit> {
|
||||
}
|
||||
}
|
||||
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl fmt::Debug for Command {
|
||||
/// Format the program and arguments of a Command for display. Any
|
||||
/// non-utf8 data is lossily converted using the utf8 replacement
|
||||
/// character.
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
try!(write!(f, "{}", String::from_utf8_lossy(self.program.as_bytes())));
|
||||
try!(write!(f, "{:?}", self.program));
|
||||
for arg in self.args.iter() {
|
||||
try!(write!(f, " '{}'", String::from_utf8_lossy(arg.as_bytes())));
|
||||
try!(write!(f, " '{:?}'", arg));
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
@ -382,8 +382,8 @@ impl<T> !Sync for SyncSender<T> {}
|
||||
/// A `send` operation can only fail if the receiving end of a channel is
|
||||
/// disconnected, implying that the data could never be received. The error
|
||||
/// contains the data being sent as a payload so it can be recovered.
|
||||
#[derive(PartialEq, Eq)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[derive(PartialEq, Eq, Clone, Copy)]
|
||||
pub struct SendError<T>(pub T);
|
||||
|
||||
/// An error returned from the `recv` function on a `Receiver`.
|
||||
@ -396,7 +396,7 @@ impl<T> !Sync for SyncSender<T> {}
|
||||
|
||||
/// This enumeration is the list of the possible reasons that try_recv could not
|
||||
/// return data when called.
|
||||
#[derive(PartialEq, Clone, Copy, Debug)]
|
||||
#[derive(PartialEq, Eq, Clone, Copy, Debug)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub enum TryRecvError {
|
||||
/// This channel is currently empty, but the sender(s) have not yet
|
||||
@ -412,8 +412,8 @@ pub enum TryRecvError {
|
||||
|
||||
/// This enumeration is the list of the possible error outcomes for the
|
||||
/// `SyncSender::try_send` method.
|
||||
#[derive(PartialEq, Clone)]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[derive(PartialEq, Eq, Clone, Copy)]
|
||||
pub enum TrySendError<T> {
|
||||
/// The data could not be sent on the channel because it would require that
|
||||
/// the callee block to send the data.
|
||||
|
@ -17,7 +17,7 @@
|
||||
use ext::base;
|
||||
use ext::build::AstBuilder;
|
||||
use fmt_macros as parse;
|
||||
use parse::token::{InternedString, special_idents};
|
||||
use parse::token::special_idents;
|
||||
use parse::token;
|
||||
use ptr::P;
|
||||
|
||||
@ -300,56 +300,35 @@ fn verify_same(&self,
|
||||
}
|
||||
}
|
||||
|
||||
/// These attributes are applied to all statics that this syntax extension
|
||||
/// will generate.
|
||||
fn static_attrs(ecx: &ExtCtxt, fmtsp: Span) -> Vec<ast::Attribute> {
|
||||
// Flag statics as `inline` so LLVM can merge duplicate globals as much
|
||||
// as possible (which we're generating a whole lot of).
|
||||
let unnamed = ecx.meta_word(fmtsp, InternedString::new("inline"));
|
||||
let unnamed = ecx.attribute(fmtsp, unnamed);
|
||||
|
||||
// Do not warn format string as dead code
|
||||
let dead_code = ecx.meta_word(fmtsp, InternedString::new("dead_code"));
|
||||
let allow_dead_code = ecx.meta_list(fmtsp,
|
||||
InternedString::new("allow"),
|
||||
vec![dead_code]);
|
||||
let allow_dead_code = ecx.attribute(fmtsp, allow_dead_code);
|
||||
vec![unnamed, allow_dead_code]
|
||||
}
|
||||
|
||||
fn rtpath(ecx: &ExtCtxt, s: &str) -> Vec<ast::Ident> {
|
||||
vec![ecx.ident_of("std"), ecx.ident_of("fmt"), ecx.ident_of("rt"), ecx.ident_of(s)]
|
||||
vec![ecx.ident_of("std"), ecx.ident_of("fmt"), ecx.ident_of("rt"),
|
||||
ecx.ident_of("v1"), ecx.ident_of(s)]
|
||||
}
|
||||
|
||||
fn trans_count(&self, c: parse::Count) -> P<ast::Expr> {
|
||||
let sp = self.fmtsp;
|
||||
let count = |: c, arg| {
|
||||
let mut path = Context::rtpath(self.ecx, "Count");
|
||||
path.push(self.ecx.ident_of(c));
|
||||
match arg {
|
||||
Some(arg) => self.ecx.expr_call_global(sp, path, vec![arg]),
|
||||
None => self.ecx.expr_path(self.ecx.path_global(sp, path)),
|
||||
}
|
||||
};
|
||||
match c {
|
||||
parse::CountIs(i) => {
|
||||
self.ecx.expr_call_global(sp, Context::rtpath(self.ecx, "CountIs"),
|
||||
vec!(self.ecx.expr_usize(sp, i)))
|
||||
}
|
||||
parse::CountIs(i) => count("Is", Some(self.ecx.expr_usize(sp, i))),
|
||||
parse::CountIsParam(i) => {
|
||||
self.ecx.expr_call_global(sp, Context::rtpath(self.ecx, "CountIsParam"),
|
||||
vec!(self.ecx.expr_usize(sp, i)))
|
||||
}
|
||||
parse::CountImplied => {
|
||||
let path = self.ecx.path_global(sp, Context::rtpath(self.ecx,
|
||||
"CountImplied"));
|
||||
self.ecx.expr_path(path)
|
||||
}
|
||||
parse::CountIsNextParam => {
|
||||
let path = self.ecx.path_global(sp, Context::rtpath(self.ecx,
|
||||
"CountIsNextParam"));
|
||||
self.ecx.expr_path(path)
|
||||
count("Param", Some(self.ecx.expr_usize(sp, i)))
|
||||
}
|
||||
parse::CountImplied => count("Implied", None),
|
||||
parse::CountIsNextParam => count("NextParam", None),
|
||||
parse::CountIsName(n) => {
|
||||
let i = match self.name_positions.get(n) {
|
||||
Some(&i) => i,
|
||||
None => 0, // error already emitted elsewhere
|
||||
};
|
||||
let i = i + self.args.len();
|
||||
self.ecx.expr_call_global(sp, Context::rtpath(self.ecx, "CountIsParam"),
|
||||
vec!(self.ecx.expr_usize(sp, i)))
|
||||
count("Param", Some(self.ecx.expr_usize(sp, i)))
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -373,27 +352,35 @@ fn trans_piece(&mut self, piece: &parse::Piece) -> Option<P<ast::Expr>> {
|
||||
}
|
||||
parse::NextArgument(ref arg) => {
|
||||
// Translate the position
|
||||
let pos = match arg.position {
|
||||
// These two have a direct mapping
|
||||
parse::ArgumentNext => {
|
||||
let path = self.ecx.path_global(sp, Context::rtpath(self.ecx,
|
||||
"ArgumentNext"));
|
||||
self.ecx.expr_path(path)
|
||||
}
|
||||
parse::ArgumentIs(i) => {
|
||||
self.ecx.expr_call_global(sp, Context::rtpath(self.ecx, "ArgumentIs"),
|
||||
vec!(self.ecx.expr_usize(sp, i)))
|
||||
}
|
||||
// Named arguments are converted to positional arguments at
|
||||
// the end of the list of arguments
|
||||
parse::ArgumentNamed(n) => {
|
||||
let i = match self.name_positions.get(n) {
|
||||
Some(&i) => i,
|
||||
None => 0, // error already emitted elsewhere
|
||||
};
|
||||
let i = i + self.args.len();
|
||||
self.ecx.expr_call_global(sp, Context::rtpath(self.ecx, "ArgumentIs"),
|
||||
vec!(self.ecx.expr_usize(sp, i)))
|
||||
let pos = {
|
||||
let pos = |: c, arg| {
|
||||
let mut path = Context::rtpath(self.ecx, "Position");
|
||||
path.push(self.ecx.ident_of(c));
|
||||
match arg {
|
||||
Some(i) => {
|
||||
let arg = self.ecx.expr_usize(sp, i);
|
||||
self.ecx.expr_call_global(sp, path, vec![arg])
|
||||
}
|
||||
None => {
|
||||
self.ecx.expr_path(self.ecx.path_global(sp, path))
|
||||
}
|
||||
}
|
||||
};
|
||||
match arg.position {
|
||||
// These two have a direct mapping
|
||||
parse::ArgumentNext => pos("Next", None),
|
||||
parse::ArgumentIs(i) => pos("At", Some(i)),
|
||||
|
||||
// Named arguments are converted to positional arguments
|
||||
// at the end of the list of arguments
|
||||
parse::ArgumentNamed(n) => {
|
||||
let i = match self.name_positions.get(n) {
|
||||
Some(&i) => i,
|
||||
None => 0, // error already emitted elsewhere
|
||||
};
|
||||
let i = i + self.args.len();
|
||||
pos("At", Some(i))
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@ -417,19 +404,16 @@ fn trans_piece(&mut self, piece: &parse::Piece) -> Option<P<ast::Expr>> {
|
||||
|
||||
// Translate the format
|
||||
let fill = self.ecx.expr_lit(sp, ast::LitChar(fill));
|
||||
let align = |:name| {
|
||||
let mut p = Context::rtpath(self.ecx, "Alignment");
|
||||
p.push(self.ecx.ident_of(name));
|
||||
self.ecx.path_global(sp, p)
|
||||
};
|
||||
let align = match arg.format.align {
|
||||
parse::AlignLeft => {
|
||||
self.ecx.path_global(sp, Context::rtpath(self.ecx, "AlignLeft"))
|
||||
}
|
||||
parse::AlignRight => {
|
||||
self.ecx.path_global(sp, Context::rtpath(self.ecx, "AlignRight"))
|
||||
}
|
||||
parse::AlignCenter => {
|
||||
self.ecx.path_global(sp, Context::rtpath(self.ecx, "AlignCenter"))
|
||||
}
|
||||
parse::AlignUnknown => {
|
||||
self.ecx.path_global(sp, Context::rtpath(self.ecx, "AlignUnknown"))
|
||||
}
|
||||
parse::AlignLeft => align("Left"),
|
||||
parse::AlignRight => align("Right"),
|
||||
parse::AlignCenter => align("Center"),
|
||||
parse::AlignUnknown => align("Unknown"),
|
||||
};
|
||||
let align = self.ecx.expr_path(align);
|
||||
let flags = self.ecx.expr_usize(sp, arg.format.flags);
|
||||
@ -465,7 +449,7 @@ fn static_array(ecx: &mut ExtCtxt,
|
||||
let st = ast::ItemStatic(ty, ast::MutImmutable, slice);
|
||||
|
||||
let name = ecx.ident_of(name);
|
||||
let item = ecx.item(fmtsp, name, Context::static_attrs(ecx, fmtsp), st);
|
||||
let item = ecx.item(fmtsp, name, vec![], st);
|
||||
let decl = respan(fmtsp, ast::DeclItem(item));
|
||||
|
||||
// Wrap the declaration in a block so that it forms a single expression.
|
||||
@ -575,7 +559,7 @@ fn into_expr(mut self) -> P<ast::Expr> {
|
||||
|
||||
// Now create the fmt::Arguments struct with all our locals we created.
|
||||
let (fn_name, fn_args) = if self.all_pieces_simple {
|
||||
("new", vec![pieces, args_slice])
|
||||
("new_v1", vec![pieces, args_slice])
|
||||
} else {
|
||||
// Build up the static array which will store our precompiled
|
||||
// nonstandard placeholders, if there are any.
|
||||
@ -587,7 +571,7 @@ fn into_expr(mut self) -> P<ast::Expr> {
|
||||
piece_ty,
|
||||
self.pieces);
|
||||
|
||||
("with_placeholders", vec![pieces, fmt, args_slice])
|
||||
("new_v1_formatted", vec![pieces, args_slice, fmt])
|
||||
};
|
||||
|
||||
self.ecx.expr_call_global(self.fmtsp, vec!(
|
||||
@ -624,7 +608,8 @@ fn format_arg(ecx: &ExtCtxt, sp: Span,
|
||||
return ecx.expr_call_global(sp, vec![
|
||||
ecx.ident_of("std"),
|
||||
ecx.ident_of("fmt"),
|
||||
ecx.ident_of("argumentuint")], vec![arg])
|
||||
ecx.ident_of("ArgumentV1"),
|
||||
ecx.ident_of("from_uint")], vec![arg])
|
||||
}
|
||||
};
|
||||
|
||||
@ -636,7 +621,8 @@ fn format_arg(ecx: &ExtCtxt, sp: Span,
|
||||
ecx.expr_call_global(sp, vec![
|
||||
ecx.ident_of("std"),
|
||||
ecx.ident_of("fmt"),
|
||||
ecx.ident_of("argument")], vec![ecx.expr_path(format_fn), arg])
|
||||
ecx.ident_of("ArgumentV1"),
|
||||
ecx.ident_of("new")], vec![arg, ecx.expr_path(format_fn)])
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -13,7 +13,6 @@
|
||||
#![deny(dead_code)]
|
||||
#![feature(libc)]
|
||||
#![feature(core)]
|
||||
#![feature(collections)]
|
||||
|
||||
extern crate libc;
|
||||
|
||||
|
@ -11,7 +11,6 @@
|
||||
// compile-flags: --crate-type lib
|
||||
#![deny(missing_debug_implementations)]
|
||||
#![allow(unused, missing_copy_implementations)]
|
||||
#![feature(core)]
|
||||
|
||||
use std::fmt;
|
||||
|
||||
|
@ -41,41 +41,39 @@ pub fn bar() {
|
||||
|
||||
|
||||
((::std::fmt::format as
|
||||
fn(core::fmt::Arguments<'_>) -> collections::string::String {std::fmt::format})(((::std::fmt::Arguments::new
|
||||
fn(core::fmt::Arguments<'_>) -> collections::string::String {std::fmt::format})(((::std::fmt::Arguments::new_v1
|
||||
as
|
||||
fn(&[&str], &[core::fmt::Argument<'_>]) -> core::fmt::Arguments<'_> {core::fmt::Arguments<'a>::new})(({
|
||||
#[inline]
|
||||
#[allow(dead_code)]
|
||||
static __STATIC_FMTSTR:
|
||||
&'static [&'static str]
|
||||
=
|
||||
(&([("test"
|
||||
as
|
||||
&'static str)]
|
||||
as
|
||||
[&'static str; 1])
|
||||
as
|
||||
&'static [&'static str; 1]);
|
||||
(__STATIC_FMTSTR
|
||||
fn(&[&str], &[core::fmt::ArgumentV1<'_>]) -> core::fmt::Arguments<'_> {core::fmt::Arguments<'a>::new_v1})(({
|
||||
static __STATIC_FMTSTR:
|
||||
&'static [&'static str]
|
||||
=
|
||||
(&([("test"
|
||||
as
|
||||
&'static str)]
|
||||
as
|
||||
[&'static str; 1])
|
||||
as
|
||||
&'static [&'static str; 1]);
|
||||
(__STATIC_FMTSTR
|
||||
as
|
||||
&'static [&'static str])
|
||||
}
|
||||
as
|
||||
&'static [&'static str])
|
||||
}
|
||||
as
|
||||
&[&str]),
|
||||
(&(match (()
|
||||
as
|
||||
())
|
||||
{
|
||||
()
|
||||
=>
|
||||
([]
|
||||
&[&str]),
|
||||
(&(match (()
|
||||
as
|
||||
())
|
||||
{
|
||||
()
|
||||
=>
|
||||
([]
|
||||
as
|
||||
[core::fmt::ArgumentV1<'_>; 0]),
|
||||
}
|
||||
as
|
||||
[core::fmt::Argument<'_>; 0]),
|
||||
}
|
||||
as
|
||||
[core::fmt::Argument<'_>; 0])
|
||||
as
|
||||
&[core::fmt::Argument<'_>; 0]))
|
||||
[core::fmt::ArgumentV1<'_>; 0])
|
||||
as
|
||||
&[core::fmt::ArgumentV1<'_>; 0]))
|
||||
as
|
||||
core::fmt::Arguments<'_>))
|
||||
as collections::string::String);
|
||||
|
Loading…
Reference in New Issue
Block a user