about summary refs log tree commit diff
path: root/src/libstd/io/stdio.rs
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2015-03-13 20:22:16 +0000
committerbors <bors@rust-lang.org>2015-03-13 20:22:16 +0000
commit3e4be02b80a3dd27bce20870958fe0aef7e7336d (patch)
tree156b54e84eeb1df2818be29b53ab7f35b5bc80f0 /src/libstd/io/stdio.rs
parent9eb69abad8ffbce840e7dc7038ddea434dc987f1 (diff)
parent981bf5f690d1d7c5cf3e1419ac7a7c86dbc7a4d5 (diff)
downloadrust-3e4be02b80a3dd27bce20870958fe0aef7e7336d.tar.gz
rust-3e4be02b80a3dd27bce20870958fe0aef7e7336d.zip
Auto merge of #23292 - alexcrichton:stabilize-io, r=aturon
The new `std::io` module has had some time to bake now, and this commit
stabilizes its functionality. There are still portions of the module which
remain unstable, and below contains a summart of the actions taken.

This commit also deprecates the entire contents of the `old_io` module in a
blanket fashion. All APIs should now have a reasonable replacement in the
new I/O modules.

Stable APIs:

* `std::io` (the name)
* `std::io::prelude` (the name)
* `Read`
* `Read::read`
* `Read::{read_to_end, read_to_string}` after being modified to return a `usize`
  for the number of bytes read.
* `ReadExt`
* `Write`
* `Write::write`
* `Write::{write_all, write_fmt}`
* `WriteExt`
* `BufRead`
* `BufRead::{fill_buf, consume}`
* `BufRead::{read_line, read_until}` after being modified to return a `usize`
  for the number of bytes read.
* `BufReadExt`
* `BufReader`
* `BufReader::{new, with_capacity}`
* `BufReader::{get_ref, get_mut, into_inner}`
* `{Read,BufRead} for BufReader`
* `BufWriter`
* `BufWriter::{new, with_capacity}`
* `BufWriter::{get_ref, get_mut, into_inner}`
* `Write for BufWriter`
* `IntoInnerError`
* `IntoInnerError::{error, into_inner}`
* `{Error,Display} for IntoInnerError`
* `LineWriter`
* `LineWriter::{new, with_capacity}` - `with_capacity` was added
* `LineWriter::{get_ref, get_mut, into_inner}` - `get_mut` was added)
* `Write for LineWriter`
* `BufStream`
* `BufStream::{new, with_capacities}`
* `BufStream::{get_ref, get_mut, into_inner}`
* `{BufRead,Read,Write} for BufStream`
* `stdin`
* `Stdin`
* `Stdin::lock`
* `Stdin::read_line` - added method
* `StdinLock`
* `Read for Stdin`
* `{Read,BufRead} for StdinLock`
* `stdout`
* `Stdout`
* `Stdout::lock`
* `StdoutLock`
* `Write for Stdout`
* `Write for StdoutLock`
* `stderr`
* `Stderr`
* `Stderr::lock`
* `StderrLock`
* `Write for Stderr`
* `Write for StderrLock`
* `io::Result`
* `io::Error`
* `io::Error::last_os_error`
* `{Display, Error} for Error`

Unstable APIs:

(reasons can be found in the commit itself)

* `Write::flush`
* `Seek`
* `ErrorKind`
* `Error::new`
* `Error::from_os_error`
* `Error::kind`

Deprecated APIs

* `Error::description` - available via the `Error` trait
* `Error::detail` - available via the `Display` implementation
* `thread::Builder::{stdout, stderr}`

Changes in functionality:

* `old_io::stdio::set_stderr` is now a noop as the infrastructure for printing
  backtraces has migrated to `std::io`.

[breaking-change]
Diffstat (limited to 'src/libstd/io/stdio.rs')
-rw-r--r--src/libstd/io/stdio.rs57
1 files changed, 53 insertions, 4 deletions
diff --git a/src/libstd/io/stdio.rs b/src/libstd/io/stdio.rs
index 4027f741654..3b4e396953d 100644
--- a/src/libstd/io/stdio.rs
+++ b/src/libstd/io/stdio.rs
@@ -86,6 +86,7 @@ impl Write for StderrRaw {
 ///
 /// This handle implements the `Read` trait, but beware that concurrent reads
 /// of `Stdin` must be executed with care.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Stdin {
     inner: Arc<Mutex<BufReader<StdinRaw>>>,
 }
@@ -94,6 +95,7 @@ pub struct Stdin {
 ///
 /// This handle implements both the `Read` and `BufRead` traits and is
 /// constructed via the `lock` method on `Stdin`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct StdinLock<'a> {
     inner: MutexGuard<'a, BufReader<StdinRaw>>,
 }
@@ -110,6 +112,7 @@ pub struct StdinLock<'a> {
 ///
 /// To avoid locking and buffering altogether, it is recommended to use the
 /// `stdin_raw` constructor.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn stdin() -> Stdin {
     static INSTANCE: Lazy<Mutex<BufReader<StdinRaw>>> = lazy_init!(stdin_init);
     return Stdin {
@@ -136,30 +139,41 @@ impl Stdin {
     /// The lock is released when the returned lock goes out of scope. The
     /// returned guard also implements the `Read` and `BufRead` traits for
     /// accessing the underlying data.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn lock(&self) -> StdinLock {
         StdinLock { inner: self.inner.lock().unwrap() }
     }
+
+    /// Locks this handle and reads a line of input into the specified buffer.
+    ///
+    /// For detailed semantics of this method, see the documentation on
+    /// `BufRead::read_line`.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    pub fn read_line(&mut self, buf: &mut String) -> io::Result<usize> {
+        self.lock().read_line(buf)
+    }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Read for Stdin {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.lock().read(buf)
     }
-
-    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<()> {
+    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<usize> {
         self.lock().read_to_end(buf)
     }
-
-    fn read_to_string(&mut self, buf: &mut String) -> io::Result<()> {
+    fn read_to_string(&mut self, buf: &mut String) -> io::Result<usize> {
         self.lock().read_to_string(buf)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Read for StdinLock<'a> {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.inner.read(buf)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> BufRead for StdinLock<'a> {
     fn fill_buf(&mut self) -> io::Result<&[u8]> { self.inner.fill_buf() }
     fn consume(&mut self, n: usize) { self.inner.consume(n) }
@@ -186,6 +200,7 @@ const OUT_MAX: usize = ::usize::MAX;
 /// Each handle shares a global buffer of data to be written to the standard
 /// output stream. Access is also synchronized via a lock and explicit control
 /// over locking is available via the `lock` method.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Stdout {
     // FIXME: this should be LineWriter or BufWriter depending on the state of
     //        stdout (tty or not). Note that if this is not line buffered it
@@ -197,6 +212,7 @@ pub struct Stdout {
 ///
 /// This handle implements the `Write` trait and is constructed via the `lock`
 /// method on `Stdout`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct StdoutLock<'a> {
     inner: MutexGuard<'a, LineWriter<StdoutRaw>>,
 }
@@ -211,6 +227,7 @@ pub struct StdoutLock<'a> {
 ///
 /// To avoid locking and buffering altogether, it is recommended to use the
 /// `stdout_raw` constructor.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn stdout() -> Stdout {
     static INSTANCE: Lazy<Mutex<LineWriter<StdoutRaw>>> = lazy_init!(stdout_init);
     return Stdout {
@@ -228,11 +245,13 @@ impl Stdout {
     ///
     /// The lock is released when the returned lock goes out of scope. The
     /// returned guard also implements the `Write` trait for writing data.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn lock(&self) -> StdoutLock {
         StdoutLock { inner: self.inner.lock().unwrap() }
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for Stdout {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.lock().write(buf)
@@ -247,6 +266,7 @@ impl Write for Stdout {
         self.lock().write_fmt(fmt)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Write for StdoutLock<'a> {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.inner.write(&buf[..cmp::min(buf.len(), OUT_MAX)])
@@ -257,6 +277,7 @@ impl<'a> Write for StdoutLock<'a> {
 /// A handle to the standard error stream of a process.
 ///
 /// For more information, see `stderr`
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Stderr {
     inner: Arc<Mutex<StderrRaw>>,
 }
@@ -265,6 +286,7 @@ pub struct Stderr {
 ///
 /// This handle implements the `Write` trait and is constructed via the `lock`
 /// method on `Stderr`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct StderrLock<'a> {
     inner: MutexGuard<'a, StderrRaw>,
 }
@@ -278,6 +300,7 @@ pub struct StderrLock<'a> {
 ///
 /// To avoid locking altogether, it is recommended to use the `stderr_raw`
 /// constructor.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn stderr() -> Stderr {
     static INSTANCE: Lazy<Mutex<StderrRaw>> = lazy_init!(stderr_init);
     return Stderr {
@@ -295,11 +318,13 @@ impl Stderr {
     ///
     /// The lock is released when the returned lock goes out of scope. The
     /// returned guard also implements the `Write` trait for writing data.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn lock(&self) -> StderrLock {
         StderrLock { inner: self.inner.lock().unwrap() }
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for Stderr {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.lock().write(buf)
@@ -314,9 +339,33 @@ impl Write for Stderr {
         self.lock().write_fmt(fmt)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Write for StderrLock<'a> {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.inner.write(&buf[..cmp::min(buf.len(), OUT_MAX)])
     }
     fn flush(&mut self) -> io::Result<()> { self.inner.flush() }
 }
+
+/// Resets the task-local stdout handle to the specified writer
+///
+/// This will replace the current task's stdout handle, returning the old
+/// handle. All future calls to `print` and friends will emit their output to
+/// this specified handle.
+///
+/// Note that this does not need to be called for all new tasks; the default
+/// output handle is to the process's stdout stream.
+#[unstable(feature = "set_panic",
+           reason = "this function may disappear completely or be replaced \
+                     with a more general mechanism")]
+#[doc(hidden)]
+pub fn set_panic(sink: Box<Write + Send>) -> Option<Box<Write + Send>> {
+    use panicking::LOCAL_STDERR;
+    use mem;
+    LOCAL_STDERR.with(move |slot| {
+        mem::replace(&mut *slot.borrow_mut(), Some(sink))
+    }).and_then(|mut s| {
+        let _ = s.flush();
+        Some(s)
+    })
+}