auto merge of #16092 : alexcrichton/rust/rollup, r=alexcrichton

This commit is contained in:
bors 2014-07-30 05:06:41 +00:00
commit 1b0dc6a3fc
29 changed files with 455 additions and 91 deletions

View File

@ -36,6 +36,10 @@ pub struct TestProps {
pub no_prefer_dynamic: bool,
// Don't run --pretty expanded when running pretty printing tests
pub no_pretty_expanded: bool,
// Which pretty mode are we testing with, default to 'normal'
pub pretty_mode: String,
// Only compare pretty output and don't try compiling
pub pretty_compare_only: bool,
}
// Load any test directives embedded in the file
@ -51,6 +55,8 @@ pub fn load_props(testfile: &Path) -> TestProps {
let mut check_stdout = false;
let mut no_prefer_dynamic = false;
let mut no_pretty_expanded = false;
let mut pretty_mode = None;
let mut pretty_compare_only = false;
iter_header(testfile, |ln| {
match parse_error_pattern(ln) {
Some(ep) => error_patterns.push(ep),
@ -85,6 +91,14 @@ pub fn load_props(testfile: &Path) -> TestProps {
no_pretty_expanded = parse_no_pretty_expanded(ln);
}
if pretty_mode.is_none() {
pretty_mode = parse_pretty_mode(ln);
}
if !pretty_compare_only {
pretty_compare_only = parse_pretty_compare_only(ln);
}
match parse_aux_build(ln) {
Some(ab) => { aux_builds.push(ab); }
None => {}
@ -115,6 +129,8 @@ pub fn load_props(testfile: &Path) -> TestProps {
check_stdout: check_stdout,
no_prefer_dynamic: no_prefer_dynamic,
no_pretty_expanded: no_pretty_expanded,
pretty_mode: pretty_mode.unwrap_or("normal".to_string()),
pretty_compare_only: pretty_compare_only
}
}
@ -205,6 +221,14 @@ fn parse_no_pretty_expanded(line: &str) -> bool {
parse_name_directive(line, "no-pretty-expanded")
}
fn parse_pretty_mode(line: &str) -> Option<String> {
parse_name_value_directive(line, "pretty-mode")
}
fn parse_pretty_compare_only(line: &str) -> bool {
parse_name_directive(line, "pretty-compare-only")
}
fn parse_exec_env(line: &str) -> Option<(String, String)> {
parse_name_value_directive(line, "exec-env").map(|nv| {
// nv is either FOO or FOO=BAR

View File

@ -168,7 +168,7 @@ fn run_pretty_test(config: &Config, props: &TestProps, testfile: &Path) {
props,
testfile,
srcs[round].to_string(),
"normal");
props.pretty_mode.as_slice());
if !proc_res.status.success() {
fatal_proc_rec(format!("pretty-printing failed in round {}",
@ -200,6 +200,9 @@ fn run_pretty_test(config: &Config, props: &TestProps, testfile: &Path) {
compare_source(expected.as_slice(), actual.as_slice());
// If we're only making sure that the output matches then just stop here
if props.pretty_compare_only { return; }
// Finally, let's make sure it actually appears to remain valid code
let proc_res = typecheck_source(config, props, testfile, actual);

View File

@ -84,6 +84,7 @@ as that for which this documentation was generated.*
* [Reddit](http://reddit.com/r/rust)
* [Stack Overflow](http://stackoverflow.com/questions/tagged/rust)
* [Developer Forum](http://discuss.rust-lang.org/)
* The Rust IRC channels on [irc.mozilla.org](http://irc.mozilla.org/):
* [`#rust`](http://chat.mibbit.com/?server=irc.mozilla.org&channel=%23rust) - general discussion
* [`#rust-gamedev`](http://chat.mibbit.com/?server=irc.mozilla.org&channel=%23rust-gamedev) - game development

View File

@ -36,8 +36,8 @@ int add_one(void)
}
```
**Note: obviously this is very simple and non-idiomatic C++.
You wouldn't write it in practice; it is for illustrative purposes.**
**Note: The above C++ code is deliberately simple and non-idiomatic for the purpose
of demonstration. It is not representative of production-quality C++ code.**
This function allocates an integer on the stack,
and stores it in a variable, `i`.

View File

@ -1950,6 +1950,12 @@ interpreted:
- `unsafe_no_drop_flag` - on structs, remove the flag that prevents
destructors from being run twice. Destructors might be run multiple times on
the same object with this attribute.
- `phase` - on `extern crate` statements, allows specifying which "phase" of
compilation the crate should be loaded for. Currently, there are two
choices: `link` and `plugin`. `link` is the default. `plugin` will load the
crate at compile-time and use any syntax extensions or lints that the crate
defines. They can both be specified, `#[phase(link, plugin)]` to use a crate
both at runtime and compiletime.
### Conditional compilation
@ -2395,17 +2401,17 @@ The currently implemented features of the reference compiler are:
closure as `once` is unlikely to be supported going forward. So
they are hidden behind this feature until they are to be removed.
* `managed_boxes` - Usage of `@` pointers is gated due to many
* `asm` - The `asm!` macro provides a means for inline assembly. This is often
useful, but the exact syntax for this feature along with its semantics
are likely to change, so this macro usage must be opted into.
* `managed_boxes` - Usage of `@` is gated due to many
planned changes to this feature. In the past, this has meant
"a GC pointer", but the current implementation uses
reference counting and will likely change drastically over
time. Additionally, the `@` syntax will no longer be used to
create GC boxes.
* `asm` - The `asm!` macro provides a means for inline assembly. This is often
useful, but the exact syntax for this feature along with its semantics
are likely to change, so this macro usage must be opted into.
* `non_ascii_idents` - The compiler supports the use of non-ascii identifiers,
but the implementation is a little rough around the
edges, so this can be seen as an experimental feature for
@ -2427,6 +2433,66 @@ The currently implemented features of the reference compiler are:
if the system linker is not used then specifying custom flags
doesn't have much meaning.
* `phase` - Usage of the `#[phase]` attribute allows loading compiler plugins
for custom lints or syntax extensions. The implementation is considered
unwholesome and in need of overhaul, and it is not clear what they
will look like moving forward.
* `plugin_registrar` - Indicates that a crate has compiler plugins that it
wants to load. As with `phase`, the implementation is
in need of a overhaul, and it is not clear that plugins
defined using this will continue to work.
* `log_syntax` - Allows use of the `log_syntax` macro attribute, which is a
nasty hack that will certainly be removed.
* `trace_macros` - Allows use of the `trace_macros` macro, which is a nasty
hack that will certainly be removed.
* `concat_idents` - Allows use of the `concat_idents` macro, which is in many
ways insufficient for concatenating identifiers, and may
be removed entirely for something more wholsome.
* `unsafe_destructor` - Allows use of the `#[unsafe_destructor]` attribute,
which is considered wildly unsafe and will be
obsoleted by language improvements.
* `intrinsics` - Allows use of the "rust-intrinsics" ABI. Compiler intrinsics
are inherently unstable and no promise about them is made.
* `lang_items` - Allows use of the `#[lang]` attribute. Like `intrinsics`,
lang items are inherently unstable and no promise about
them is made.
* `simd` - Allows use of the `#[simd]` attribute, which is overly simple and
not the SIMD interface we want to expose in the long term.
* `default_type_params` - Allows use of default type parameters. The future of
this feature is uncertain.
* `quote` - Allows use of the `quote_*!` family of macros, which are
implemented very poorly and will likely change significantly
with a proper implementation.
* `linkage` - Allows use of the `linkage` attribute, which is not portable.
* `struct_inherit` - Allows using struct inheritance, which is barely
implemented and will probably be removed. Don't use this.
* `overloaded_calls` - Allow implementing the `Fn*` family of traits on user
types, allowing overloading the call operator (`()`).
This feature may still undergo changes before being
stabilized.
* `unboxed_closure_sugar` - Allows using `|Foo| -> Bar` as a trait bound
meaning one of the `Fn` traits. Still
experimental.
* `rustc_diagnostic_macros`- A mysterious feature, used in the implementation
of rustc, not meant for mortals.
* `unboxed_closures` - A work in progress feature with many known bugs.
If a feature is promoted to a language feature, then all existing programs will
start to receive compilation warnings about #[feature] directives which enabled
the new feature (because the directive is no longer necessary). However, if

View File

@ -269,6 +269,14 @@
<match>\\\%{common_escape}</match>
</context>
<context id="raw-string" style-ref="string" class="string" class-disabled="no-spell-check">
<start>r(#*)"</start>
<end>"\%{1@start}</end>
<include>
<context ref="def:line-continue"/>
</include>
</context>
<context id="string" style-ref="string" class="string" class-disabled="no-spell-check">
<start>"</start>
<end>"</end>
@ -287,6 +295,8 @@
<end>\]</end>
<include>
<context ref="def:in-comment"/>
<context ref="string"/>
<context ref="raw-string"/>
</include>
</context>
@ -305,6 +315,7 @@
<context ref="number"/>
<context ref="scope"/>
<context ref="string"/>
<context ref="raw-string"/>
<context ref="char"/>
<context ref="lifetime"/>
<context ref="attribute"/>

View File

@ -92,7 +92,7 @@ impl<T: Share + Send> Arc<T> {
}
#[inline]
fn inner<'a>(&'a self) -> &'a ArcInner<T> {
fn inner(&self) -> &ArcInner<T> {
// This unsafety is ok because while this arc is alive we're guaranteed
// that the inner pointer is valid. Furthermore, we know that the
// `ArcInner` structure itself is `Share` because the inner data is
@ -142,7 +142,7 @@ impl<T: Share + Send> Clone for Arc<T> {
#[experimental = "Deref is experimental."]
impl<T: Send + Share> Deref<T> for Arc<T> {
#[inline]
fn deref<'a>(&'a self) -> &'a T {
fn deref(&self) -> &T {
&self.inner().data
}
}
@ -155,7 +155,7 @@ impl<T: Send + Share + Clone> Arc<T> {
/// data is cloned if the reference count is greater than one.
#[inline]
#[experimental]
pub fn make_unique<'a>(&'a mut self) -> &'a mut T {
pub fn make_unique(&mut self) -> &mut T {
// Note that we hold a strong reference, which also counts as
// a weak reference, so we only clone if there is an
// additional reference of either kind.
@ -238,7 +238,7 @@ impl<T: Share + Send> Weak<T> {
}
#[inline]
fn inner<'a>(&'a self) -> &'a ArcInner<T> {
fn inner(&self) -> &ArcInner<T> {
// See comments above for why this is "safe"
unsafe { &*self._ptr }
}

View File

@ -29,6 +29,7 @@ use core::fmt;
use core::iter;
use core::mem;
use core::ptr;
use std::hash::{Writer, Hash};
use {Collection, Mutable, Deque, MutableSeq};
@ -707,10 +708,20 @@ impl<A: fmt::Show> fmt::Show for DList<A> {
}
}
impl<S: Writer, A: Hash<S>> Hash<S> for DList<A> {
fn hash(&self, state: &mut S) {
self.len().hash(state);
for elt in self.iter() {
elt.hash(state);
}
}
}
#[cfg(test)]
mod tests {
use std::prelude::*;
use std::rand;
use std::hash;
use test::Bencher;
use test;
@ -1075,6 +1086,24 @@ mod tests {
assert!(n != m);
}
#[test]
fn test_hash() {
let mut x = DList::new();
let mut y = DList::new();
assert!(hash::hash(&x) == hash::hash(&y));
x.push_back(1i);
x.push_back(2);
x.push_back(3);
y.push_front(3i);
y.push_front(2);
y.push_front(1);
assert!(hash::hash(&x) == hash::hash(&y));
}
#[test]
fn test_ord() {
let n: DList<int> = list_from([]);

View File

@ -579,7 +579,7 @@ pub trait MutableVectorAllocating<'a, T> {
*
* * src - A mutable vector of `T`
* * start - The index into `src` to start copying from
* * end - The index into `str` to stop copying from
* * end - The index into `src` to stop copying from
*/
fn move_from(self, src: Vec<T>, start: uint, end: uint) -> uint;
}

View File

@ -117,23 +117,23 @@ impl Float for f32 {
#[inline]
fn neg_zero() -> f32 { -0.0 }
/// Returns `true` if the number is NaN
/// Returns `true` if the number is NaN.
#[inline]
fn is_nan(self) -> bool { self != self }
/// Returns `true` if the number is infinite
/// Returns `true` if the number is infinite.
#[inline]
fn is_infinite(self) -> bool {
self == Float::infinity() || self == Float::neg_infinity()
}
/// Returns `true` if the number is neither infinite or NaN
/// Returns `true` if the number is neither infinite or NaN.
#[inline]
fn is_finite(self) -> bool {
!(self.is_nan() || self.is_infinite())
}
/// Returns `true` if the number is neither zero, infinite, subnormal or NaN
/// Returns `true` if the number is neither zero, infinite, subnormal or NaN.
#[inline]
fn is_normal(self) -> bool {
self.classify() == FPNormal
@ -195,25 +195,25 @@ impl Float for f32 {
(mantissa as u64, exponent, sign)
}
/// Round half-way cases toward `NEG_INFINITY`
/// Rounds towards minus infinity.
#[inline]
fn floor(self) -> f32 {
unsafe { intrinsics::floorf32(self) }
}
/// Round half-way cases toward `INFINITY`
/// Rounds towards plus infinity.
#[inline]
fn ceil(self) -> f32 {
unsafe { intrinsics::ceilf32(self) }
}
/// Round half-way cases away from `0.0`
/// Rounds to nearest integer. Rounds half-way cases away from zero.
#[inline]
fn round(self) -> f32 {
unsafe { intrinsics::roundf32(self) }
}
/// The integer part of the number (rounds towards `0.0`)
/// Returns the integer part of the number (rounds towards zero).
#[inline]
fn trunc(self) -> f32 {
unsafe { intrinsics::truncf32(self) }
@ -236,7 +236,7 @@ impl Float for f32 {
unsafe { intrinsics::fmaf32(self, a, b) }
}
/// The reciprocal (multiplicative inverse) of the number
/// Returns the reciprocal (multiplicative inverse) of the number.
#[inline]
fn recip(self) -> f32 { 1.0 / self }
@ -325,45 +325,45 @@ impl Float for f32 {
#[inline]
fn ln_10() -> f32 { consts::LN_10 }
/// Returns the exponential of the number
/// Returns the exponential of the number.
#[inline]
fn exp(self) -> f32 {
unsafe { intrinsics::expf32(self) }
}
/// Returns 2 raised to the power of the number
/// Returns 2 raised to the power of the number.
#[inline]
fn exp2(self) -> f32 {
unsafe { intrinsics::exp2f32(self) }
}
/// Returns the natural logarithm of the number
/// Returns the natural logarithm of the number.
#[inline]
fn ln(self) -> f32 {
unsafe { intrinsics::logf32(self) }
}
/// Returns the logarithm of the number with respect to an arbitrary base
/// Returns the logarithm of the number with respect to an arbitrary base.
#[inline]
fn log(self, base: f32) -> f32 { self.ln() / base.ln() }
/// Returns the base 2 logarithm of the number
/// Returns the base 2 logarithm of the number.
#[inline]
fn log2(self) -> f32 {
unsafe { intrinsics::log2f32(self) }
}
/// Returns the base 10 logarithm of the number
/// Returns the base 10 logarithm of the number.
#[inline]
fn log10(self) -> f32 {
unsafe { intrinsics::log10f32(self) }
}
/// Converts to degrees, assuming the number is in radians
/// Converts to degrees, assuming the number is in radians.
#[inline]
fn to_degrees(self) -> f32 { self * (180.0f32 / Float::pi()) }
/// Converts to radians, assuming the number is in degrees
/// Converts to radians, assuming the number is in degrees.
#[inline]
fn to_radians(self) -> f32 {
let value: f32 = Float::pi();

View File

@ -123,23 +123,23 @@ impl Float for f64 {
#[inline]
fn neg_zero() -> f64 { -0.0 }
/// Returns `true` if the number is NaN
/// Returns `true` if the number is NaN.
#[inline]
fn is_nan(self) -> bool { self != self }
/// Returns `true` if the number is infinite
/// Returns `true` if the number is infinite.
#[inline]
fn is_infinite(self) -> bool {
self == Float::infinity() || self == Float::neg_infinity()
}
/// Returns `true` if the number is neither infinite or NaN
/// Returns `true` if the number is neither infinite or NaN.
#[inline]
fn is_finite(self) -> bool {
!(self.is_nan() || self.is_infinite())
}
/// Returns `true` if the number is neither zero, infinite, subnormal or NaN
/// Returns `true` if the number is neither zero, infinite, subnormal or NaN.
#[inline]
fn is_normal(self) -> bool {
self.classify() == FPNormal
@ -201,25 +201,25 @@ impl Float for f64 {
(mantissa, exponent, sign)
}
/// Round half-way cases toward `NEG_INFINITY`
/// Rounds towards minus infinity.
#[inline]
fn floor(self) -> f64 {
unsafe { intrinsics::floorf64(self) }
}
/// Round half-way cases toward `INFINITY`
/// Rounds towards plus infinity.
#[inline]
fn ceil(self) -> f64 {
unsafe { intrinsics::ceilf64(self) }
}
/// Round half-way cases away from `0.0`
/// Rounds to nearest integer. Rounds half-way cases away from zero.
#[inline]
fn round(self) -> f64 {
unsafe { intrinsics::roundf64(self) }
}
/// The integer part of the number (rounds towards `0.0`)
/// Returns the integer part of the number (rounds towards zero).
#[inline]
fn trunc(self) -> f64 {
unsafe { intrinsics::truncf64(self) }
@ -242,7 +242,7 @@ impl Float for f64 {
unsafe { intrinsics::fmaf64(self, a, b) }
}
/// The reciprocal (multiplicative inverse) of the number
/// Returns the reciprocal (multiplicative inverse) of the number.
#[inline]
fn recip(self) -> f64 { 1.0 / self }
@ -332,46 +332,45 @@ impl Float for f64 {
#[inline]
fn ln_10() -> f64 { consts::LN_10 }
/// Returns the exponential of the number
/// Returns the exponential of the number.
#[inline]
fn exp(self) -> f64 {
unsafe { intrinsics::expf64(self) }
}
/// Returns 2 raised to the power of the number
/// Returns 2 raised to the power of the number.
#[inline]
fn exp2(self) -> f64 {
unsafe { intrinsics::exp2f64(self) }
}
/// Returns the natural logarithm of the number
/// Returns the natural logarithm of the number.
#[inline]
fn ln(self) -> f64 {
unsafe { intrinsics::logf64(self) }
}
/// Returns the logarithm of the number with respect to an arbitrary base
/// Returns the logarithm of the number with respect to an arbitrary base.
#[inline]
fn log(self, base: f64) -> f64 { self.ln() / base.ln() }
/// Returns the base 2 logarithm of the number
/// Returns the base 2 logarithm of the number.
#[inline]
fn log2(self) -> f64 {
unsafe { intrinsics::log2f64(self) }
}
/// Returns the base 10 logarithm of the number
/// Returns the base 10 logarithm of the number.
#[inline]
fn log10(self) -> f64 {
unsafe { intrinsics::log10f64(self) }
}
/// Converts to degrees, assuming the number is in radians
/// Converts to degrees, assuming the number is in radians.
#[inline]
fn to_degrees(self) -> f64 { self * (180.0f64 / Float::pi()) }
/// Converts to radians, assuming the number is in degrees
/// Converts to radians, assuming the number is in degrees.
#[inline]
fn to_radians(self) -> f64 {
let value: f64 = Float::pi();

View File

@ -514,9 +514,14 @@ impl Integer for BigUint {
#[inline]
fn lcm(&self, other: &BigUint) -> BigUint { ((*self * *other) / self.gcd(other)) }
/// Returns `true` if the number can be divided by `other` without leaving a remainder.
/// Deprecated, use `is_multiple_of` instead.
#[deprecated = "function renamed to `is_multiple_of`"]
#[inline]
fn divides(&self, other: &BigUint) -> bool { (*self % *other).is_zero() }
fn divides(&self, other: &BigUint) -> bool { return self.is_multiple_of(other); }
/// Returns `true` if the number is a multiple of `other`.
#[inline]
fn is_multiple_of(&self, other: &BigUint) -> bool { (*self % *other).is_zero() }
/// Returns `true` if the number is divisible by `2`.
#[inline]
@ -1112,9 +1117,14 @@ impl Integer for BigInt {
BigInt::from_biguint(Plus, self.data.lcm(&other.data))
}
/// Returns `true` if the number can be divided by `other` without leaving a remainder.
/// Deprecated, use `is_multiple_of` instead.
#[deprecated = "function renamed to `is_multiple_of`"]
#[inline]
fn divides(&self, other: &BigInt) -> bool { self.data.divides(&other.data) }
fn divides(&self, other: &BigInt) -> bool { return self.is_multiple_of(other); }
/// Returns `true` if the number is a multiple of `other`.
#[inline]
fn is_multiple_of(&self, other: &BigInt) -> bool { self.data.is_multiple_of(&other.data) }
/// Returns `true` if the number is divisible by `2`.
#[inline]

View File

@ -77,16 +77,20 @@ pub trait Integer: Num + PartialOrd
/// ~~~
fn lcm(&self, other: &Self) -> Self;
/// Returns `true` if `other` divides evenly into `self`.
/// Deprecated, use `is_multiple_of` instead.
#[deprecated = "function renamed to `is_multiple_of`"]
fn divides(&self, other: &Self) -> bool;
/// Returns `true` if `other` is a multiple of `self`.
///
/// # Examples
///
/// ~~~
/// # use num::Integer;
/// assert_eq!(9i.divides(&3), true);
/// assert_eq!(3i.divides(&9), false);
/// assert_eq!(9i.is_multiple_of(&3), true);
/// assert_eq!(3i.is_multiple_of(&9), false);
/// ~~~
fn divides(&self, other: &Self) -> bool;
fn is_multiple_of(&self, other: &Self) -> bool;
/// Returns `true` if the number is even.
///
@ -231,10 +235,14 @@ macro_rules! impl_integer_for_int {
((*self * *other) / self.gcd(other)).abs()
}
/// Returns `true` if the number can be divided by `other` without
/// leaving a remainder
/// Deprecated, use `is_multiple_of` instead.
#[deprecated = "function renamed to `is_multiple_of`"]
#[inline]
fn divides(&self, other: &$T) -> bool { *self % *other == 0 }
fn divides(&self, other: &$T) -> bool { return self.is_multiple_of(other); }
/// Returns `true` if the number is a multiple of `other`.
#[inline]
fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 }
/// Returns `true` if the number is divisible by `2`
#[inline]
@ -393,21 +401,26 @@ macro_rules! impl_integer_for_uint {
n
}
/// Calculates the Lowest Common Multiple (LCM) of the number and `other`
/// Calculates the Lowest Common Multiple (LCM) of the number and `other`.
#[inline]
fn lcm(&self, other: &$T) -> $T {
(*self * *other) / self.gcd(other)
}
/// Returns `true` if the number can be divided by `other` without leaving a remainder
/// Deprecated, use `is_multiple_of` instead.
#[deprecated = "function renamed to `is_multiple_of`"]
#[inline]
fn divides(&self, other: &$T) -> bool { *self % *other == 0 }
fn divides(&self, other: &$T) -> bool { return self.is_multiple_of(other); }
/// Returns `true` if the number is divisible by `2`
/// Returns `true` if the number is a multiple of `other`.
#[inline]
fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 }
/// Returns `true` if the number is divisible by `2`.
#[inline]
fn is_even(&self) -> bool { self & 1 == 0 }
/// Returns `true` if the number is not divisible by `2`
/// Returns `true` if the number is not divisible by `2`.
#[inline]
fn is_odd(&self) -> bool { !self.is_even() }
}
@ -449,10 +462,10 @@ macro_rules! impl_integer_for_uint {
}
#[test]
fn test_divides() {
assert!((6 as $T).divides(&(6 as $T)));
assert!((6 as $T).divides(&(3 as $T)));
assert!((6 as $T).divides(&(1 as $T)));
fn test_is_multiple_of() {
assert!((6 as $T).is_multiple_of(&(6 as $T)));
assert!((6 as $T).is_multiple_of(&(3 as $T)));
assert!((6 as $T).is_multiple_of(&(1 as $T)));
}
#[test]

View File

@ -38,13 +38,13 @@ pub type BigRational = Ratio<BigInt>;
impl<T: Clone + Integer + PartialOrd>
Ratio<T> {
/// Create a ratio representing the integer `t`.
/// Creates a ratio representing the integer `t`.
#[inline]
pub fn from_integer(t: T) -> Ratio<T> {
Ratio::new_raw(t, One::one())
}
/// Create a ratio without checking for `denom == 0` or reducing.
/// Creates a ratio without checking for `denom == 0` or reducing.
#[inline]
pub fn new_raw(numer: T, denom: T) -> Ratio<T> {
Ratio { numer: numer, denom: denom }
@ -61,7 +61,7 @@ impl<T: Clone + Integer + PartialOrd>
ret
}
/// Convert to an integer.
/// Converts to an integer.
#[inline]
pub fn to_integer(&self) -> T {
self.trunc().numer
@ -79,7 +79,7 @@ impl<T: Clone + Integer + PartialOrd>
&self.denom
}
/// Return true if the rational number is an integer (denominator is 1).
/// Returns true if the rational number is an integer (denominator is 1).
#[inline]
pub fn is_integer(&self) -> bool {
self.denom == One::one()
@ -103,19 +103,21 @@ impl<T: Clone + Integer + PartialOrd>
}
}
/// Return a `reduce`d copy of self.
/// Returns a `reduce`d copy of self.
pub fn reduced(&self) -> Ratio<T> {
let mut ret = self.clone();
ret.reduce();
ret
}
/// Return the reciprocal
/// Returns the reciprocal.
#[inline]
pub fn recip(&self) -> Ratio<T> {
Ratio::new_raw(self.denom.clone(), self.numer.clone())
}
/// Rounds towards minus infinity.
#[inline]
pub fn floor(&self) -> Ratio<T> {
if *self < Zero::zero() {
Ratio::from_integer((self.numer - self.denom + One::one()) / self.denom)
@ -124,6 +126,8 @@ impl<T: Clone + Integer + PartialOrd>
}
}
/// Rounds towards plus infinity.
#[inline]
pub fn ceil(&self) -> Ratio<T> {
if *self < Zero::zero() {
Ratio::from_integer(self.numer / self.denom)
@ -132,8 +136,12 @@ impl<T: Clone + Integer + PartialOrd>
}
}
/// Rounds to the nearest integer. Rounds half-way cases away from zero.
///
/// Note: This function is currently broken and always rounds away from zero.
#[inline]
pub fn round(&self) -> Ratio<T> {
// FIXME(#15826)
if *self < Zero::zero() {
Ratio::from_integer((self.numer - self.denom + One::one()) / self.denom)
} else {
@ -141,18 +149,21 @@ impl<T: Clone + Integer + PartialOrd>
}
}
/// Rounds towards zero.
#[inline]
pub fn trunc(&self) -> Ratio<T> {
Ratio::from_integer(self.numer / self.denom)
}
///Returns the fractional part of a number.
#[inline]
pub fn fract(&self) -> Ratio<T> {
Ratio::new_raw(self.numer % self.denom, self.denom.clone())
}
}
impl Ratio<BigInt> {
/// Converts a float into a rational number
/// Converts a float into a rational number.
pub fn from_float<T: Float>(f: T) -> Option<BigRational> {
if !f.is_finite() {
return None;
@ -328,7 +339,7 @@ impl<T: ToStrRadix> ToStrRadix for Ratio<T> {
impl<T: FromStr + Clone + Integer + PartialOrd>
FromStr for Ratio<T> {
/// Parses `numer/denom` or just `numer`
/// Parses `numer/denom` or just `numer`.
fn from_str(s: &str) -> Option<Ratio<T>> {
let mut split = s.splitn('/', 1);

View File

@ -1230,7 +1230,7 @@ fn link_natively(sess: &Session, trans: &CrateTranslation, dylib: bool,
// the symbols
if (sess.targ_cfg.os == abi::OsMacos || sess.targ_cfg.os == abi::OsiOS)
&& (sess.opts.debuginfo != NoDebugInfo) {
match Command::new("dsymutil").arg(out_filename).status() {
match Command::new("dsymutil").arg(out_filename).output() {
Ok(..) => {}
Err(e) => {
sess.err(format!("failed to run dsymutil: {}", e).as_slice());

View File

@ -69,6 +69,8 @@ static KNOWN_FEATURES: &'static [(&'static str, Status)] = &[
("rustc_diagnostic_macros", Active),
("unboxed_closures", Active),
// if you change this list without updating src/doc/rust.md, cmr will be sad
// A temporary feature gate used to enable parser extensions needed
// to bootstrap fix for #5723.
("issue_5723_bootstrap", Active),

View File

@ -358,9 +358,9 @@ impl LintPass for CTypes {
def::DefTy(def_id) => {
if !adt::is_ffi_safe(cx.tcx, def_id) {
cx.span_lint(CTYPES, ty.span,
"found enum type without foreign-function-safe \
representation annotation in foreign module");
// hmm... this message could be more helpful
"found enum type without foreign-function-safe
representation annotation in foreign module, consider \
adding a #[repr(...)] attribute to the enumeration");
}
}
_ => ()

View File

@ -877,6 +877,7 @@ pub fn ast_ty_to_ty<AC:AstConv, RS:RegionScope>(
}
}
ast::TyFixedLengthVec(ty, e) => {
typeck::write_ty_to_tcx(tcx, e.id, ty::mk_uint());
match const_eval::eval_const_expr_partial(tcx, &*e) {
Ok(ref r) => {
match *r {

View File

@ -430,6 +430,18 @@ impl<'a> Visitor<()> for GatherLocalsVisitor<'a> {
self.fcx.with_region_lb(b.id, || visit::walk_block(self, b, ()));
}
// Since an expr occurs as part of the type fixed size arrays we
// need to record the type for that node
fn visit_ty(&mut self, t: &ast::Ty, _: ()) {
match t.node {
ast::TyFixedLengthVec(ref ty, ref count_expr) => {
self.visit_ty(&**ty, ());
check_expr_with_hint(self.fcx, &**count_expr, ty::mk_uint());
}
_ => visit::walk_ty(self, t, ())
}
}
// Don't descend into fns and items
fn visit_fn(&mut self, _: &visit::FnKind, _: &ast::FnDecl,
_: &ast::Block, _: Span, _: ast::NodeId, _: ()) { }
@ -3444,6 +3456,12 @@ fn check_expr_with_unifier(fcx: &FnCtxt,
}
}
ast::ExprCast(ref e, ref t) => {
match t.node {
ast::TyFixedLengthVec(_, ref count_expr) => {
check_expr_with_hint(fcx, &**count_expr, ty::mk_uint());
}
_ => {}
}
check_cast(fcx, &**e, &**t, id, expr.span);
}
ast::ExprVec(ref args) => {

View File

@ -181,8 +181,14 @@ impl<'cx> Visitor<()> for WritebackCx<'cx> {
visit::walk_local(self, l, ());
}
fn visit_ty(&mut self, _t: &ast::Ty, _: ()) {
// ignore
fn visit_ty(&mut self, t: &ast::Ty, _: ()) {
match t.node {
ast::TyFixedLengthVec(ref ty, ref count_expr) => {
self.visit_ty(&**ty, ());
write_ty_to_tcx(self.tcx(), count_expr.id, ty::mk_uint());
}
_ => visit::walk_ty(self, t, ())
}
}
}

View File

@ -129,6 +129,14 @@ pre {
padding: 20px;
}
.content.source {
margin-top: 50px;
max-width: none;
overflow: visible;
margin-left: 0px;
min-width: 70em;
}
nav.sub {
font-size: 16px;
text-transform: uppercase;

View File

@ -114,7 +114,7 @@ impl File {
/// `FileMode` and `FileAccess` provide information about the permissions
/// context in which a given stream is created. More information about them
/// can be found in `std::io`'s docs. If a file is opened with `Write`
/// or `ReadWrite` access, then it will be created it does not already
/// or `ReadWrite` access, then it will be created if it does not already
/// exist.
///
/// Note that, with this function, a `File` is returned regardless of the

View File

@ -178,16 +178,13 @@ pub trait GenericPath: Clone + GenericPathUnsafe {
fn into_vec(self) -> Vec<u8>;
/// Returns an object that implements `Show` for printing paths
///
/// This will print the equivalent of `to_display_str()` when used with a {} format parameter.
fn display<'a>(&'a self) -> Display<'a, Self> {
Display{ path: self, filename: false }
}
/// Returns an object that implements `Show` for printing filenames
///
/// This will print the equivalent of `to_filename_display_str()` when used with a {}
/// format parameter. If there is no filename, nothing will be printed.
/// If there is no filename, nothing will be printed.
fn filename_display<'a>(&'a self) -> Display<'a, Self> {
Display{ path: self, filename: true }
}

View File

@ -536,13 +536,16 @@ fn expand_non_macro_stmt(s: &Stmt, fld: &mut MacroExpander)
} => {
// take it apart:
let Local {
ty: _,
ty: ty,
pat: pat,
init: init,
id: id,
span: span,
source: source,
} = **local;
// expand the ty since TyFixedLengthVec contains an Expr
// and thus may have a macro use
let expanded_ty = fld.fold_ty(ty);
// expand the pat (it might contain macro uses):
let expanded_pat = fld.fold_pat(pat);
// find the PatIdents in the pattern:
@ -566,7 +569,7 @@ fn expand_non_macro_stmt(s: &Stmt, fld: &mut MacroExpander)
let new_init_opt = init.map(|e| fld.fold_expr(e));
let rewritten_local =
box(GC) Local {
ty: local.ty,
ty: expanded_ty,
pat: rewritten_pat,
init: new_init_opt,
id: id,

@ -1 +1 @@
Subproject commit cd24b5c6633b27df2b84249a65a46a610b734494
Subproject commit 0d999e5b315b6ff78fcea772466d985ce53fd8dc

View File

@ -1,4 +1,4 @@
# If this file is modified, then llvm will be forcibly cleaned and then rebuilt.
# The actual contents of this file do not matter, but to trigger a change on the
# build bots then the contents should be changed so git updates the mtime.
2014-07-22
2014-07-29

View File

@ -0,0 +1,95 @@
#![feature(phase)]
#![no_std]
#![feature(globs)]
#[phase(plugin, link)]
extern crate std = "std";
extern crate rt = "native";
use std::prelude::*;
// Copyright 2014 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.
// pretty-compare-only
// pretty-mode:typed
// pp-exact:issue-4264.pp
// #4264 fixed-length vector types
pub fn foo(_: [int, ..(3 as uint)]) { }
pub fn bar() {
static FOO: uint = ((5u as uint) - (4u as uint) as uint);
let _: [(), ..(FOO as uint)] = ([(() as ())] as [(), .. 1]);
let _: [(), ..(1u as uint)] = ([(() as ())] as [(), .. 1]);
let _ =
(((&((([(1i as int), (2 as int), (3 as int)] as [int, .. 3])) as
[int, .. 3]) as &[int, .. 3]) as *const _ as
*const [int, .. 3]) as *const [int, ..(3u as uint)] as
*const [int, .. 3]);
(match (() as ()) {
() => {
#[inline]
#[allow(dead_code)]
static __STATIC_FMTSTR:
[::std::fmt::rt::Piece<'static>, ..(1u as uint)] =
([((::std::fmt::rt::String as
fn(&'static str) -> core::fmt::rt::Piece<'static>)(("test"
as
&'static str))
as core::fmt::rt::Piece<'static>)] as
[core::fmt::rt::Piece<'static>, .. 1]);
let __args_vec =
(&([] as &'static [core::fmt::Argument<'static>]) as
&'static [core::fmt::Argument<'static>]);
let __args =
(unsafe {
((::std::fmt::Arguments::new as
unsafe fn(&'static [core::fmt::rt::Piece<'static>], &'a [core::fmt::Argument<'a>]) -> core::fmt::Arguments<'a>)((__STATIC_FMTSTR
as
[core::fmt::rt::Piece<'static>, .. 1]),
(__args_vec
as
&'static [core::fmt::Argument<'static>]))
as core::fmt::Arguments<'static>)
} as core::fmt::Arguments<'static>);
((::std::fmt::format as
fn(&core::fmt::Arguments<'_>) -> collections::string::String)((&(__args
as
core::fmt::Arguments<'static>)
as
&core::fmt::Arguments<'static>))
as collections::string::String)
}
} as collections::string::String);
}
pub type Foo = [int, ..(3u as uint)];
pub struct Bar {
pub x: [int, ..(3u as uint)],
}
pub struct TupleBar([int, ..(4u as uint)]);
pub enum Baz { BazVariant([int, ..(5u as uint)]), }
pub fn id<T>(x: T) -> T { (x as T) }
pub fn use_id() {
let _ =
((id::<[int, ..(3u as uint)]> as
fn([int, .. 3]) -> [int, .. 3])(([(1 as int), (2 as int),
(3 as int)] as [int, .. 3])) as
[int, .. 3]);
}
fn main() { }

View File

@ -0,0 +1,49 @@
// Copyright 2014 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.
// pretty-compare-only
// pretty-mode:typed
// pp-exact:issue-4264.pp
// #4264 fixed-length vector types
pub fn foo(_: [int, ..3]) {}
pub fn bar() {
static FOO: uint = 5u - 4u;
let _: [(), ..FOO] = [()];
let _ : [(), ..1u] = [()];
let _ = &([1i,2,3]) as *const _ as *const [int, ..3u];
format!("test");
}
pub type Foo = [int, ..3u];
pub struct Bar {
pub x: [int, ..3u]
}
pub struct TupleBar([int, ..4u]);
pub enum Baz {
BazVariant([int, ..5u])
}
pub fn id<T>(x: T) -> T { x }
pub fn use_id() {
let _ = id::<[int, ..3u]>([1,2,3]);
}
fn main() {}

View File

@ -0,0 +1,18 @@
// Copyright 2014 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.
#![feature(macro_rules)]
macro_rules! four (
() => (4)
)
fn main() {
let _x: [u16, ..four!()];
}