Format libstd with rustfmt

This commit applies rustfmt with rust-lang/rust's default settings to
files in src/libstd *that are not involved in any currently open PR* to
minimize merge conflicts. THe list of files involved in open PRs was
determined by querying GitHub's GraphQL API with this script:
https://gist.github.com/dtolnay/aa9c34993dc051a4f344d1b10e4487e8

With the list of files from the script in outstanding_files, the
relevant commands were:

    $ find src/libstd -name '*.rs' \
        | xargs rustfmt --edition=2018 --unstable-features --skip-children
    $ rg libstd outstanding_files | xargs git checkout --

Repeating this process several months apart should get us coverage of
most of the rest of libstd.

To confirm no funny business:

    $ git checkout $THIS_COMMIT^
    $ git show --pretty= --name-only $THIS_COMMIT \
        | xargs rustfmt --edition=2018 --unstable-features --skip-children
    $ git diff $THIS_COMMIT  # there should be no difference
This commit is contained in:
David Tolnay 2019-11-27 10:29:00 -08:00
parent 9081929d45
commit 4436c9d354
No known key found for this signature in database
GPG key ID: F9BA143B95FF6D82
50 changed files with 2906 additions and 2669 deletions

View file

@ -17,7 +17,7 @@
#![stable(feature = "rust1", since = "1.0.0")]
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::ascii::{EscapeDefault, escape_default};
pub use core::ascii::{escape_default, EscapeDefault};
/// Extension methods for ASCII-subset only operations.
///

View file

@ -95,10 +95,10 @@ use crate::env;
use crate::fmt;
use crate::sync::atomic::{AtomicUsize, Ordering::SeqCst};
use crate::sync::Mutex;
use crate::sys_common::backtrace::{output_filename, lock};
use crate::sys_common::backtrace::{lock, output_filename};
use crate::vec::Vec;
use backtrace_rs as backtrace;
use backtrace::BytesOrWideString;
use backtrace_rs as backtrace;
/// A captured OS thread stack backtrace.
///

View file

@ -1,7 +1,7 @@
#![cfg(test)]
use test::Bencher;
use std::collections::HashMap;
use test::Bencher;
#[bench]
fn new_drop(b: &mut Bencher) {

View file

@ -413,20 +413,20 @@
#[doc(hidden)]
pub use crate::ops::Bound;
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{BinaryHeap, BTreeMap, BTreeSet};
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{LinkedList, VecDeque};
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{binary_heap, btree_map, btree_set};
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{linked_list, vec_deque};
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{BTreeMap, BTreeSet, BinaryHeap};
#[stable(feature = "rust1", since = "1.0.0")]
pub use alloc_crate::collections::{LinkedList, VecDeque};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::hash_map::HashMap;
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::hash_set::HashSet;
#[unstable(feature = "try_reserve", reason = "new API", issue="48043")]
#[unstable(feature = "try_reserve", reason = "new API", issue = "48043")]
pub use alloc_crate::collections::TryReserveError;
mod hash;

View file

@ -78,7 +78,9 @@ pub fn set_current_dir<P: AsRef<Path>>(path: P) -> io::Result<()> {
///
/// [`std::env::vars`]: fn.vars.html
#[stable(feature = "env", since = "1.0.0")]
pub struct Vars { inner: VarsOs }
pub struct Vars {
inner: VarsOs,
}
/// An iterator over a snapshot of the environment variables of this process.
///
@ -87,7 +89,9 @@ pub struct Vars { inner: VarsOs }
///
/// [`std::env::vars_os`]: fn.vars_os.html
#[stable(feature = "env", since = "1.0.0")]
pub struct VarsOs { inner: os_imp::Env }
pub struct VarsOs {
inner: os_imp::Env,
}
/// Returns an iterator of (variable, value) pairs of strings, for all the
/// environment variables of the current process.
@ -147,11 +151,11 @@ pub fn vars_os() -> VarsOs {
impl Iterator for Vars {
type Item = (String, String);
fn next(&mut self) -> Option<(String, String)> {
self.inner.next().map(|(a, b)| {
(a.into_string().unwrap(), b.into_string().unwrap())
})
self.inner.next().map(|(a, b)| (a.into_string().unwrap(), b.into_string().unwrap()))
}
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
fn size_hint(&self) -> (usize, Option<usize>) { self.inner.size_hint() }
}
#[stable(feature = "std_debug", since = "1.16.0")]
@ -164,8 +168,12 @@ impl fmt::Debug for Vars {
#[stable(feature = "env", since = "1.0.0")]
impl Iterator for VarsOs {
type Item = (OsString, OsString);
fn next(&mut self) -> Option<(OsString, OsString)> { self.inner.next() }
fn size_hint(&self) -> (usize, Option<usize>) { self.inner.size_hint() }
fn next(&mut self) -> Option<(OsString, OsString)> {
self.inner.next()
}
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
}
#[stable(feature = "std_debug", since = "1.16.0")]
@ -239,9 +247,8 @@ pub fn var_os<K: AsRef<OsStr>>(key: K) -> Option<OsString> {
}
fn _var_os(key: &OsStr) -> Option<OsString> {
os_imp::getenv(key).unwrap_or_else(|e| {
panic!("failed to get environment variable `{:?}`: {}", key, e)
})
os_imp::getenv(key)
.unwrap_or_else(|e| panic!("failed to get environment variable `{:?}`: {}", key, e))
}
/// The error type for operations interacting with environment variables.
@ -321,8 +328,7 @@ pub fn set_var<K: AsRef<OsStr>, V: AsRef<OsStr>>(k: K, v: V) {
fn _set_var(k: &OsStr, v: &OsStr) {
os_imp::setenv(k, v).unwrap_or_else(|e| {
panic!("failed to set environment variable `{:?}` to `{:?}`: {}",
k, v, e)
panic!("failed to set environment variable `{:?}` to `{:?}`: {}", k, v, e)
})
}
@ -363,9 +369,8 @@ pub fn remove_var<K: AsRef<OsStr>>(k: K) {
}
fn _remove_var(k: &OsStr) {
os_imp::unsetenv(k).unwrap_or_else(|e| {
panic!("failed to remove environment variable `{:?}`: {}", k, e)
})
os_imp::unsetenv(k)
.unwrap_or_else(|e| panic!("failed to remove environment variable `{:?}`: {}", k, e))
}
/// An iterator that splits an environment variable into paths according to
@ -379,7 +384,9 @@ fn _remove_var(k: &OsStr) {
/// [`PathBuf`]: ../../std/path/struct.PathBuf.html
/// [`std::env::split_paths`]: fn.split_paths.html
#[stable(feature = "env", since = "1.0.0")]
pub struct SplitPaths<'a> { inner: os_imp::SplitPaths<'a> }
pub struct SplitPaths<'a> {
inner: os_imp::SplitPaths<'a>,
}
/// Parses input according to platform conventions for the `PATH`
/// environment variable.
@ -412,8 +419,12 @@ pub fn split_paths<T: AsRef<OsStr> + ?Sized>(unparsed: &T) -> SplitPaths<'_> {
#[stable(feature = "env", since = "1.0.0")]
impl<'a> Iterator for SplitPaths<'a> {
type Item = PathBuf;
fn next(&mut self) -> Option<PathBuf> { self.inner.next() }
fn size_hint(&self) -> (usize, Option<usize>) { self.inner.size_hint() }
fn next(&mut self) -> Option<PathBuf> {
self.inner.next()
}
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
}
#[stable(feature = "std_debug", since = "1.16.0")]
@ -430,7 +441,7 @@ impl fmt::Debug for SplitPaths<'_> {
#[derive(Debug)]
#[stable(feature = "env", since = "1.0.0")]
pub struct JoinPathsError {
inner: os_imp::JoinPathsError
inner: os_imp::JoinPathsError,
}
/// Joins a collection of [`Path`]s appropriately for the `PATH`
@ -499,11 +510,11 @@ pub struct JoinPathsError {
/// [`env::split_paths`]: fn.split_paths.html
#[stable(feature = "env", since = "1.0.0")]
pub fn join_paths<I, T>(paths: I) -> Result<OsString, JoinPathsError>
where I: IntoIterator<Item=T>, T: AsRef<OsStr>
where
I: IntoIterator<Item = T>,
T: AsRef<OsStr>,
{
os_imp::join_paths(paths.into_iter()).map_err(|e| {
JoinPathsError { inner: e }
})
os_imp::join_paths(paths.into_iter()).map_err(|e| JoinPathsError { inner: e })
}
#[stable(feature = "env", since = "1.0.0")]
@ -515,7 +526,9 @@ impl fmt::Display for JoinPathsError {
#[stable(feature = "env", since = "1.0.0")]
impl Error for JoinPathsError {
fn description(&self) -> &str { self.inner.description() }
fn description(&self) -> &str {
self.inner.description()
}
}
/// Returns the path of the current user's home directory if known.
@ -549,9 +562,11 @@ impl Error for JoinPathsError {
/// None => println!("Impossible to get your home dir!"),
/// }
/// ```
#[rustc_deprecated(since = "1.29.0",
#[rustc_deprecated(
since = "1.29.0",
reason = "This function's behavior is unexpected and probably not what you want. \
Consider using the home_dir function from https://crates.io/crates/dirs instead.")]
Consider using the home_dir function from https://crates.io/crates/dirs instead."
)]
#[stable(feature = "env", since = "1.0.0")]
pub fn home_dir() -> Option<PathBuf> {
os_imp::home_dir()
@ -674,7 +689,9 @@ pub fn current_exe() -> io::Result<PathBuf> {
/// [`String`]: ../string/struct.String.html
/// [`std::env::args`]: ./fn.args.html
#[stable(feature = "env", since = "1.0.0")]
pub struct Args { inner: ArgsOs }
pub struct Args {
inner: ArgsOs,
}
/// An iterator over the arguments of a process, yielding an [`OsString`] value
/// for each argument.
@ -689,7 +706,9 @@ pub struct Args { inner: ArgsOs }
/// [`OsString`]: ../ffi/struct.OsString.html
/// [`std::env::args_os`]: ./fn.args_os.html
#[stable(feature = "env", since = "1.0.0")]
pub struct ArgsOs { inner: sys::args::Args }
pub struct ArgsOs {
inner: sys::args::Args,
}
/// Returns the arguments which this program was started with (normally passed
/// via the command line).
@ -769,13 +788,19 @@ impl Iterator for Args {
fn next(&mut self) -> Option<String> {
self.inner.next().map(|s| s.into_string().unwrap())
}
fn size_hint(&self) -> (usize, Option<usize>) { self.inner.size_hint() }
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
}
#[stable(feature = "env", since = "1.0.0")]
impl ExactSizeIterator for Args {
fn len(&self) -> usize { self.inner.len() }
fn is_empty(&self) -> bool { self.inner.is_empty() }
fn len(&self) -> usize {
self.inner.len()
}
fn is_empty(&self) -> bool {
self.inner.is_empty()
}
}
#[stable(feature = "env_iterators", since = "1.12.0")]
@ -788,9 +813,7 @@ impl DoubleEndedIterator for Args {
#[stable(feature = "std_debug", since = "1.16.0")]
impl fmt::Debug for Args {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("Args")
.field("inner", &self.inner.inner.inner_debug())
.finish()
f.debug_struct("Args").field("inner", &self.inner.inner.inner_debug()).finish()
}
}
@ -803,27 +826,35 @@ impl !Sync for ArgsOs {}
#[stable(feature = "env", since = "1.0.0")]
impl Iterator for ArgsOs {
type Item = OsString;
fn next(&mut self) -> Option<OsString> { self.inner.next() }
fn size_hint(&self) -> (usize, Option<usize>) { self.inner.size_hint() }
fn next(&mut self) -> Option<OsString> {
self.inner.next()
}
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
}
#[stable(feature = "env", since = "1.0.0")]
impl ExactSizeIterator for ArgsOs {
fn len(&self) -> usize { self.inner.len() }
fn is_empty(&self) -> bool { self.inner.is_empty() }
fn len(&self) -> usize {
self.inner.len()
}
fn is_empty(&self) -> bool {
self.inner.is_empty()
}
}
#[stable(feature = "env_iterators", since = "1.12.0")]
impl DoubleEndedIterator for ArgsOs {
fn next_back(&mut self) -> Option<OsString> { self.inner.next_back() }
fn next_back(&mut self) -> Option<OsString> {
self.inner.next_back()
}
}
#[stable(feature = "std_debug", since = "1.16.0")]
impl fmt::Debug for ArgsOs {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("ArgsOs")
.field("inner", &self.inner.inner_debug())
.finish()
f.debug_struct("ArgsOs").field("inner", &self.inner.inner_debug()).finish()
}
}
@ -1033,8 +1064,8 @@ mod tests {
use crate::path::PathBuf;
fn check_parse(unparsed: &str, parsed: &[&str]) -> bool {
split_paths(unparsed).collect::<Vec<_>>() ==
parsed.iter().map(|s| PathBuf::from(*s)).collect::<Vec<_>>()
split_paths(unparsed).collect::<Vec<_>>()
== parsed.iter().map(|s| PathBuf::from(*s)).collect::<Vec<_>>()
}
assert!(check_parse("", &mut [""]));
@ -1042,11 +1073,12 @@ mod tests {
assert!(check_parse(";;", &mut ["", "", ""]));
assert!(check_parse(r"c:\", &mut [r"c:\"]));
assert!(check_parse(r"c:\;", &mut [r"c:\", ""]));
assert!(check_parse(r"c:\;c:\Program Files\",
&mut [r"c:\", r"c:\Program Files\"]));
assert!(check_parse(r"c:\;c:\Program Files\", &mut [r"c:\", r"c:\Program Files\"]));
assert!(check_parse(r#"c:\;c:\"foo"\"#, &mut [r"c:\", r"c:\foo\"]));
assert!(check_parse(r#"c:\;c:\"foo;bar"\;c:\baz"#,
&mut [r"c:\", r"c:\foo;bar\", r"c:\baz"]));
assert!(check_parse(
r#"c:\;c:\"foo;bar"\;c:\baz"#,
&mut [r"c:\", r"c:\foo;bar\", r"c:\baz"]
));
}
#[test]
@ -1055,8 +1087,8 @@ mod tests {
use crate::path::PathBuf;
fn check_parse(unparsed: &str, parsed: &[&str]) -> bool {
split_paths(unparsed).collect::<Vec<_>>() ==
parsed.iter().map(|s| PathBuf::from(*s)).collect::<Vec<_>>()
split_paths(unparsed).collect::<Vec<_>>()
== parsed.iter().map(|s| PathBuf::from(*s)).collect::<Vec<_>>()
}
assert!(check_parse("", &mut [""]));
@ -1072,15 +1104,12 @@ mod tests {
use crate::ffi::OsStr;
fn test_eq(input: &[&str], output: &str) -> bool {
&*join_paths(input.iter().cloned()).unwrap() ==
OsStr::new(output)
&*join_paths(input.iter().cloned()).unwrap() == OsStr::new(output)
}
assert!(test_eq(&[], ""));
assert!(test_eq(&["/bin", "/usr/bin", "/usr/local/bin"],
"/bin:/usr/bin:/usr/local/bin"));
assert!(test_eq(&["", "/bin", "", "", "/usr/bin", ""],
":/bin:::/usr/bin:"));
assert!(test_eq(&["/bin", "/usr/bin", "/usr/local/bin"], "/bin:/usr/bin:/usr/local/bin"));
assert!(test_eq(&["", "/bin", "", "", "/usr/bin", ""], ":/bin:::/usr/bin:"));
assert!(join_paths(["/te:st"].iter().cloned()).is_err());
}
@ -1090,17 +1119,13 @@ mod tests {
use crate::ffi::OsStr;
fn test_eq(input: &[&str], output: &str) -> bool {
&*join_paths(input.iter().cloned()).unwrap() ==
OsStr::new(output)
&*join_paths(input.iter().cloned()).unwrap() == OsStr::new(output)
}
assert!(test_eq(&[], ""));
assert!(test_eq(&[r"c:\windows", r"c:\"],
r"c:\windows;c:\"));
assert!(test_eq(&["", r"c:\windows", "", "", r"c:\", ""],
r";c:\windows;;;c:\;"));
assert!(test_eq(&[r"c:\te;st", r"c:\"],
r#""c:\te;st";c:\"#));
assert!(test_eq(&[r"c:\windows", r"c:\"], r"c:\windows;c:\"));
assert!(test_eq(&["", r"c:\windows", "", "", r"c:\", ""], r";c:\windows;;;c:\;"));
assert!(test_eq(&[r"c:\te;st", r"c:\"], r#""c:\te;st";c:\"#));
assert!(join_paths([r#"c:\te"st"#].iter().cloned()).is_err());
}
@ -1108,9 +1133,11 @@ mod tests {
fn args_debug() {
assert_eq!(
format!("Args {{ inner: {:?} }}", args().collect::<Vec<_>>()),
format!("{:?}", args()));
format!("{:?}", args())
);
assert_eq!(
format!("ArgsOs {{ inner: {:?} }}", args_os().collect::<Vec<_>>()),
format!("{:?}", args_os()));
format!("{:?}", args_os())
);
}
}

View file

@ -13,16 +13,16 @@ use crate::intrinsics;
#[cfg(not(test))]
use crate::sys::cmath;
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{RADIX, MANTISSA_DIGITS, DIGITS, EPSILON};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{MIN_EXP, MAX_EXP, MIN_10_EXP};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{MAX_10_EXP, NAN, INFINITY, NEG_INFINITY};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{MIN, MIN_POSITIVE, MAX};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::consts;
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{DIGITS, EPSILON, MANTISSA_DIGITS, RADIX};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{INFINITY, MAX_10_EXP, NAN, NEG_INFINITY};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{MAX, MIN, MIN_POSITIVE};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f32::{MAX_EXP, MIN_10_EXP, MIN_EXP};
#[cfg(not(test))]
#[lang = "f32_runtime"]
@ -142,7 +142,9 @@ impl f32 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn fract(self) -> f32 { self - self.trunc() }
pub fn fract(self) -> f32 {
self - self.trunc()
}
/// Computes the absolute value of `self`. Returns `NAN` if the
/// number is `NAN`.
@ -192,11 +194,7 @@ impl f32 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn signum(self) -> f32 {
if self.is_nan() {
NAN
} else {
1.0_f32.copysign(self)
}
if self.is_nan() { NAN } else { 1.0_f32.copysign(self) }
}
/// Returns a number composed of the magnitude of `self` and the sign of
@ -277,7 +275,7 @@ impl f32 {
pub fn div_euclid(self, rhs: f32) -> f32 {
let q = (self / rhs).trunc();
if self % rhs < 0.0 {
return if rhs > 0.0 { q - 1.0 } else { q + 1.0 }
return if rhs > 0.0 { q - 1.0 } else { q + 1.0 };
}
q
}
@ -310,13 +308,8 @@ impl f32 {
#[stable(feature = "euclidean_division", since = "1.38.0")]
pub fn rem_euclid(self, rhs: f32) -> f32 {
let r = self % rhs;
if r < 0.0 {
r + rhs.abs()
} else {
r
if r < 0.0 { r + rhs.abs() } else { r }
}
}
/// Raises a number to an integer power.
///
@ -383,11 +376,7 @@ impl f32 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn sqrt(self) -> f32 {
if self < 0.0 {
NAN
} else {
unsafe { intrinsics::sqrtf32(self) }
}
if self < 0.0 { NAN } else { unsafe { intrinsics::sqrtf32(self) } }
}
/// Returns `e^(self)`, (the exponential function).
@ -486,7 +475,9 @@ impl f32 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn log(self, base: f32) -> f32 { self.ln() / base.ln() }
pub fn log(self, base: f32) -> f32 {
self.ln() / base.ln()
}
/// Returns the base 2 logarithm of the number.
///
@ -559,14 +550,16 @@ impl f32 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
#[rustc_deprecated(since = "1.10.0",
#[rustc_deprecated(
since = "1.10.0",
reason = "you probably meant `(self - other).abs()`: \
this operation is `(self - other).max(0.0)` \
except that `abs_sub` also propagates NaNs (also \
known as `fdimf` in C). If you truly need the positive \
difference, consider using that expression or the C function \
`fdimf`, depending on how you wish to handle NaN (please consider \
filing an issue describing your use-case too).")]
filing an issue describing your use-case too)."
)]
pub fn abs_sub(self, other: f32) -> f32 {
unsafe { cmath::fdimf(self, other) }
}
@ -967,11 +960,7 @@ impl f32 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn acosh(self) -> f32 {
if self < 1.0 {
crate::f32::NAN
} else {
(self + ((self * self) - 1.0).sqrt()).ln()
}
if self < 1.0 { crate::f32::NAN } else { (self + ((self * self) - 1.0).sqrt()).ln() }
}
/// Inverse hyperbolic tangent function.
@ -1022,19 +1011,22 @@ impl f32 {
pub fn clamp(self, min: f32, max: f32) -> f32 {
assert!(min <= max);
let mut x = self;
if x < min { x = min; }
if x > max { x = max; }
if x < min {
x = min;
}
if x > max {
x = max;
}
x
}
}
#[cfg(test)]
mod tests {
use crate::f32;
use crate::f32::*;
use crate::num::*;
use crate::num::FpCategory as Fp;
use crate::num::*;
#[test]
fn test_num_f32() {
@ -1279,7 +1271,7 @@ mod tests {
assert_eq!((-0f32).abs(), 0f32);
assert_eq!((-1f32).abs(), 1f32);
assert_eq!(NEG_INFINITY.abs(), INFINITY);
assert_eq!((1f32/NEG_INFINITY).abs(), 0f32);
assert_eq!((1f32 / NEG_INFINITY).abs(), 0f32);
assert!(NAN.abs().is_nan());
}
@ -1291,7 +1283,7 @@ mod tests {
assert_eq!((-0f32).signum(), -1f32);
assert_eq!((-1f32).signum(), -1f32);
assert_eq!(NEG_INFINITY.signum(), -1f32);
assert_eq!((1f32/NEG_INFINITY).signum(), -1f32);
assert_eq!((1f32 / NEG_INFINITY).signum(), -1f32);
assert!(NAN.signum().is_nan());
}
@ -1303,7 +1295,7 @@ mod tests {
assert!(!(-0f32).is_sign_positive());
assert!(!(-1f32).is_sign_positive());
assert!(!NEG_INFINITY.is_sign_positive());
assert!(!(1f32/NEG_INFINITY).is_sign_positive());
assert!(!(1f32 / NEG_INFINITY).is_sign_positive());
assert!(NAN.is_sign_positive());
assert!(!(-NAN).is_sign_positive());
}
@ -1316,7 +1308,7 @@ mod tests {
assert!((-0f32).is_sign_negative());
assert!((-1f32).is_sign_negative());
assert!(NEG_INFINITY.is_sign_negative());
assert!((1f32/NEG_INFINITY).is_sign_negative());
assert!((1f32 / NEG_INFINITY).is_sign_negative());
assert!(!NAN.is_sign_negative());
assert!((-NAN).is_sign_negative());
}

View file

@ -13,16 +13,16 @@ use crate::intrinsics;
#[cfg(not(test))]
use crate::sys::cmath;
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{RADIX, MANTISSA_DIGITS, DIGITS, EPSILON};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{MIN_EXP, MAX_EXP, MIN_10_EXP};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{MAX_10_EXP, NAN, INFINITY, NEG_INFINITY};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{MIN, MIN_POSITIVE, MAX};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::consts;
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{DIGITS, EPSILON, MANTISSA_DIGITS, RADIX};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{INFINITY, MAX_10_EXP, NAN, NEG_INFINITY};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{MAX, MIN, MIN_POSITIVE};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::f64::{MAX_EXP, MIN_10_EXP, MIN_EXP};
#[cfg(not(test))]
#[lang = "f64_runtime"]
@ -120,7 +120,9 @@ impl f64 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn fract(self) -> f64 { self - self.trunc() }
pub fn fract(self) -> f64 {
self - self.trunc()
}
/// Computes the absolute value of `self`. Returns `NAN` if the
/// number is `NAN`.
@ -170,11 +172,7 @@ impl f64 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn signum(self) -> f64 {
if self.is_nan() {
NAN
} else {
1.0_f64.copysign(self)
}
if self.is_nan() { NAN } else { 1.0_f64.copysign(self) }
}
/// Returns a number composed of the magnitude of `self` and the sign of
@ -286,11 +284,7 @@ impl f64 {
#[stable(feature = "euclidean_division", since = "1.38.0")]
pub fn rem_euclid(self, rhs: f64) -> f64 {
let r = self % rhs;
if r < 0.0 {
r + rhs.abs()
} else {
r
}
if r < 0.0 { r + rhs.abs() } else { r }
}
/// Raises a number to an integer power.
@ -348,11 +342,7 @@ impl f64 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn sqrt(self) -> f64 {
if self < 0.0 {
NAN
} else {
unsafe { intrinsics::sqrtf64(self) }
}
if self < 0.0 { NAN } else { unsafe { intrinsics::sqrtf64(self) } }
}
/// Returns `e^(self)`, (the exponential function).
@ -413,7 +403,7 @@ impl f64 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn ln(self) -> f64 {
self.log_wrapper(|n| { unsafe { intrinsics::logf64(n) } })
self.log_wrapper(|n| unsafe { intrinsics::logf64(n) })
}
/// Returns the logarithm of the number with respect to an arbitrary base.
@ -435,7 +425,9 @@ impl f64 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn log(self, base: f64) -> f64 { self.ln() / base.ln() }
pub fn log(self, base: f64) -> f64 {
self.ln() / base.ln()
}
/// Returns the base 2 logarithm of the number.
///
@ -477,7 +469,7 @@ impl f64 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn log10(self) -> f64 {
self.log_wrapper(|n| { unsafe { intrinsics::log10f64(n) } })
self.log_wrapper(|n| unsafe { intrinsics::log10f64(n) })
}
/// The positive difference of two numbers.
@ -500,14 +492,16 @@ impl f64 {
#[must_use = "method returns a new number and does not mutate the original value"]
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
#[rustc_deprecated(since = "1.10.0",
#[rustc_deprecated(
since = "1.10.0",
reason = "you probably meant `(self - other).abs()`: \
this operation is `(self - other).max(0.0)` \
except that `abs_sub` also propagates NaNs (also \
known as `fdim` in C). If you truly need the positive \
difference, consider using that expression or the C function \
`fdim`, depending on how you wish to handle NaN (please consider \
filing an issue describing your use-case too).")]
filing an issue describing your use-case too)."
)]
pub fn abs_sub(self, other: f64) -> f64 {
unsafe { cmath::fdim(self, other) }
}
@ -888,11 +882,7 @@ impl f64 {
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub fn acosh(self) -> f64 {
if self < 1.0 {
NAN
} else {
(self + ((self * self) - 1.0).sqrt()).ln()
}
if self < 1.0 { NAN } else { (self + ((self * self) - 1.0).sqrt()).ln() }
}
/// Inverse hyperbolic tangent function.
@ -943,8 +933,12 @@ impl f64 {
pub fn clamp(self, min: f64, max: f64) -> f64 {
assert!(min <= max);
let mut x = self;
if x < min { x = min; }
if x > max { x = max; }
if x < min {
x = min;
}
if x > max {
x = max;
}
x
}
@ -978,8 +972,8 @@ impl f64 {
mod tests {
use crate::f64;
use crate::f64::*;
use crate::num::*;
use crate::num::FpCategory as Fp;
use crate::num::*;
#[test]
fn test_num_f64() {

View file

@ -155,21 +155,23 @@
#![stable(feature = "rust1", since = "1.0.0")]
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::c_str::{CString, CStr, NulError, IntoStringError};
#[stable(feature = "cstr_from_bytes", since = "1.10.0")]
pub use self::c_str::{FromBytesWithNulError};
pub use self::c_str::FromBytesWithNulError;
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::c_str::{CStr, CString, IntoStringError, NulError};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::os_str::{OsString, OsStr};
pub use self::os_str::{OsStr, OsString};
#[stable(feature = "core_c_void", since = "1.30.0")]
pub use core::ffi::c_void;
#[unstable(feature = "c_variadic",
#[unstable(
feature = "c_variadic",
reason = "the `c_variadic` feature has not been properly tested on \
all supported platforms",
issue = "44930")]
issue = "44930"
)]
pub use core::ffi::{VaList, VaListImpl};
mod c_str;

View file

@ -9,12 +9,12 @@
#![stable(feature = "rust1", since = "1.0.0")]
use crate::fmt;
use crate::ffi::OsString;
use crate::io::{self, SeekFrom, Seek, Read, Initializer, Write, IoSlice, IoSliceMut};
use crate::fmt;
use crate::io::{self, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write};
use crate::path::{Path, PathBuf};
use crate::sys::fs as fs_imp;
use crate::sys_common::{AsInnerMut, FromInner, AsInner, IntoInner};
use crate::sys_common::{AsInner, AsInnerMut, FromInner, IntoInner};
use crate::time::SystemTime;
/// A reference to an open file on the filesystem.
@ -585,9 +585,7 @@ impl File {
/// ```
#[stable(feature = "file_try_clone", since = "1.9.0")]
pub fn try_clone(&self) -> io::Result<File> {
Ok(File {
inner: self.inner.duplicate()?
})
Ok(File { inner: self.inner.duplicate()? })
}
/// Changes the permissions on the underlying file.
@ -629,7 +627,9 @@ impl File {
}
impl AsInner<fs_imp::File> for File {
fn as_inner(&self) -> &fs_imp::File { &self.inner }
fn as_inner(&self) -> &fs_imp::File {
&self.inner
}
}
impl FromInner<fs_imp::File> for File {
fn from_inner(f: fs_imp::File) -> File {
@ -674,7 +674,9 @@ impl Write for File {
self.inner.write_vectored(bufs)
}
fn flush(&mut self) -> io::Result<()> { self.inner.flush() }
fn flush(&mut self) -> io::Result<()> {
self.inner.flush()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Seek for File {
@ -707,7 +709,9 @@ impl Write for &File {
self.inner.write_vectored(bufs)
}
fn flush(&mut self) -> io::Result<()> { self.inner.flush() }
fn flush(&mut self) -> io::Result<()> {
self.inner.flush()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Seek for &File {
@ -748,7 +752,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn read(&mut self, read: bool) -> &mut OpenOptions {
self.0.read(read); self
self.0.read(read);
self
}
/// Sets the option for write access.
@ -768,7 +773,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn write(&mut self, write: bool) -> &mut OpenOptions {
self.0.write(write); self
self.0.write(write);
self
}
/// Sets the option for the append mode.
@ -814,7 +820,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn append(&mut self, append: bool) -> &mut OpenOptions {
self.0.append(append); self
self.0.append(append);
self
}
/// Sets the option for truncating a previous file.
@ -833,7 +840,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn truncate(&mut self, truncate: bool) -> &mut OpenOptions {
self.0.truncate(truncate); self
self.0.truncate(truncate);
self
}
/// Sets the option for creating a new file.
@ -856,7 +864,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn create(&mut self, create: bool) -> &mut OpenOptions {
self.0.create(create); self
self.0.create(create);
self
}
/// Sets the option to always create a new file.
@ -889,7 +898,8 @@ impl OpenOptions {
/// ```
#[stable(feature = "expand_open_options2", since = "1.9.0")]
pub fn create_new(&mut self, create_new: bool) -> &mut OpenOptions {
self.0.create_new(create_new); self
self.0.create_new(create_new);
self
}
/// Opens a file at `path` with the options specified by `self`.
@ -946,11 +956,15 @@ impl OpenOptions {
}
impl AsInner<fs_imp::OpenOptions> for OpenOptions {
fn as_inner(&self) -> &fs_imp::OpenOptions { &self.0 }
fn as_inner(&self) -> &fs_imp::OpenOptions {
&self.0
}
}
impl AsInnerMut<fs_imp::OpenOptions> for OpenOptions {
fn as_inner_mut(&mut self) -> &mut fs_imp::OpenOptions { &mut self.0 }
fn as_inner_mut(&mut self) -> &mut fs_imp::OpenOptions {
&mut self.0
}
}
impl Metadata {
@ -994,7 +1008,9 @@ impl Metadata {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn is_dir(&self) -> bool { self.file_type().is_dir() }
pub fn is_dir(&self) -> bool {
self.file_type().is_dir()
}
/// Returns `true` if this metadata is for a regular file. The
/// result is mutually exclusive to the result of
@ -1017,7 +1033,9 @@ impl Metadata {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn is_file(&self) -> bool { self.file_type().is_file() }
pub fn is_file(&self) -> bool {
self.file_type().is_file()
}
/// Returns the size of the file, in bytes, this metadata is for.
///
@ -1034,7 +1052,9 @@ impl Metadata {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn len(&self) -> u64 { self.0.size() }
pub fn len(&self) -> u64 {
self.0.size()
}
/// Returns the permissions of the file this metadata is for.
///
@ -1170,11 +1190,15 @@ impl fmt::Debug for Metadata {
}
impl AsInner<fs_imp::FileAttr> for Metadata {
fn as_inner(&self) -> &fs_imp::FileAttr { &self.0 }
fn as_inner(&self) -> &fs_imp::FileAttr {
&self.0
}
}
impl FromInner<fs_imp::FileAttr> for Metadata {
fn from_inner(attr: fs_imp::FileAttr) -> Metadata { Metadata(attr) }
fn from_inner(attr: fs_imp::FileAttr) -> Metadata {
Metadata(attr)
}
}
impl Permissions {
@ -1194,7 +1218,9 @@ impl Permissions {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn readonly(&self) -> bool { self.0.readonly() }
pub fn readonly(&self) -> bool {
self.0.readonly()
}
/// Modifies the readonly flag for this set of permissions. If the
/// `readonly` argument is `true`, using the resulting `Permission` will
@ -1256,7 +1282,9 @@ impl FileType {
/// }
/// ```
#[stable(feature = "file_type", since = "1.1.0")]
pub fn is_dir(&self) -> bool { self.0.is_dir() }
pub fn is_dir(&self) -> bool {
self.0.is_dir()
}
/// Tests whether this file type represents a regular file.
/// The result is mutually exclusive to the results of
@ -1280,7 +1308,9 @@ impl FileType {
/// }
/// ```
#[stable(feature = "file_type", since = "1.1.0")]
pub fn is_file(&self) -> bool { self.0.is_file() }
pub fn is_file(&self) -> bool {
self.0.is_file()
}
/// Tests whether this file type represents a symbolic link.
/// The result is mutually exclusive to the results of
@ -1314,11 +1344,15 @@ impl FileType {
/// }
/// ```
#[stable(feature = "file_type", since = "1.1.0")]
pub fn is_symlink(&self) -> bool { self.0.is_symlink() }
pub fn is_symlink(&self) -> bool {
self.0.is_symlink()
}
}
impl AsInner<fs_imp::FileType> for FileType {
fn as_inner(&self) -> &fs_imp::FileType { &self.0 }
fn as_inner(&self) -> &fs_imp::FileType {
&self.0
}
}
impl FromInner<fs_imp::FilePermissions> for Permissions {
@ -1328,7 +1362,9 @@ impl FromInner<fs_imp::FilePermissions> for Permissions {
}
impl AsInner<fs_imp::FilePermissions> for Permissions {
fn as_inner(&self) -> &fs_imp::FilePermissions { &self.0 }
fn as_inner(&self) -> &fs_imp::FilePermissions {
&self.0
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1370,7 +1406,9 @@ impl DirEntry {
///
/// The exact text, of course, depends on what files you have in `.`.
#[stable(feature = "rust1", since = "1.0.0")]
pub fn path(&self) -> PathBuf { self.0.path() }
pub fn path(&self) -> PathBuf {
self.0.path()
}
/// Returns the metadata for the file that this entry points at.
///
@ -1468,14 +1506,14 @@ impl DirEntry {
#[stable(feature = "dir_entry_debug", since = "1.13.0")]
impl fmt::Debug for DirEntry {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_tuple("DirEntry")
.field(&self.path())
.finish()
f.debug_tuple("DirEntry").field(&self.path()).finish()
}
}
impl AsInner<fs_imp::DirEntry> for DirEntry {
fn as_inner(&self) -> &fs_imp::DirEntry { &self.0 }
fn as_inner(&self) -> &fs_imp::DirEntry {
&self.0
}
}
/// Removes a file from the filesystem.
@ -1744,9 +1782,11 @@ pub fn hard_link<P: AsRef<Path>, Q: AsRef<Path>>(src: P, dst: Q) -> io::Result<(
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
#[rustc_deprecated(since = "1.1.0",
#[rustc_deprecated(
since = "1.1.0",
reason = "replaced with std::os::unix::fs::symlink and \
std::os::windows::fs::{symlink_file, symlink_dir}")]
std::os::windows::fs::{symlink_file, symlink_dir}"
)]
pub fn soft_link<P: AsRef<Path>, Q: AsRef<Path>>(src: P, dst: Q) -> io::Result<()> {
fs_imp::symlink(src.as_ref(), dst.as_ref())
}
@ -2089,8 +2129,7 @@ pub fn read_dir<P: AsRef<Path>>(path: P) -> io::Result<ReadDir> {
/// }
/// ```
#[stable(feature = "set_permissions", since = "1.1.0")]
pub fn set_permissions<P: AsRef<Path>>(path: P, perm: Permissions)
-> io::Result<()> {
pub fn set_permissions<P: AsRef<Path>>(path: P, perm: Permissions) -> io::Result<()> {
fs_imp::set_perm(path.as_ref(), perm.0)
}
@ -2107,10 +2146,7 @@ impl DirBuilder {
/// ```
#[stable(feature = "dir_builder", since = "1.6.0")]
pub fn new() -> DirBuilder {
DirBuilder {
inner: fs_imp::DirBuilder::new(),
recursive: false,
}
DirBuilder { inner: fs_imp::DirBuilder::new(), recursive: false }
}
/// Indicates that directories should be created recursively, creating all
@ -2157,16 +2193,12 @@ impl DirBuilder {
}
fn _create(&self, path: &Path) -> io::Result<()> {
if self.recursive {
self.create_dir_all(path)
} else {
self.inner.mkdir(path)
}
if self.recursive { self.create_dir_all(path) } else { self.inner.mkdir(path) }
}
fn create_dir_all(&self, path: &Path) -> io::Result<()> {
if path == Path::new("") {
return Ok(())
return Ok(());
}
match self.inner.mkdir(path) {
@ -2177,7 +2209,9 @@ impl DirBuilder {
}
match path.parent() {
Some(p) => self.create_dir_all(p)?,
None => return Err(io::Error::new(io::ErrorKind::Other, "failed to create whole tree")),
None => {
return Err(io::Error::new(io::ErrorKind::Other, "failed to create whole tree"));
}
}
match self.inner.mkdir(path) {
Ok(()) => Ok(()),
@ -2201,48 +2235,62 @@ mod tests {
use crate::io::{ErrorKind, SeekFrom};
use crate::path::Path;
use crate::str;
use crate::sys_common::io::test::{TempDir, tmpdir};
use crate::sys_common::io::test::{tmpdir, TempDir};
use crate::thread;
use rand::{rngs::StdRng, RngCore, SeedableRng};
#[cfg(windows)]
use crate::os::windows::fs::{symlink_dir, symlink_file};
#[cfg(windows)]
use crate::sys::fs::symlink_junction;
#[cfg(unix)]
use crate::os::unix::fs::symlink as symlink_dir;
#[cfg(unix)]
use crate::os::unix::fs::symlink as symlink_file;
#[cfg(unix)]
use crate::os::unix::fs::symlink as symlink_junction;
#[cfg(windows)]
use crate::os::windows::fs::{symlink_dir, symlink_file};
#[cfg(windows)]
use crate::sys::fs::symlink_junction;
macro_rules! check { ($e:expr) => (
macro_rules! check {
($e:expr) => {
match $e {
Ok(t) => t,
Err(e) => panic!("{} failed with: {}", stringify!($e), e),
}
) }
};
}
#[cfg(windows)]
macro_rules! error { ($e:expr, $s:expr) => (
macro_rules! error {
($e:expr, $s:expr) => {
match $e {
Ok(_) => panic!("Unexpected success. Should've been: {:?}", $s),
Err(ref err) => assert!(err.raw_os_error() == Some($s),
format!("`{}` did not have a code of `{}`", err, $s))
Err(ref err) => assert!(
err.raw_os_error() == Some($s),
format!("`{}` did not have a code of `{}`", err, $s)
),
}
};
}
) }
#[cfg(unix)]
macro_rules! error { ($e:expr, $s:expr) => ( error_contains!($e, $s) ) }
macro_rules! error {
($e:expr, $s:expr) => {
error_contains!($e, $s)
};
}
macro_rules! error_contains { ($e:expr, $s:expr) => (
macro_rules! error_contains {
($e:expr, $s:expr) => {
match $e {
Ok(_) => panic!("Unexpected success. Should've been: {:?}", $s),
Err(ref err) => assert!(err.to_string().contains($s),
format!("`{}` did not contain `{}`", err, $s))
Err(ref err) => assert!(
err.to_string().contains($s),
format!("`{}` did not contain `{}`", err, $s)
),
}
};
}
) }
// Several test fail on windows if the user does not have permission to
// create symlinks (the `SeCreateSymbolicLinkPrivilege`). Instead of
@ -2251,7 +2299,9 @@ mod tests {
// tests most of the time, but at least we do if the user has the right
// permissions.
pub fn got_symlink_permission(tmpdir: &TempDir) -> bool {
if cfg!(unix) { return true }
if cfg!(unix) {
return true;
}
let link = tmpdir.join("some_hopefully_unique_link_name");
match symlink_file(r"nonexisting_target", link) {
@ -2276,7 +2326,7 @@ mod tests {
let mut read_buf = [0; 1028];
let read_str = match check!(read_stream.read(&mut read_buf)) {
0 => panic!("shouldn't happen"),
n => str::from_utf8(&read_buf[..n]).unwrap().to_string()
n => str::from_utf8(&read_buf[..n]).unwrap().to_string(),
};
assert_eq!(read_str, message);
}
@ -2497,13 +2547,11 @@ mod tests {
check!(fs::create_dir(filename));
let mask = 0o7777;
check!(fs::set_permissions(filename,
fs::Permissions::from_mode(0)));
check!(fs::set_permissions(filename, fs::Permissions::from_mode(0)));
let metadata0 = check!(fs::metadata(filename));
assert_eq!(mask & metadata0.permissions().mode(), 0);
check!(fs::set_permissions(filename,
fs::Permissions::from_mode(0o1777)));
check!(fs::set_permissions(filename, fs::Permissions::from_mode(0o1777)));
let metadata1 = check!(fs::metadata(filename));
assert_eq!(mask & metadata1.permissions().mode(), 0o1777);
}
@ -2568,8 +2616,7 @@ mod tests {
let filename = &tmpdir.join("file_stat_correct_on_is_file.txt");
{
let mut opts = OpenOptions::new();
let mut fs = check!(opts.read(true).write(true)
.create(true).open(filename));
let mut fs = check!(opts.read(true).write(true).create(true).open(filename));
let msg = "hw";
fs.write(msg.as_bytes()).unwrap();
@ -2703,7 +2750,7 @@ mod tests {
for _ in 0..40 {
dir = dir.join("a");
}
let mut join = vec!();
let mut join = vec![];
for _ in 0..8 {
let dir = dir.clone();
join.push(thread::spawn(move || {
@ -2771,7 +2818,9 @@ mod tests {
#[cfg(windows)]
fn recursive_rmdir_of_file_symlink() {
let tmpdir = tmpdir();
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
let f1 = tmpdir.join("f1");
let f2 = tmpdir.join("f2");
@ -2854,8 +2903,7 @@ mod tests {
check!(check!(File::open(&out)).read_to_end(&mut v));
assert_eq!(v, b"hello");
assert_eq!(check!(input.metadata()).permissions(),
check!(out.metadata()).permissions());
assert_eq!(check!(input.metadata()).permissions(), check!(out.metadata()).permissions());
}
#[test]
@ -2865,7 +2913,8 @@ mod tests {
check!(File::create(&out));
match fs::copy(&*out, tmpdir.path()) {
Ok(..) => panic!(), Err(..) => {}
Ok(..) => panic!(),
Err(..) => {}
}
}
@ -2890,7 +2939,8 @@ mod tests {
let out = tmpdir.join("out");
match fs::copy(tmpdir.path(), &out) {
Ok(..) => panic!(), Err(..) => {}
Ok(..) => panic!(),
Err(..) => {}
}
assert!(!out.exists());
}
@ -2938,7 +2988,9 @@ mod tests {
#[test]
fn copy_file_follows_dst_symlink() {
let tmp = tmpdir();
if !got_symlink_permission(&tmp) { return };
if !got_symlink_permission(&tmp) {
return;
};
let in_path = tmp.join("in.txt");
let out_path = tmp.join("out.txt");
@ -2958,7 +3010,9 @@ mod tests {
#[test]
fn symlinks_work() {
let tmpdir = tmpdir();
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
let input = tmpdir.join("in.txt");
let out = tmpdir.join("out.txt");
@ -2966,8 +3020,7 @@ mod tests {
check!(check!(File::create(&input)).write("foobar".as_bytes()));
check!(symlink_file(&input, &out));
assert!(check!(out.symlink_metadata()).file_type().is_symlink());
assert_eq!(check!(fs::metadata(&out)).len(),
check!(fs::metadata(&input)).len());
assert_eq!(check!(fs::metadata(&out)).len(), check!(fs::metadata(&input)).len());
let mut v = Vec::new();
check!(check!(File::open(&out)).read_to_end(&mut v));
assert_eq!(v, b"foobar".to_vec());
@ -2977,31 +3030,40 @@ mod tests {
fn symlink_noexist() {
// Symlinks can point to things that don't exist
let tmpdir = tmpdir();
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
// Use a relative path for testing. Symlinks get normalized by Windows,
// so we may not get the same path back for absolute paths
check!(symlink_file(&"foo", &tmpdir.join("bar")));
assert_eq!(check!(fs::read_link(&tmpdir.join("bar"))).to_str().unwrap(),
"foo");
assert_eq!(check!(fs::read_link(&tmpdir.join("bar"))).to_str().unwrap(), "foo");
}
#[test]
fn read_link() {
if cfg!(windows) {
// directory symlink
assert_eq!(check!(fs::read_link(r"C:\Users\All Users")).to_str().unwrap(),
r"C:\ProgramData");
assert_eq!(
check!(fs::read_link(r"C:\Users\All Users")).to_str().unwrap(),
r"C:\ProgramData"
);
// junction
assert_eq!(check!(fs::read_link(r"C:\Users\Default User")).to_str().unwrap(),
r"C:\Users\Default");
assert_eq!(
check!(fs::read_link(r"C:\Users\Default User")).to_str().unwrap(),
r"C:\Users\Default"
);
// junction with special permissions
assert_eq!(check!(fs::read_link(r"C:\Documents and Settings\")).to_str().unwrap(),
r"C:\Users");
assert_eq!(
check!(fs::read_link(r"C:\Documents and Settings\")).to_str().unwrap(),
r"C:\Users"
);
}
let tmpdir = tmpdir();
let link = tmpdir.join("link");
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
check!(symlink_file(&"foo", &link));
assert_eq!(check!(fs::read_link(&link)).to_str().unwrap(), "foo");
}
@ -3023,10 +3085,8 @@ mod tests {
check!(check!(File::create(&input)).write("foobar".as_bytes()));
check!(fs::hard_link(&input, &out));
assert_eq!(check!(fs::metadata(&out)).len(),
check!(fs::metadata(&input)).len());
assert_eq!(check!(fs::metadata(&out)).len(),
check!(input.metadata()).len());
assert_eq!(check!(fs::metadata(&out)).len(), check!(fs::metadata(&input)).len());
assert_eq!(check!(fs::metadata(&out)).len(), check!(input.metadata()).len());
let mut v = Vec::new();
check!(check!(File::open(&out)).read_to_end(&mut v));
assert_eq!(v, b"foobar".to_vec());
@ -3134,15 +3194,22 @@ mod tests {
#[test]
fn open_flavors() {
use crate::fs::OpenOptions as OO;
fn c<T: Clone>(t: &T) -> T { t.clone() }
fn c<T: Clone>(t: &T) -> T {
t.clone()
}
let tmpdir = tmpdir();
let mut r = OO::new(); r.read(true);
let mut w = OO::new(); w.write(true);
let mut rw = OO::new(); rw.read(true).write(true);
let mut a = OO::new(); a.append(true);
let mut ra = OO::new(); ra.read(true).append(true);
let mut r = OO::new();
r.read(true);
let mut w = OO::new();
w.write(true);
let mut rw = OO::new();
rw.read(true).write(true);
let mut a = OO::new();
a.append(true);
let mut ra = OO::new();
ra.read(true).append(true);
#[cfg(windows)]
let invalid_options = 87; // ERROR_INVALID_PARAMETER
@ -3279,8 +3346,10 @@ mod tests {
assert!(v == &bytes[..]);
check!(fs::write(&tmpdir.join("not-utf8"), &[0xFF]));
error_contains!(fs::read_to_string(&tmpdir.join("not-utf8")),
"stream did not contain valid UTF-8");
error_contains!(
fs::read_to_string(&tmpdir.join("not-utf8")),
"stream did not contain valid UTF-8"
);
let s = "𐁁𐀓𐀠𐀴𐀍";
check!(fs::write(&tmpdir.join("utf8"), s.as_bytes()));
@ -3292,11 +3361,9 @@ mod tests {
fn file_try_clone() {
let tmpdir = tmpdir();
let mut f1 = check!(OpenOptions::new()
.read(true)
.write(true)
.create(true)
.open(&tmpdir.join("test")));
let mut f1 = check!(
OpenOptions::new().read(true).write(true).create(true).open(&tmpdir.join("test"))
);
let mut f2 = check!(f1.try_clone());
check!(f1.write_all(b"hello world"));
@ -3341,7 +3408,9 @@ mod tests {
#[test]
fn realpath_works() {
let tmpdir = tmpdir();
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
let tmpdir = fs::canonicalize(tmpdir.path()).unwrap();
let file = tmpdir.join("test");
@ -3366,7 +3435,9 @@ mod tests {
#[test]
fn realpath_works_tricky() {
let tmpdir = tmpdir();
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
let tmpdir = fs::canonicalize(tmpdir.path()).unwrap();
let a = tmpdir.join("a");
@ -3452,7 +3523,9 @@ mod tests {
assert!(junction.is_dir());
assert!(b.exists());
if !got_symlink_permission(&tmpdir) { return };
if !got_symlink_permission(&tmpdir) {
return;
};
check!(symlink_dir(&target, &link));
check!(fs::create_dir_all(&d));
assert!(link.is_dir());
@ -3482,8 +3555,8 @@ mod tests {
// Not always available
match (a.created(), b.created()) {
(Ok(t1), Ok(t2)) => assert!(t1 <= t2),
(Err(e1), Err(e2)) if e1.kind() == ErrorKind::Other &&
e2.kind() == ErrorKind::Other => {}
(Err(e1), Err(e2))
if e1.kind() == ErrorKind::Other && e2.kind() == ErrorKind::Other => {}
(a, b) => panic!(
"creation time must be always supported or not supported: {:?} {:?}",
a, b,

View file

@ -5,8 +5,9 @@ use crate::io::prelude::*;
use crate::cmp;
use crate::error;
use crate::fmt;
use crate::io::{self, Initializer, DEFAULT_BUF_SIZE, Error, ErrorKind, SeekFrom, IoSlice,
IoSliceMut};
use crate::io::{
self, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, SeekFrom, DEFAULT_BUF_SIZE,
};
use crate::memchr;
/// The `BufReader<R>` struct adds buffering to any reader.
@ -100,12 +101,7 @@ impl<R: Read> BufReader<R> {
let mut buffer = Vec::with_capacity(capacity);
buffer.set_len(capacity);
inner.initializer().initialize(&mut buffer);
BufReader {
inner,
buf: buffer.into_boxed_slice(),
pos: 0,
cap: 0,
}
BufReader { inner, buf: buffer.into_boxed_slice(), pos: 0, cap: 0 }
}
}
}
@ -130,7 +126,9 @@ impl<R> BufReader<R> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_ref(&self) -> &R { &self.inner }
pub fn get_ref(&self) -> &R {
&self.inner
}
/// Gets a mutable reference to the underlying reader.
///
@ -151,7 +149,9 @@ impl<R> BufReader<R> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_mut(&mut self) -> &mut R { &mut self.inner }
pub fn get_mut(&mut self) -> &mut R {
&mut self.inner
}
/// Returns a reference to the internally buffered data.
///
@ -199,7 +199,9 @@ impl<R> BufReader<R> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn into_inner(self) -> R { self.inner }
pub fn into_inner(self) -> R {
self.inner
}
/// Invalidates all data in the internal buffer.
#[inline]
@ -220,17 +222,17 @@ impl<R: Seek> BufReader<R> {
if offset < 0 {
if let Some(new_pos) = pos.checked_sub((-offset) as u64) {
self.pos = new_pos as usize;
return Ok(())
return Ok(());
}
} else {
if let Some(new_pos) = pos.checked_add(offset as u64) {
if new_pos <= self.cap as u64 {
self.pos = new_pos as usize;
return Ok(())
return Ok(());
}
}
}
self.seek(SeekFrom::Current(offset)).map(|_|())
self.seek(SeekFrom::Current(offset)).map(|_| ())
}
}
@ -293,7 +295,10 @@ impl<R: Read> BufRead for BufReader<R> {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<R> fmt::Debug for BufReader<R> where R: fmt::Debug {
impl<R> fmt::Debug for BufReader<R>
where
R: fmt::Debug,
{
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt.debug_struct("BufReader")
.field("reader", &self.inner)
@ -483,11 +488,7 @@ impl<W: Write> BufWriter<W> {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn with_capacity(capacity: usize, inner: W) -> BufWriter<W> {
BufWriter {
inner: Some(inner),
buf: Vec::with_capacity(capacity),
panicked: false,
}
BufWriter { inner: Some(inner), buf: Vec::with_capacity(capacity), panicked: false }
}
fn flush_buf(&mut self) -> io::Result<()> {
@ -501,14 +502,16 @@ impl<W: Write> BufWriter<W> {
match r {
Ok(0) => {
ret = Err(Error::new(ErrorKind::WriteZero,
"failed to write the buffered data"));
ret =
Err(Error::new(ErrorKind::WriteZero, "failed to write the buffered data"));
break;
}
Ok(n) => written += n,
Err(ref e) if e.kind() == io::ErrorKind::Interrupted => {}
Err(e) => { ret = Err(e); break }
Err(e) => {
ret = Err(e);
break;
}
}
}
if written > 0 {
@ -531,7 +534,9 @@ impl<W: Write> BufWriter<W> {
/// let reference = buffer.get_ref();
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_ref(&self) -> &W { self.inner.as_ref().unwrap() }
pub fn get_ref(&self) -> &W {
self.inner.as_ref().unwrap()
}
/// Gets a mutable reference to the underlying writer.
///
@ -549,7 +554,9 @@ impl<W: Write> BufWriter<W> {
/// let reference = buffer.get_mut();
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_mut(&mut self) -> &mut W { self.inner.as_mut().unwrap() }
pub fn get_mut(&mut self) -> &mut W {
self.inner.as_mut().unwrap()
}
/// Returns a reference to the internally buffered data.
///
@ -592,7 +599,7 @@ impl<W: Write> BufWriter<W> {
pub fn into_inner(mut self) -> Result<W, IntoInnerError<BufWriter<W>>> {
match self.flush_buf() {
Err(e) => Err(IntoInnerError(self, e)),
Ok(()) => Ok(self.inner.take().unwrap())
Ok(()) => Ok(self.inner.take().unwrap()),
}
}
}
@ -634,7 +641,10 @@ impl<W: Write> Write for BufWriter<W> {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<W: Write> fmt::Debug for BufWriter<W> where W: fmt::Debug {
impl<W: Write> fmt::Debug for BufWriter<W>
where
W: fmt::Debug,
{
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt.debug_struct("BufWriter")
.field("writer", &self.inner.as_ref().unwrap())
@ -693,7 +703,9 @@ impl<W> IntoInnerError<W> {
/// };
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn error(&self) -> &Error { &self.1 }
pub fn error(&self) -> &Error {
&self.1
}
/// Returns the buffered writer instance which generated the error.
///
@ -726,12 +738,16 @@ impl<W> IntoInnerError<W> {
/// };
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn into_inner(self) -> W { self.0 }
pub fn into_inner(self) -> W {
self.0
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<W> From<IntoInnerError<W>> for Error {
fn from(iie: IntoInnerError<W>) -> Error { iie.1 }
fn from(iie: IntoInnerError<W>) -> Error {
iie.1
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -856,10 +872,7 @@ impl<W: Write> LineWriter<W> {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn with_capacity(capacity: usize, inner: W) -> LineWriter<W> {
LineWriter {
inner: BufWriter::with_capacity(capacity, inner),
need_flush: false,
}
LineWriter { inner: BufWriter::with_capacity(capacity, inner), need_flush: false }
}
/// Gets a reference to the underlying writer.
@ -879,7 +892,9 @@ impl<W: Write> LineWriter<W> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_ref(&self) -> &W { self.inner.get_ref() }
pub fn get_ref(&self) -> &W {
self.inner.get_ref()
}
/// Gets a mutable reference to the underlying writer.
///
@ -902,7 +917,9 @@ impl<W: Write> LineWriter<W> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn get_mut(&mut self) -> &mut W { self.inner.get_mut() }
pub fn get_mut(&mut self) -> &mut W {
self.inner.get_mut()
}
/// Unwraps this `LineWriter`, returning the underlying writer.
///
@ -930,10 +947,7 @@ impl<W: Write> LineWriter<W> {
#[stable(feature = "rust1", since = "1.0.0")]
pub fn into_inner(self) -> Result<W, IntoInnerError<LineWriter<W>>> {
self.inner.into_inner().map_err(|IntoInnerError(buf, e)| {
IntoInnerError(LineWriter {
inner: buf,
need_flush: false,
}, e)
IntoInnerError(LineWriter { inner: buf, need_flush: false }, e)
})
}
}
@ -953,7 +967,6 @@ impl<W: Write> Write for LineWriter<W> {
None => return self.inner.write(buf),
};
// Ok, we're going to write a partial amount of the data given first
// followed by flushing the newline. After we've successfully written
// some data then we *must* report that we wrote that data, so future
@ -962,7 +975,7 @@ impl<W: Write> Write for LineWriter<W> {
let n = self.inner.write(&buf[..=i])?;
self.need_flush = true;
if self.flush().is_err() || n != i + 1 {
return Ok(n)
return Ok(n);
}
// At this point we successfully wrote `i + 1` bytes and flushed it out,
@ -984,12 +997,17 @@ impl<W: Write> Write for LineWriter<W> {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<W: Write> fmt::Debug for LineWriter<W> where W: fmt::Debug {
impl<W: Write> fmt::Debug for LineWriter<W>
where
W: fmt::Debug,
{
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt.debug_struct("LineWriter")
.field("writer", &self.inner.inner)
.field("buffer",
&format_args!("{}/{}", self.inner.buf.len(), self.inner.buf.capacity()))
.field(
"buffer",
&format_args!("{}/{}", self.inner.buf.len(), self.inner.buf.capacity()),
)
.finish()
}
}
@ -1008,11 +1026,7 @@ mod tests {
impl Read for ShortReader {
fn read(&mut self, _: &mut [u8]) -> io::Result<usize> {
if self.lengths.is_empty() {
Ok(0)
} else {
Ok(self.lengths.remove(0))
}
if self.lengths.is_empty() { Ok(0) } else { Ok(self.lengths.remove(0)) }
}
}
@ -1123,7 +1137,7 @@ mod tests {
fn test_buffered_reader_seek_underflow() {
// gimmick reader that yields its position modulo 256 for each byte
struct PositionReader {
pos: u64
pos: u64,
}
impl Read for PositionReader {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
@ -1154,7 +1168,7 @@ mod tests {
let mut reader = BufReader::with_capacity(5, PositionReader { pos: 0 });
assert_eq!(reader.fill_buf().ok(), Some(&[0, 1, 2, 3, 4][..]));
assert_eq!(reader.seek(SeekFrom::End(-5)).ok(), Some(u64::max_value()-5));
assert_eq!(reader.seek(SeekFrom::End(-5)).ok(), Some(u64::max_value() - 5));
assert_eq!(reader.fill_buf().ok().map(|s| s.len()), Some(5));
// the following seek will require two underlying seeks
let expected = 9223372036854775802;
@ -1361,7 +1375,7 @@ mod tests {
#[test]
fn test_short_reads() {
let inner = ShortReader{lengths: vec![0, 1, 2, 0, 1, 0]};
let inner = ShortReader { lengths: vec![0, 1, 2, 0, 1, 0] };
let mut reader = BufReader::new(inner);
let mut buf = [0, 0];
assert_eq!(reader.read(&mut buf).unwrap(), 0);
@ -1379,7 +1393,9 @@ mod tests {
struct FailFlushWriter;
impl Write for FailFlushWriter {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { Ok(buf.len()) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
Ok(buf.len())
}
fn flush(&mut self) -> io::Result<()> {
Err(io::Error::last_os_error())
}
@ -1405,30 +1421,30 @@ mod tests {
WRITES.fetch_add(1, Ordering::SeqCst);
panic!();
}
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
thread::spawn(|| {
let mut writer = BufWriter::new(PanicWriter);
let _ = writer.write(b"hello world");
let _ = writer.flush();
}).join().unwrap_err();
})
.join()
.unwrap_err();
assert_eq!(WRITES.load(Ordering::SeqCst), 1);
}
#[bench]
fn bench_buffered_reader(b: &mut test::Bencher) {
b.iter(|| {
BufReader::new(io::empty())
});
b.iter(|| BufReader::new(io::empty()));
}
#[bench]
fn bench_buffered_writer(b: &mut test::Bencher) {
b.iter(|| {
BufWriter::new(io::sink())
});
b.iter(|| BufWriter::new(io::sink()));
}
struct AcceptOneThenFail {
@ -1457,10 +1473,7 @@ mod tests {
#[test]
fn erroneous_flush_retried() {
let a = AcceptOneThenFail {
written: false,
flushed: false,
};
let a = AcceptOneThenFail { written: false, flushed: false };
let mut l = LineWriter::new(a);
assert_eq!(l.write(b"a\nb\na").unwrap(), 4);

View file

@ -1,8 +1,8 @@
use crate::convert::From;
use crate::error;
use crate::fmt;
use crate::result;
use crate::sys;
use crate::convert::From;
/// A specialized [`Result`](../result/enum.Result.html) type for I/O
/// operations.
@ -73,7 +73,7 @@ enum Repr {
#[derive(Debug)]
struct Custom {
kind: ErrorKind,
error: Box<dyn error::Error+Send+Sync>,
error: Box<dyn error::Error + Send + Sync>,
}
/// A list specifying general categories of I/O error.
@ -220,9 +220,7 @@ impl From<ErrorKind> for Error {
/// [`Error`]: ../../std/io/struct.Error.html
#[inline]
fn from(kind: ErrorKind) -> Error {
Error {
repr: Repr::Simple(kind)
}
Error { repr: Repr::Simple(kind) }
}
}
@ -247,18 +245,14 @@ impl Error {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn new<E>(kind: ErrorKind, error: E) -> Error
where E: Into<Box<dyn error::Error+Send+Sync>>
where
E: Into<Box<dyn error::Error + Send + Sync>>,
{
Self::_new(kind, error.into())
}
fn _new(kind: ErrorKind, error: Box<dyn error::Error+Send+Sync>) -> Error {
Error {
repr: Repr::Custom(Box::new(Custom {
kind,
error,
}))
}
fn _new(kind: ErrorKind, error: Box<dyn error::Error + Send + Sync>) -> Error {
Error { repr: Repr::Custom(Box::new(Custom { kind, error })) }
}
/// Returns an error representing the last OS error which occurred.
@ -370,7 +364,7 @@ impl Error {
/// }
/// ```
#[stable(feature = "io_error_inner", since = "1.3.0")]
pub fn get_ref(&self) -> Option<&(dyn error::Error+Send+Sync+'static)> {
pub fn get_ref(&self) -> Option<&(dyn error::Error + Send + Sync + 'static)> {
match self.repr {
Repr::Os(..) => None,
Repr::Simple(..) => None,
@ -441,7 +435,7 @@ impl Error {
/// }
/// ```
#[stable(feature = "io_error_inner", since = "1.3.0")]
pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error+Send+Sync+'static)> {
pub fn get_mut(&mut self) -> Option<&mut (dyn error::Error + Send + Sync + 'static)> {
match self.repr {
Repr::Os(..) => None,
Repr::Simple(..) => None,
@ -475,11 +469,11 @@ impl Error {
/// }
/// ```
#[stable(feature = "io_error_inner", since = "1.3.0")]
pub fn into_inner(self) -> Option<Box<dyn error::Error+Send+Sync>> {
pub fn into_inner(self) -> Option<Box<dyn error::Error + Send + Sync>> {
match self.repr {
Repr::Os(..) => None,
Repr::Simple(..) => None,
Repr::Custom(c) => Some(c.error)
Repr::Custom(c) => Some(c.error),
}
}
@ -514,11 +508,12 @@ impl Error {
impl fmt::Debug for Repr {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
match *self {
Repr::Os(code) =>
fmt.debug_struct("Os")
Repr::Os(code) => fmt
.debug_struct("Os")
.field("code", &code)
.field("kind", &sys::decode_error_kind(code))
.field("message", &sys::os::error_string(code)).finish(),
.field("message", &sys::os::error_string(code))
.finish(),
Repr::Custom(ref c) => fmt::Debug::fmt(&c, fmt),
Repr::Simple(kind) => fmt.debug_tuple("Kind").field(&kind).finish(),
}
@ -567,17 +562,17 @@ impl error::Error for Error {
}
fn _assert_error_is_sync_send() {
fn _is_sync_send<T: Sync+Send>() {}
fn _is_sync_send<T: Sync + Send>() {}
_is_sync_send::<Error>();
}
#[cfg(test)]
mod test {
use super::{Error, ErrorKind, Repr, Custom};
use super::{Custom, Error, ErrorKind, Repr};
use crate::error;
use crate::fmt;
use crate::sys::os::error_string;
use crate::sys::decode_error_kind;
use crate::sys::os::error_string;
#[test]
fn test_debug_error() {
@ -587,10 +582,8 @@ mod test {
let err = Error {
repr: Repr::Custom(box Custom {
kind: ErrorKind::InvalidInput,
error: box Error {
repr: super::Repr::Os(code)
},
})
error: box Error { repr: super::Repr::Os(code) },
}),
};
let expected = format!(
"Custom {{ \

View file

@ -1,7 +1,8 @@
use crate::cmp;
use crate::io::{self, SeekFrom, Read, Initializer, Write, Seek, BufRead, Error, ErrorKind,
IoSliceMut, IoSlice};
use crate::fmt;
use crate::io::{
self, BufRead, Error, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Seek, SeekFrom, Write,
};
use crate::mem;
// =============================================================================
@ -42,7 +43,9 @@ impl<R: Read + ?Sized> Read for &mut R {
#[stable(feature = "rust1", since = "1.0.0")]
impl<W: Write + ?Sized> Write for &mut W {
#[inline]
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { (**self).write(buf) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
(**self).write(buf)
}
#[inline]
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
@ -50,7 +53,9 @@ impl<W: Write + ?Sized> Write for &mut W {
}
#[inline]
fn flush(&mut self) -> io::Result<()> { (**self).flush() }
fn flush(&mut self) -> io::Result<()> {
(**self).flush()
}
#[inline]
fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
@ -65,15 +70,21 @@ impl<W: Write + ?Sized> Write for &mut W {
#[stable(feature = "rust1", since = "1.0.0")]
impl<S: Seek + ?Sized> Seek for &mut S {
#[inline]
fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> { (**self).seek(pos) }
fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> {
(**self).seek(pos)
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<B: BufRead + ?Sized> BufRead for &mut B {
#[inline]
fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() }
fn fill_buf(&mut self) -> io::Result<&[u8]> {
(**self).fill_buf()
}
#[inline]
fn consume(&mut self, amt: usize) { (**self).consume(amt) }
fn consume(&mut self, amt: usize) {
(**self).consume(amt)
}
#[inline]
fn read_until(&mut self, byte: u8, buf: &mut Vec<u8>) -> io::Result<usize> {
@ -121,7 +132,9 @@ impl<R: Read + ?Sized> Read for Box<R> {
#[stable(feature = "rust1", since = "1.0.0")]
impl<W: Write + ?Sized> Write for Box<W> {
#[inline]
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { (**self).write(buf) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
(**self).write(buf)
}
#[inline]
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
@ -129,7 +142,9 @@ impl<W: Write + ?Sized> Write for Box<W> {
}
#[inline]
fn flush(&mut self) -> io::Result<()> { (**self).flush() }
fn flush(&mut self) -> io::Result<()> {
(**self).flush()
}
#[inline]
fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
@ -144,15 +159,21 @@ impl<W: Write + ?Sized> Write for Box<W> {
#[stable(feature = "rust1", since = "1.0.0")]
impl<S: Seek + ?Sized> Seek for Box<S> {
#[inline]
fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> { (**self).seek(pos) }
fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> {
(**self).seek(pos)
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<B: BufRead + ?Sized> BufRead for Box<B> {
#[inline]
fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() }
fn fill_buf(&mut self) -> io::Result<&[u8]> {
(**self).fill_buf()
}
#[inline]
fn consume(&mut self, amt: usize) { (**self).consume(amt) }
fn consume(&mut self, amt: usize) {
(**self).consume(amt)
}
#[inline]
fn read_until(&mut self, byte: u8, buf: &mut Vec<u8>) -> io::Result<usize> {
@ -227,8 +248,7 @@ impl Read for &[u8] {
#[inline]
fn read_exact(&mut self, buf: &mut [u8]) -> io::Result<()> {
if buf.len() > self.len() {
return Err(Error::new(ErrorKind::UnexpectedEof,
"failed to fill whole buffer"));
return Err(Error::new(ErrorKind::UnexpectedEof, "failed to fill whole buffer"));
}
let (a, b) = self.split_at(buf.len());
@ -257,10 +277,14 @@ impl Read for &[u8] {
#[stable(feature = "rust1", since = "1.0.0")]
impl BufRead for &[u8] {
#[inline]
fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) }
fn fill_buf(&mut self) -> io::Result<&[u8]> {
Ok(*self)
}
#[inline]
fn consume(&mut self, amt: usize) { *self = &self[amt..]; }
fn consume(&mut self, amt: usize) {
*self = &self[amt..];
}
}
/// Write is implemented for `&mut [u8]` by copying into the slice, overwriting
@ -302,7 +326,9 @@ impl Write for &mut [u8] {
}
#[inline]
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
/// Write is implemented for `Vec<u8>` by appending to the vector.
@ -332,7 +358,9 @@ impl Write for Vec<u8> {
}
#[inline]
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
#[cfg(test)]

View file

@ -261,49 +261,54 @@
use crate::cmp;
use crate::fmt;
use crate::slice;
use crate::str;
use crate::memchr;
use crate::ops::{Deref, DerefMut};
use crate::ptr;
use crate::slice;
use crate::str;
use crate::sys;
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::buffered::{BufReader, BufWriter, LineWriter};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::buffered::IntoInnerError;
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::buffered::{BufReader, BufWriter, LineWriter};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::cursor::Cursor;
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::error::{Result, Error, ErrorKind};
pub use self::error::{Error, ErrorKind, Result};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::util::{copy, sink, Sink, empty, Empty, repeat, Repeat};
pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::stdio::{stdin, stdout, stderr, Stdin, Stdout, Stderr};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::stdio::{StdoutLock, StderrLock, StdinLock};
pub use self::stdio::{StderrLock, StdinLock, StdoutLock};
#[unstable(feature = "print_internals", issue = "0")]
pub use self::stdio::{_print, _eprint};
pub use self::stdio::{_eprint, _print};
#[unstable(feature = "libstd_io_internals", issue = "42788")]
#[doc(no_inline, hidden)]
pub use self::stdio::{set_panic, set_print};
#[stable(feature = "rust1", since = "1.0.0")]
pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink};
pub mod prelude;
mod buffered;
mod cursor;
mod error;
mod impls;
mod lazy;
mod util;
pub mod prelude;
mod stdio;
mod util;
const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE;
struct Guard<'a> { buf: &'a mut Vec<u8>, len: usize }
struct Guard<'a> {
buf: &'a mut Vec<u8>,
len: usize,
}
impl Drop for Guard<'_> {
fn drop(&mut self) {
unsafe { self.buf.set_len(self.len); }
unsafe {
self.buf.set_len(self.len);
}
}
}
@ -326,15 +331,15 @@ impl Drop for Guard<'_> {
// the function only *appends* bytes to the buffer. We'll get undefined
// behavior if existing bytes are overwritten to have non-UTF-8 data.
fn append_to_string<F>(buf: &mut String, f: F) -> Result<usize>
where F: FnOnce(&mut Vec<u8>) -> Result<usize>
where
F: FnOnce(&mut Vec<u8>) -> Result<usize>,
{
unsafe {
let mut g = Guard { len: buf.len(), buf: buf.as_mut_vec() };
let ret = f(g.buf);
if str::from_utf8(&g.buf[g.len..]).is_err() {
ret.and_then(|_| {
Err(Error::new(ErrorKind::InvalidData,
"stream did not contain valid UTF-8"))
Err(Error::new(ErrorKind::InvalidData, "stream did not contain valid UTF-8"))
})
} else {
g.len = g.buf.len();
@ -405,23 +410,17 @@ where
pub(crate) fn default_read_vectored<F>(read: F, bufs: &mut [IoSliceMut<'_>]) -> Result<usize>
where
F: FnOnce(&mut [u8]) -> Result<usize>
F: FnOnce(&mut [u8]) -> Result<usize>,
{
let buf = bufs
.iter_mut()
.find(|b| !b.is_empty())
.map_or(&mut [][..], |b| &mut **b);
let buf = bufs.iter_mut().find(|b| !b.is_empty()).map_or(&mut [][..], |b| &mut **b);
read(buf)
}
pub(crate) fn default_write_vectored<F>(write: F, bufs: &[IoSlice<'_>]) -> Result<usize>
where
F: FnOnce(&[u8]) -> Result<usize>
F: FnOnce(&[u8]) -> Result<usize>,
{
let buf = bufs
.iter()
.find(|b| !b.is_empty())
.map_or(&[][..], |b| &**b);
let buf = bufs.iter().find(|b| !b.is_empty()).map_or(&[][..], |b| &**b);
write(buf)
}
@ -767,14 +766,16 @@ pub trait Read {
while !buf.is_empty() {
match self.read(buf) {
Ok(0) => break,
Ok(n) => { let tmp = buf; buf = &mut tmp[n..]; }
Ok(n) => {
let tmp = buf;
buf = &mut tmp[n..];
}
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
}
}
if !buf.is_empty() {
Err(Error::new(ErrorKind::UnexpectedEof,
"failed to fill whole buffer"))
Err(Error::new(ErrorKind::UnexpectedEof, "failed to fill whole buffer"))
} else {
Ok(())
}
@ -815,7 +816,12 @@ pub trait Read {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn by_ref(&mut self) -> &mut Self where Self: Sized { self }
fn by_ref(&mut self) -> &mut Self
where
Self: Sized,
{
self
}
/// Transforms this `Read` instance to an [`Iterator`] over its bytes.
///
@ -852,7 +858,10 @@ pub trait Read {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn bytes(self) -> Bytes<Self> where Self: Sized {
fn bytes(self) -> Bytes<Self>
where
Self: Sized,
{
Bytes { inner: self }
}
@ -887,7 +896,10 @@ pub trait Read {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn chain<R: Read>(self, next: R) -> Chain<Self, R> where Self: Sized {
fn chain<R: Read>(self, next: R) -> Chain<Self, R>
where
Self: Sized,
{
Chain { first: self, second: next, done_first: false }
}
@ -923,7 +935,10 @@ pub trait Read {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn take(self, limit: u64) -> Take<Self> where Self: Sized {
fn take(self, limit: u64) -> Take<Self>
where
Self: Sized,
{
Take { inner: self, limit: limit }
}
}
@ -1339,8 +1354,9 @@ pub trait Write {
fn write_all(&mut self, mut buf: &[u8]) -> Result<()> {
while !buf.is_empty() {
match self.write(buf) {
Ok(0) => return Err(Error::new(ErrorKind::WriteZero,
"failed to write whole buffer")),
Ok(0) => {
return Err(Error::new(ErrorKind::WriteZero, "failed to write whole buffer"));
}
Ok(n) => buf = &buf[n..],
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
@ -1444,7 +1460,12 @@ pub trait Write {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn by_ref(&mut self) -> &mut Self where Self: Sized { self }
fn by_ref(&mut self) -> &mut Self
where
Self: Sized,
{
self
}
}
/// The `Seek` trait provides a cursor which can be moved within a stream of
@ -1601,15 +1622,14 @@ pub enum SeekFrom {
Current(#[stable(feature = "rust1", since = "1.0.0")] i64),
}
fn read_until<R: BufRead + ?Sized>(r: &mut R, delim: u8, buf: &mut Vec<u8>)
-> Result<usize> {
fn read_until<R: BufRead + ?Sized>(r: &mut R, delim: u8, buf: &mut Vec<u8>) -> Result<usize> {
let mut read = 0;
loop {
let (done, used) = {
let available = match r.fill_buf() {
Ok(n) => n,
Err(ref e) if e.kind() == ErrorKind::Interrupted => continue,
Err(e) => return Err(e)
Err(e) => return Err(e),
};
match memchr::memchr(delim, available) {
Some(i) => {
@ -1900,7 +1920,10 @@ pub trait BufRead: Read {
/// assert_eq!(split_iter.next(), None);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
fn split(self, byte: u8) -> Split<Self> where Self: Sized {
fn split(self, byte: u8) -> Split<Self>
where
Self: Sized,
{
Split { buf: self, delim: byte }
}
@ -1939,7 +1962,10 @@ pub trait BufRead: Read {
///
/// [`BufRead::read_line`]: trait.BufRead.html#method.read_line
#[stable(feature = "rust1", since = "1.0.0")]
fn lines(self) -> Lines<Self> where Self: Sized {
fn lines(self) -> Lines<Self>
where
Self: Sized,
{
Lines { buf: self }
}
}
@ -2035,10 +2061,7 @@ impl<T, U> Chain<T, U> {
#[stable(feature = "std_debug", since = "1.16.0")]
impl<T: fmt::Debug, U: fmt::Debug> fmt::Debug for Chain<T, U> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("Chain")
.field("t", &self.first)
.field("u", &self.second)
.finish()
f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish()
}
}
@ -2066,11 +2089,7 @@ impl<T: Read, U: Read> Read for Chain<T, U> {
unsafe fn initializer(&self) -> Initializer {
let initializer = self.first.initializer();
if initializer.should_initialize() {
initializer
} else {
self.second.initializer()
}
if initializer.should_initialize() { initializer } else { self.second.initializer() }
}
}
@ -2079,7 +2098,9 @@ impl<T: BufRead, U: BufRead> BufRead for Chain<T, U> {
fn fill_buf(&mut self) -> Result<&[u8]> {
if !self.done_first {
match self.first.fill_buf()? {
buf if buf.is_empty() => { self.done_first = true; }
buf if buf.is_empty() => {
self.done_first = true;
}
buf => return Ok(buf),
}
}
@ -2087,11 +2108,7 @@ impl<T: BufRead, U: BufRead> BufRead for Chain<T, U> {
}
fn consume(&mut self, amt: usize) {
if !self.done_first {
self.first.consume(amt)
} else {
self.second.consume(amt)
}
if !self.done_first { self.first.consume(amt) } else { self.second.consume(amt) }
}
}
@ -2137,7 +2154,9 @@ impl<T> Take<T> {
/// }
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn limit(&self) -> u64 { self.limit }
pub fn limit(&self) -> u64 {
self.limit
}
/// Sets the number of bytes that can be read before this instance will
/// return EOF. This is the same as constructing a new `Take` instance, so
@ -2351,7 +2370,7 @@ impl<B: BufRead> Iterator for Split<B> {
}
Some(Ok(buf))
}
Err(e) => Some(Err(e))
Err(e) => Some(Err(e)),
}
}
}
@ -2385,16 +2404,16 @@ impl<B: BufRead> Iterator for Lines<B> {
}
Some(Ok(buf))
}
Err(e) => Some(Err(e))
Err(e) => Some(Err(e)),
}
}
}
#[cfg(test)]
mod tests {
use super::{repeat, Cursor, SeekFrom};
use crate::cmp;
use crate::io::prelude::*;
use super::{Cursor, SeekFrom, repeat};
use crate::io::{self, IoSlice, IoSliceMut};
use crate::mem;
use crate::ops::Deref;
@ -2509,16 +2528,14 @@ mod tests {
let mut buf = [0; 4];
let mut c = Cursor::new(&b""[..]);
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(),
io::ErrorKind::UnexpectedEof);
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(), io::ErrorKind::UnexpectedEof);
let mut c = Cursor::new(&b"123"[..]).chain(Cursor::new(&b"456789"[..]));
c.read_exact(&mut buf).unwrap();
assert_eq!(&buf, b"1234");
c.read_exact(&mut buf).unwrap();
assert_eq!(&buf, b"5678");
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(),
io::ErrorKind::UnexpectedEof);
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(), io::ErrorKind::UnexpectedEof);
}
#[test]
@ -2526,12 +2543,10 @@ mod tests {
let mut buf = [0; 4];
let mut c = &b""[..];
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(),
io::ErrorKind::UnexpectedEof);
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(), io::ErrorKind::UnexpectedEof);
let mut c = &b"123"[..];
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(),
io::ErrorKind::UnexpectedEof);
assert_eq!(c.read_exact(&mut buf).unwrap_err().kind(), io::ErrorKind::UnexpectedEof);
// make sure the optimized (early returning) method is being used
assert_eq!(&buf, &[0; 4]);
@ -2558,7 +2573,7 @@ mod tests {
fn fill_buf(&mut self) -> io::Result<&[u8]> {
Err(io::Error::new(io::ErrorKind::Other, ""))
}
fn consume(&mut self, _amt: usize) { }
fn consume(&mut self, _amt: usize) {}
}
let mut buf = [0; 1];
@ -2591,11 +2606,9 @@ mod tests {
#[test]
fn chain_bufread() {
let testdata = b"ABCDEFGHIJKL";
let chain1 = (&testdata[..3]).chain(&testdata[3..6])
.chain(&testdata[6..9])
.chain(&testdata[9..]);
let chain2 = (&testdata[..4]).chain(&testdata[4..8])
.chain(&testdata[8..]);
let chain1 =
(&testdata[..3]).chain(&testdata[3..6]).chain(&testdata[6..9]).chain(&testdata[9..]);
let chain2 = (&testdata[..4]).chain(&testdata[4..8]).chain(&testdata[8..]);
cmp_bufread(chain1, chain2, &testdata[..]);
}
@ -2651,7 +2664,6 @@ mod tests {
assert_eq!(c.stream_position()?, 15);
assert_eq!(c.stream_position()?, 15);
c.seek(SeekFrom::Start(7))?;
c.seek(SeekFrom::Current(2))?;
assert_eq!(c.stream_position()?, 9);
@ -2700,9 +2712,7 @@ mod tests {
// that will not allocate when the limit has already been reached. In
// this case, vec2 never grows.
let mut vec2 = Vec::with_capacity(input.len());
ExampleSliceReader { slice: input }
.take(input.len() as u64)
.read_to_end(&mut vec2)?;
ExampleSliceReader { slice: input }.take(input.len() as u64).read_to_end(&mut vec2)?;
assert_eq!(vec2.len(), input.len());
assert_eq!(vec2.capacity(), input.len(), "did not allocate more");

View file

@ -11,4 +11,4 @@
#![stable(feature = "rust1", since = "1.0.0")]
#[stable(feature = "rust1", since = "1.0.0")]
pub use super::{Read, Write, BufRead, Seek};
pub use super::{BufRead, Read, Seek, Write};

View file

@ -1,7 +1,7 @@
#![allow(missing_copy_implementations)]
use crate::fmt;
use crate::io::{self, Read, Initializer, Write, ErrorKind, BufRead, IoSlice, IoSliceMut};
use crate::io::{self, BufRead, ErrorKind, Initializer, IoSlice, IoSliceMut, Read, Write};
use crate::mem::MaybeUninit;
/// Copies the entire contents of a reader into a writer.
@ -41,7 +41,9 @@ use crate::mem::MaybeUninit;
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn copy<R: ?Sized, W: ?Sized>(reader: &mut R, writer: &mut W) -> io::Result<u64>
where R: Read, W: Write
where
R: Read,
W: Write,
{
let mut buf = MaybeUninit::<[u8; super::DEFAULT_BUF_SIZE]>::uninit();
// FIXME(#53491): This is calling `get_mut` and `get_ref` on an uninitialized
@ -49,7 +51,9 @@ pub fn copy<R: ?Sized, W: ?Sized>(reader: &mut R, writer: &mut W) -> io::Result<
// This is still technically undefined behavior due to creating a reference
// to uninitialized data, but within libstd we can rely on more guarantees
// than if this code were in an external lib.
unsafe { reader.initializer().initialize(buf.get_mut()); }
unsafe {
reader.initializer().initialize(buf.get_mut());
}
let mut written = 0;
loop {
@ -71,7 +75,9 @@ pub fn copy<R: ?Sized, W: ?Sized>(reader: &mut R, writer: &mut W) -> io::Result<
///
/// [`empty`]: fn.empty.html
#[stable(feature = "rust1", since = "1.0.0")]
pub struct Empty { _priv: () }
pub struct Empty {
_priv: (),
}
/// Constructs a new handle to an empty reader.
///
@ -91,12 +97,16 @@ pub struct Empty { _priv: () }
/// assert!(buffer.is_empty());
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn empty() -> Empty { Empty { _priv: () } }
pub fn empty() -> Empty {
Empty { _priv: () }
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Read for Empty {
#[inline]
fn read(&mut self, _buf: &mut [u8]) -> io::Result<usize> { Ok(0) }
fn read(&mut self, _buf: &mut [u8]) -> io::Result<usize> {
Ok(0)
}
#[inline]
unsafe fn initializer(&self) -> Initializer {
@ -106,7 +116,9 @@ impl Read for Empty {
#[stable(feature = "rust1", since = "1.0.0")]
impl BufRead for Empty {
#[inline]
fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) }
fn fill_buf(&mut self) -> io::Result<&[u8]> {
Ok(&[])
}
#[inline]
fn consume(&mut self, _n: usize) {}
}
@ -125,7 +137,9 @@ impl fmt::Debug for Empty {
///
/// [repeat]: fn.repeat.html
#[stable(feature = "rust1", since = "1.0.0")]
pub struct Repeat { byte: u8 }
pub struct Repeat {
byte: u8,
}
/// Creates an instance of a reader that infinitely repeats one byte.
///
@ -142,7 +156,9 @@ pub struct Repeat { byte: u8 }
/// assert_eq!(buffer, [0b101, 0b101, 0b101]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn repeat(byte: u8) -> Repeat { Repeat { byte } }
pub fn repeat(byte: u8) -> Repeat {
Repeat { byte }
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Read for Repeat {
@ -183,7 +199,9 @@ impl fmt::Debug for Repeat {
///
/// [sink]: fn.sink.html
#[stable(feature = "rust1", since = "1.0.0")]
pub struct Sink { _priv: () }
pub struct Sink {
_priv: (),
}
/// Creates an instance of a writer which will successfully consume all data.
///
@ -200,12 +218,16 @@ pub struct Sink { _priv: () }
/// assert_eq!(num_bytes, 5);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn sink() -> Sink { Sink { _priv: () } }
pub fn sink() -> Sink {
Sink { _priv: () }
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Write for Sink {
#[inline]
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { Ok(buf.len()) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
Ok(buf.len())
}
#[inline]
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
@ -214,7 +236,9 @@ impl Write for Sink {
}
#[inline]
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
#[stable(feature = "std_debug", since = "1.16.0")]
@ -227,7 +251,7 @@ impl fmt::Debug for Sink {
#[cfg(test)]
mod tests {
use crate::io::prelude::*;
use crate::io::{copy, sink, empty, repeat};
use crate::io::{copy, empty, repeat, sink};
#[test]
fn copy_copies() {

View file

@ -313,9 +313,8 @@ macro_rules! dbg {
#[cfg(test)]
macro_rules! assert_approx_eq {
($a:expr, $b:expr) => ({
($a:expr, $b:expr) => {{
let (a, b) = (&$a, &$b);
assert!((*a - *b).abs() < 1.0e-6,
"{} is not approximately equal to {}", *a, *b);
})
assert!((*a - *b).abs() < 1.0e-6, "{} is not approximately equal to {}", *a, *b);
}};
}

View file

@ -1,16 +1,16 @@
use crate::convert::TryInto;
use crate::fmt;
use crate::hash;
use crate::io;
use crate::mem;
use crate::net::{ntoh, hton, IpAddr, Ipv4Addr, Ipv6Addr};
use crate::option;
use crate::sys::net::netc as c;
use crate::sys_common::{FromInner, AsInner, IntoInner};
use crate::sys_common::net::LookupHost;
use crate::vec;
use crate::iter;
use crate::mem;
use crate::net::{hton, ntoh, IpAddr, Ipv4Addr, Ipv6Addr};
use crate::option;
use crate::slice;
use crate::convert::TryInto;
use crate::sys::net::netc as c;
use crate::sys_common::net::LookupHost;
use crate::sys_common::{AsInner, FromInner, IntoInner};
use crate::vec;
/// An internet socket address, either IPv4 or IPv6.
///
@ -74,7 +74,9 @@ pub enum SocketAddr {
/// ```
#[derive(Copy)]
#[stable(feature = "rust1", since = "1.0.0")]
pub struct SocketAddrV4 { inner: c::sockaddr_in }
pub struct SocketAddrV4 {
inner: c::sockaddr_in,
}
/// An IPv6 socket address.
///
@ -104,7 +106,9 @@ pub struct SocketAddrV4 { inner: c::sockaddr_in }
/// ```
#[derive(Copy)]
#[stable(feature = "rust1", since = "1.0.0")]
pub struct SocketAddrV6 { inner: c::sockaddr_in6 }
pub struct SocketAddrV6 {
inner: c::sockaddr_in6,
}
impl SocketAddr {
/// Creates a new socket address from an [IP address] and a port number.
@ -274,7 +278,7 @@ impl SocketAddrV4 {
sin_family: c::AF_INET as c::sa_family_t,
sin_port: hton(port),
sin_addr: *ip.as_inner(),
.. unsafe { mem::zeroed() }
..unsafe { mem::zeroed() }
},
}
}
@ -291,9 +295,7 @@ impl SocketAddrV4 {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn ip(&self) -> &Ipv4Addr {
unsafe {
&*(&self.inner.sin_addr as *const c::in_addr as *const Ipv4Addr)
}
unsafe { &*(&self.inner.sin_addr as *const c::in_addr as *const Ipv4Addr) }
}
/// Changes the IP address associated with this socket address.
@ -362,8 +364,7 @@ impl SocketAddrV6 {
/// let socket = SocketAddrV6::new(Ipv6Addr::new(0, 0, 0, 0, 0, 0, 0, 1), 8080, 0, 0);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn new(ip: Ipv6Addr, port: u16, flowinfo: u32, scope_id: u32)
-> SocketAddrV6 {
pub fn new(ip: Ipv6Addr, port: u16, flowinfo: u32, scope_id: u32) -> SocketAddrV6 {
SocketAddrV6 {
inner: c::sockaddr_in6 {
sin6_family: c::AF_INET6 as c::sa_family_t,
@ -371,7 +372,7 @@ impl SocketAddrV6 {
sin6_addr: *ip.as_inner(),
sin6_flowinfo: flowinfo,
sin6_scope_id: scope_id,
.. unsafe { mem::zeroed() }
..unsafe { mem::zeroed() }
},
}
}
@ -388,9 +389,7 @@ impl SocketAddrV6 {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn ip(&self) -> &Ipv6Addr {
unsafe {
&*(&self.inner.sin6_addr as *const c::in6_addr as *const Ipv6Addr)
}
unsafe { &*(&self.inner.sin6_addr as *const c::in6_addr as *const Ipv6Addr) }
}
/// Changes the IP address associated with this socket address.
@ -633,27 +632,31 @@ impl fmt::Debug for SocketAddrV6 {
#[stable(feature = "rust1", since = "1.0.0")]
impl Clone for SocketAddrV4 {
fn clone(&self) -> SocketAddrV4 { *self }
fn clone(&self) -> SocketAddrV4 {
*self
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Clone for SocketAddrV6 {
fn clone(&self) -> SocketAddrV6 { *self }
fn clone(&self) -> SocketAddrV6 {
*self
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl PartialEq for SocketAddrV4 {
fn eq(&self, other: &SocketAddrV4) -> bool {
self.inner.sin_port == other.inner.sin_port &&
self.inner.sin_addr.s_addr == other.inner.sin_addr.s_addr
self.inner.sin_port == other.inner.sin_port
&& self.inner.sin_addr.s_addr == other.inner.sin_addr.s_addr
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl PartialEq for SocketAddrV6 {
fn eq(&self, other: &SocketAddrV6) -> bool {
self.inner.sin6_port == other.inner.sin6_port &&
self.inner.sin6_addr.s6_addr == other.inner.sin6_addr.s6_addr &&
self.inner.sin6_flowinfo == other.inner.sin6_flowinfo &&
self.inner.sin6_scope_id == other.inner.sin6_scope_id
self.inner.sin6_port == other.inner.sin6_port
&& self.inner.sin6_addr.s6_addr == other.inner.sin6_addr.s6_addr
&& self.inner.sin6_flowinfo == other.inner.sin6_flowinfo
&& self.inner.sin6_scope_id == other.inner.sin6_scope_id
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -670,8 +673,13 @@ impl hash::Hash for SocketAddrV4 {
#[stable(feature = "rust1", since = "1.0.0")]
impl hash::Hash for SocketAddrV6 {
fn hash<H: hash::Hasher>(&self, s: &mut H) {
(self.inner.sin6_port, &self.inner.sin6_addr.s6_addr,
self.inner.sin6_flowinfo, self.inner.sin6_scope_id).hash(s)
(
self.inner.sin6_port,
&self.inner.sin6_addr.s6_addr,
self.inner.sin6_flowinfo,
self.inner.sin6_scope_id,
)
.hash(s)
}
}
@ -795,7 +803,7 @@ pub trait ToSocketAddrs {
/// Returned iterator over socket addresses which this type may correspond
/// to.
#[stable(feature = "rust1", since = "1.0.0")]
type Iter: Iterator<Item=SocketAddr>;
type Iter: Iterator<Item = SocketAddr>;
/// Converts this object to an iterator of resolved `SocketAddr`s.
///
@ -864,7 +872,12 @@ impl ToSocketAddrs for (Ipv6Addr, u16) {
fn resolve_socket_addr(lh: LookupHost) -> io::Result<vec::IntoIter<SocketAddr>> {
let p = lh.port();
let v: Vec<_> = lh.map(|mut a| { a.set_port(p); a }).collect();
let v: Vec<_> = lh
.map(|mut a| {
a.set_port(p);
a
})
.collect();
Ok(v.into_iter())
}
@ -877,11 +890,11 @@ impl ToSocketAddrs for (&str, u16) {
// try to parse the host as a regular IP address first
if let Ok(addr) = host.parse::<Ipv4Addr>() {
let addr = SocketAddrV4::new(addr, port);
return Ok(vec![SocketAddr::V4(addr)].into_iter())
return Ok(vec![SocketAddr::V4(addr)].into_iter());
}
if let Ok(addr) = host.parse::<Ipv6Addr>() {
let addr = SocketAddrV6::new(addr, port, 0, 0);
return Ok(vec![SocketAddr::V6(addr)].into_iter())
return Ok(vec![SocketAddr::V6(addr)].into_iter());
}
resolve_socket_addr((host, port).try_into()?)
@ -929,8 +942,8 @@ impl ToSocketAddrs for String {
#[cfg(all(test, not(target_os = "emscripten")))]
mod tests {
use crate::net::test::{sa4, sa6, tsa};
use crate::net::*;
use crate::net::test::{tsa, sa6, sa4};
#[test]
fn to_socket_addr_ipaddr_u16() {
@ -991,8 +1004,12 @@ mod tests {
#[test]
fn set_ip() {
fn ip4(low: u8) -> Ipv4Addr { Ipv4Addr::new(77, 88, 21, low) }
fn ip6(low: u16) -> Ipv6Addr { Ipv6Addr::new(0x2a02, 0x6b8, 0, 1, 0, 0, 0, low) }
fn ip4(low: u8) -> Ipv4Addr {
Ipv4Addr::new(77, 88, 21, low)
}
fn ip6(low: u16) -> Ipv6Addr {
Ipv6Addr::new(0x2a02, 0x6b8, 0, 1, 0, 0, 0, low)
}
let mut v4 = SocketAddrV4::new(ip4(11), 80);
assert_eq!(v4.ip(), &ip4(11));
@ -1068,7 +1085,11 @@ mod tests {
#[test]
fn is_v6() {
let v6 = SocketAddr::V6(SocketAddrV6::new(
Ipv6Addr::new(0x2a02, 0x6b8, 0, 1, 0, 0, 0, 1), 80, 10, 0));
Ipv6Addr::new(0x2a02, 0x6b8, 0, 1, 0, 0, 0, 1),
80,
10,
0,
));
assert!(!v6.is_ipv4());
assert!(v6.is_ipv6());
}

View file

@ -16,10 +16,7 @@ struct Parser<'a> {
impl<'a> Parser<'a> {
fn new(s: &'a str) -> Parser<'a> {
Parser {
s: s.as_bytes(),
pos: 0,
}
Parser { s: s.as_bytes(), pos: 0 }
}
fn is_eof(&self) -> bool {
@ -27,7 +24,8 @@ impl<'a> Parser<'a> {
}
// Commit only if parser returns Some
fn read_atomically<T, F>(&mut self, cb: F) -> Option<T> where
fn read_atomically<T, F>(&mut self, cb: F) -> Option<T>
where
F: FnOnce(&mut Parser<'_>) -> Option<T>,
{
let pos = self.pos;
@ -39,17 +37,18 @@ impl<'a> Parser<'a> {
}
// Commit only if parser read till EOF
fn read_till_eof<T, F>(&mut self, cb: F) -> Option<T> where
fn read_till_eof<T, F>(&mut self, cb: F) -> Option<T>
where
F: FnOnce(&mut Parser<'_>) -> Option<T>,
{
self.read_atomically(move |p| {
cb(p).filter(|_| p.is_eof())
})
self.read_atomically(move |p| cb(p).filter(|_| p.is_eof()))
}
// Return result of first successful parser
fn read_or<T>(&mut self, parsers: &mut [Box<dyn FnMut(&mut Parser<'_>) -> Option<T> + 'static>])
-> Option<T> {
fn read_or<T>(
&mut self,
parsers: &mut [Box<dyn FnMut(&mut Parser<'_>) -> Option<T> + 'static>],
) -> Option<T> {
for pf in parsers {
if let Some(r) = self.read_atomically(|p: &mut Parser<'_>| pf(p)) {
return Some(r);
@ -59,11 +58,8 @@ impl<'a> Parser<'a> {
}
// Apply 3 parsers sequentially
fn read_seq_3<A, B, C, PA, PB, PC>(&mut self,
pa: PA,
pb: PB,
pc: PC)
-> Option<(A, B, C)> where
fn read_seq_3<A, B, C, PA, PB, PC>(&mut self, pa: PA, pb: PB, pc: PC) -> Option<(A, B, C)>
where
PA: FnOnce(&mut Parser<'_>) -> Option<A>,
PB: FnOnce(&mut Parser<'_>) -> Option<B>,
PC: FnOnce(&mut Parser<'_>) -> Option<C>,
@ -74,7 +70,7 @@ impl<'a> Parser<'a> {
let c = if b.is_some() { pc(p) } else { None };
match (a, b, c) {
(Some(a), Some(b), Some(c)) => Some((a, b, c)),
_ => None
_ => None,
}
})
}
@ -92,11 +88,9 @@ impl<'a> Parser<'a> {
// Return char and advance iff next char is equal to requested
fn read_given_char(&mut self, c: char) -> Option<char> {
self.read_atomically(|p| {
match p.read_char() {
self.read_atomically(|p| match p.read_char() {
Some(next) if next == c => Some(next),
_ => None,
}
})
}
@ -116,9 +110,7 @@ impl<'a> Parser<'a> {
}
}
self.read_atomically(|p| {
p.read_char().and_then(|c| parse_digit(c, radix))
})
self.read_atomically(|p| p.read_char().and_then(|c| parse_digit(c, radix)))
}
fn read_number_impl(&mut self, radix: u8, max_digits: u32, upto: u32) -> Option<u32> {
@ -130,14 +122,14 @@ impl<'a> Parser<'a> {
r = r * (radix as u32) + (d as u32);
digit_count += 1;
if digit_count > max_digits || r >= upto {
return None
return None;
}
}
None => {
if digit_count == 0 {
return None
return None;
} else {
return Some(r)
return Some(r);
}
}
};
@ -173,12 +165,11 @@ impl<'a> Parser<'a> {
assert!(head.len() + tail.len() <= 8);
let mut gs = [0; 8];
gs[..head.len()].copy_from_slice(head);
gs[(8 - tail.len()) .. 8].copy_from_slice(tail);
gs[(8 - tail.len())..8].copy_from_slice(tail);
Ipv6Addr::new(gs[0], gs[1], gs[2], gs[3], gs[4], gs[5], gs[6], gs[7])
}
fn read_groups(p: &mut Parser<'_>, groups: &mut [u16; 8], limit: usize)
-> (usize, bool) {
fn read_groups(p: &mut Parser<'_>, groups: &mut [u16; 8], limit: usize) -> (usize, bool) {
let mut i = 0;
while i < limit {
if i < limit - 1 {
@ -206,7 +197,7 @@ impl<'a> Parser<'a> {
});
match group {
Some(g) => groups[i] = g,
None => return (i, false)
None => return (i, false),
}
i += 1;
}
@ -218,13 +209,13 @@ impl<'a> Parser<'a> {
if head_size == 8 {
return Some(Ipv6Addr::new(
head[0], head[1], head[2], head[3],
head[4], head[5], head[6], head[7]))
head[0], head[1], head[2], head[3], head[4], head[5], head[6], head[7],
));
}
// IPv4 part is not allowed before `::`
if head_ipv4 {
return None
return None;
}
// read `::` if previous code parsed less than 8 groups
@ -252,9 +243,7 @@ impl<'a> Parser<'a> {
fn read_socket_addr_v4(&mut self) -> Option<SocketAddrV4> {
let ip_addr = |p: &mut Parser<'_>| p.read_ipv4_addr();
let colon = |p: &mut Parser<'_>| p.read_given_char(':');
let port = |p: &mut Parser<'_>| {
p.read_number(10, 5, 0x10000).map(|n| n as u16)
};
let port = |p: &mut Parser<'_>| p.read_number(10, 5, 0x10000).map(|n| n as u16);
self.read_seq_3(ip_addr, colon, port).map(|t| {
let (ip, _, port): (Ipv4Addr, char, u16) = t;
@ -270,9 +259,7 @@ impl<'a> Parser<'a> {
p.read_seq_3(open_br, ip_addr, clos_br).map(|t| t.1)
};
let colon = |p: &mut Parser<'_>| p.read_given_char(':');
let port = |p: &mut Parser<'_>| {
p.read_number(10, 5, 0x10000).map(|n| n as u16)
};
let port = |p: &mut Parser<'_>| p.read_number(10, 5, 0x10000).map(|n| n as u16);
self.read_seq_3(ip_addr, colon, port).map(|t| {
let (ip, _, port): (Ipv6Addr, char, u16) = t;
@ -293,7 +280,7 @@ impl FromStr for IpAddr {
fn from_str(s: &str) -> Result<IpAddr, AddrParseError> {
match Parser::new(s).read_till_eof(|p| p.read_ip_addr()) {
Some(s) => Ok(s),
None => Err(AddrParseError(()))
None => Err(AddrParseError(())),
}
}
}
@ -304,7 +291,7 @@ impl FromStr for Ipv4Addr {
fn from_str(s: &str) -> Result<Ipv4Addr, AddrParseError> {
match Parser::new(s).read_till_eof(|p| p.read_ipv4_addr()) {
Some(s) => Ok(s),
None => Err(AddrParseError(()))
None => Err(AddrParseError(())),
}
}
}
@ -315,7 +302,7 @@ impl FromStr for Ipv6Addr {
fn from_str(s: &str) -> Result<Ipv6Addr, AddrParseError> {
match Parser::new(s).read_till_eof(|p| p.read_ipv6_addr()) {
Some(s) => Ok(s),
None => Err(AddrParseError(()))
None => Err(AddrParseError(())),
}
}
}

View file

@ -2,7 +2,7 @@ use crate::io::prelude::*;
use crate::fmt;
use crate::io::{self, Initializer, IoSlice, IoSliceMut};
use crate::net::{ToSocketAddrs, SocketAddr, Shutdown};
use crate::net::{Shutdown, SocketAddr, ToSocketAddrs};
use crate::sys_common::net as net_imp;
use crate::sys_common::{AsInner, FromInner, IntoInner};
use crate::time::Duration;
@ -93,7 +93,9 @@ pub struct TcpListener(net_imp::TcpListener);
/// [`TcpListener`]: ../../std/net/struct.TcpListener.html
#[stable(feature = "rust1", since = "1.0.0")]
#[derive(Debug)]
pub struct Incoming<'a> { listener: &'a TcpListener }
pub struct Incoming<'a> {
listener: &'a TcpListener,
}
impl TcpStream {
/// Opens a TCP connection to a remote host.
@ -567,7 +569,9 @@ impl TcpStream {
#[stable(feature = "rust1", since = "1.0.0")]
impl Read for TcpStream {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> { self.0.read(buf) }
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
self.0.read(buf)
}
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
self.0.read_vectored(bufs)
@ -580,17 +584,23 @@ impl Read for TcpStream {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Write for TcpStream {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { self.0.write(buf) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
self.0.write(buf)
}
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
self.0.write_vectored(bufs)
}
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Read for &TcpStream {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> { self.0.read(buf) }
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
self.0.read(buf)
}
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
self.0.read_vectored(bufs)
@ -603,25 +613,35 @@ impl Read for &TcpStream {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl Write for &TcpStream {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> { self.0.write(buf) }
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
self.0.write(buf)
}
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
self.0.write_vectored(bufs)
}
fn flush(&mut self) -> io::Result<()> { Ok(()) }
fn flush(&mut self) -> io::Result<()> {
Ok(())
}
}
impl AsInner<net_imp::TcpStream> for TcpStream {
fn as_inner(&self) -> &net_imp::TcpStream { &self.0 }
fn as_inner(&self) -> &net_imp::TcpStream {
&self.0
}
}
impl FromInner<net_imp::TcpStream> for TcpStream {
fn from_inner(inner: net_imp::TcpStream) -> TcpStream { TcpStream(inner) }
fn from_inner(inner: net_imp::TcpStream) -> TcpStream {
TcpStream(inner)
}
}
impl IntoInner<net_imp::TcpStream> for TcpStream {
fn into_inner(self) -> net_imp::TcpStream { self.0 }
fn into_inner(self) -> net_imp::TcpStream {
self.0
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -814,16 +834,20 @@ impl TcpListener {
}
#[stable(feature = "net2_mutators", since = "1.9.0")]
#[rustc_deprecated(since = "1.16.0",
reason = "this option can only be set before the socket is bound")]
#[rustc_deprecated(
since = "1.16.0",
reason = "this option can only be set before the socket is bound"
)]
#[allow(missing_docs)]
pub fn set_only_v6(&self, only_v6: bool) -> io::Result<()> {
self.0.set_only_v6(only_v6)
}
#[stable(feature = "net2_mutators", since = "1.9.0")]
#[rustc_deprecated(since = "1.16.0",
reason = "this option can only be set before the socket is bound")]
#[rustc_deprecated(
since = "1.16.0",
reason = "this option can only be set before the socket is bound"
)]
#[allow(missing_docs)]
pub fn only_v6(&self) -> io::Result<bool> {
self.0.only_v6()
@ -907,7 +931,9 @@ impl<'a> Iterator for Incoming<'a> {
}
impl AsInner<net_imp::TcpListener> for TcpListener {
fn as_inner(&self) -> &net_imp::TcpListener { &self.0 }
fn as_inner(&self) -> &net_imp::TcpListener {
&self.0
}
}
impl FromInner<net_imp::TcpListener> for TcpListener {
@ -917,7 +943,9 @@ impl FromInner<net_imp::TcpListener> for TcpListener {
}
impl IntoInner<net_imp::TcpListener> for TcpListener {
fn into_inner(self) -> net_imp::TcpListener { self.0 }
fn into_inner(self) -> net_imp::TcpListener {
self.0
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -930,13 +958,13 @@ impl fmt::Debug for TcpListener {
#[cfg(all(test, not(any(target_os = "cloudabi", target_os = "emscripten"))))]
mod tests {
use crate::fmt;
use crate::io::{ErrorKind, IoSlice, IoSliceMut};
use crate::io::prelude::*;
use crate::net::*;
use crate::io::{ErrorKind, IoSlice, IoSliceMut};
use crate::net::test::{next_test_ip4, next_test_ip6};
use crate::net::*;
use crate::sync::mpsc::channel;
use crate::time::{Instant, Duration};
use crate::thread;
use crate::time::{Duration, Instant};
fn each_ip(f: &mut dyn FnMut(SocketAddr)) {
f(next_test_ip4());
@ -949,15 +977,14 @@ mod tests {
Ok(t) => t,
Err(e) => panic!("received error for `{}`: {}", stringify!($e), e),
}
}
};
}
#[test]
fn bind_error() {
match TcpListener::bind("1.1.1.1:9999") {
Ok(..) => panic!(),
Err(e) =>
assert_eq!(e.kind(), ErrorKind::AddrNotAvailable),
Err(e) => assert_eq!(e.kind(), ErrorKind::AddrNotAvailable),
}
}
@ -965,11 +992,15 @@ mod tests {
fn connect_error() {
match TcpStream::connect("0.0.0.0:1") {
Ok(..) => panic!(),
Err(e) => assert!(e.kind() == ErrorKind::ConnectionRefused ||
e.kind() == ErrorKind::InvalidInput ||
e.kind() == ErrorKind::AddrInUse ||
e.kind() == ErrorKind::AddrNotAvailable,
"bad error: {} {:?}", e, e.kind()),
Err(e) => assert!(
e.kind() == ErrorKind::ConnectionRefused
|| e.kind() == ErrorKind::InvalidInput
|| e.kind() == ErrorKind::AddrInUse
|| e.kind() == ErrorKind::AddrNotAvailable,
"bad error: {} {:?}",
e,
e.kind()
),
}
}
@ -979,8 +1010,7 @@ mod tests {
let listener = t!(TcpListener::bind(&socket_addr));
let _t = thread::spawn(move || {
let mut stream = t!(TcpStream::connect(&("localhost",
socket_addr.port())));
let mut stream = t!(TcpStream::connect(&("localhost", socket_addr.port())));
t!(stream.write(&[144]));
});
@ -995,7 +1025,7 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let host = match addr {
SocketAddr::V4(..) => "127.0.0.1",
SocketAddr::V6(..) => "::1",
@ -1017,7 +1047,7 @@ mod tests {
let acceptor = t!(TcpListener::bind(&addr));
let (tx, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut stream = t!(TcpStream::connect(&addr));
t!(stream.write(&[99]));
tx.send(t!(stream.local_addr())).unwrap();
@ -1036,7 +1066,7 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _stream = t!(TcpStream::connect(&addr));
// Close
});
@ -1056,7 +1086,7 @@ mod tests {
let acceptor = t!(TcpListener::bind(&addr));
let (tx, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
drop(t!(TcpStream::connect(&addr)));
tx.send(()).unwrap();
});
@ -1067,10 +1097,13 @@ mod tests {
match stream.write(&buf) {
Ok(..) => {}
Err(e) => {
assert!(e.kind() == ErrorKind::ConnectionReset ||
e.kind() == ErrorKind::BrokenPipe ||
e.kind() == ErrorKind::ConnectionAborted,
"unknown error: {}", e);
assert!(
e.kind() == ErrorKind::ConnectionReset
|| e.kind() == ErrorKind::BrokenPipe
|| e.kind() == ErrorKind::ConnectionAborted,
"unknown error: {}",
e
);
}
}
})
@ -1082,7 +1115,7 @@ mod tests {
let max = 10;
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
for _ in 0..max {
let mut stream = t!(TcpStream::connect(&addr));
t!(stream.write(&[99]));
@ -1104,11 +1137,11 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let acceptor = acceptor;
for (i, stream) in acceptor.incoming().enumerate().take(MAX) {
// Start another thread to handle the connection
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut stream = t!(stream);
let mut buf = [0];
t!(stream.read(&mut buf));
@ -1121,9 +1154,11 @@ mod tests {
});
fn connect(i: usize, addr: SocketAddr) {
if i == MAX { return }
if i == MAX {
return;
}
let t = thread::spawn(move|| {
let t = thread::spawn(move || {
let mut stream = t!(TcpStream::connect(&addr));
// Connect again before writing
connect(i + 1, addr);
@ -1139,10 +1174,10 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
for stream in acceptor.incoming().take(MAX) {
// Start another thread to handle the connection
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut stream = t!(stream);
let mut buf = [0];
t!(stream.read(&mut buf));
@ -1155,9 +1190,11 @@ mod tests {
});
fn connect(i: usize, addr: SocketAddr) {
if i == MAX { return }
if i == MAX {
return;
}
let t = thread::spawn(move|| {
let t = thread::spawn(move || {
let mut stream = t!(TcpStream::connect(&addr));
connect(i + 1, addr);
t!(stream.write(&[99]));
@ -1172,7 +1209,7 @@ mod tests {
let listener = t!(TcpListener::bind(&addr));
let so_name = t!(listener.local_addr());
assert_eq!(addr, so_name);
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
t!(listener.accept());
});
@ -1186,7 +1223,7 @@ mod tests {
each_ip(&mut |addr| {
let (tx, rx) = channel();
let srv = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut cl = t!(srv.accept()).0;
cl.write(&[10]).unwrap();
let mut b = [0];
@ -1215,9 +1252,11 @@ mod tests {
let mut a = [];
let mut b = [0];
let mut c = [0; 3];
let len = t!(s2.read_vectored(
&mut [IoSliceMut::new(&mut a), IoSliceMut::new(&mut b), IoSliceMut::new(&mut c)],
));
let len = t!(s2.read_vectored(&mut [
IoSliceMut::new(&mut a),
IoSliceMut::new(&mut b),
IoSliceMut::new(&mut c)
],));
assert!(len > 0);
assert_eq!(b, [10]);
// some implementations don't support readv, so we may only fill the first buffer
@ -1260,10 +1299,14 @@ mod tests {
listener1, listener2
),
Err(e) => {
assert!(e.kind() == ErrorKind::ConnectionRefused ||
e.kind() == ErrorKind::Other ||
e.kind() == ErrorKind::AddrInUse,
"unknown error: {} {:?}", e, e.kind());
assert!(
e.kind() == ErrorKind::ConnectionRefused
|| e.kind() == ErrorKind::Other
|| e.kind() == ErrorKind::AddrInUse,
"unknown error: {} {:?}",
e,
e.kind()
);
}
}
})
@ -1274,7 +1317,7 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
t!(TcpStream::connect(&addr));
});
@ -1289,7 +1332,7 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s = t!(TcpStream::connect(&addr));
let mut buf = [0, 0];
assert_eq!(s.read(&mut buf).unwrap(), 1);
@ -1302,7 +1345,7 @@ mod tests {
let (tx1, rx1) = channel();
let (tx2, rx2) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s2 = s2;
rx1.recv().unwrap();
t!(s2.write(&[1]));
@ -1322,7 +1365,7 @@ mod tests {
let (tx1, rx) = channel();
let tx2 = tx1.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s = t!(TcpStream::connect(&addr));
t!(s.write(&[1]));
rx.recv().unwrap();
@ -1334,7 +1377,7 @@ mod tests {
let s2 = t!(s1.try_clone());
let (done, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s2 = s2;
let mut buf = [0, 0];
t!(s2.read(&mut buf));
@ -1354,7 +1397,7 @@ mod tests {
each_ip(&mut |addr| {
let acceptor = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s = t!(TcpStream::connect(&addr));
let mut buf = [0, 1];
t!(s.read(&mut buf));
@ -1365,7 +1408,7 @@ mod tests {
let s2 = t!(s1.try_clone());
let (done, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s2 = s2;
t!(s2.write(&[1]));
done.send(()).unwrap();
@ -1382,7 +1425,7 @@ mod tests {
fn shutdown_smoke() {
each_ip(&mut |addr| {
let a = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut c = t!(a.accept()).0;
let mut b = [0];
assert_eq!(c.read(&mut b).unwrap(), 0);
@ -1405,7 +1448,7 @@ mod tests {
each_ip(&mut |addr| {
let a = t!(TcpListener::bind(&addr));
let (tx, rx) = channel::<()>();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _s = t!(a.accept());
let _ = rx.recv();
});
@ -1444,7 +1487,7 @@ mod tests {
each_ip(&mut |addr| {
let a = t!(TcpListener::bind(&addr));
let (tx1, rx) = channel::<()>();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _s = t!(a.accept());
let _ = rx.recv();
});
@ -1452,7 +1495,7 @@ mod tests {
let s = t!(TcpStream::connect(&addr));
let s2 = t!(s.try_clone());
let (tx, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut s2 = s2;
assert_eq!(t!(s2.read(&mut [0])), 0);
tx.send(()).unwrap();
@ -1475,7 +1518,7 @@ mod tests {
let (tx, rx) = channel();
let (txdone, rxdone) = channel();
let txdone2 = txdone.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut tcp = t!(TcpStream::connect(&addr));
rx.recv().unwrap();
t!(tcp.write(&[0]));
@ -1486,7 +1529,7 @@ mod tests {
let tcp = t!(accept.accept()).0;
let tcp2 = t!(tcp.try_clone());
let txdone3 = txdone.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut tcp2 = tcp2;
t!(tcp2.read(&mut [0]));
txdone3.send(()).unwrap();
@ -1512,10 +1555,10 @@ mod tests {
let a = t!(TcpListener::bind(&addr));
let a2 = t!(a.try_clone());
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _ = TcpStream::connect(&addr);
});
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _ = TcpStream::connect(&addr);
});
@ -1533,17 +1576,17 @@ mod tests {
let (tx, rx) = channel();
let tx2 = tx.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
tx.send(t!(a.accept())).unwrap();
});
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
tx2.send(t!(a2.accept())).unwrap();
});
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _ = TcpStream::connect(&addr);
});
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let _ = TcpStream::connect(&addr);
});
@ -1563,10 +1606,10 @@ mod tests {
addr.to_string()
}
#[cfg(unix)]
use crate::os::unix::io::AsRawFd;
#[cfg(target_env = "sgx")]
use crate::os::fortanix_sgx::io::AsRawFd;
#[cfg(unix)]
use crate::os::unix::io::AsRawFd;
#[cfg(not(windows))]
fn render_inner(addr: &dyn AsRawFd) -> impl fmt::Debug {
addr.as_raw_fd()
@ -1576,22 +1619,26 @@ mod tests {
addr.as_raw_socket()
}
let inner_name = if cfg!(windows) {"socket"} else {"fd"};
let inner_name = if cfg!(windows) { "socket" } else { "fd" };
let socket_addr = next_test_ip4();
let listener = t!(TcpListener::bind(&socket_addr));
let compare = format!("TcpListener {{ addr: {:?}, {}: {:?} }}",
let compare = format!(
"TcpListener {{ addr: {:?}, {}: {:?} }}",
render_socket_addr(&socket_addr),
inner_name,
render_inner(&listener));
render_inner(&listener)
);
assert_eq!(format!("{:?}", listener), compare);
let stream = t!(TcpStream::connect(&("localhost", socket_addr.port())));
let compare = format!("TcpStream {{ addr: {:?}, peer: {:?}, {}: {:?} }}",
let compare = format!(
"TcpStream {{ addr: {:?}, peer: {:?}, {}: {:?} }}",
render_socket_addr(&stream.local_addr().unwrap()),
render_socket_addr(&stream.peer_addr().unwrap()),
inner_name,
render_inner(&stream));
render_inner(&stream)
);
assert_eq!(format!("{:?}", stream), compare);
}
@ -1638,8 +1685,11 @@ mod tests {
let mut buf = [0; 10];
let start = Instant::now();
let kind = stream.read_exact(&mut buf).err().expect("expected error").kind();
assert!(kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}", kind);
assert!(
kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}",
kind
);
assert!(start.elapsed() > Duration::from_millis(400));
drop(listener);
}
@ -1662,8 +1712,11 @@ mod tests {
let start = Instant::now();
let kind = stream.read_exact(&mut buf).err().expect("expected error").kind();
assert!(kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}", kind);
assert!(
kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}",
kind
);
assert!(start.elapsed() > Duration::from_millis(400));
drop(listener);
}
@ -1749,9 +1802,9 @@ mod tests {
let (txdone, rxdone) = channel();
let srv = t!(TcpListener::bind(&addr));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut cl = t!(srv.accept()).0;
cl.write(&[1,3,3,7]).unwrap();
cl.write(&[1, 3, 3, 7]).unwrap();
t!(rxdone.recv());
});

View file

@ -1,7 +1,7 @@
#![allow(warnings)] // not used on emscripten
use crate::env;
use crate::net::{SocketAddr, SocketAddrV4, SocketAddrV6, Ipv4Addr, Ipv6Addr, ToSocketAddrs};
use crate::net::{Ipv4Addr, Ipv6Addr, SocketAddr, SocketAddrV4, SocketAddrV6, ToSocketAddrs};
use crate::sync::atomic::{AtomicUsize, Ordering};
static PORT: AtomicUsize = AtomicUsize::new(0);
@ -13,8 +13,7 @@ pub fn next_test_ip4() -> SocketAddr {
pub fn next_test_ip6() -> SocketAddr {
let port = PORT.fetch_add(1, Ordering::SeqCst) as u16 + base_port();
SocketAddr::V6(SocketAddrV6::new(Ipv6Addr::new(0, 0, 0, 0, 0, 0, 0, 1),
port, 0, 0))
SocketAddr::V6(SocketAddrV6::new(Ipv6Addr::new(0, 0, 0, 0, 0, 0, 0, 1), port, 0, 0))
}
pub fn sa4(a: Ipv4Addr, p: u16) -> SocketAddr {
@ -41,11 +40,21 @@ fn base_port() -> u16 {
} else {
env::current_dir().unwrap().into_os_string().into_string().unwrap()
};
let dirs = ["32-opt", "32-nopt",
"musl-64-opt", "cross-opt",
"64-opt", "64-nopt", "64-opt-vg", "64-debug-opt",
"all-opt", "snap3", "dist", "sgx"];
dirs.iter().enumerate().find(|&(_, dir)| {
cwd.contains(dir)
}).map(|p| p.0).unwrap_or(0) as u16 * 1000 + 19600
let dirs = [
"32-opt",
"32-nopt",
"musl-64-opt",
"cross-opt",
"64-opt",
"64-nopt",
"64-opt-vg",
"64-debug-opt",
"all-opt",
"snap3",
"dist",
"sgx",
];
dirs.iter().enumerate().find(|&(_, dir)| cwd.contains(dir)).map(|p| p.0).unwrap_or(0) as u16
* 1000
+ 19600
}

View file

@ -1,6 +1,6 @@
use crate::fmt;
use crate::io::{self, Error, ErrorKind};
use crate::net::{ToSocketAddrs, SocketAddr, Ipv4Addr, Ipv6Addr};
use crate::net::{Ipv4Addr, Ipv6Addr, SocketAddr, ToSocketAddrs};
use crate::sys_common::net as net_imp;
use crate::sys_common::{AsInner, FromInner, IntoInner};
use crate::time::Duration;
@ -171,12 +171,10 @@ impl UdpSocket {
/// socket.send_to(&[0; 10], "127.0.0.1:4242").expect("couldn't send data");
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn send_to<A: ToSocketAddrs>(&self, buf: &[u8], addr: A)
-> io::Result<usize> {
pub fn send_to<A: ToSocketAddrs>(&self, buf: &[u8], addr: A) -> io::Result<usize> {
match addr.to_socket_addrs()?.next() {
Some(addr) => self.0.send_to(buf, &addr),
None => Err(Error::new(ErrorKind::InvalidInput,
"no addresses to send data to")),
None => Err(Error::new(ErrorKind::InvalidInput, "no addresses to send data to")),
}
}
@ -817,15 +815,21 @@ impl UdpSocket {
}
impl AsInner<net_imp::UdpSocket> for UdpSocket {
fn as_inner(&self) -> &net_imp::UdpSocket { &self.0 }
fn as_inner(&self) -> &net_imp::UdpSocket {
&self.0
}
}
impl FromInner<net_imp::UdpSocket> for UdpSocket {
fn from_inner(inner: net_imp::UdpSocket) -> UdpSocket { UdpSocket(inner) }
fn from_inner(inner: net_imp::UdpSocket) -> UdpSocket {
UdpSocket(inner)
}
}
impl IntoInner<net_imp::UdpSocket> for UdpSocket {
fn into_inner(self) -> net_imp::UdpSocket { self.0 }
fn into_inner(self) -> net_imp::UdpSocket {
self.0
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -838,12 +842,12 @@ impl fmt::Debug for UdpSocket {
#[cfg(all(test, not(any(target_os = "cloudabi", target_os = "emscripten", target_env = "sgx"))))]
mod tests {
use crate::io::ErrorKind;
use crate::net::*;
use crate::net::test::{next_test_ip4, next_test_ip6};
use crate::net::*;
use crate::sync::mpsc::channel;
use crate::sys_common::AsInner;
use crate::time::{Instant, Duration};
use crate::thread;
use crate::time::{Duration, Instant};
fn each_ip(f: &mut dyn FnMut(SocketAddr, SocketAddr)) {
f(next_test_ip4(), next_test_ip4());
@ -856,16 +860,14 @@ mod tests {
Ok(t) => t,
Err(e) => panic!("received error for `{}`: {}", stringify!($e), e),
}
}
};
}
#[test]
fn bind_error() {
match UdpSocket::bind("1.1.1.1:9999") {
Ok(..) => panic!(),
Err(e) => {
assert_eq!(e.kind(), ErrorKind::AddrNotAvailable)
}
Err(e) => assert_eq!(e.kind(), ErrorKind::AddrNotAvailable),
}
}
@ -875,7 +877,7 @@ mod tests {
let (tx1, rx1) = channel();
let (tx2, rx2) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let client = t!(UdpSocket::bind(&client_ip));
rx1.recv().unwrap();
t!(client.send_to(&[99], &server_ip));
@ -917,7 +919,7 @@ mod tests {
let sock1 = t!(UdpSocket::bind(&addr1));
let sock2 = t!(UdpSocket::bind(&addr2));
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut buf = [0, 0];
assert_eq!(sock2.recv_from(&mut buf).unwrap(), (1, addr1));
assert_eq!(buf[0], 1);
@ -928,7 +930,7 @@ mod tests {
let (tx1, rx1) = channel();
let (tx2, rx2) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
rx1.recv().unwrap();
t!(sock3.send_to(&[1], &addr2));
tx2.send(()).unwrap();
@ -948,7 +950,7 @@ mod tests {
let (tx1, rx) = channel();
let tx2 = tx1.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
t!(sock2.send_to(&[1], &addr1));
rx.recv().unwrap();
t!(sock2.send_to(&[2], &addr1));
@ -958,7 +960,7 @@ mod tests {
let sock3 = t!(sock1.try_clone());
let (done, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut buf = [0, 0];
t!(sock3.recv_from(&mut buf));
tx2.send(()).unwrap();
@ -981,7 +983,7 @@ mod tests {
let (tx, rx) = channel();
let (serv_tx, serv_rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
let mut buf = [0, 1];
rx.recv().unwrap();
t!(sock2.recv_from(&mut buf));
@ -992,15 +994,19 @@ mod tests {
let (done, rx) = channel();
let tx2 = tx.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
match sock3.send_to(&[1], &addr2) {
Ok(..) => { let _ = tx2.send(()); }
Ok(..) => {
let _ = tx2.send(());
}
Err(..) => {}
}
done.send(()).unwrap();
});
match sock1.send_to(&[2], &addr2) {
Ok(..) => { let _ = tx.send(()); }
Ok(..) => {
let _ = tx.send(());
}
Err(..) => {}
}
drop(tx);
@ -1012,13 +1018,13 @@ mod tests {
#[test]
fn debug() {
let name = if cfg!(windows) {"socket"} else {"fd"};
let name = if cfg!(windows) { "socket" } else { "fd" };
let socket_addr = next_test_ip4();
let udpsock = t!(UdpSocket::bind(&socket_addr));
let udpsock_inner = udpsock.0.socket().as_inner();
let compare = format!("UdpSocket {{ addr: {:?}, {}: {:?} }}",
socket_addr, name, udpsock_inner);
let compare =
format!("UdpSocket {{ addr: {:?}, {}: {:?} }}", socket_addr, name, udpsock_inner);
assert_eq!(format!("{:?}", udpsock), compare);
}
@ -1063,8 +1069,11 @@ mod tests {
loop {
let kind = stream.recv_from(&mut buf).err().expect("expected error").kind();
if kind != ErrorKind::Interrupted {
assert!(kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}", kind);
assert!(
kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}",
kind
);
break;
}
}
@ -1088,8 +1097,11 @@ mod tests {
loop {
let kind = stream.recv_from(&mut buf).err().expect("expected error").kind();
if kind != ErrorKind::Interrupted {
assert!(kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}", kind);
assert!(
kind == ErrorKind::WouldBlock || kind == ErrorKind::TimedOut,
"unexpected_error: {:?}",
kind
);
break;
}
}

View file

@ -6,33 +6,41 @@
#![stable(feature = "rust1", since = "1.0.0")]
#![allow(missing_docs)]
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::num::{FpCategory, ParseIntError, ParseFloatError, TryFromIntError};
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::num::Wrapping;
#[stable(feature = "rust1", since = "1.0.0")]
pub use core::num::{FpCategory, ParseFloatError, ParseIntError, TryFromIntError};
#[stable(feature = "nonzero", since = "1.28.0")]
pub use core::num::{NonZeroU8, NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU128, NonZeroUsize};
#[stable(feature = "signed_nonzero", since = "1.34.0")]
pub use core::num::{NonZeroI8, NonZeroI16, NonZeroI32, NonZeroI64, NonZeroI128, NonZeroIsize};
pub use core::num::{NonZeroI128, NonZeroI16, NonZeroI32, NonZeroI64, NonZeroI8, NonZeroIsize};
#[stable(feature = "nonzero", since = "1.28.0")]
pub use core::num::{NonZeroU128, NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU8, NonZeroUsize};
#[unstable(feature = "int_error_matching",
#[unstable(
feature = "int_error_matching",
reason = "it can be useful to match errors when making error messages \
for integer parsing",
issue = "22639")]
issue = "22639"
)]
pub use core::num::IntErrorKind;
#[cfg(test)] use crate::fmt;
#[cfg(test)] use crate::ops::{Add, Sub, Mul, Div, Rem};
#[cfg(test)]
use crate::fmt;
#[cfg(test)]
use crate::ops::{Add, Div, Mul, Rem, Sub};
/// Helper function for testing numeric operations
#[cfg(test)]
pub fn test_num<T>(ten: T, two: T) where
pub fn test_num<T>(ten: T, two: T)
where
T: PartialEq
+ Add<Output=T> + Sub<Output=T>
+ Mul<Output=T> + Div<Output=T>
+ Rem<Output=T> + fmt::Debug
+ Copy
+ Add<Output = T>
+ Sub<Output = T>
+ Mul<Output = T>
+ Div<Output = T>
+ Rem<Output = T>
+ fmt::Debug
+ Copy,
{
assert_eq!(ten.add(two), ten + two);
assert_eq!(ten.sub(two), ten - two);
@ -43,20 +51,20 @@ pub fn test_num<T>(ten: T, two: T) where
#[cfg(test)]
mod tests {
use crate::u8;
use crate::ops::Mul;
use crate::u16;
use crate::u32;
use crate::u64;
use crate::u8;
use crate::usize;
use crate::ops::Mul;
#[test]
fn test_saturating_add_uint() {
use crate::usize::MAX;
assert_eq!(3_usize.saturating_add(5_usize), 8_usize);
assert_eq!(3_usize.saturating_add(MAX-1), MAX);
assert_eq!(3_usize.saturating_add(MAX - 1), MAX);
assert_eq!(MAX.saturating_add(MAX), MAX);
assert_eq!((MAX-2).saturating_add(1), MAX-1);
assert_eq!((MAX - 2).saturating_add(1), MAX - 1);
}
#[test]
@ -65,16 +73,16 @@ mod tests {
assert_eq!(5_usize.saturating_sub(3_usize), 2_usize);
assert_eq!(3_usize.saturating_sub(5_usize), 0_usize);
assert_eq!(0_usize.saturating_sub(1_usize), 0_usize);
assert_eq!((MAX-1).saturating_sub(MAX), 0);
assert_eq!((MAX - 1).saturating_sub(MAX), 0);
}
#[test]
fn test_saturating_add_int() {
use crate::isize::{MIN,MAX};
use crate::isize::{MAX, MIN};
assert_eq!(3i32.saturating_add(5), 8);
assert_eq!(3isize.saturating_add(MAX-1), MAX);
assert_eq!(3isize.saturating_add(MAX - 1), MAX);
assert_eq!(MAX.saturating_add(MAX), MAX);
assert_eq!((MAX-2).saturating_add(1), MAX-1);
assert_eq!((MAX - 2).saturating_add(1), MAX - 1);
assert_eq!(3i32.saturating_add(-5), -2);
assert_eq!(MIN.saturating_add(-1), MIN);
assert_eq!((-2isize).saturating_add(-MAX), MIN);
@ -82,14 +90,14 @@ mod tests {
#[test]
fn test_saturating_sub_int() {
use crate::isize::{MIN,MAX};
use crate::isize::{MAX, MIN};
assert_eq!(3i32.saturating_sub(5), -2);
assert_eq!(MIN.saturating_sub(1), MIN);
assert_eq!((-2isize).saturating_sub(MAX), MIN);
assert_eq!(3i32.saturating_sub(-5), 8);
assert_eq!(3isize.saturating_sub(-(MAX-1)), MAX);
assert_eq!(3isize.saturating_sub(-(MAX - 1)), MAX);
assert_eq!(MAX.saturating_sub(-MAX), MAX);
assert_eq!((MAX-2).saturating_sub(-1), MAX-1);
assert_eq!((MAX - 2).saturating_sub(-1), MAX - 1);
}
#[test]
@ -128,7 +136,7 @@ mod tests {
}
macro_rules! test_is_power_of_two {
($test_name:ident, $T:ident) => (
($test_name:ident, $T:ident) => {
fn $test_name() {
#![test]
assert_eq!((0 as $T).is_power_of_two(), false);
@ -139,27 +147,29 @@ mod tests {
assert_eq!((5 as $T).is_power_of_two(), false);
assert_eq!(($T::MAX / 2 + 1).is_power_of_two(), true);
}
)
};
}
test_is_power_of_two!{ test_is_power_of_two_u8, u8 }
test_is_power_of_two!{ test_is_power_of_two_u16, u16 }
test_is_power_of_two!{ test_is_power_of_two_u32, u32 }
test_is_power_of_two!{ test_is_power_of_two_u64, u64 }
test_is_power_of_two!{ test_is_power_of_two_uint, usize }
test_is_power_of_two! { test_is_power_of_two_u8, u8 }
test_is_power_of_two! { test_is_power_of_two_u16, u16 }
test_is_power_of_two! { test_is_power_of_two_u32, u32 }
test_is_power_of_two! { test_is_power_of_two_u64, u64 }
test_is_power_of_two! { test_is_power_of_two_uint, usize }
macro_rules! test_next_power_of_two {
($test_name:ident, $T:ident) => (
($test_name:ident, $T:ident) => {
fn $test_name() {
#![test]
assert_eq!((0 as $T).next_power_of_two(), 1);
let mut next_power = 1;
for i in 1 as $T..40 {
assert_eq!(i.next_power_of_two(), next_power);
if i == next_power { next_power *= 2 }
if i == next_power {
next_power *= 2
}
}
)
}
};
}
test_next_power_of_two! { test_next_power_of_two_u8, u8 }
@ -169,12 +179,12 @@ mod tests {
test_next_power_of_two! { test_next_power_of_two_uint, usize }
macro_rules! test_checked_next_power_of_two {
($test_name:ident, $T:ident) => (
($test_name:ident, $T:ident) => {
fn $test_name() {
#![test]
assert_eq!((0 as $T).checked_next_power_of_two(), Some(1));
let smax = $T::MAX >> 1;
assert_eq!(smax.checked_next_power_of_two(), Some(smax+1));
assert_eq!(smax.checked_next_power_of_two(), Some(smax + 1));
assert_eq!((smax + 1).checked_next_power_of_two(), Some(smax + 1));
assert_eq!((smax + 2).checked_next_power_of_two(), None);
assert_eq!(($T::MAX - 1).checked_next_power_of_two(), None);
@ -182,10 +192,12 @@ mod tests {
let mut next_power = 1;
for i in 1 as $T..40 {
assert_eq!(i.checked_next_power_of_two(), Some(next_power));
if i == next_power { next_power *= 2 }
if i == next_power {
next_power *= 2
}
}
)
}
};
}
test_checked_next_power_of_two! { test_checked_next_power_of_two_u8, u8 }
@ -196,7 +208,7 @@ mod tests {
#[test]
fn test_pow() {
fn naive_pow<T: Mul<Output=T> + Copy>(one: T, base: T, exp: usize) -> T {
fn naive_pow<T: Mul<Output = T> + Copy>(one: T, base: T, exp: usize) -> T {
(0..exp).fold(one, |acc, _| acc * base)
}
macro_rules! assert_pow {
@ -204,7 +216,7 @@ mod tests {
let result = $num.pow($exp);
assert_eq!(result, $expected);
assert_eq!(result, naive_pow(1, $num, $exp));
}}
}};
}
assert_pow!((3u32, 0 ) => 1);
assert_pow!((5u32, 1 ) => 5);
@ -280,7 +292,6 @@ mod tests {
}
}
#[cfg(test)]
mod bench {
use test::Bencher;
@ -288,6 +299,8 @@ mod bench {
#[bench]
fn bench_pow_function(b: &mut Bencher) {
let v = (0..1024).collect::<Vec<u32>>();
b.iter(|| {v.iter().fold(0u32, |old, new| old.pow(*new as u32));});
b.iter(|| {
v.iter().fold(0u32, |old, new| old.pow(*new as u32));
});
}
}

View file

@ -7,21 +7,21 @@ use crate::cell::UnsafeCell;
use crate::collections;
use crate::fmt;
use crate::future::Future;
use crate::pin::Pin;
use crate::ops::{Deref, DerefMut};
use crate::panicking;
use crate::ptr::{Unique, NonNull};
use crate::pin::Pin;
use crate::ptr::{NonNull, Unique};
use crate::rc::Rc;
use crate::sync::{Arc, Mutex, RwLock};
use crate::sync::atomic;
use crate::sync::{Arc, Mutex, RwLock};
use crate::task::{Context, Poll};
use crate::thread::Result;
#[stable(feature = "panic_hooks", since = "1.10.0")]
pub use crate::panicking::{take_hook, set_hook};
pub use crate::panicking::{set_hook, take_hook};
#[stable(feature = "panic_hooks", since = "1.10.0")]
pub use core::panic::{PanicInfo, Location};
pub use core::panic::{Location, PanicInfo};
/// A marker trait which represents "panic safe" types in Rust.
///
@ -103,8 +103,8 @@ pub use core::panic::{PanicInfo, Location};
/// [`AssertUnwindSafe`]: ./struct.AssertUnwindSafe.html
#[stable(feature = "catch_unwind", since = "1.9.0")]
#[rustc_on_unimplemented(
message="the type `{Self}` may not be safely transferred across an unwind boundary",
label="`{Self}` may not be safely transferred across an unwind boundary",
message = "the type `{Self}` may not be safely transferred across an unwind boundary",
label = "`{Self}` may not be safely transferred across an unwind boundary"
)]
pub auto trait UnwindSafe {}
@ -121,10 +121,10 @@ pub auto trait UnwindSafe {}
/// [`UnwindSafe`]: ./trait.UnwindSafe.html
#[stable(feature = "catch_unwind", since = "1.9.0")]
#[rustc_on_unimplemented(
message="the type `{Self}` may contain interior mutability and a reference may not be safely \
transferrable across a catch_unwind boundary",
label="`{Self}` may contain interior mutability and a reference may not be safely \
message = "the type `{Self}` may contain interior mutability and a reference may not be safely \
transferrable across a catch_unwind boundary",
label = "`{Self}` may contain interior mutability and a reference may not be safely \
transferrable across a catch_unwind boundary"
)]
pub auto trait RefUnwindSafe {}
@ -187,10 +187,7 @@ pub auto trait RefUnwindSafe {}
/// // ...
/// ```
#[stable(feature = "catch_unwind", since = "1.9.0")]
pub struct AssertUnwindSafe<T>(
#[stable(feature = "catch_unwind", since = "1.9.0")]
pub T
);
pub struct AssertUnwindSafe<T>(#[stable(feature = "catch_unwind", since = "1.9.0")] pub T);
// Implementations of the `UnwindSafe` trait:
//
@ -290,7 +287,12 @@ impl<T> RefUnwindSafe for atomic::AtomicPtr<T> {}
// https://github.com/rust-lang/rust/issues/62301
#[stable(feature = "hashbrown", since = "1.36.0")]
impl<K, V, S> UnwindSafe for collections::HashMap<K, V, S>
where K: UnwindSafe, V: UnwindSafe, S: UnwindSafe {}
where
K: UnwindSafe,
V: UnwindSafe,
S: UnwindSafe,
{
}
#[stable(feature = "catch_unwind", since = "1.9.0")]
impl<T> Deref for AssertUnwindSafe<T> {
@ -320,9 +322,7 @@ impl<R, F: FnOnce() -> R> FnOnce<()> for AssertUnwindSafe<F> {
#[stable(feature = "std_debug", since = "1.16.0")]
impl<T: fmt::Debug> fmt::Debug for AssertUnwindSafe<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_tuple("AssertUnwindSafe")
.field(&self.0)
.finish()
f.debug_tuple("AssertUnwindSafe").field(&self.0).finish()
}
}
@ -391,9 +391,7 @@ impl<F: Future> Future for AssertUnwindSafe<F> {
/// ```
#[stable(feature = "catch_unwind", since = "1.9.0")]
pub fn catch_unwind<F: FnOnce() -> R + UnwindSafe, R>(f: F) -> Result<R> {
unsafe {
panicking::r#try(f)
}
unsafe { panicking::r#try(f) }
}
/// Triggers a panic without invoking the panic hook.

View file

@ -84,7 +84,7 @@ use crate::sync::Arc;
use crate::ffi::{OsStr, OsString};
use crate::sys::path::{is_sep_byte, is_verbatim_sep, MAIN_SEP_STR, parse_prefix};
use crate::sys::path::{is_sep_byte, is_verbatim_sep, parse_prefix, MAIN_SEP_STR};
////////////////////////////////////////////////////////////////////////////////
// GENERAL NOTES
@ -196,26 +196,13 @@ impl<'a> Prefix<'a> {
match *self {
Verbatim(x) => 4 + os_str_len(x),
VerbatimUNC(x, y) => {
8 + os_str_len(x) +
if os_str_len(y) > 0 {
1 + os_str_len(y)
} else {
0
8 + os_str_len(x) + if os_str_len(y) > 0 { 1 + os_str_len(y) } else { 0 }
}
},
VerbatimDisk(_) => 6,
UNC(x, y) => {
2 + os_str_len(x) +
if os_str_len(y) > 0 {
1 + os_str_len(y)
} else {
0
}
},
UNC(x, y) => 2 + os_str_len(x) + if os_str_len(y) > 0 { 1 + os_str_len(y) } else { 0 },
DeviceNS(x) => 4 + os_str_len(x),
Disk(_) => 2,
}
}
/// Determines if the prefix is verbatim, i.e., begins with `\\?\`.
@ -291,7 +278,8 @@ pub const MAIN_SEPARATOR: char = crate::sys::path::MAIN_SEP;
// is not a prefix of `iter`, otherwise return `Some(iter_after_prefix)` giving
// `iter` after having exhausted `prefix`.
fn iter_after<'a, 'b, I, J>(mut iter: I, mut prefix: J) -> Option<I>
where I: Iterator<Item = Component<'a>> + Clone,
where
I: Iterator<Item = Component<'a>> + Clone,
J: Iterator<Item = Component<'b>>,
{
loop {
@ -326,11 +314,7 @@ fn has_redox_scheme(s: &[u8]) -> bool {
/// Says whether the first byte after the prefix is a separator.
fn has_physical_root(s: &[u8], prefix: Option<Prefix<'_>>) -> bool {
let path = if let Some(p) = prefix {
&s[p.len()..]
} else {
s
};
let path = if let Some(p) = prefix { &s[p.len()..] } else { s };
!path.is_empty() && is_sep_byte(path[0])
}
@ -352,8 +336,7 @@ fn split_file_at_dot(file: &OsStr) -> (Option<&OsStr>, Option<&OsStr>) {
if before == Some(b"") {
(Some(file), None)
} else {
(before.map(|s| u8_slice_as_os_str(s)),
after.map(|s| u8_slice_as_os_str(s)))
(before.map(|s| u8_slice_as_os_str(s)), after.map(|s| u8_slice_as_os_str(s)))
}
}
}
@ -509,9 +492,7 @@ pub enum Component<'a> {
///
/// [`Prefix`]: enum.Prefix.html
#[stable(feature = "rust1", since = "1.0.0")]
Prefix(
#[stable(feature = "rust1", since = "1.0.0")] PrefixComponent<'a>
),
Prefix(#[stable(feature = "rust1", since = "1.0.0")] PrefixComponent<'a>),
/// The root directory component, appears after any prefix and before anything else.
///
@ -637,15 +618,11 @@ impl fmt::Debug for Components<'_> {
impl fmt::Debug for DebugHelper<'_> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_list()
.entries(self.0.components())
.finish()
f.debug_list().entries(self.0.components()).finish()
}
}
f.debug_tuple("Components")
.field(&DebugHelper(self.as_path()))
.finish()
f.debug_tuple("Components").field(&DebugHelper(self.as_path())).finish()
}
}
@ -664,26 +641,14 @@ impl<'a> Components<'a> {
/// how much of the prefix is left from the point of view of iteration?
#[inline]
fn prefix_remaining(&self) -> usize {
if self.front == State::Prefix {
self.prefix_len()
} else {
0
}
if self.front == State::Prefix { self.prefix_len() } else { 0 }
}
// Given the iteration so far, how much of the pre-State::Body path is left?
#[inline]
fn len_before_body(&self) -> usize {
let root = if self.front <= State::StartDir && self.has_physical_root {
1
} else {
0
};
let cur_dir = if self.front <= State::StartDir && self.include_cur_dir() {
1
} else {
0
};
let root = if self.front <= State::StartDir && self.has_physical_root { 1 } else { 0 };
let cur_dir = if self.front <= State::StartDir && self.include_cur_dir() { 1 } else { 0 };
self.prefix_remaining() + root + cur_dir
}
@ -695,11 +660,7 @@ impl<'a> Components<'a> {
#[inline]
fn is_sep_byte(&self, b: u8) -> bool {
if self.prefix_verbatim() {
is_verbatim_sep(b)
} else {
is_sep_byte(b)
}
if self.prefix_verbatim() { is_verbatim_sep(b) } else { is_sep_byte(b) }
}
/// Extracts a slice corresponding to the portion of the path remaining for iteration.
@ -835,15 +796,11 @@ impl fmt::Debug for Iter<'_> {
impl fmt::Debug for DebugHelper<'_> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_list()
.entries(self.0.iter())
.finish()
f.debug_list().entries(self.0.iter()).finish()
}
}
f.debug_tuple("Iter")
.field(&DebugHelper(self.as_path()))
.finish()
f.debug_tuple("Iter").field(&DebugHelper(self.as_path())).finish()
}
}
@ -1174,9 +1131,7 @@ impl PathBuf {
/// [`OsString`]: ../ffi/struct.OsString.html
#[unstable(feature = "path_buf_capacity", issue = "58234")]
pub fn with_capacity(capacity: usize) -> PathBuf {
PathBuf {
inner: OsString::with_capacity(capacity)
}
PathBuf { inner: OsString::with_capacity(capacity) }
}
/// Coerces to a [`Path`] slice.
@ -1239,8 +1194,10 @@ impl PathBuf {
// in the special case of `C:` on Windows, do *not* add a separator
{
let comps = self.components();
if comps.prefix_len() > 0 && comps.prefix_len() == comps.path.len() &&
comps.prefix.unwrap().is_drive() {
if comps.prefix_len() > 0
&& comps.prefix_len() == comps.path.len()
&& comps.prefix.unwrap().is_drive()
{
need_sep = false
}
}
@ -1527,7 +1484,7 @@ impl From<PathBuf> for OsString {
/// Converts a `PathBuf` into a `OsString`
///
/// This conversion does not allocate or copy memory.
fn from(path_buf : PathBuf) -> OsString {
fn from(path_buf: PathBuf) -> OsString {
path_buf.inner
}
}
@ -1992,13 +1949,11 @@ impl Path {
pub fn parent(&self) -> Option<&Path> {
let mut comps = self.components();
let comp = comps.next_back();
comp.and_then(|p| {
match p {
Component::Normal(_) |
Component::CurDir |
Component::ParentDir => Some(comps.as_path()),
_ => None,
comp.and_then(|p| match p {
Component::Normal(_) | Component::CurDir | Component::ParentDir => {
Some(comps.as_path())
}
_ => None,
})
}
@ -2026,9 +1981,7 @@ impl Path {
/// [`parent`]: struct.Path.html#method.parent
#[stable(feature = "path_ancestors", since = "1.28.0")]
pub fn ancestors(&self) -> Ancestors<'_> {
Ancestors {
next: Some(&self),
}
Ancestors { next: Some(&self) }
}
/// Returns the final component of the `Path`, if there is one.
@ -2055,11 +2008,9 @@ impl Path {
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn file_name(&self) -> Option<&OsStr> {
self.components().next_back().and_then(|p| {
match p {
self.components().next_back().and_then(|p| match p {
Component::Normal(p) => Some(p.as_ref()),
_ => None,
}
})
}
@ -2092,15 +2043,14 @@ impl Path {
/// assert_eq!(path.strip_prefix(prefix), Ok(Path::new("haha/foo.txt")));
/// ```
#[stable(since = "1.7.0", feature = "path_strip_prefix")]
pub fn strip_prefix<P>(&self, base: P)
-> Result<&Path, StripPrefixError>
where P: AsRef<Path>
pub fn strip_prefix<P>(&self, base: P) -> Result<&Path, StripPrefixError>
where
P: AsRef<Path>,
{
self._strip_prefix(base.as_ref())
}
fn _strip_prefix(&self, base: &Path)
-> Result<&Path, StripPrefixError> {
fn _strip_prefix(&self, base: &Path) -> Result<&Path, StripPrefixError> {
iter_after(self.components(), base.components())
.map(|c| c.as_path())
.ok_or(StripPrefixError(()))
@ -2329,8 +2279,8 @@ impl Path {
Components {
path: self.as_u8_slice(),
prefix,
has_physical_root: has_physical_root(self.as_u8_slice(), prefix) ||
has_redox_scheme(self.as_u8_slice()),
has_physical_root: has_physical_root(self.as_u8_slice(), prefix)
|| has_redox_scheme(self.as_u8_slice()),
front: State::Prefix,
back: State::Body,
}
@ -2727,14 +2677,18 @@ impl AsRef<Path> for PathBuf {
impl<'a> IntoIterator for &'a PathBuf {
type Item = &'a OsStr;
type IntoIter = Iter<'a>;
fn into_iter(self) -> Iter<'a> { self.iter() }
fn into_iter(self) -> Iter<'a> {
self.iter()
}
}
#[stable(feature = "path_into_iter", since = "1.6.0")]
impl<'a> IntoIterator for &'a Path {
type Item = &'a OsStr;
type IntoIter = Iter<'a>;
fn into_iter(self) -> Iter<'a> { self.iter() }
fn into_iter(self) -> Iter<'a> {
self.iter()
}
}
macro_rules! impl_cmp {
@ -2742,13 +2696,17 @@ macro_rules! impl_cmp {
#[stable(feature = "partialeq_path", since = "1.6.0")]
impl<'a, 'b> PartialEq<$rhs> for $lhs {
#[inline]
fn eq(&self, other: &$rhs) -> bool { <Path as PartialEq>::eq(self, other) }
fn eq(&self, other: &$rhs) -> bool {
<Path as PartialEq>::eq(self, other)
}
}
#[stable(feature = "partialeq_path", since = "1.6.0")]
impl<'a, 'b> PartialEq<$lhs> for $rhs {
#[inline]
fn eq(&self, other: &$lhs) -> bool { <Path as PartialEq>::eq(self, other) }
fn eq(&self, other: &$lhs) -> bool {
<Path as PartialEq>::eq(self, other)
}
}
#[stable(feature = "cmp_path", since = "1.8.0")]
@ -2766,7 +2724,7 @@ macro_rules! impl_cmp {
<Path as PartialOrd>::partial_cmp(self, other)
}
}
}
};
}
impl_cmp!(PathBuf, Path);
@ -2780,13 +2738,17 @@ macro_rules! impl_cmp_os_str {
#[stable(feature = "cmp_path", since = "1.8.0")]
impl<'a, 'b> PartialEq<$rhs> for $lhs {
#[inline]
fn eq(&self, other: &$rhs) -> bool { <Path as PartialEq>::eq(self, other.as_ref()) }
fn eq(&self, other: &$rhs) -> bool {
<Path as PartialEq>::eq(self, other.as_ref())
}
}
#[stable(feature = "cmp_path", since = "1.8.0")]
impl<'a, 'b> PartialEq<$lhs> for $rhs {
#[inline]
fn eq(&self, other: &$lhs) -> bool { <Path as PartialEq>::eq(self.as_ref(), other) }
fn eq(&self, other: &$lhs) -> bool {
<Path as PartialEq>::eq(self.as_ref(), other)
}
}
#[stable(feature = "cmp_path", since = "1.8.0")]
@ -2804,7 +2766,7 @@ macro_rules! impl_cmp_os_str {
<Path as PartialOrd>::partial_cmp(self.as_ref(), other)
}
}
}
};
}
impl_cmp_os_str!(PathBuf, OsStr);
@ -2831,7 +2793,9 @@ impl fmt::Display for StripPrefixError {
#[stable(since = "1.7.0", feature = "strip_prefix")]
impl Error for StripPrefixError {
fn description(&self) -> &str { "prefix not found" }
fn description(&self) -> &str {
"prefix not found"
}
}
#[cfg(test)]
@ -3650,7 +3614,6 @@ mod tests {
extension: Some("txt")
);
t!("\\\\?\\C:\\",
iter: ["\\\\?\\C:", "\\"],
has_root: true,
@ -3661,7 +3624,6 @@ mod tests {
extension: None
);
t!("\\\\?\\C:",
iter: ["\\\\?\\C:"],
has_root: true,
@ -3672,7 +3634,6 @@ mod tests {
extension: None
);
t!("\\\\?\\foo/bar",
iter: ["\\\\?\\foo/bar"],
has_root: true,
@ -3683,7 +3644,6 @@ mod tests {
extension: None
);
t!("\\\\?\\C:/foo",
iter: ["\\\\?\\C:/foo"],
has_root: true,
@ -3694,7 +3654,6 @@ mod tests {
extension: None
);
t!("\\\\.\\foo\\bar",
iter: ["\\\\.\\foo", "\\", "bar"],
has_root: true,
@ -3705,7 +3664,6 @@ mod tests {
extension: None
);
t!("\\\\.\\foo",
iter: ["\\\\.\\foo", "\\"],
has_root: true,
@ -3716,7 +3674,6 @@ mod tests {
extension: None
);
t!("\\\\.\\foo/bar",
iter: ["\\\\.\\foo/bar", "\\"],
has_root: true,
@ -3727,7 +3684,6 @@ mod tests {
extension: None
);
t!("\\\\.\\foo\\bar/baz",
iter: ["\\\\.\\foo", "\\", "bar", "baz"],
has_root: true,
@ -3738,7 +3694,6 @@ mod tests {
extension: None
);
t!("\\\\.\\",
iter: ["\\\\.\\", "\\"],
has_root: true,
@ -3792,20 +3747,11 @@ mod tests {
extension: Some("")
);
t!(".",
file_stem: None,
extension: None
);
t!(".", file_stem: None, extension: None);
t!("..",
file_stem: None,
extension: None
);
t!("..", file_stem: None, extension: None);
t!("",
file_stem: None,
extension: None
);
t!("", file_stem: None, extension: None);
}
#[test]
@ -3873,26 +3819,20 @@ mod tests {
tp!("C:a\\b\\c", "C:d", "C:d");
tp!("C:", r"a\b\c", r"C:a\b\c");
tp!("C:", r"..\a", r"C:..\a");
tp!("\\\\server\\share\\foo",
"bar",
"\\\\server\\share\\foo\\bar");
tp!("\\\\server\\share\\foo", "bar", "\\\\server\\share\\foo\\bar");
tp!("\\\\server\\share\\foo", "C:baz", "C:baz");
tp!("\\\\?\\C:\\a\\b", "C:c\\d", "C:c\\d");
tp!("\\\\?\\C:a\\b", "C:c\\d", "C:c\\d");
tp!("\\\\?\\C:\\a\\b", "C:\\c\\d", "C:\\c\\d");
tp!("\\\\?\\foo\\bar", "baz", "\\\\?\\foo\\bar\\baz");
tp!("\\\\?\\UNC\\server\\share\\foo",
"bar",
"\\\\?\\UNC\\server\\share\\foo\\bar");
tp!("\\\\?\\UNC\\server\\share\\foo", "bar", "\\\\?\\UNC\\server\\share\\foo\\bar");
tp!("\\\\?\\UNC\\server\\share", "C:\\a", "C:\\a");
tp!("\\\\?\\UNC\\server\\share", "C:a", "C:a");
// Note: modified from old path API
tp!("\\\\?\\UNC\\server", "foo", "\\\\?\\UNC\\server\\foo");
tp!("C:\\a",
"\\\\?\\UNC\\server\\share",
"\\\\?\\UNC\\server\\share");
tp!("C:\\a", "\\\\?\\UNC\\server\\share", "\\\\?\\UNC\\server\\share");
tp!("\\\\.\\foo\\bar", "baz", "\\\\.\\foo\\bar\\baz");
tp!("\\\\.\\foo\\bar", "C:a", "C:a");
// again, not sure about the following, but I'm assuming \\.\ should be verbatim
@ -3945,15 +3885,9 @@ mod tests {
tp!("\\\\?\\C:\\a\\b", "\\\\?\\C:\\a", true);
tp!("\\\\?\\C:\\a", "\\\\?\\C:\\", true);
tp!("\\\\?\\C:\\", "\\\\?\\C:\\", false);
tp!("\\\\?\\UNC\\server\\share\\a\\b",
"\\\\?\\UNC\\server\\share\\a",
true);
tp!("\\\\?\\UNC\\server\\share\\a",
"\\\\?\\UNC\\server\\share\\",
true);
tp!("\\\\?\\UNC\\server\\share",
"\\\\?\\UNC\\server\\share",
false);
tp!("\\\\?\\UNC\\server\\share\\a\\b", "\\\\?\\UNC\\server\\share\\a", true);
tp!("\\\\?\\UNC\\server\\share\\a", "\\\\?\\UNC\\server\\share\\", true);
tp!("\\\\?\\UNC\\server\\share", "\\\\?\\UNC\\server\\share", false);
tp!("\\\\.\\a\\b\\c", "\\\\.\\a\\b", true);
tp!("\\\\.\\a\\b", "\\\\.\\a\\", true);
tp!("\\\\.\\a", "\\\\.\\a", false);
@ -4051,8 +3985,8 @@ mod tests {
#[test]
pub fn test_compare() {
use crate::hash::{Hash, Hasher};
use crate::collections::hash_map::DefaultHasher;
use crate::hash::{Hash, Hasher};
fn hash<T: Hash>(t: T) -> u64 {
let mut s = DefaultHasher::new();

View file

@ -2,8 +2,6 @@
//!
//! See the [module-level documentation](../index.html) for more.
#![stable(feature = "rust1", since = "1.0.0")]
// Re-exported core operators
@ -22,45 +20,27 @@ pub use crate::mem::drop;
// Re-exported types and traits
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::convert::{AsRef, AsMut, Into, From};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::iter::{Iterator, Extend, IntoIterator};
pub use crate::convert::{AsMut, AsRef, From, Into};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::iter::{DoubleEndedIterator, ExactSizeIterator};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::option::Option::{self, Some, None};
pub use crate::iter::{Extend, IntoIterator, Iterator};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::result::Result::{self, Ok, Err};
pub use crate::option::Option::{self, None, Some};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::result::Result::{self, Err, Ok};
// Re-exported built-in macros
#[stable(feature = "builtin_macro_prelude", since = "1.38.0")]
#[doc(no_inline)]
pub use core::prelude::v1::{
asm,
assert,
cfg,
column,
compile_error,
concat,
concat_idents,
env,
file,
format_args,
format_args_nl,
global_asm,
include,
include_bytes,
include_str,
line,
log_syntax,
module_path,
option_env,
stringify,
trace_macros,
asm, assert, cfg, column, compile_error, concat, concat_idents, env, file, format_args,
format_args_nl, global_asm, include, include_bytes, include_str, line, log_syntax, module_path,
option_env, stringify, trace_macros,
};
// FIXME: Attribute and derive macros are not documented because for them rustdoc generates
@ -69,21 +49,8 @@ pub use core::prelude::v1::{
#[allow(deprecated)]
#[doc(hidden)]
pub use core::prelude::v1::{
Clone,
Copy,
Debug,
Default,
Eq,
Hash,
Ord,
PartialEq,
PartialOrd,
RustcDecodable,
RustcEncodable,
bench,
global_allocator,
test,
test_case,
bench, global_allocator, test, test_case, Clone, Copy, Debug, Default, Eq, Hash, Ord,
PartialEq, PartialOrd, RustcDecodable, RustcEncodable,
};
// The file so far is equivalent to src/libcore/prelude/v1.rs,
@ -91,15 +58,14 @@ pub use core::prelude::v1::{
// Those files are duplicated rather than using glob imports
// because we want docs to show these re-exports as pointing to within `std`.
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::boxed::Box;
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::borrow::ToOwned;
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::boxed::Box;
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]
pub use crate::string::{String, ToString};
#[stable(feature = "rust1", since = "1.0.0")]
#[doc(no_inline)]

View file

@ -186,7 +186,9 @@ pub struct Child {
}
impl AsInner<imp::Process> for Child {
fn as_inner(&self) -> &imp::Process { &self.handle }
fn as_inner(&self) -> &imp::Process {
&self.handle
}
}
impl FromInner<(imp::Process, imp::StdioPipes)> for Child {
@ -201,7 +203,9 @@ impl FromInner<(imp::Process, imp::StdioPipes)> for Child {
}
impl IntoInner<imp::Process> for Child {
fn into_inner(self) -> imp::Process { self.handle }
fn into_inner(self) -> imp::Process {
self.handle
}
}
#[stable(feature = "std_debug", since = "1.16.0")]
@ -228,7 +232,7 @@ impl fmt::Debug for Child {
/// [dropped]: ../ops/trait.Drop.html
#[stable(feature = "process", since = "1.0.0")]
pub struct ChildStdin {
inner: AnonPipe
inner: AnonPipe,
}
#[stable(feature = "process", since = "1.0.0")]
@ -247,11 +251,15 @@ impl Write for ChildStdin {
}
impl AsInner<AnonPipe> for ChildStdin {
fn as_inner(&self) -> &AnonPipe { &self.inner }
fn as_inner(&self) -> &AnonPipe {
&self.inner
}
}
impl IntoInner<AnonPipe> for ChildStdin {
fn into_inner(self) -> AnonPipe { self.inner }
fn into_inner(self) -> AnonPipe {
self.inner
}
}
impl FromInner<AnonPipe> for ChildStdin {
@ -279,7 +287,7 @@ impl fmt::Debug for ChildStdin {
/// [dropped]: ../ops/trait.Drop.html
#[stable(feature = "process", since = "1.0.0")]
pub struct ChildStdout {
inner: AnonPipe
inner: AnonPipe,
}
#[stable(feature = "process", since = "1.0.0")]
@ -299,11 +307,15 @@ impl Read for ChildStdout {
}
impl AsInner<AnonPipe> for ChildStdout {
fn as_inner(&self) -> &AnonPipe { &self.inner }
fn as_inner(&self) -> &AnonPipe {
&self.inner
}
}
impl IntoInner<AnonPipe> for ChildStdout {
fn into_inner(self) -> AnonPipe { self.inner }
fn into_inner(self) -> AnonPipe {
self.inner
}
}
impl FromInner<AnonPipe> for ChildStdout {
@ -331,7 +343,7 @@ impl fmt::Debug for ChildStdout {
/// [dropped]: ../ops/trait.Drop.html
#[stable(feature = "process", since = "1.0.0")]
pub struct ChildStderr {
inner: AnonPipe
inner: AnonPipe,
}
#[stable(feature = "process", since = "1.0.0")]
@ -351,11 +363,15 @@ impl Read for ChildStderr {
}
impl AsInner<AnonPipe> for ChildStderr {
fn as_inner(&self) -> &AnonPipe { &self.inner }
fn as_inner(&self) -> &AnonPipe {
&self.inner
}
}
impl IntoInner<AnonPipe> for ChildStderr {
fn into_inner(self) -> AnonPipe { self.inner }
fn into_inner(self) -> AnonPipe {
self.inner
}
}
impl FromInner<AnonPipe> for ChildStderr {
@ -533,7 +549,9 @@ impl Command {
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn args<I, S>(&mut self, args: I) -> &mut Command
where I: IntoIterator<Item=S>, S: AsRef<OsStr>
where
I: IntoIterator<Item = S>,
S: AsRef<OsStr>,
{
for arg in args {
self.arg(arg.as_ref());
@ -560,7 +578,9 @@ impl Command {
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn env<K, V>(&mut self, key: K, val: V) -> &mut Command
where K: AsRef<OsStr>, V: AsRef<OsStr>
where
K: AsRef<OsStr>,
V: AsRef<OsStr>,
{
self.inner.env_mut().set(key.as_ref(), val.as_ref());
self
@ -592,7 +612,10 @@ impl Command {
/// ```
#[stable(feature = "command_envs", since = "1.19.0")]
pub fn envs<I, K, V>(&mut self, vars: I) -> &mut Command
where I: IntoIterator<Item=(K, V)>, K: AsRef<OsStr>, V: AsRef<OsStr>
where
I: IntoIterator<Item = (K, V)>,
K: AsRef<OsStr>,
V: AsRef<OsStr>,
{
for (ref key, ref val) in vars {
self.inner.env_mut().set(key.as_ref(), val.as_ref());
@ -794,7 +817,9 @@ impl Command {
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn output(&mut self) -> io::Result<Output> {
self.inner.spawn(imp::Stdio::MakePipe, false).map(Child::from_inner)
self.inner
.spawn(imp::Stdio::MakePipe, false)
.map(Child::from_inner)
.and_then(|p| p.wait_with_output())
}
@ -819,7 +844,9 @@ impl Command {
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn status(&mut self) -> io::Result<ExitStatus> {
self.inner.spawn(imp::Stdio::Inherit, true).map(Child::from_inner)
self.inner
.spawn(imp::Stdio::Inherit, true)
.map(Child::from_inner)
.and_then(|mut p| p.wait())
}
}
@ -835,11 +862,15 @@ impl fmt::Debug for Command {
}
impl AsInner<imp::Command> for Command {
fn as_inner(&self) -> &imp::Command { &self.inner }
fn as_inner(&self) -> &imp::Command {
&self.inner
}
}
impl AsInnerMut<imp::Command> for Command {
fn as_inner_mut(&mut self) -> &mut imp::Command { &mut self.inner }
fn as_inner_mut(&mut self) -> &mut imp::Command {
&mut self.inner
}
}
/// The output of a finished process.
@ -871,17 +902,16 @@ pub struct Output {
#[stable(feature = "process_output_debug", since = "1.7.0")]
impl fmt::Debug for Output {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
let stdout_utf8 = str::from_utf8(&self.stdout);
let stdout_debug: &dyn fmt::Debug = match stdout_utf8 {
Ok(ref str) => str,
Err(_) => &self.stdout
Err(_) => &self.stdout,
};
let stderr_utf8 = str::from_utf8(&self.stderr);
let stderr_debug: &dyn fmt::Debug = match stderr_utf8 {
Ok(ref str) => str,
Err(_) => &self.stderr
Err(_) => &self.stderr,
};
fmt.debug_struct("Output")
@ -943,7 +973,9 @@ impl Stdio {
/// assert_eq!(String::from_utf8_lossy(&output.stdout), "!dlrow ,olleH");
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn piped() -> Stdio { Stdio(imp::Stdio::MakePipe) }
pub fn piped() -> Stdio {
Stdio(imp::Stdio::MakePipe)
}
/// The child inherits from the corresponding parent descriptor.
///
@ -980,7 +1012,9 @@ impl Stdio {
/// io::stdout().write_all(&output.stdout).unwrap();
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn inherit() -> Stdio { Stdio(imp::Stdio::Inherit) }
pub fn inherit() -> Stdio {
Stdio(imp::Stdio::Inherit)
}
/// This stream will be ignored. This is the equivalent of attaching the
/// stream to `/dev/null`
@ -1017,7 +1051,9 @@ impl Stdio {
/// // Ignores any piped-in input
/// ```
#[stable(feature = "process", since = "1.0.0")]
pub fn null() -> Stdio { Stdio(imp::Stdio::Null) }
pub fn null() -> Stdio {
Stdio(imp::Stdio::Null)
}
}
impl FromInner<imp::Stdio> for Stdio {
@ -1217,7 +1253,9 @@ impl ExitStatus {
}
impl AsInner<imp::ExitStatus> for ExitStatus {
fn as_inner(&self) -> &imp::ExitStatus { &self.0 }
fn as_inner(&self) -> &imp::ExitStatus {
&self.0
}
}
impl FromInner<imp::ExitStatus> for ExitStatus {
@ -1449,11 +1487,7 @@ impl Child {
}
let status = self.wait()?;
Ok(Output {
status,
stdout,
stderr,
})
Ok(Output { status, stdout, stderr })
}
}
@ -1604,8 +1638,9 @@ pub fn id() -> u32 {
#[cfg_attr(not(test), lang = "termination")]
#[unstable(feature = "termination_trait_lib", issue = "43301")]
#[rustc_on_unimplemented(
message="`main` has invalid return type `{Self}`",
label="`main` can only return types that implement `{Termination}`")]
message = "`main` has invalid return type `{Self}`",
label = "`main` can only return types that implement `{Termination}`"
)]
pub trait Termination {
/// Is called to get the representation of the value as status code.
/// This status code is returned to the operating system.
@ -1615,7 +1650,9 @@ pub trait Termination {
#[unstable(feature = "termination_trait_lib", issue = "43301")]
impl Termination for () {
#[inline]
fn report(self) -> i32 { ExitCode::SUCCESS.report() }
fn report(self) -> i32 {
ExitCode::SUCCESS.report()
}
}
#[unstable(feature = "termination_trait_lib", issue = "43301")]
@ -1630,7 +1667,9 @@ impl<E: fmt::Debug> Termination for Result<(), E> {
#[unstable(feature = "termination_trait_lib", issue = "43301")]
impl Termination for ! {
fn report(self) -> i32 { self }
fn report(self) -> i32 {
self
}
}
#[unstable(feature = "termination_trait_lib", issue = "43301")]
@ -1654,9 +1693,9 @@ impl Termination for ExitCode {
mod tests {
use crate::io::prelude::*;
use super::{Command, Output, Stdio};
use crate::io::ErrorKind;
use crate::str;
use super::{Command, Output, Stdio};
// FIXME(#10380) these tests should not all be ignored on android.
@ -1702,15 +1741,12 @@ mod tests {
fn signal_reported_right() {
use crate::os::unix::process::ExitStatusExt;
let mut p = Command::new("/bin/sh")
.arg("-c").arg("read a")
.stdin(Stdio::piped())
.spawn().unwrap();
let mut p =
Command::new("/bin/sh").arg("-c").arg("read a").stdin(Stdio::piped()).spawn().unwrap();
p.kill().unwrap();
match p.wait().unwrap().signal() {
Some(9) => {},
result => panic!("not terminated by signal 9 (instead, {:?})",
result),
Some(9) => {}
result => panic!("not terminated by signal 9 (instead, {:?})", result),
}
}
@ -1743,9 +1779,7 @@ mod tests {
#[cfg_attr(any(windows, target_os = "android", target_os = "vxworks"), ignore)]
fn set_current_dir_works() {
let mut cmd = Command::new("/bin/sh");
cmd.arg("-c").arg("pwd")
.current_dir("/")
.stdout(Stdio::piped());
cmd.arg("-c").arg("pwd").current_dir("/").stdout(Stdio::piped());
assert_eq!(run_output(cmd), "/\n");
}
@ -1753,10 +1787,12 @@ mod tests {
#[cfg_attr(any(windows, target_os = "android", target_os = "vxworks"), ignore)]
fn stdin_works() {
let mut p = Command::new("/bin/sh")
.arg("-c").arg("read line; echo $line")
.arg("-c")
.arg("read line; echo $line")
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.spawn().unwrap();
.spawn()
.unwrap();
p.stdin.as_mut().unwrap().write("foobar".as_bytes()).unwrap();
drop(p.stdin.take());
let mut out = String::new();
@ -1787,15 +1823,14 @@ mod tests {
fn test_process_output_fail_to_start() {
match Command::new("/no-binary-by-this-name-should-exist").output() {
Err(e) => assert_eq!(e.kind(), ErrorKind::NotFound),
Ok(..) => panic!()
Ok(..) => panic!(),
}
}
#[test]
#[cfg_attr(any(target_os = "vxworks", target_os = "android"), ignore)]
fn test_process_output_output() {
let Output {status, stdout, stderr}
= if cfg!(target_os = "windows") {
let Output { status, stdout, stderr } = if cfg!(target_os = "windows") {
Command::new("cmd").args(&["/C", "echo hello"]).output().unwrap()
} else {
Command::new("echo").arg("hello").output().unwrap()
@ -1810,8 +1845,7 @@ mod tests {
#[test]
#[cfg_attr(any(target_os = "vxworks", target_os = "android"), ignore)]
fn test_process_output_error() {
let Output {status, stdout, stderr}
= if cfg!(target_os = "windows") {
let Output { status, stdout, stderr } = if cfg!(target_os = "windows") {
Command::new("cmd").args(&["/C", "mkdir ."]).output().unwrap()
} else {
Command::new("mkdir").arg("./").output().unwrap()
@ -1854,7 +1888,7 @@ mod tests {
Command::new("echo").arg("hello").stdout(Stdio::piped()).spawn().unwrap()
};
let Output {status, stdout, stderr} = prog.wait_with_output().unwrap();
let Output { status, stdout, stderr } = prog.wait_with_output().unwrap();
let output_str = str::from_utf8(&stdout).unwrap();
assert!(status.success());
@ -1862,11 +1896,11 @@ mod tests {
assert_eq!(stderr, Vec::new());
}
#[cfg(all(unix, not(target_os="android")))]
#[cfg(all(unix, not(target_os = "android")))]
pub fn env_cmd() -> Command {
Command::new("env")
}
#[cfg(target_os="android")]
#[cfg(target_os = "android")]
pub fn env_cmd() -> Command {
let mut cmd = Command::new("/system/bin/sh");
cmd.arg("-c").arg("set");
@ -1897,8 +1931,11 @@ mod tests {
let result = cmd.output().unwrap();
let output = String::from_utf8_lossy(&result.stdout).to_string();
assert!(output.contains("RUN_TEST_NEW_ENV=123"),
"didn't find RUN_TEST_NEW_ENV inside of:\n\n{}", output);
assert!(
output.contains("RUN_TEST_NEW_ENV=123"),
"didn't find RUN_TEST_NEW_ENV inside of:\n\n{}",
output
);
}
#[test]
@ -1907,8 +1944,11 @@ mod tests {
let result = env_cmd().env("RUN_TEST_NEW_ENV", "123").output().unwrap();
let output = String::from_utf8_lossy(&result.stdout).to_string();
assert!(output.contains("RUN_TEST_NEW_ENV=123"),
"didn't find RUN_TEST_NEW_ENV inside of:\n\n{}", output);
assert!(
output.contains("RUN_TEST_NEW_ENV=123"),
"didn't find RUN_TEST_NEW_ENV inside of:\n\n{}",
output
);
}
#[test]
@ -1927,10 +1967,16 @@ mod tests {
let output = String::from_utf8_lossy(&result.stdout).to_string();
assert!(output.contains("RUN_TEST_NEW_ENV1=123"),
"didn't find RUN_TEST_NEW_ENV1 inside of:\n\n{}", output);
assert!(output.contains("RUN_TEST_NEW_ENV2=456"),
"didn't find RUN_TEST_NEW_ENV2 inside of:\n\n{}", output);
assert!(
output.contains("RUN_TEST_NEW_ENV1=123"),
"didn't find RUN_TEST_NEW_ENV1 inside of:\n\n{}",
output
);
assert!(
output.contains("RUN_TEST_NEW_ENV2=456"),
"didn't find RUN_TEST_NEW_ENV2 inside of:\n\n{}",
output
);
}
// Regression tests for #30858.
@ -2005,8 +2051,11 @@ mod tests {
extern "system" {
fn WaitForDebugEvent(lpDebugEvent: *mut DEBUG_EVENT, dwMilliseconds: DWORD) -> BOOL;
fn ContinueDebugEvent(dwProcessId: DWORD, dwThreadId: DWORD,
dwContinueStatus: DWORD) -> BOOL;
fn ContinueDebugEvent(
dwProcessId: DWORD,
dwThreadId: DWORD,
dwContinueStatus: DWORD,
) -> BOOL;
}
const DEBUG_PROCESS: DWORD = 1;
@ -2015,15 +2064,12 @@ mod tests {
let mut child = Command::new("cmd")
.creation_flags(DEBUG_PROCESS)
.stdin(Stdio::piped()).spawn().unwrap();
.stdin(Stdio::piped())
.spawn()
.unwrap();
child.stdin.take().unwrap().write_all(b"exit\r\n").unwrap();
let mut events = 0;
let mut event = DEBUG_EVENT {
event_code: 0,
process_id: 0,
thread_id: 0,
_junk: [0; 164],
};
let mut event = DEBUG_EVENT { event_code: 0, process_id: 0, thread_id: 0, _junk: [0; 164] };
loop {
if unsafe { WaitForDebugEvent(&mut event as *mut DEBUG_EVENT, INFINITE) } == 0 {
panic!("WaitForDebugEvent failed!");
@ -2034,9 +2080,10 @@ mod tests {
break;
}
if unsafe { ContinueDebugEvent(event.process_id,
event.thread_id,
DBG_EXCEPTION_NOT_HANDLED) } == 0 {
if unsafe {
ContinueDebugEvent(event.process_id, event.thread_id, DBG_EXCEPTION_NOT_HANDLED)
} == 0
{
panic!("ContinueDebugEvent failed!");
}
}

View file

@ -6,21 +6,25 @@
//! and should be considered as private implementation details for the
//! time being.
#![unstable(feature = "rt",
#![unstable(
feature = "rt",
reason = "this public module should not exist and is highly likely \
to disappear",
issue = "0")]
issue = "0"
)]
#![doc(hidden)]
// Re-export some of our utilities which are expected by other crates.
pub use crate::panicking::{begin_panic, begin_panic_fmt, update_panic_count};
// To reduce the generated code of the new `lang_start`, this function is doing
// the real work.
#[cfg(not(test))]
fn lang_start_internal(main: &(dyn Fn() -> i32 + Sync + crate::panic::RefUnwindSafe),
argc: isize, argv: *const *const u8) -> isize {
fn lang_start_internal(
main: &(dyn Fn() -> i32 + Sync + crate::panic::RefUnwindSafe),
argc: isize,
argv: *const *const u8,
) -> isize {
use crate::panic;
use crate::sys;
use crate::sys_common;
@ -55,8 +59,10 @@ fn lang_start_internal(main: &(dyn Fn() -> i32 + Sync + crate::panic::RefUnwindS
#[cfg(not(test))]
#[lang = "start"]
fn lang_start<T: crate::process::Termination + 'static>
(main: fn() -> T, argc: isize, argv: *const *const u8) -> isize
{
fn lang_start<T: crate::process::Termination + 'static>(
main: fn() -> T,
argc: isize,
argv: *const *const u8,
) -> isize {
lang_start_internal(&move || main().report(), argc, argv)
}

View file

@ -1,5 +1,5 @@
use crate::fmt;
use crate::sync::{Mutex, Condvar};
use crate::sync::{Condvar, Mutex};
/// A barrier enables multiple threads to synchronize the beginning
/// of some computation.
@ -82,10 +82,7 @@ impl Barrier {
#[stable(feature = "rust1", since = "1.0.0")]
pub fn new(n: usize) -> Barrier {
Barrier {
lock: Mutex::new(BarrierState {
count: 0,
generation_id: 0,
}),
lock: Mutex::new(BarrierState { count: 0, generation_id: 0 }),
cvar: Condvar::new(),
num_threads: n,
}
@ -135,8 +132,7 @@ impl Barrier {
if lock.count < self.num_threads {
// We need a while loop to guard against spurious wakeups.
// http://en.wikipedia.org/wiki/Spurious_wakeup
while local_gen == lock.generation_id &&
lock.count < self.num_threads {
while local_gen == lock.generation_id && lock.count < self.num_threads {
lock = self.cvar.wait(lock).unwrap();
}
BarrierWaitResult(false)
@ -152,9 +148,7 @@ impl Barrier {
#[stable(feature = "std_debug", since = "1.16.0")]
impl fmt::Debug for BarrierWaitResult {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("BarrierWaitResult")
.field("is_leader", &self.is_leader())
.finish()
f.debug_struct("BarrierWaitResult").field("is_leader", &self.is_leader()).finish()
}
}
@ -176,13 +170,15 @@ impl BarrierWaitResult {
/// println!("{:?}", barrier_wait_result.is_leader());
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn is_leader(&self) -> bool { self.0 }
pub fn is_leader(&self) -> bool {
self.0
}
}
#[cfg(test)]
mod tests {
use crate::sync::{Arc, Barrier};
use crate::sync::mpsc::{channel, TryRecvError};
use crate::sync::{Arc, Barrier};
use crate::thread;
#[test]
@ -196,7 +192,7 @@ mod tests {
for _ in 0..N - 1 {
let c = barrier.clone();
let tx = tx.clone();
thread::spawn(move|| {
thread::spawn(move || {
tx.send(c.wait().is_leader()).unwrap();
});
}

View file

@ -1,9 +1,9 @@
//! Generic support for building blocking abstractions.
use crate::thread::{self, Thread};
use crate::mem;
use crate::sync::atomic::{AtomicBool, Ordering};
use crate::sync::Arc;
use crate::mem;
use crate::thread::{self, Thread};
use crate::time::Instant;
struct Inner {
@ -28,16 +28,9 @@ impl !Send for WaitToken {}
impl !Sync for WaitToken {}
pub fn tokens() -> (WaitToken, SignalToken) {
let inner = Arc::new(Inner {
thread: thread::current(),
woken: AtomicBool::new(false),
});
let wait_token = WaitToken {
inner: inner.clone(),
};
let signal_token = SignalToken {
inner,
};
let inner = Arc::new(Inner { thread: thread::current(), woken: AtomicBool::new(false) });
let wait_token = WaitToken { inner: inner.clone() };
let signal_token = SignalToken { inner };
(wait_token, signal_token)
}

File diff suppressed because it is too large Load diff

View file

@ -13,8 +13,8 @@
pub use self::PopResult::*;
use core::ptr;
use core::cell::UnsafeCell;
use core::ptr;
use crate::boxed::Box;
use crate::sync::atomic::{AtomicPtr, Ordering};
@ -45,15 +45,12 @@ pub struct Queue<T> {
tail: UnsafeCell<*mut Node<T>>,
}
unsafe impl<T: Send> Send for Queue<T> { }
unsafe impl<T: Send> Sync for Queue<T> { }
unsafe impl<T: Send> Send for Queue<T> {}
unsafe impl<T: Send> Sync for Queue<T> {}
impl<T> Node<T> {
unsafe fn new(v: Option<T>) -> *mut Node<T> {
Box::into_raw(box Node {
next: AtomicPtr::new(ptr::null_mut()),
value: v,
})
Box::into_raw(box Node { next: AtomicPtr::new(ptr::null_mut()), value: v })
}
}
@ -62,10 +59,7 @@ impl<T> Queue<T> {
/// one consumer.
pub fn new() -> Queue<T> {
let stub = unsafe { Node::new(None) };
Queue {
head: AtomicPtr::new(stub),
tail: UnsafeCell::new(stub),
}
Queue { head: AtomicPtr::new(stub), tail: UnsafeCell::new(stub) }
}
/// Pushes a new value onto this queue.
@ -101,7 +95,7 @@ impl<T> Queue<T> {
return Data(ret);
}
if self.head.load(Ordering::Acquire) == tail {Empty} else {Inconsistent}
if self.head.load(Ordering::Acquire) == tail { Empty } else { Inconsistent }
}
}
}
@ -121,7 +115,7 @@ impl<T> Drop for Queue<T> {
#[cfg(all(test, not(target_os = "emscripten")))]
mod tests {
use super::{Queue, Data, Empty, Inconsistent};
use super::{Data, Empty, Inconsistent, Queue};
use crate::sync::mpsc::channel;
use crate::sync::Arc;
use crate::thread;
@ -140,7 +134,7 @@ mod tests {
let q = Queue::new();
match q.pop() {
Empty => {}
Inconsistent | Data(..) => panic!()
Inconsistent | Data(..) => panic!(),
}
let (tx, rx) = channel();
let q = Arc::new(q);
@ -148,7 +142,7 @@ mod tests {
for _ in 0..nthreads {
let tx = tx.clone();
let q = q.clone();
thread::spawn(move|| {
thread::spawn(move || {
for i in 0..nmsgs {
q.push(i);
}
@ -159,8 +153,8 @@ mod tests {
let mut i = 0;
while i < nthreads * nmsgs {
match q.pop() {
Empty | Inconsistent => {},
Data(_) => { i += 1 }
Empty | Inconsistent => {}
Data(_) => i += 1,
}
}
drop(tx);

View file

@ -21,16 +21,15 @@
/// consuming the port). This upgrade is then also stored in the shared packet.
/// The one caveat to consider is that when a port sees a disconnected channel
/// it must check for data because there is no "data plus upgrade" state.
pub use self::Failure::*;
pub use self::UpgradeResult::*;
use self::MyUpgrade::*;
pub use self::UpgradeResult::*;
use crate::sync::mpsc::Receiver;
use crate::sync::mpsc::blocking::{self, SignalToken};
use crate::cell::UnsafeCell;
use crate::ptr;
use crate::sync::atomic::{AtomicUsize, Ordering};
use crate::sync::mpsc::blocking::{self, SignalToken};
use crate::sync::mpsc::Receiver;
use crate::time::Instant;
// Various states you can find a port in.
@ -178,21 +177,17 @@ impl<T> Packet<T> {
// and an upgrade flags the channel as disconnected, so when we see
// this we first need to check if there's data available and *then*
// we go through and process the upgrade.
DISCONNECTED => {
match (&mut *self.data.get()).take() {
DISCONNECTED => match (&mut *self.data.get()).take() {
Some(data) => Ok(data),
None => {
match ptr::replace(self.upgrade.get(), SendUsed) {
None => match ptr::replace(self.upgrade.get(), SendUsed) {
SendUsed | NothingSent => Err(Disconnected),
GoUp(upgrade) => Err(Upgraded(upgrade))
}
}
}
}
GoUp(upgrade) => Err(Upgraded(upgrade)),
},
},
// We are the sole receiver; there cannot be a blocking
// receiver already.
_ => unreachable!()
_ => unreachable!(),
}
}
}
@ -217,10 +212,13 @@ impl<T> Packet<T> {
// If the other end is already disconnected, then we failed the
// upgrade. Be sure to trash the port we were given.
DISCONNECTED => { ptr::replace(self.upgrade.get(), prev); UpDisconnected }
DISCONNECTED => {
ptr::replace(self.upgrade.get(), prev);
UpDisconnected
}
// If someone's waiting, we gotta wake them up
ptr => UpWoke(SignalToken::cast_from_usize(ptr))
ptr => UpWoke(SignalToken::cast_from_usize(ptr)),
}
}
}
@ -232,7 +230,7 @@ impl<T> Packet<T> {
// If someone's waiting, we gotta wake them up
ptr => unsafe {
SignalToken::cast_from_usize(ptr).signal();
}
},
}
}
@ -246,10 +244,12 @@ impl<T> Packet<T> {
// There's data on the channel, so make sure we destroy it promptly.
// This is why not using an arc is a little difficult (need the box
// to stay valid while we take the data).
DATA => unsafe { (&mut *self.data.get()).take().unwrap(); },
DATA => unsafe {
(&mut *self.data.get()).take().unwrap();
},
// We're the only ones that can block on this port
_ => unreachable!()
_ => unreachable!(),
}
}
@ -265,13 +265,11 @@ impl<T> Packet<T> {
let state = match self.state.load(Ordering::SeqCst) {
// Each of these states means that no further activity will happen
// with regard to abortion selection
s @ EMPTY |
s @ DATA |
s @ DISCONNECTED => s,
s @ EMPTY | s @ DATA | s @ DISCONNECTED => s,
// If we've got a blocked thread, then use an atomic to gain ownership
// of it (may fail)
ptr => self.state.compare_and_swap(ptr, EMPTY, Ordering::SeqCst)
ptr => self.state.compare_and_swap(ptr, EMPTY, Ordering::SeqCst),
};
// Now that we've got ownership of our state, figure out what to do
@ -302,7 +300,7 @@ impl<T> Packet<T> {
ptr => unsafe {
drop(SignalToken::cast_from_usize(ptr));
Ok(false)
}
},
}
}
}

View file

@ -7,7 +7,6 @@
/// High level implementation details can be found in the comment of the parent
/// module. You'll also note that the implementation of the shared and stream
/// channels are quite similar, and this is no coincidence!
pub use self::Failure::*;
use self::StartResult::*;
@ -17,7 +16,7 @@ use core::isize;
use crate::cell::UnsafeCell;
use crate::ptr;
use crate::sync::atomic::{AtomicUsize, AtomicIsize, AtomicBool, Ordering};
use crate::sync::atomic::{AtomicBool, AtomicIsize, AtomicUsize, Ordering};
use crate::sync::mpsc::blocking::{self, SignalToken};
use crate::sync::mpsc::mpsc_queue as mpsc;
use crate::sync::{Mutex, MutexGuard};
@ -92,9 +91,7 @@ impl<T> Packet<T> {
// threads in select().
//
// This can only be called at channel-creation time
pub fn inherit_blocker(&self,
token: Option<SignalToken>,
guard: MutexGuard<'_, ()>) {
pub fn inherit_blocker(&self, token: Option<SignalToken>, guard: MutexGuard<'_, ()>) {
token.map(|token| {
assert_eq!(self.cnt.load(Ordering::SeqCst), 0);
assert_eq!(self.to_wake.load(Ordering::SeqCst), 0);
@ -119,7 +116,9 @@ impl<T> Packet<T> {
// To offset this bad increment, we initially set the steal count to
// -1. You'll find some special code in abort_selection() as well to
// ensure that this -1 steal count doesn't escape too far.
unsafe { *self.steals.get() = -1; }
unsafe {
*self.steals.get() = -1;
}
});
// When the shared packet is constructed, we grabbed this lock. The
@ -132,7 +131,9 @@ impl<T> Packet<T> {
pub fn send(&self, t: T) -> Result<(), T> {
// See Port::drop for what's going on
if self.port_dropped.load(Ordering::SeqCst) { return Err(t) }
if self.port_dropped.load(Ordering::SeqCst) {
return Err(t);
}
// Note that the multiple sender case is a little trickier
// semantically than the single sender case. The logic for
@ -160,7 +161,7 @@ impl<T> Packet<T> {
// received". Once we get beyond this check, we have permanently
// entered the realm of "this may be received"
if self.cnt.load(Ordering::SeqCst) < DISCONNECTED + FUDGE {
return Err(t)
return Err(t);
}
self.queue.push(t);
@ -197,7 +198,7 @@ impl<T> Packet<T> {
// maybe we're done, if we're not the last ones
// here, then we need to go try again.
if self.sender_drain.fetch_sub(1, Ordering::SeqCst) == 1 {
break
break;
}
}
@ -236,7 +237,10 @@ impl<T> Packet<T> {
}
match self.try_recv() {
data @ Ok(..) => unsafe { *self.steals.get() -= 1; data },
data @ Ok(..) => unsafe {
*self.steals.get() -= 1;
data
},
data => data,
}
}
@ -252,12 +256,16 @@ impl<T> Packet<T> {
let steals = ptr::replace(self.steals.get(), 0);
match self.cnt.fetch_sub(1 + steals, Ordering::SeqCst) {
DISCONNECTED => { self.cnt.store(DISCONNECTED, Ordering::SeqCst); }
DISCONNECTED => {
self.cnt.store(DISCONNECTED, Ordering::SeqCst);
}
// If we factor in our steals and notice that the channel has no
// data, we successfully sleep
n => {
assert!(n >= 0);
if n - steals <= 0 { return Installed }
if n - steals <= 0 {
return Installed;
}
}
}
@ -290,7 +298,10 @@ impl<T> Packet<T> {
loop {
thread::yield_now();
match self.queue.pop() {
mpsc::Data(t) => { data = t; break }
mpsc::Data(t) => {
data = t;
break;
}
mpsc::Empty => panic!("inconsistent => empty"),
mpsc::Inconsistent => {}
}
@ -361,9 +372,13 @@ impl<T> Packet<T> {
}
match self.cnt.swap(DISCONNECTED, Ordering::SeqCst) {
-1 => { self.take_to_wake().signal(); }
-1 => {
self.take_to_wake().signal();
}
DISCONNECTED => {}
n => { assert!(n >= 0); }
n => {
assert!(n >= 0);
}
}
}
@ -380,7 +395,9 @@ impl<T> Packet<T> {
// control of this thread.
loop {
match self.queue.pop() {
mpsc::Data(..) => { steals += 1; }
mpsc::Data(..) => {
steals += 1;
}
mpsc::Empty | mpsc::Inconsistent => break,
}
}
@ -406,7 +423,7 @@ impl<T> Packet<T> {
self.cnt.store(DISCONNECTED, Ordering::SeqCst);
DISCONNECTED
}
n => n
n => n,
}
}
@ -432,7 +449,7 @@ impl<T> Packet<T> {
// positive.
let steals = {
let cnt = self.cnt.load(Ordering::SeqCst);
if cnt < 0 && cnt != DISCONNECTED {-cnt} else {0}
if cnt < 0 && cnt != DISCONNECTED { -cnt } else { 0 }
};
let prev = self.bump(steals + 1);

View file

@ -6,8 +6,8 @@
// http://www.1024cores.net/home/lock-free-algorithms/queues/unbounded-spsc-queue
use core::ptr;
use core::cell::UnsafeCell;
use core::ptr;
use crate::boxed::Box;
use crate::sync::atomic::{AtomicPtr, AtomicUsize, Ordering};
@ -28,7 +28,7 @@ struct Node<T> {
/// but it can be safely shared in an Arc if it is guaranteed that there
/// is only one popper and one pusher touching the queue at any one point in
/// time.
pub struct Queue<T, ProducerAddition=(), ConsumerAddition=()> {
pub struct Queue<T, ProducerAddition = (), ConsumerAddition = ()> {
// consumer fields
consumer: CacheAligned<Consumer<T, ConsumerAddition>>,
@ -51,9 +51,9 @@ struct Producer<T, Addition> {
addition: Addition,
}
unsafe impl<T: Send, P: Send + Sync, C: Send + Sync> Send for Queue<T, P, C> { }
unsafe impl<T: Send, P: Send + Sync, C: Send + Sync> Send for Queue<T, P, C> {}
unsafe impl<T: Send, P: Send + Sync, C: Send + Sync> Sync for Queue<T, P, C> { }
unsafe impl<T: Send, P: Send + Sync, C: Send + Sync> Sync for Queue<T, P, C> {}
impl<T> Node<T> {
fn new() -> *mut Node<T> {
@ -66,7 +66,6 @@ impl<T> Node<T> {
}
impl<T, ProducerAddition, ConsumerAddition> Queue<T, ProducerAddition, ConsumerAddition> {
/// Creates a new queue. With given additional elements in the producer and
/// consumer portions of the queue.
///
@ -107,13 +106,13 @@ impl<T, ProducerAddition, ConsumerAddition> Queue<T, ProducerAddition, ConsumerA
tail_prev: AtomicPtr::new(n1),
cache_bound: bound,
cached_nodes: AtomicUsize::new(0),
addition: consumer_addition
addition: consumer_addition,
}),
producer: CacheAligned::new(Producer {
head: UnsafeCell::new(n2),
first: UnsafeCell::new(n1),
tail_copy: UnsafeCell::new(n1),
addition: producer_addition
addition: producer_addition,
}),
}
}
@ -142,8 +141,7 @@ impl<T, ProducerAddition, ConsumerAddition> Queue<T, ProducerAddition, ConsumerA
}
// If the above fails, then update our copy of the tail and try
// again.
*self.producer.0.tail_copy.get() =
self.consumer.tail_prev.load(Ordering::Acquire);
*self.producer.0.tail_copy.get() = self.consumer.tail_prev.load(Ordering::Acquire);
if *self.producer.first.get() != *self.producer.tail_copy.get() {
let ret = *self.producer.first.get();
*self.producer.0.first.get() = (*ret).next.load(Ordering::Relaxed);
@ -164,7 +162,9 @@ impl<T, ProducerAddition, ConsumerAddition> Queue<T, ProducerAddition, ConsumerA
// the current tail node is a candidate for going into the cache.
let tail = *self.consumer.tail.get();
let next = (*tail).next.load(Ordering::Acquire);
if next.is_null() { return None }
if next.is_null() {
return None;
}
assert!((*next).value.is_some());
let ret = (*next).value.take();
@ -182,7 +182,8 @@ impl<T, ProducerAddition, ConsumerAddition> Queue<T, ProducerAddition, ConsumerA
self.consumer.tail_prev.store(tail, Ordering::Release);
} else {
(*self.consumer.tail_prev.load(Ordering::Relaxed))
.next.store(next, Ordering::Relaxed);
.next
.store(next, Ordering::Relaxed);
// We have successfully erased all references to 'tail', so
// now we can safely drop it.
let _: Box<Node<T>> = Box::from_raw(tail);
@ -234,9 +235,9 @@ impl<T, ProducerAddition, ConsumerAddition> Drop for Queue<T, ProducerAddition,
#[cfg(all(test, not(target_os = "emscripten")))]
mod tests {
use super::Queue;
use crate::sync::mpsc::channel;
use crate::sync::Arc;
use crate::thread;
use crate::sync::mpsc::channel;
#[test]
fn smoke() {
@ -265,15 +266,15 @@ mod tests {
match queue.peek() {
Some(vec) => {
assert_eq!(&*vec, &[1]);
},
None => unreachable!()
}
None => unreachable!(),
}
match queue.pop() {
Some(vec) => {
assert_eq!(&*vec, &[1]);
},
None => unreachable!()
}
None => unreachable!(),
}
}
}
@ -316,7 +317,7 @@ mod tests {
let (tx, rx) = channel();
let q2 = q.clone();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
for _ in 0..100000 {
loop {
match q2.pop() {

View file

@ -6,10 +6,9 @@
///
/// High level implementation details can be found in the comment of the parent
/// module.
pub use self::Failure::*;
pub use self::UpgradeResult::*;
use self::Message::*;
pub use self::UpgradeResult::*;
use core::cmp;
use core::isize;
@ -19,10 +18,10 @@ use crate::ptr;
use crate::thread;
use crate::time::Instant;
use crate::sync::atomic::{AtomicIsize, AtomicUsize, Ordering, AtomicBool};
use crate::sync::mpsc::Receiver;
use crate::sync::atomic::{AtomicBool, AtomicIsize, AtomicUsize, Ordering};
use crate::sync::mpsc::blocking::{self, SignalToken};
use crate::sync::mpsc::spsc_queue as spsc;
use crate::sync::mpsc::Receiver;
const DISCONNECTED: isize = isize::MIN;
#[cfg(test)]
@ -46,7 +45,6 @@ struct ConsumerAddition {
steals: UnsafeCell<isize>, // How many times has a port received without blocking?
}
pub enum Failure<T> {
Empty,
Disconnected,
@ -69,7 +67,8 @@ enum Message<T> {
impl<T> Packet<T> {
pub fn new() -> Packet<T> {
Packet {
queue: unsafe { spsc::Queue::with_additions(
queue: unsafe {
spsc::Queue::with_additions(
128,
ProducerAddition {
cnt: AtomicIsize::new(0),
@ -77,10 +76,9 @@ impl<T> Packet<T> {
port_dropped: AtomicBool::new(false),
},
ConsumerAddition {
steals: UnsafeCell::new(0),
}
)},
ConsumerAddition { steals: UnsafeCell::new(0) },
)
},
}
}
@ -88,11 +86,15 @@ impl<T> Packet<T> {
// If the other port has deterministically gone away, then definitely
// must return the data back up the stack. Otherwise, the data is
// considered as being sent.
if self.queue.producer_addition().port_dropped.load(Ordering::SeqCst) { return Err(t) }
if self.queue.producer_addition().port_dropped.load(Ordering::SeqCst) {
return Err(t);
}
match self.do_send(Data(t)) {
UpSuccess | UpDisconnected => {},
UpWoke(token) => { token.signal(); }
UpSuccess | UpDisconnected => {}
UpWoke(token) => {
token.signal();
}
}
Ok(())
}
@ -101,7 +103,7 @@ impl<T> Packet<T> {
// If the port has gone away, then there's no need to proceed any
// further.
if self.queue.producer_addition().port_dropped.load(Ordering::SeqCst) {
return UpDisconnected
return UpDisconnected;
}
self.do_send(GoUp(up))
@ -136,7 +138,10 @@ impl<T> Packet<T> {
// Otherwise we just sent some data on a non-waiting queue, so just
// make sure the world is sane and carry on!
n => { assert!(n >= 0); UpSuccess }
n => {
assert!(n >= 0);
UpSuccess
}
}
}
@ -166,7 +171,9 @@ impl<T> Packet<T> {
// data, we successfully sleep
n => {
assert!(n >= 0);
if n - steals <= 0 { return Ok(()) }
if n - steals <= 0 {
return Ok(());
}
}
}
@ -199,8 +206,7 @@ impl<T> Packet<T> {
// Messages which actually popped from the queue shouldn't count as
// a steal, so offset the decrement here (we already have our
// "steal" factored into the channel count above).
data @ Ok(..) |
data @ Err(Upgraded(..)) => unsafe {
data @ Ok(..) | data @ Err(Upgraded(..)) => unsafe {
*self.queue.consumer_addition().steals.get() -= 1;
data
},
@ -226,8 +232,10 @@ impl<T> Packet<T> {
if *self.queue.consumer_addition().steals.get() > MAX_STEALS {
match self.queue.producer_addition().cnt.swap(0, Ordering::SeqCst) {
DISCONNECTED => {
self.queue.producer_addition().cnt.store(
DISCONNECTED, Ordering::SeqCst);
self.queue
.producer_addition()
.cnt
.store(DISCONNECTED, Ordering::SeqCst);
}
n => {
let m = cmp::min(n, *self.queue.consumer_addition().steals.get());
@ -259,13 +267,11 @@ impl<T> Packet<T> {
// We can ignore steals because the other end is
// disconnected and we'll never need to really factor in our
// steals again.
_ => {
match self.queue.pop() {
_ => match self.queue.pop() {
Some(Data(t)) => Ok(t),
Some(GoUp(up)) => Err(Upgraded(up)),
None => Err(Disconnected),
}
}
},
}
}
}
@ -275,9 +281,13 @@ impl<T> Packet<T> {
// Dropping a channel is pretty simple, we just flag it as disconnected
// and then wakeup a blocker if there is one.
match self.queue.producer_addition().cnt.swap(DISCONNECTED, Ordering::SeqCst) {
-1 => { self.take_to_wake().signal(); }
-1 => {
self.take_to_wake().signal();
}
DISCONNECTED => {}
n => { assert!(n >= 0); }
n => {
assert!(n >= 0);
}
}
}
@ -314,10 +324,15 @@ impl<T> Packet<T> {
let mut steals = unsafe { *self.queue.consumer_addition().steals.get() };
while {
let cnt = self.queue.producer_addition().cnt.compare_and_swap(
steals, DISCONNECTED, Ordering::SeqCst);
steals,
DISCONNECTED,
Ordering::SeqCst,
);
cnt != DISCONNECTED && cnt != steals
} {
while let Some(_) = self.queue.pop() { steals += 1; }
while let Some(_) = self.queue.pop() {
steals += 1;
}
}
// At this point in time, we have gated all future senders from sending,
@ -338,13 +353,12 @@ impl<T> Packet<T> {
self.queue.producer_addition().cnt.store(DISCONNECTED, Ordering::SeqCst);
DISCONNECTED
}
n => n
n => n,
}
}
// Removes a previous thread from being blocked in this port
pub fn abort_selection(&self,
was_upgrade: bool) -> Result<bool, Receiver<T>> {
pub fn abort_selection(&self, was_upgrade: bool) -> Result<bool, Receiver<T>> {
// If we're aborting selection after upgrading from a oneshot, then
// we're guarantee that no one is waiting. The only way that we could
// have seen the upgrade is if data was actually sent on the channel
@ -361,7 +375,7 @@ impl<T> Packet<T> {
if was_upgrade {
assert_eq!(unsafe { *self.queue.consumer_addition().steals.get() }, 0);
assert_eq!(self.queue.producer_addition().to_wake.load(Ordering::SeqCst), 0);
return Ok(true)
return Ok(true);
}
// We want to make sure that the count on the channel goes non-negative,
@ -416,12 +430,10 @@ impl<T> Packet<T> {
// upgraded port.
if has_data {
match self.queue.peek() {
Some(&mut GoUp(..)) => {
match self.queue.pop() {
Some(&mut GoUp(..)) => match self.queue.pop() {
Some(GoUp(port)) => Err(port),
_ => unreachable!(),
}
}
},
_ => Ok(true),
}
} else {

View file

@ -1,3 +1,4 @@
use self::Blocker::*;
/// Synchronous channels/ports
///
/// This channel implementation differs significantly from the asynchronous
@ -22,17 +23,15 @@
/// implementation shares almost all code for the buffered and unbuffered cases
/// of a synchronous channel. There are a few branches for the unbuffered case,
/// but they're mostly just relevant to blocking senders.
pub use self::Failure::*;
use self::Blocker::*;
use core::intrinsics::abort;
use core::isize;
use core::mem;
use core::ptr;
use crate::sync::atomic::{Ordering, AtomicUsize};
use crate::sync::mpsc::blocking::{self, WaitToken, SignalToken};
use crate::sync::atomic::{AtomicUsize, Ordering};
use crate::sync::mpsc::blocking::{self, SignalToken, WaitToken};
use crate::sync::{Mutex, MutexGuard};
use crate::time::Instant;
@ -46,9 +45,9 @@ pub struct Packet<T> {
lock: Mutex<State<T>>,
}
unsafe impl<T: Send> Send for Packet<T> { }
unsafe impl<T: Send> Send for Packet<T> {}
unsafe impl<T: Send> Sync for Packet<T> { }
unsafe impl<T: Send> Sync for Packet<T> {}
struct State<T> {
disconnected: bool, // Is the channel disconnected yet?
@ -72,7 +71,7 @@ unsafe impl<T: Send> Send for State<T> {}
enum Blocker {
BlockedSender(SignalToken),
BlockedReceiver(SignalToken),
NoneBlocked
NoneBlocked,
}
/// Simple queue for threading threads together. Nodes are stack-allocated, so
@ -104,11 +103,11 @@ pub enum Failure {
/// Atomically blocks the current thread, placing it into `slot`, unlocking `lock`
/// in the meantime. This re-locks the mutex upon returning.
fn wait<'a, 'b, T>(lock: &'a Mutex<State<T>>,
fn wait<'a, 'b, T>(
lock: &'a Mutex<State<T>>,
mut guard: MutexGuard<'b, State<T>>,
f: fn(SignalToken) -> Blocker)
-> MutexGuard<'a, State<T>>
{
f: fn(SignalToken) -> Blocker,
) -> MutexGuard<'a, State<T>> {
let (wait_token, signal_token) = blocking::tokens();
match mem::replace(&mut guard.blocker, f(signal_token)) {
NoneBlocked => {}
@ -120,12 +119,12 @@ fn wait<'a, 'b, T>(lock: &'a Mutex<State<T>>,
}
/// Same as wait, but waiting at most until `deadline`.
fn wait_timeout_receiver<'a, 'b, T>(lock: &'a Mutex<State<T>>,
fn wait_timeout_receiver<'a, 'b, T>(
lock: &'a Mutex<State<T>>,
deadline: Instant,
mut guard: MutexGuard<'b, State<T>>,
success: &mut bool)
-> MutexGuard<'a, State<T>>
{
success: &mut bool,
) -> MutexGuard<'a, State<T>> {
let (wait_token, signal_token) = blocking::tokens();
match mem::replace(&mut guard.blocker, BlockedReceiver(signal_token)) {
NoneBlocked => {}
@ -147,7 +146,10 @@ fn abort_selection<T>(guard: &mut MutexGuard<'_, State<T>>) -> bool {
guard.blocker = BlockedSender(token);
true
}
BlockedReceiver(token) => { drop(token); false }
BlockedReceiver(token) => {
drop(token);
false
}
}
}
@ -168,12 +170,9 @@ impl<T> Packet<T> {
blocker: NoneBlocked,
cap: capacity,
canceled: None,
queue: Queue {
head: ptr::null_mut(),
tail: ptr::null_mut(),
},
queue: Queue { head: ptr::null_mut(), tail: ptr::null_mut() },
buf: Buffer {
buf: (0..capacity + if capacity == 0 {1} else {0}).map(|_| None).collect(),
buf: (0..capacity + if capacity == 0 { 1 } else { 0 }).map(|_| None).collect(),
start: 0,
size: 0,
},
@ -200,7 +199,9 @@ impl<T> Packet<T> {
pub fn send(&self, t: T) -> Result<(), T> {
let mut guard = self.acquire_send_slot();
if guard.disconnected { return Err(t) }
if guard.disconnected {
return Err(t);
}
guard.buf.enqueue(t);
match mem::replace(&mut guard.blocker, NoneBlocked) {
@ -213,14 +214,17 @@ impl<T> Packet<T> {
assert!(guard.canceled.is_none());
guard.canceled = Some(unsafe { mem::transmute(&mut canceled) });
let mut guard = wait(&self.lock, guard, BlockedSender);
if canceled {Err(guard.buf.dequeue())} else {Ok(())}
if canceled { Err(guard.buf.dequeue()) } else { Ok(()) }
}
// success, we buffered some data
NoneBlocked => Ok(()),
// success, someone's about to receive our buffered data.
BlockedReceiver(token) => { wakeup(token, guard); Ok(()) }
BlockedReceiver(token) => {
wakeup(token, guard);
Ok(())
}
BlockedSender(..) => panic!("lolwut"),
}
@ -271,10 +275,8 @@ impl<T> Packet<T> {
// while loop because we're the only receiver.
if !guard.disconnected && guard.buf.size() == 0 {
if let Some(deadline) = deadline {
guard = wait_timeout_receiver(&self.lock,
deadline,
guard,
&mut woke_up_after_waiting);
guard =
wait_timeout_receiver(&self.lock, deadline, guard, &mut woke_up_after_waiting);
} else {
guard = wait(&self.lock, guard, BlockedReceiver);
woke_up_after_waiting = true;
@ -290,7 +292,9 @@ impl<T> Packet<T> {
// Pick up the data, wake up our neighbors, and carry on
assert!(guard.buf.size() > 0 || (deadline.is_some() && !woke_up_after_waiting));
if guard.buf.size() == 0 { return Err(Empty); }
if guard.buf.size() == 0 {
return Err(Empty);
}
let ret = guard.buf.dequeue();
self.wakeup_senders(woke_up_after_waiting, guard);
@ -301,8 +305,12 @@ impl<T> Packet<T> {
let mut guard = self.lock.lock().unwrap();
// Easy cases first
if guard.disconnected && guard.buf.size() == 0 { return Err(Disconnected) }
if guard.buf.size() == 0 { return Err(Empty) }
if guard.disconnected && guard.buf.size() == 0 {
return Err(Disconnected);
}
if guard.buf.size() == 0 {
return Err(Empty);
}
// Be sure to wake up neighbors
let ret = Ok(guard.buf.dequeue());
@ -357,12 +365,14 @@ impl<T> Packet<T> {
// Only flag the channel as disconnected if we're the last channel
match self.channels.fetch_sub(1, Ordering::SeqCst) {
1 => {}
_ => return
_ => return,
}
// Not much to do other than wake up a receiver if one's there
let mut guard = self.lock.lock().unwrap();
if guard.disconnected { return }
if guard.disconnected {
return;
}
guard.disconnected = true;
match mem::replace(&mut guard.blocker, NoneBlocked) {
NoneBlocked => {}
@ -374,7 +384,9 @@ impl<T> Packet<T> {
pub fn drop_port(&self) {
let mut guard = self.lock.lock().unwrap();
if guard.disconnected { return }
if guard.disconnected {
return;
}
guard.disconnected = true;
// If the capacity is 0, then the sender may want its data back after
@ -382,15 +394,9 @@ impl<T> Packet<T> {
// the buffered data. As with many other portions of this code, this
// needs to be careful to destroy the data *outside* of the lock to
// prevent deadlock.
let _data = if guard.cap != 0 {
mem::take(&mut guard.buf.buf)
} else {
Vec::new()
};
let mut queue = mem::replace(&mut guard.queue, Queue {
head: ptr::null_mut(),
tail: ptr::null_mut(),
});
let _data = if guard.cap != 0 { mem::take(&mut guard.buf.buf) } else { Vec::new() };
let mut queue =
mem::replace(&mut guard.queue, Queue { head: ptr::null_mut(), tail: ptr::null_mut() });
let waiter = match mem::replace(&mut guard.blocker, NoneBlocked) {
NoneBlocked => None,
@ -402,7 +408,9 @@ impl<T> Packet<T> {
};
mem::drop(guard);
while let Some(token) = queue.dequeue() { token.signal(); }
while let Some(token) = queue.dequeue() {
token.signal();
}
waiter.map(|t| t.signal());
}
}
@ -416,7 +424,6 @@ impl<T> Drop for Packet<T> {
}
}
////////////////////////////////////////////////////////////////////////////////
// Buffer, a simple ring buffer backed by Vec<T>
////////////////////////////////////////////////////////////////////////////////
@ -437,8 +444,12 @@ impl<T> Buffer<T> {
result.take().unwrap()
}
fn size(&self) -> usize { self.size }
fn capacity(&self) -> usize { self.buf.len() }
fn size(&self) -> usize {
self.size
}
fn capacity(&self) -> usize {
self.buf.len()
}
}
////////////////////////////////////////////////////////////////////////////////
@ -466,7 +477,7 @@ impl Queue {
fn dequeue(&mut self) -> Option<SignalToken> {
if self.head.is_null() {
return None
return None;
}
let node = self.head;
self.head = unsafe { (*node).next };

View file

@ -6,20 +6,24 @@ use crate::ptr;
// The minimum alignment guaranteed by the architecture. This value is used to
// add fast paths for low alignment values.
#[cfg(all(any(target_arch = "x86",
#[cfg(all(any(
target_arch = "x86",
target_arch = "arm",
target_arch = "mips",
target_arch = "powerpc",
target_arch = "powerpc64",
target_arch = "asmjs",
target_arch = "wasm32",
target_arch = "hexagon")))]
target_arch = "hexagon"
)))]
pub const MIN_ALIGN: usize = 8;
#[cfg(all(any(target_arch = "x86_64",
#[cfg(all(any(
target_arch = "x86_64",
target_arch = "aarch64",
target_arch = "mips64",
target_arch = "s390x",
target_arch = "sparc64")))]
target_arch = "sparc64"
)))]
pub const MIN_ALIGN: usize = 16;
pub unsafe fn realloc_fallback(

View file

@ -25,7 +25,7 @@ pub fn debug_fmt_bytestring(slice: &[u8], f: &mut Formatter<'_>) -> Result {
#[cfg(test)]
mod tests {
use super::*;
use crate::fmt::{Formatter, Result, Debug};
use crate::fmt::{Debug, Formatter, Result};
#[test]
fn smoke() {

View file

@ -1,13 +1,15 @@
#![allow(dead_code)] // not used on all platforms
use crate::path::Path;
use crate::fs;
use crate::io::{self, Error, ErrorKind};
use crate::path::Path;
pub fn copy(from: &Path, to: &Path) -> io::Result<u64> {
if !from.is_file() {
return Err(Error::new(ErrorKind::InvalidInput,
"the source path is not an existing regular file"))
return Err(Error::new(
ErrorKind::InvalidInput,
"the source path is not an existing regular file",
));
}
let mut reader = fs::File::open(from)?;
@ -21,11 +23,7 @@ pub fn copy(from: &Path, to: &Path) -> io::Result<u64> {
pub fn remove_dir_all(path: &Path) -> io::Result<()> {
let filetype = fs::symlink_metadata(path)?.file_type();
if filetype.is_symlink() {
fs::remove_file(path)
} else {
remove_dir_all_recursive(path)
}
if filetype.is_symlink() { fs::remove_file(path) } else { remove_dir_all_recursive(path) }
}
fn remove_dir_all_recursive(path: &Path) -> io::Result<()> {

View file

@ -3,9 +3,9 @@ pub const DEFAULT_BUF_SIZE: usize = 8 * 1024;
#[cfg(test)]
#[allow(dead_code)] // not used on emscripten
pub mod test {
use crate::path::{Path, PathBuf};
use crate::env;
use crate::fs;
use crate::path::{Path, PathBuf};
use rand::RngCore;
pub struct TempDir(PathBuf);

View file

@ -1,79 +1,119 @@
use crate::cmp;
use crate::convert::{TryFrom, TryInto};
use crate::ffi::CString;
use crate::fmt;
use crate::io::{self, Error, ErrorKind, IoSlice, IoSliceMut};
use crate::mem;
use crate::net::{SocketAddr, Shutdown, Ipv4Addr, Ipv6Addr};
use crate::net::{Ipv4Addr, Ipv6Addr, Shutdown, SocketAddr};
use crate::ptr;
use crate::sys::net::{cvt, cvt_r, cvt_gai, Socket, init, wrlen_t};
use crate::sys::net::netc as c;
use crate::sys::net::{cvt, cvt_gai, cvt_r, init, wrlen_t, Socket};
use crate::sys_common::{AsInner, FromInner, IntoInner};
use crate::time::Duration;
use crate::convert::{TryFrom, TryInto};
use libc::{c_int, c_void};
#[cfg(any(target_os = "dragonfly", target_os = "freebsd",
target_os = "ios", target_os = "macos",
target_os = "openbsd", target_os = "netbsd",
target_os = "solaris", target_os = "haiku", target_os = "l4re"))]
use crate::sys::net::netc::IPV6_JOIN_GROUP as IPV6_ADD_MEMBERSHIP;
#[cfg(not(any(target_os = "dragonfly", target_os = "freebsd",
target_os = "ios", target_os = "macos",
target_os = "openbsd", target_os = "netbsd",
target_os = "solaris", target_os = "haiku", target_os = "l4re")))]
#[cfg(not(any(
target_os = "dragonfly",
target_os = "freebsd",
target_os = "ios",
target_os = "macos",
target_os = "openbsd",
target_os = "netbsd",
target_os = "solaris",
target_os = "haiku",
target_os = "l4re"
)))]
use crate::sys::net::netc::IPV6_ADD_MEMBERSHIP;
#[cfg(any(target_os = "dragonfly", target_os = "freebsd",
target_os = "ios", target_os = "macos",
target_os = "openbsd", target_os = "netbsd",
target_os = "solaris", target_os = "haiku", target_os = "l4re"))]
use crate::sys::net::netc::IPV6_LEAVE_GROUP as IPV6_DROP_MEMBERSHIP;
#[cfg(not(any(target_os = "dragonfly", target_os = "freebsd",
target_os = "ios", target_os = "macos",
target_os = "openbsd", target_os = "netbsd",
target_os = "solaris", target_os = "haiku", target_os = "l4re")))]
#[cfg(not(any(
target_os = "dragonfly",
target_os = "freebsd",
target_os = "ios",
target_os = "macos",
target_os = "openbsd",
target_os = "netbsd",
target_os = "solaris",
target_os = "haiku",
target_os = "l4re"
)))]
use crate::sys::net::netc::IPV6_DROP_MEMBERSHIP;
#[cfg(any(
target_os = "dragonfly",
target_os = "freebsd",
target_os = "ios",
target_os = "macos",
target_os = "openbsd",
target_os = "netbsd",
target_os = "solaris",
target_os = "haiku",
target_os = "l4re"
))]
use crate::sys::net::netc::IPV6_JOIN_GROUP as IPV6_ADD_MEMBERSHIP;
#[cfg(any(
target_os = "dragonfly",
target_os = "freebsd",
target_os = "ios",
target_os = "macos",
target_os = "openbsd",
target_os = "netbsd",
target_os = "solaris",
target_os = "haiku",
target_os = "l4re"
))]
use crate::sys::net::netc::IPV6_LEAVE_GROUP as IPV6_DROP_MEMBERSHIP;
#[cfg(any(target_os = "linux", target_os = "android",
target_os = "dragonfly", target_os = "freebsd",
target_os = "openbsd", target_os = "netbsd",
target_os = "haiku"))]
#[cfg(any(
target_os = "linux",
target_os = "android",
target_os = "dragonfly",
target_os = "freebsd",
target_os = "openbsd",
target_os = "netbsd",
target_os = "haiku"
))]
use libc::MSG_NOSIGNAL;
#[cfg(not(any(target_os = "linux", target_os = "android",
target_os = "dragonfly", target_os = "freebsd",
target_os = "openbsd", target_os = "netbsd",
target_os = "haiku")))]
#[cfg(not(any(
target_os = "linux",
target_os = "android",
target_os = "dragonfly",
target_os = "freebsd",
target_os = "openbsd",
target_os = "netbsd",
target_os = "haiku"
)))]
const MSG_NOSIGNAL: c_int = 0x0;
////////////////////////////////////////////////////////////////////////////////
// sockaddr and misc bindings
////////////////////////////////////////////////////////////////////////////////
pub fn setsockopt<T>(sock: &Socket, opt: c_int, val: c_int,
payload: T) -> io::Result<()> {
pub fn setsockopt<T>(sock: &Socket, opt: c_int, val: c_int, payload: T) -> io::Result<()> {
unsafe {
let payload = &payload as *const T as *const c_void;
cvt(c::setsockopt(*sock.as_inner(), opt, val, payload,
mem::size_of::<T>() as c::socklen_t))?;
cvt(c::setsockopt(
*sock.as_inner(),
opt,
val,
payload,
mem::size_of::<T>() as c::socklen_t,
))?;
Ok(())
}
}
pub fn getsockopt<T: Copy>(sock: &Socket, opt: c_int,
val: c_int) -> io::Result<T> {
pub fn getsockopt<T: Copy>(sock: &Socket, opt: c_int, val: c_int) -> io::Result<T> {
unsafe {
let mut slot: T = mem::zeroed();
let mut len = mem::size_of::<T>() as c::socklen_t;
cvt(c::getsockopt(*sock.as_inner(), opt, val,
&mut slot as *mut _ as *mut _,
&mut len))?;
cvt(c::getsockopt(*sock.as_inner(), opt, val, &mut slot as *mut _ as *mut _, &mut len))?;
assert_eq!(len as usize, mem::size_of::<T>());
Ok(slot)
}
}
fn sockname<F>(f: F) -> io::Result<SocketAddr>
where F: FnOnce(*mut c::sockaddr, *mut c::socklen_t) -> c_int
where
F: FnOnce(*mut c::sockaddr, *mut c::socklen_t) -> c_int,
{
unsafe {
let mut storage: c::sockaddr_storage = mem::zeroed();
@ -83,8 +123,7 @@ fn sockname<F>(f: F) -> io::Result<SocketAddr>
}
}
pub fn sockaddr_to_addr(storage: &c::sockaddr_storage,
len: usize) -> io::Result<SocketAddr> {
pub fn sockaddr_to_addr(storage: &c::sockaddr_storage, len: usize) -> io::Result<SocketAddr> {
match storage.ss_family as c_int {
c::AF_INET => {
assert!(len as usize >= mem::size_of::<c::sockaddr_in>());
@ -98,9 +137,7 @@ pub fn sockaddr_to_addr(storage: &c::sockaddr_storage,
*(storage as *const _ as *const c::sockaddr_in6)
})))
}
_ => {
Err(Error::new(ErrorKind::InvalidInput, "invalid argument"))
}
_ => Err(Error::new(ErrorKind::InvalidInput, "invalid argument")),
}
}
@ -121,7 +158,7 @@ fn to_ipv6mr_interface(value: u32) -> libc::c_uint {
pub struct LookupHost {
original: *mut c::addrinfo,
cur: *mut c::addrinfo,
port: u16
port: u16,
}
impl LookupHost {
@ -137,9 +174,7 @@ impl Iterator for LookupHost {
unsafe {
let cur = self.cur.as_ref()?;
self.cur = cur.ai_next;
match sockaddr_to_addr(mem::transmute(cur.ai_addr),
cur.ai_addrlen as usize)
{
match sockaddr_to_addr(mem::transmute(cur.ai_addr), cur.ai_addrlen as usize) {
Ok(addr) => return Some(addr),
Err(_) => continue,
}
@ -162,13 +197,12 @@ impl TryFrom<&str> for LookupHost {
fn try_from(s: &str) -> io::Result<LookupHost> {
macro_rules! try_opt {
($e:expr, $msg:expr) => (
($e:expr, $msg:expr) => {
match $e {
Some(r) => r,
None => return Err(io::Error::new(io::ErrorKind::InvalidInput,
$msg)),
None => return Err(io::Error::new(io::ErrorKind::InvalidInput, $msg)),
}
)
};
}
// split the string by ':' and convert the second part to u16
@ -192,9 +226,8 @@ impl<'a> TryFrom<(&'a str, u16)> for LookupHost {
hints.ai_socktype = c::SOCK_STREAM;
let mut res = ptr::null_mut();
unsafe {
cvt_gai(c::getaddrinfo(c_host.as_ptr(), ptr::null(), &hints, &mut res)).map(|_| {
LookupHost { original: res, cur: res, port }
})
cvt_gai(c::getaddrinfo(c_host.as_ptr(), ptr::null(), &hints, &mut res))
.map(|_| LookupHost { original: res, cur: res, port })
}
}
}
@ -228,9 +261,13 @@ impl TcpStream {
Ok(TcpStream { inner: sock })
}
pub fn socket(&self) -> &Socket { &self.inner }
pub fn socket(&self) -> &Socket {
&self.inner
}
pub fn into_socket(self) -> Socket { self.inner }
pub fn into_socket(self) -> Socket {
self.inner
}
pub fn set_read_timeout(&self, dur: Option<Duration>) -> io::Result<()> {
self.inner.set_timeout(dur, c::SO_RCVTIMEO)
@ -263,10 +300,7 @@ impl TcpStream {
pub fn write(&self, buf: &[u8]) -> io::Result<usize> {
let len = cmp::min(buf.len(), <wrlen_t>::max_value() as usize) as wrlen_t;
let ret = cvt(unsafe {
c::send(*self.inner.as_inner(),
buf.as_ptr() as *const c_void,
len,
MSG_NOSIGNAL)
c::send(*self.inner.as_inner(), buf.as_ptr() as *const c_void, len, MSG_NOSIGNAL)
})?;
Ok(ret as usize)
}
@ -276,15 +310,11 @@ impl TcpStream {
}
pub fn peer_addr(&self) -> io::Result<SocketAddr> {
sockname(|buf, len| unsafe {
c::getpeername(*self.inner.as_inner(), buf, len)
})
sockname(|buf, len| unsafe { c::getpeername(*self.inner.as_inner(), buf, len) })
}
pub fn socket_addr(&self) -> io::Result<SocketAddr> {
sockname(|buf, len| unsafe {
c::getsockname(*self.inner.as_inner(), buf, len)
})
sockname(|buf, len| unsafe { c::getsockname(*self.inner.as_inner(), buf, len) })
}
pub fn shutdown(&self, how: Shutdown) -> io::Result<()> {
@ -339,9 +369,8 @@ impl fmt::Debug for TcpStream {
res.field("peer", &peer);
}
let name = if cfg!(windows) {"socket"} else {"fd"};
res.field(name, &self.inner.as_inner())
.finish()
let name = if cfg!(windows) { "socket" } else { "fd" };
res.field(name, &self.inner.as_inner()).finish()
}
}
@ -365,8 +394,7 @@ impl TcpListener {
// to quickly rebind a socket, without needing to wait for
// the OS to clean up the previous one.
if !cfg!(windows) {
setsockopt(&sock, c::SOL_SOCKET, c::SO_REUSEADDR,
1 as c_int)?;
setsockopt(&sock, c::SOL_SOCKET, c::SO_REUSEADDR, 1 as c_int)?;
}
// Bind our new socket
@ -378,23 +406,24 @@ impl TcpListener {
Ok(TcpListener { inner: sock })
}
pub fn socket(&self) -> &Socket { &self.inner }
pub fn socket(&self) -> &Socket {
&self.inner
}
pub fn into_socket(self) -> Socket { self.inner }
pub fn into_socket(self) -> Socket {
self.inner
}
pub fn socket_addr(&self) -> io::Result<SocketAddr> {
sockname(|buf, len| unsafe {
c::getsockname(*self.inner.as_inner(), buf, len)
})
sockname(|buf, len| unsafe { c::getsockname(*self.inner.as_inner(), buf, len) })
}
pub fn accept(&self) -> io::Result<(TcpStream, SocketAddr)> {
let mut storage: c::sockaddr_storage = unsafe { mem::zeroed() };
let mut len = mem::size_of_val(&storage) as c::socklen_t;
let sock = self.inner.accept(&mut storage as *mut _ as *mut _,
&mut len)?;
let sock = self.inner.accept(&mut storage as *mut _ as *mut _, &mut len)?;
let addr = sockaddr_to_addr(&storage, len as usize)?;
Ok((TcpStream { inner: sock, }, addr))
Ok((TcpStream { inner: sock }, addr))
}
pub fn duplicate(&self) -> io::Result<TcpListener> {
@ -442,9 +471,8 @@ impl fmt::Debug for TcpListener {
res.field("addr", &addr);
}
let name = if cfg!(windows) {"socket"} else {"fd"};
res.field(name, &self.inner.as_inner())
.finish()
let name = if cfg!(windows) { "socket" } else { "fd" };
res.field(name, &self.inner.as_inner()).finish()
}
}
@ -468,20 +496,20 @@ impl UdpSocket {
Ok(UdpSocket { inner: sock })
}
pub fn socket(&self) -> &Socket { &self.inner }
pub fn socket(&self) -> &Socket {
&self.inner
}
pub fn into_socket(self) -> Socket { self.inner }
pub fn into_socket(self) -> Socket {
self.inner
}
pub fn peer_addr(&self) -> io::Result<SocketAddr> {
sockname(|buf, len| unsafe {
c::getpeername(*self.inner.as_inner(), buf, len)
})
sockname(|buf, len| unsafe { c::getpeername(*self.inner.as_inner(), buf, len) })
}
pub fn socket_addr(&self) -> io::Result<SocketAddr> {
sockname(|buf, len| unsafe {
c::getsockname(*self.inner.as_inner(), buf, len)
})
sockname(|buf, len| unsafe { c::getsockname(*self.inner.as_inner(), buf, len) })
}
pub fn recv_from(&self, buf: &mut [u8]) -> io::Result<(usize, SocketAddr)> {
@ -496,9 +524,14 @@ impl UdpSocket {
let len = cmp::min(buf.len(), <wrlen_t>::max_value() as usize) as wrlen_t;
let (dstp, dstlen) = dst.into_inner();
let ret = cvt(unsafe {
c::sendto(*self.inner.as_inner(),
buf.as_ptr() as *const c_void, len,
MSG_NOSIGNAL, dstp, dstlen)
c::sendto(
*self.inner.as_inner(),
buf.as_ptr() as *const c_void,
len,
MSG_NOSIGNAL,
dstp,
dstlen,
)
})?;
Ok(ret as usize)
}
@ -559,8 +592,7 @@ impl UdpSocket {
Ok(raw != 0)
}
pub fn join_multicast_v4(&self, multiaddr: &Ipv4Addr, interface: &Ipv4Addr)
-> io::Result<()> {
pub fn join_multicast_v4(&self, multiaddr: &Ipv4Addr, interface: &Ipv4Addr) -> io::Result<()> {
let mreq = c::ip_mreq {
imr_multiaddr: *multiaddr.as_inner(),
imr_interface: *interface.as_inner(),
@ -568,8 +600,7 @@ impl UdpSocket {
setsockopt(&self.inner, c::IPPROTO_IP, c::IP_ADD_MEMBERSHIP, mreq)
}
pub fn join_multicast_v6(&self, multiaddr: &Ipv6Addr, interface: u32)
-> io::Result<()> {
pub fn join_multicast_v6(&self, multiaddr: &Ipv6Addr, interface: u32) -> io::Result<()> {
let mreq = c::ipv6_mreq {
ipv6mr_multiaddr: *multiaddr.as_inner(),
ipv6mr_interface: to_ipv6mr_interface(interface),
@ -577,8 +608,7 @@ impl UdpSocket {
setsockopt(&self.inner, c::IPPROTO_IPV6, IPV6_ADD_MEMBERSHIP, mreq)
}
pub fn leave_multicast_v4(&self, multiaddr: &Ipv4Addr, interface: &Ipv4Addr)
-> io::Result<()> {
pub fn leave_multicast_v4(&self, multiaddr: &Ipv4Addr, interface: &Ipv4Addr) -> io::Result<()> {
let mreq = c::ip_mreq {
imr_multiaddr: *multiaddr.as_inner(),
imr_interface: *interface.as_inner(),
@ -586,8 +616,7 @@ impl UdpSocket {
setsockopt(&self.inner, c::IPPROTO_IP, c::IP_DROP_MEMBERSHIP, mreq)
}
pub fn leave_multicast_v6(&self, multiaddr: &Ipv6Addr, interface: u32)
-> io::Result<()> {
pub fn leave_multicast_v6(&self, multiaddr: &Ipv6Addr, interface: u32) -> io::Result<()> {
let mreq = c::ipv6_mreq {
ipv6mr_multiaddr: *multiaddr.as_inner(),
ipv6mr_interface: to_ipv6mr_interface(interface),
@ -623,10 +652,7 @@ impl UdpSocket {
pub fn send(&self, buf: &[u8]) -> io::Result<usize> {
let len = cmp::min(buf.len(), <wrlen_t>::max_value() as usize) as wrlen_t;
let ret = cvt(unsafe {
c::send(*self.inner.as_inner(),
buf.as_ptr() as *const c_void,
len,
MSG_NOSIGNAL)
c::send(*self.inner.as_inner(), buf.as_ptr() as *const c_void, len, MSG_NOSIGNAL)
})?;
Ok(ret as usize)
}
@ -651,9 +677,8 @@ impl fmt::Debug for UdpSocket {
res.field("addr", &addr);
}
let name = if cfg!(windows) {"socket"} else {"fd"};
res.field(name, &self.inner.as_inner())
.finish()
let name = if cfg!(windows) { "socket" } else { "fd" };
res.field(name, &self.inner.as_inner()).finish()
}
}
@ -667,10 +692,15 @@ mod tests {
let mut addrs = HashMap::new();
let lh = match LookupHost::try_from(("localhost", 0)) {
Ok(lh) => lh,
Err(e) => panic!("couldn't resolve `localhost': {}", e)
Err(e) => panic!("couldn't resolve `localhost': {}", e),
};
for sa in lh { *addrs.entry(sa).or_insert(0) += 1; };
assert_eq!(addrs.iter().filter(|&(_, &v)| v > 1).collect::<Vec<_>>(), vec![],
"There should be no duplicate localhost entries");
for sa in lh {
*addrs.entry(sa).or_insert(0) += 1;
}
assert_eq!(
addrs.iter().filter(|&(_, &v)| v > 1).collect::<Vec<_>>(),
vec![],
"There should be no duplicate localhost entries"
);
}
}

View file

@ -4,18 +4,18 @@
use crate::borrow::Cow;
use crate::ffi::{OsStr, OsString};
use crate::fmt;
use crate::str;
use crate::mem;
use crate::rc::Rc;
use crate::str;
use crate::sync::Arc;
use crate::sys_common::{FromInner, IntoInner, AsInner};
use crate::sys_common::bytestring::debug_fmt_bytestring;
use crate::sys_common::{AsInner, FromInner, IntoInner};
use core::str::lossy::Utf8Lossy;
#[derive(Clone, Hash)]
pub(crate) struct Buf {
pub inner: Vec<u8>
pub inner: Vec<u8>,
}
// FIXME:
@ -25,7 +25,7 @@ pub(crate) struct Buf {
// Anyway, `Slice` representation and layout are considered implementation detail, are
// not documented and must not be relied upon.
pub(crate) struct Slice {
pub inner: [u8]
pub inner: [u8],
}
impl fmt::Debug for Slice {
@ -64,7 +64,6 @@ impl AsInner<[u8]> for Buf {
}
}
impl Buf {
pub fn from_string(s: String) -> Buf {
Buf { inner: s.into_bytes() }
@ -72,9 +71,7 @@ impl Buf {
#[inline]
pub fn with_capacity(capacity: usize) -> Buf {
Buf {
inner: Vec::with_capacity(capacity)
}
Buf { inner: Vec::with_capacity(capacity) }
}
#[inline]
@ -112,7 +109,7 @@ impl Buf {
}
pub fn into_string(self) -> Result<String, Buf> {
String::from_utf8(self.inner).map_err(|p| Buf { inner: p.into_bytes() } )
String::from_utf8(self.inner).map_err(|p| Buf { inner: p.into_bytes() })
}
pub fn push_slice(&mut self, s: &Slice) {

View file

@ -1,9 +1,11 @@
use crate::error::{Error};
use crate::error::Error;
use crate::fmt;
use crate::sync::atomic::{AtomicBool, Ordering};
use crate::thread;
pub struct Flag { failed: AtomicBool }
pub struct Flag {
failed: AtomicBool,
}
// Note that the Ordering uses to access the `failed` field of `Flag` below is
// always `Relaxed`, and that's because this isn't actually protecting any data,
@ -24,11 +26,7 @@ impl Flag {
#[inline]
pub fn borrow(&self) -> LockResult<Guard> {
let ret = Guard { panicking: thread::panicking() };
if self.get() {
Err(PoisonError::new(ret))
} else {
Ok(ret)
}
if self.get() { Err(PoisonError::new(ret)) } else { Ok(ret) }
}
#[inline]
@ -192,17 +190,23 @@ impl<T> PoisonError<T> {
/// println!("recovered {} items", data.len());
/// ```
#[stable(feature = "sync_poison", since = "1.2.0")]
pub fn into_inner(self) -> T { self.guard }
pub fn into_inner(self) -> T {
self.guard
}
/// Reaches into this error indicating that a lock is poisoned, returning a
/// reference to the underlying guard to allow access regardless.
#[stable(feature = "sync_poison", since = "1.2.0")]
pub fn get_ref(&self) -> &T { &self.guard }
pub fn get_ref(&self) -> &T {
&self.guard
}
/// Reaches into this error indicating that a lock is poisoned, returning a
/// mutable reference to the underlying guard to allow access regardless.
#[stable(feature = "sync_poison", since = "1.2.0")]
pub fn get_mut(&mut self) -> &mut T { &mut self.guard }
pub fn get_mut(&mut self) -> &mut T {
&mut self.guard
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -217,7 +221,7 @@ impl<T> fmt::Debug for TryLockError<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match *self {
TryLockError::Poisoned(..) => "Poisoned(..)".fmt(f),
TryLockError::WouldBlock => "WouldBlock".fmt(f)
TryLockError::WouldBlock => "WouldBlock".fmt(f),
}
}
}
@ -227,8 +231,9 @@ impl<T> fmt::Display for TryLockError<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match *self {
TryLockError::Poisoned(..) => "poisoned lock: another task failed inside",
TryLockError::WouldBlock => "try_lock failed because the operation would block"
}.fmt(f)
TryLockError::WouldBlock => "try_lock failed because the operation would block",
}
.fmt(f)
}
}
@ -237,23 +242,24 @@ impl<T> Error for TryLockError<T> {
fn description(&self) -> &str {
match *self {
TryLockError::Poisoned(ref p) => p.description(),
TryLockError::WouldBlock => "try_lock failed because the operation would block"
TryLockError::WouldBlock => "try_lock failed because the operation would block",
}
}
fn cause(&self) -> Option<&dyn Error> {
match *self {
TryLockError::Poisoned(ref p) => Some(p),
_ => None
_ => None,
}
}
}
pub fn map_result<T, U, F>(result: LockResult<T>, f: F)
-> LockResult<U>
where F: FnOnce(T) -> U {
pub fn map_result<T, U, F>(result: LockResult<T>, f: F) -> LockResult<U>
where
F: FnOnce(T) -> U,
{
match result {
Ok(t) => Ok(f(t)),
Err(PoisonError { guard }) => Err(PoisonError::new(f(guard)))
Err(PoisonError { guard }) => Err(PoisonError::new(f(guard))),
}
}

View file

@ -11,16 +11,12 @@ use crate::sys::process::EnvKey;
pub struct CommandEnv {
clear: bool,
saw_path: bool,
vars: BTreeMap<EnvKey, Option<OsString>>
vars: BTreeMap<EnvKey, Option<OsString>>,
}
impl Default for CommandEnv {
fn default() -> Self {
CommandEnv {
clear: false,
saw_path: false,
vars: Default::default()
}
CommandEnv { clear: false, saw_path: false, vars: Default::default() }
}
}
@ -64,11 +60,7 @@ impl CommandEnv {
}
pub fn capture_if_changed(&self) -> Option<BTreeMap<EnvKey, OsString>> {
if self.is_unchanged() {
None
} else {
Some(self.capture())
}
if self.is_unchanged() { None } else { Some(self.capture()) }
}
// The following functions build up changes

View file

@ -12,16 +12,19 @@ struct ThreadInfo {
thread_local! { static THREAD_INFO: RefCell<Option<ThreadInfo>> = RefCell::new(None) }
impl ThreadInfo {
fn with<R, F>(f: F) -> Option<R> where F: FnOnce(&mut ThreadInfo) -> R {
THREAD_INFO.try_with(move |c| {
fn with<R, F>(f: F) -> Option<R>
where
F: FnOnce(&mut ThreadInfo) -> R,
{
THREAD_INFO
.try_with(move |c| {
if c.borrow().is_none() {
*c.borrow_mut() = Some(ThreadInfo {
stack_guard: None,
thread: Thread::new(None),
})
*c.borrow_mut() =
Some(ThreadInfo { stack_guard: None, thread: Thread::new(None) })
}
f(c.borrow_mut().as_mut().unwrap())
}).ok()
})
.ok()
}
}
@ -35,10 +38,7 @@ pub fn stack_guard() -> Option<Guard> {
pub fn set(stack_guard: Option<Guard>, thread: Thread) {
THREAD_INFO.with(|c| assert!(c.borrow().is_none()));
THREAD_INFO.with(move |c| *c.borrow_mut() = Some(ThreadInfo{
stack_guard,
thread,
}));
THREAD_INFO.with(move |c| *c.borrow_mut() = Some(ThreadInfo { stack_guard, thread }));
}
pub fn reset_guard(stack_guard: Option<Guard>) {

View file

@ -16,11 +16,15 @@ pub fn dumb_print(args: fmt::Arguments<'_>) {
pub fn abort(args: fmt::Arguments<'_>) -> ! {
dumb_print(format_args!("fatal runtime error: {}\n", args));
unsafe { crate::sys::abort_internal(); }
unsafe {
crate::sys::abort_internal();
}
}
#[allow(dead_code)] // stack overflow detection not enabled on all platforms
pub unsafe fn report_overflow() {
dumb_print(format_args!("\nthread '{}' has overflowed its stack\n",
thread::current().name().unwrap_or("<unknown>")));
dumb_print(format_args!(
"\nthread '{}' has overflowed its stack\n",
thread::current().name().unwrap_or("<unknown>")
));
}

View file

@ -39,7 +39,7 @@ const UTF8_REPLACEMENT_CHARACTER: &str = "\u{FFFD}";
/// a code point that is not a surrogate (U+D800 to U+DFFF).
#[derive(Eq, PartialEq, Ord, PartialOrd, Clone, Copy)]
pub struct CodePoint {
value: u32
value: u32,
}
/// Format the code point as `U+` followed by four to six hexadecimal digits.
@ -66,8 +66,8 @@ impl CodePoint {
#[inline]
pub fn from_u32(value: u32) -> Option<CodePoint> {
match value {
0 ..= 0x10FFFF => Some(CodePoint { value }),
_ => None
0..=0x10FFFF => Some(CodePoint { value }),
_ => None,
}
}
@ -91,8 +91,8 @@ impl CodePoint {
#[inline]
pub fn to_char(&self) -> Option<char> {
match self.value {
0xD800 ..= 0xDFFF => None,
_ => Some(unsafe { char::from_u32_unchecked(self.value) })
0xD800..=0xDFFF => None,
_ => Some(unsafe { char::from_u32_unchecked(self.value) }),
}
}
@ -112,7 +112,7 @@ impl CodePoint {
/// if theyre not in a surrogate pair.
#[derive(Eq, PartialEq, Ord, PartialOrd, Clone)]
pub struct Wtf8Buf {
bytes: Vec<u8>
bytes: Vec<u8>,
}
impl ops::Deref for Wtf8Buf {
@ -188,9 +188,7 @@ impl Wtf8Buf {
Err(surrogate) => {
let surrogate = surrogate.unpaired_surrogate();
// Surrogates are known to be in the code point range.
let code_point = unsafe {
CodePoint::from_u32_unchecked(surrogate as u32)
};
let code_point = unsafe { CodePoint::from_u32_unchecked(surrogate as u32) };
// Skip the WTF-8 concatenation check,
// surrogate pairs are already decoded by decode_utf16
string.push_code_point_unchecked(code_point)
@ -203,9 +201,7 @@ impl Wtf8Buf {
/// Copied from String::push
/// This does **not** include the WTF-8 concatenation check.
fn push_code_point_unchecked(&mut self, code_point: CodePoint) {
let c = unsafe {
char::from_u32_unchecked(code_point.value)
};
let c = unsafe { char::from_u32_unchecked(code_point.value) };
let mut bytes = [0; 4];
let bytes = c.encode_utf8(&mut bytes).as_bytes();
self.bytes.extend_from_slice(bytes)
@ -278,7 +274,7 @@ impl Wtf8Buf {
self.push_char(decode_surrogate_pair(lead, trail));
self.bytes.extend_from_slice(other_without_trail_surrogate);
}
_ => self.bytes.extend_from_slice(&other.bytes)
_ => self.bytes.extend_from_slice(&other.bytes),
}
}
@ -300,7 +296,7 @@ impl Wtf8Buf {
let len_without_lead_surrogate = self.len() - 3;
self.bytes.truncate(len_without_lead_surrogate);
self.push_char(decode_surrogate_pair(lead, trail as u16));
return
return;
}
}
@ -347,8 +343,8 @@ impl Wtf8Buf {
pos = surrogate_pos + 3;
self.bytes[surrogate_pos..pos]
.copy_from_slice(UTF8_REPLACEMENT_CHARACTER.as_bytes());
},
None => return unsafe { String::from_utf8_unchecked(self.bytes) }
}
None => return unsafe { String::from_utf8_unchecked(self.bytes) },
}
}
}
@ -371,7 +367,7 @@ impl Wtf8Buf {
/// This replaces surrogate code point pairs with supplementary code points,
/// like concatenating ill-formed UTF-16 strings effectively would.
impl FromIterator<CodePoint> for Wtf8Buf {
fn from_iter<T: IntoIterator<Item=CodePoint>>(iter: T) -> Wtf8Buf {
fn from_iter<T: IntoIterator<Item = CodePoint>>(iter: T) -> Wtf8Buf {
let mut string = Wtf8Buf::new();
string.extend(iter);
string
@ -383,7 +379,7 @@ impl FromIterator<CodePoint> for Wtf8Buf {
/// This replaces surrogate code point pairs with supplementary code points,
/// like concatenating ill-formed UTF-16 strings effectively would.
impl Extend<CodePoint> for Wtf8Buf {
fn extend<T: IntoIterator<Item=CodePoint>>(&mut self, iter: T) {
fn extend<T: IntoIterator<Item = CodePoint>>(&mut self, iter: T) {
let iterator = iter.into_iter();
let (low, _high) = iterator.size_hint();
// Lower bound of one byte per code point (ASCII only)
@ -398,11 +394,13 @@ impl Extend<CodePoint> for Wtf8Buf {
/// if theyre not in a surrogate pair.
#[derive(Eq, Ord, PartialEq, PartialOrd)]
pub struct Wtf8 {
bytes: [u8]
bytes: [u8],
}
impl AsInner<[u8]> for Wtf8 {
fn as_inner(&self) -> &[u8] { &self.bytes }
fn as_inner(&self) -> &[u8] {
&self.bytes
}
}
/// Format the slice with double quotes,
@ -421,19 +419,13 @@ impl fmt::Debug for Wtf8 {
formatter.write_str("\"")?;
let mut pos = 0;
while let Some((surrogate_pos, surrogate)) = self.next_surrogate(pos) {
write_str_escaped(
formatter,
unsafe { str::from_utf8_unchecked(
&self.bytes[pos .. surrogate_pos]
)},
)?;
write_str_escaped(formatter, unsafe {
str::from_utf8_unchecked(&self.bytes[pos..surrogate_pos])
})?;
write!(formatter, "\\u{{{:x}}}", surrogate)?;
pos = surrogate_pos + 3;
}
write_str_escaped(
formatter,
unsafe { str::from_utf8_unchecked(&self.bytes[pos..]) },
)?;
write_str_escaped(formatter, unsafe { str::from_utf8_unchecked(&self.bytes[pos..]) })?;
formatter.write_str("\"")
}
}
@ -446,20 +438,14 @@ impl fmt::Display for Wtf8 {
match self.next_surrogate(pos) {
Some((surrogate_pos, _)) => {
formatter.write_str(unsafe {
str::from_utf8_unchecked(&wtf8_bytes[pos .. surrogate_pos])
str::from_utf8_unchecked(&wtf8_bytes[pos..surrogate_pos])
})?;
formatter.write_str(UTF8_REPLACEMENT_CHARACTER)?;
pos = surrogate_pos + 3;
},
None => {
let s = unsafe {
str::from_utf8_unchecked(&wtf8_bytes[pos..])
};
if pos == 0 {
return s.fmt(formatter)
} else {
return formatter.write_str(s)
}
None => {
let s = unsafe { str::from_utf8_unchecked(&wtf8_bytes[pos..]) };
if pos == 0 { return s.fmt(formatter) } else { return formatter.write_str(s) }
}
}
}
@ -513,8 +499,8 @@ impl Wtf8 {
#[inline]
pub fn ascii_byte_at(&self, position: usize) -> u8 {
match self.bytes[position] {
ascii_byte @ 0x00 ..= 0x7F => ascii_byte,
_ => 0xFF
ascii_byte @ 0x00..=0x7F => ascii_byte,
_ => 0xFF,
}
}
@ -558,13 +544,13 @@ impl Wtf8 {
loop {
match self.next_surrogate(pos) {
Some((surrogate_pos, _)) => {
utf8_bytes.extend_from_slice(&wtf8_bytes[pos .. surrogate_pos]);
utf8_bytes.extend_from_slice(&wtf8_bytes[pos..surrogate_pos]);
utf8_bytes.extend_from_slice(UTF8_REPLACEMENT_CHARACTER.as_bytes());
pos = surrogate_pos + 3;
},
}
None => {
utf8_bytes.extend_from_slice(&wtf8_bytes[pos..]);
return Cow::Owned(unsafe { String::from_utf8_unchecked(utf8_bytes) })
return Cow::Owned(unsafe { String::from_utf8_unchecked(utf8_bytes) });
}
}
}
@ -594,9 +580,9 @@ impl Wtf8 {
} else if b == 0xED {
match (iter.next(), iter.next()) {
(Some(&b2), Some(&b3)) if b2 >= 0xA0 => {
return Some((pos, decode_surrogate(b2, b3)))
return Some((pos, decode_surrogate(b2, b3)));
}
_ => pos += 3
_ => pos += 3,
}
} else if b < 0xF0 {
iter.next();
@ -615,11 +601,11 @@ impl Wtf8 {
fn final_lead_surrogate(&self) -> Option<u16> {
let len = self.len();
if len < 3 {
return None
return None;
}
match &self.bytes[(len - 3)..] {
&[0xED, b2 @ 0xA0..=0xAF, b3] => Some(decode_surrogate(b2, b3)),
_ => None
_ => None,
}
}
@ -627,11 +613,11 @@ impl Wtf8 {
fn initial_trail_surrogate(&self) -> Option<u16> {
let len = self.len();
if len < 3 {
return None
return None;
}
match &self.bytes[..3] {
&[0xED, b2 @ 0xB0..=0xBF, b3] => Some(decode_surrogate(b2, b3)),
_ => None
_ => None,
}
}
@ -661,7 +647,6 @@ impl Wtf8 {
}
}
/// Returns a slice of the given string for the byte range [`begin`..`end`).
///
/// # Panics
@ -674,9 +659,10 @@ impl ops::Index<ops::Range<usize>> for Wtf8 {
#[inline]
fn index(&self, range: ops::Range<usize>) -> &Wtf8 {
// is_code_point_boundary checks that the index is in [0, .len()]
if range.start <= range.end &&
is_code_point_boundary(self, range.start) &&
is_code_point_boundary(self, range.end) {
if range.start <= range.end
&& is_code_point_boundary(self, range.start)
&& is_code_point_boundary(self, range.end)
{
unsafe { slice_unchecked(self, range.start, range.end) }
} else {
slice_error_fail(self, range.start, range.end)
@ -748,7 +734,9 @@ fn decode_surrogate_pair(lead: u16, trail: u16) -> char {
/// Copied from core::str::StrPrelude::is_char_boundary
#[inline]
pub fn is_code_point_boundary(slice: &Wtf8, index: usize) -> bool {
if index == slice.len() { return true; }
if index == slice.len() {
return true;
}
match slice.bytes.get(index) {
None => false,
Some(&b) => b < 128 || b >= 192,
@ -759,18 +747,14 @@ pub fn is_code_point_boundary(slice: &Wtf8, index: usize) -> bool {
#[inline]
pub unsafe fn slice_unchecked(s: &Wtf8, begin: usize, end: usize) -> &Wtf8 {
// memory layout of an &[u8] and &Wtf8 are the same
Wtf8::from_bytes_unchecked(slice::from_raw_parts(
s.bytes.as_ptr().add(begin),
end - begin
))
Wtf8::from_bytes_unchecked(slice::from_raw_parts(s.bytes.as_ptr().add(begin), end - begin))
}
/// Copied from core::str::raw::slice_error_fail
#[inline(never)]
pub fn slice_error_fail(s: &Wtf8, begin: usize, end: usize) -> ! {
assert!(begin <= end);
panic!("index {} and/or {} in `{:?}` do not lie on character boundary",
begin, end, s);
panic!("index {} and/or {} in `{:?}` do not lie on character boundary", begin, end, s);
}
/// Iterator for the code points of a WTF-8 string.
@ -778,7 +762,7 @@ pub fn slice_error_fail(s: &Wtf8, begin: usize, end: usize) -> ! {
/// Created with the method `.code_points()`.
#[derive(Clone)]
pub struct Wtf8CodePoints<'a> {
bytes: slice::Iter<'a, u8>
bytes: slice::Iter<'a, u8>,
}
impl<'a> Iterator for Wtf8CodePoints<'a> {
@ -801,7 +785,7 @@ impl<'a> Iterator for Wtf8CodePoints<'a> {
#[derive(Clone)]
pub struct EncodeWide<'a> {
code_points: Wtf8CodePoints<'a>,
extra: u16
extra: u16,
}
// Copied from libunicode/u_str.rs
@ -819,9 +803,7 @@ impl<'a> Iterator for EncodeWide<'a> {
let mut buf = [0; 2];
self.code_points.next().map(|code_point| {
let c = unsafe {
char::from_u32_unchecked(code_point.value)
};
let c = unsafe { char::from_u32_unchecked(code_point.value) };
let n = c.encode_utf16(&mut buf).len();
if n == 2 {
self.extra = buf[1];
@ -864,13 +846,15 @@ impl Hash for Wtf8 {
}
impl Wtf8 {
pub fn make_ascii_uppercase(&mut self) { self.bytes.make_ascii_uppercase() }
pub fn make_ascii_uppercase(&mut self) {
self.bytes.make_ascii_uppercase()
}
}
#[cfg(test)]
mod tests {
use crate::borrow::Cow;
use super::*;
use crate::borrow::Cow;
#[test]
fn code_point_from_u32() {
@ -882,7 +866,9 @@ mod tests {
#[test]
fn code_point_to_u32() {
fn c(value: u32) -> CodePoint { CodePoint::from_u32(value).unwrap() }
fn c(value: u32) -> CodePoint {
CodePoint::from_u32(value).unwrap()
}
assert_eq!(c(0).to_u32(), 0);
assert_eq!(c(0xD800).to_u32(), 0xD800);
assert_eq!(c(0x10FFFF).to_u32(), 0x10FFFF);
@ -902,7 +888,9 @@ mod tests {
#[test]
fn code_point_to_char() {
fn c(value: u32) -> CodePoint { CodePoint::from_u32(value).unwrap() }
fn c(value: u32) -> CodePoint {
CodePoint::from_u32(value).unwrap()
}
assert_eq!(c(0x61).to_char(), Some('a'));
assert_eq!(c(0x1F4A9).to_char(), Some('💩'));
assert_eq!(c(0xD800).to_char(), None);
@ -910,7 +898,9 @@ mod tests {
#[test]
fn code_point_to_char_lossy() {
fn c(value: u32) -> CodePoint { CodePoint::from_u32(value).unwrap() }
fn c(value: u32) -> CodePoint {
CodePoint::from_u32(value).unwrap()
}
assert_eq!(c(0x61).to_char_lossy(), 'a');
assert_eq!(c(0x1F4A9).to_char_lossy(), '💩');
assert_eq!(c(0xD800).to_char_lossy(), '\u{FFFD}');
@ -924,23 +914,25 @@ mod tests {
#[test]
fn wtf8buf_from_str() {
assert_eq!(Wtf8Buf::from_str("").bytes, b"");
assert_eq!(Wtf8Buf::from_str("aé 💩").bytes,
b"a\xC3\xA9 \xF0\x9F\x92\xA9");
assert_eq!(Wtf8Buf::from_str("aé 💩").bytes, b"a\xC3\xA9 \xF0\x9F\x92\xA9");
}
#[test]
fn wtf8buf_from_string() {
assert_eq!(Wtf8Buf::from_string(String::from("")).bytes, b"");
assert_eq!(Wtf8Buf::from_string(String::from("aé 💩")).bytes,
b"a\xC3\xA9 \xF0\x9F\x92\xA9");
assert_eq!(
Wtf8Buf::from_string(String::from("aé 💩")).bytes,
b"a\xC3\xA9 \xF0\x9F\x92\xA9"
);
}
#[test]
fn wtf8buf_from_wide() {
assert_eq!(Wtf8Buf::from_wide(&[]).bytes, b"");
assert_eq!(Wtf8Buf::from_wide(
&[0x61, 0xE9, 0x20, 0xD83D, 0xD83D, 0xDCA9]).bytes,
b"a\xC3\xA9 \xED\xA0\xBD\xF0\x9F\x92\xA9");
assert_eq!(
Wtf8Buf::from_wide(&[0x61, 0xE9, 0x20, 0xD83D, 0xD83D, 0xDCA9]).bytes,
b"a\xC3\xA9 \xED\xA0\xBD\xF0\x9F\x92\xA9"
);
}
#[test]
@ -966,7 +958,9 @@ mod tests {
string.push(CodePoint::from_char('💩'));
assert_eq!(string.bytes, b"a\xC3\xA9 \xF0\x9F\x92\xA9");
fn c(value: u32) -> CodePoint { CodePoint::from_u32(value).unwrap() }
fn c(value: u32) -> CodePoint {
CodePoint::from_u32(value).unwrap()
}
let mut string = Wtf8Buf::new();
string.push(c(0xD83D)); // lead
@ -1011,7 +1005,9 @@ mod tests {
string.push_wtf8(Wtf8::from_str(" 💩"));
assert_eq!(string.bytes, b"a\xC3\xA9 \xF0\x9F\x92\xA9");
fn w(v: &[u8]) -> &Wtf8 { unsafe { Wtf8::from_bytes_unchecked(v) } }
fn w(v: &[u8]) -> &Wtf8 {
unsafe { Wtf8::from_bytes_unchecked(v) }
}
let mut string = Wtf8Buf::new();
string.push_wtf8(w(b"\xED\xA0\xBD")); // lead
@ -1105,14 +1101,15 @@ mod tests {
#[test]
fn wtf8buf_extend() {
fn e(initial: &[u32], extended: &[u32]) -> Wtf8Buf {
fn c(value: &u32) -> CodePoint { CodePoint::from_u32(*value).unwrap() }
fn c(value: &u32) -> CodePoint {
CodePoint::from_u32(*value).unwrap()
}
let mut string = initial.iter().map(c).collect::<Wtf8Buf>();
string.extend(extended.iter().map(c));
string
}
assert_eq!(e(&[0x61, 0xE9], &[0x20, 0x1F4A9]).bytes,
b"a\xC3\xA9 \xF0\x9F\x92\xA9");
assert_eq!(e(&[0x61, 0xE9], &[0x20, 0x1F4A9]).bytes, b"a\xC3\xA9 \xF0\x9F\x92\xA9");
assert_eq!(e(&[0xD83D], &[0xDCA9]).bytes, b"\xF0\x9F\x92\xA9"); // Magic!
assert_eq!(e(&[0xD83D, 0x20], &[0xDCA9]).bytes, b"\xED\xA0\xBD \xED\xB2\xA9");
@ -1156,13 +1153,13 @@ mod tests {
#[test]
fn wtf8_slice() {
assert_eq!(&Wtf8::from_str("aé 💩")[1.. 4].bytes, b"\xC3\xA9 ");
assert_eq!(&Wtf8::from_str("aé 💩")[1..4].bytes, b"\xC3\xA9 ");
}
#[test]
#[should_panic]
fn wtf8_slice_not_code_point_boundary() {
&Wtf8::from_str("aé 💩")[2.. 4];
&Wtf8::from_str("aé 💩")[2..4];
}
#[test]
@ -1199,7 +1196,9 @@ mod tests {
#[test]
fn wtf8_code_points() {
fn c(value: u32) -> CodePoint { CodePoint::from_u32(value).unwrap() }
fn c(value: u32) -> CodePoint {
CodePoint::from_u32(value).unwrap()
}
fn cp(string: &Wtf8Buf) -> Vec<Option<char>> {
string.code_points().map(|c| c.to_char()).collect::<Vec<_>>()
}
@ -1249,7 +1248,9 @@ mod tests {
let mut string = Wtf8Buf::from_str("");
string.push(CodePoint::from_u32(0xD83D).unwrap());
string.push_char('💩');
assert_eq!(string.encode_wide().collect::<Vec<_>>(),
vec![0x61, 0xE9, 0x20, 0xD83D, 0xD83D, 0xDCA9]);
assert_eq!(
string.encode_wide().collect::<Vec<_>>(),
vec![0x61, 0xE9, 0x20, 0xD83D, 0xD83D, 0xDCA9]
);
}
}

View file

@ -1,13 +1,12 @@
use std::env::*;
use std::ffi::{OsString, OsStr};
use std::ffi::{OsStr, OsString};
use rand::{thread_rng, Rng};
use rand::distributions::Alphanumeric;
use rand::{thread_rng, Rng};
fn make_rand_name() -> OsString {
let rng = thread_rng();
let n = format!("TEST{}", rng.sample_iter(&Alphanumeric).take(10)
.collect::<String>());
let n = format!("TEST{}", rng.sample_iter(&Alphanumeric).take(10).collect::<String>());
let n = OsString::from(n);
assert!(var_os(&n).is_none());
n
@ -73,11 +72,7 @@ fn test_env_set_var() {
let mut e = vars_os();
set_var(&n, "VALUE");
assert!(!e.any(|(k, v)| {
&*k == &*n && &*v == "VALUE"
}));
assert!(!e.any(|(k, v)| { &*k == &*n && &*v == "VALUE" }));
assert!(vars_os().any(|(k, v)| {
&*k == &*n && &*v == "VALUE"
}));
assert!(vars_os().any(|(k, v)| { &*k == &*n && &*v == "VALUE" }));
}

View file

@ -142,9 +142,7 @@ macro_rules! thread_local {
}
#[doc(hidden)]
#[unstable(feature = "thread_local_internals",
reason = "should not be necessary",
issue = "0")]
#[unstable(feature = "thread_local_internals", reason = "should not be necessary", issue = "0")]
#[macro_export]
#[allow_internal_unstable(thread_local_internals, cfg_target_thread_local, thread_local)]
#[allow_internal_unsafe]
@ -214,13 +212,13 @@ impl Error for AccessError {}
impl<T: 'static> LocalKey<T> {
#[doc(hidden)]
#[unstable(feature = "thread_local_internals",
#[unstable(
feature = "thread_local_internals",
reason = "recently added to create a key",
issue = "0")]
issue = "0"
)]
pub const unsafe fn new(inner: unsafe fn() -> Option<&'static T>) -> LocalKey<T> {
LocalKey {
inner,
}
LocalKey { inner }
}
/// Acquires a reference to the value in this TLS key.
@ -235,9 +233,13 @@ impl<T: 'static> LocalKey<T> {
/// previously been run for this thread.
#[stable(feature = "rust1", since = "1.0.0")]
pub fn with<F, R>(&'static self, f: F) -> R
where F: FnOnce(&T) -> R {
self.try_with(f).expect("cannot access a Thread Local Storage value \
during or after destruction")
where
F: FnOnce(&T) -> R,
{
self.try_with(f).expect(
"cannot access a Thread Local Storage value \
during or after destruction",
)
}
/// Acquires a reference to the value in this TLS key.
@ -256,9 +258,7 @@ impl<T: 'static> LocalKey<T> {
F: FnOnce(&T) -> R,
{
unsafe {
let thread_local = (self.inner)().ok_or(AccessError {
_private: (),
})?;
let thread_local = (self.inner)().ok_or(AccessError { _private: () })?;
Ok(f(thread_local))
}
}
@ -266,8 +266,8 @@ impl<T: 'static> LocalKey<T> {
mod lazy {
use crate::cell::UnsafeCell;
use crate::mem;
use crate::hint;
use crate::mem;
pub struct LazyKeyInner<T> {
inner: UnsafeCell<Option<T>>,
@ -275,9 +275,7 @@ mod lazy {
impl<T> LazyKeyInner<T> {
pub const fn new() -> LazyKeyInner<T> {
LazyKeyInner {
inner: UnsafeCell::new(None),
}
LazyKeyInner { inner: UnsafeCell::new(None) }
}
pub unsafe fn get(&self) -> Option<&'static T> {
@ -334,7 +332,7 @@ pub mod statik {
inner: LazyKeyInner<T>,
}
unsafe impl<T> Sync for Key<T> { }
unsafe impl<T> Sync for Key<T> {}
impl<T> fmt::Debug for Key<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
@ -344,9 +342,7 @@ pub mod statik {
impl<T> Key<T> {
pub const fn new() -> Key<T> {
Key {
inner: LazyKeyInner::new(),
}
Key { inner: LazyKeyInner::new() }
}
pub unsafe fn get(&self, init: fn() -> T) -> Option<&'static T> {
@ -404,10 +400,7 @@ pub mod fast {
impl<T> Key<T> {
pub const fn new() -> Key<T> {
Key {
inner: LazyKeyInner::new(),
dtor_state: Cell::new(DtorState::Unregistered),
}
Key { inner: LazyKeyInner::new(), dtor_state: Cell::new(DtorState::Unregistered) }
}
pub unsafe fn get<F: FnOnce() -> T>(&self, init: F) -> Option<&'static T> {
@ -441,8 +434,7 @@ pub mod fast {
match self.dtor_state.get() {
DtorState::Unregistered => {
// dtor registration happens before initialization.
register_dtor(self as *const _ as *mut u8,
destroy_value::<T>);
register_dtor(self as *const _ as *mut u8, destroy_value::<T>);
self.dtor_state.set(DtorState::Registered);
true
}
@ -450,14 +442,12 @@ pub mod fast {
// recursively initialized
true
}
DtorState::RunningOrHasRun => {
false
}
DtorState::RunningOrHasRun => false,
}
}
}
unsafe extern fn destroy_value<T>(ptr: *mut u8) {
unsafe extern "C" fn destroy_value<T>(ptr: *mut u8) {
let ptr = ptr as *mut Key<T>;
// Right before we run the user destructor be sure to set the
@ -491,7 +481,7 @@ pub mod os {
}
}
unsafe impl<T> Sync for Key<T> { }
unsafe impl<T> Sync for Key<T> {}
struct Value<T: 'static> {
inner: LazyKeyInner<T>,
@ -500,10 +490,7 @@ pub mod os {
impl<T: 'static> Key<T> {
pub const fn new() -> Key<T> {
Key {
os: OsStaticKey::new(Some(destroy_value::<T>)),
marker: marker::PhantomData
}
Key { os: OsStaticKey::new(Some(destroy_value::<T>)), marker: marker::PhantomData }
}
pub unsafe fn get(&'static self, init: fn() -> T) -> Option<&'static T> {
@ -523,16 +510,13 @@ pub mod os {
let ptr = self.os.get() as *mut Value<T>;
if ptr as usize == 1 {
// destructor is running
return None
return None;
}
let ptr = if ptr.is_null() {
// If the lookup returned null, we haven't initialized our own
// local copy, so do that now.
let ptr: Box<Value<T>> = box Value {
inner: LazyKeyInner::new(),
key: self,
};
let ptr: Box<Value<T>> = box Value { inner: LazyKeyInner::new(), key: self };
let ptr = Box::into_raw(ptr);
self.os.set(ptr as *mut u8);
ptr
@ -545,7 +529,7 @@ pub mod os {
}
}
unsafe extern fn destroy_value<T: 'static>(ptr: *mut u8) {
unsafe extern "C" fn destroy_value<T: 'static>(ptr: *mut u8) {
// The OS TLS ensures that this key contains a NULL value when this
// destructor starts to run. We set it back to a sentinel value of 1 to
// ensure that any future calls to `get` for this thread will return
@ -563,8 +547,8 @@ pub mod os {
#[cfg(all(test, not(target_os = "emscripten")))]
mod tests {
use crate::sync::mpsc::{channel, Sender};
use crate::cell::{Cell, UnsafeCell};
use crate::sync::mpsc::{channel, Sender};
use crate::thread;
struct Foo(Sender<()>);
@ -585,7 +569,7 @@ mod tests {
f.set(2);
});
let (tx, rx) = channel();
let _t = thread::spawn(move|| {
let _t = thread::spawn(move || {
FOO.with(|f| {
assert_eq!(f.get(), 1);
});
@ -610,7 +594,10 @@ mod tests {
thread::spawn(|| {
assert!(FOO.try_with(|_| ()).is_ok());
}).join().ok().expect("thread panicked");
})
.join()
.ok()
.expect("thread panicked");
}
#[test]
@ -618,7 +605,7 @@ mod tests {
thread_local!(static FOO: UnsafeCell<Option<Foo>> = UnsafeCell::new(None));
let (tx, rx) = channel();
let _t = thread::spawn(move|| unsafe {
let _t = thread::spawn(move || unsafe {
let mut tx = Some(tx);
FOO.with(|f| {
*f.get() = Some(Foo(tx.take().unwrap()));
@ -662,9 +649,12 @@ mod tests {
}
}
thread::spawn(move|| {
thread::spawn(move || {
drop(S1);
}).join().ok().expect("thread panicked");
})
.join()
.ok()
.expect("thread panicked");
}
#[test]
@ -678,9 +668,12 @@ mod tests {
}
}
thread::spawn(move|| unsafe {
thread::spawn(move || unsafe {
K1.with(|s| *s.get() = Some(S1));
}).join().ok().expect("thread panicked");
})
.join()
.ok()
.expect("thread panicked");
}
// Note that this test will deadlock if TLS destructors aren't run (this
@ -701,7 +694,7 @@ mod tests {
}
let (tx, rx) = channel();
let _t = thread::spawn(move|| unsafe {
let _t = thread::spawn(move || unsafe {
let mut tx = Some(tx);
K1.with(|s| *s.get() = Some(S1(tx.take().unwrap())));
});
@ -716,7 +709,9 @@ mod dynamic_tests {
#[test]
fn smoke() {
fn square(i: i32) -> i32 { i * i }
fn square(i: i32) -> i32 {
i * i
}
thread_local!(static FOO: i32 = square(3));
FOO.with(|f| {