(index<- )        ./libstd/rt/io/mod.rs

   1  // Copyright 2013 The Rust Project Developers. See the COPYRIGHT
   2  // file at the top-level directory of this distribution and at
   3  // http://rust-lang.org/COPYRIGHT.
   4  //
   5  // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
   6  // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
   7  // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
   8  // option. This file may not be copied, modified, or distributed
   9  // except according to those terms.
  10  
  11  /*! Synchronous I/O
  12  
  13  This module defines the Rust interface for synchronous I/O.
  14  It models byte-oriented input and output with the Reader and Writer traits.
  15  Types that implement both `Reader` and `Writer` and called 'streams',
  16  and automatically implement trait `Stream`.
  17  Implementations are provided for common I/O streams like
  18  file, TCP, UDP, Unix domain sockets.
  19  Readers and Writers may be composed to add capabilities like string
  20  parsing, encoding, and compression.
  21  
  22  This will likely live in std::io, not std::rt::io.
  23  
  24  # Examples
  25  
  26  Some examples of obvious things you might want to do
  27  
  28  * Read lines from stdin
  29  
  30      for stdin().each_line |line| {
  31          println(line)
  32      }
  33  
  34  * Read a complete file to a string, (converting newlines?)
  35  
  36      let contents = File::open("message.txt").read_to_str(); // read_to_str??
  37  
  38  * Write a line to a file
  39  
  40      let file = File::open("message.txt", Create, Write);
  41      file.write_line("hello, file!");
  42  
  43  * Iterate over the lines of a file
  44  
  45      do File::open("message.txt").each_line |line| {
  46          println(line)
  47      }
  48  
  49  * Pull the lines of a file into a vector of strings
  50  
  51      let lines = File::open("message.txt").line_iter().to_vec();
  52  
  53  * Make an simple HTTP request
  54  
  55      let socket = TcpStream::open("localhost:8080");
  56      socket.write_line("GET / HTTP/1.0");
  57      socket.write_line("");
  58      let response = socket.read_to_end();
  59  
  60  * Connect based on URL? Requires thinking about where the URL type lives
  61    and how to make protocol handlers extensible, e.g. the "tcp" protocol
  62    yields a `TcpStream`.
  63  
  64      connect("tcp://localhost:8080");
  65  
  66  # Terms
  67  
  68  * Reader - An I/O source, reads bytes into a buffer
  69  * Writer - An I/O sink, writes bytes from a buffer
  70  * Stream - Typical I/O sources like files and sockets are both Readers and Writers,
  71    and are collectively referred to a `streams`.
  72  * Decorator - A Reader or Writer that composes with others to add additional capabilities
  73    such as encoding or decoding
  74  
  75  # Blocking and synchrony
  76  
  77  When discussing I/O you often hear the terms 'synchronous' and
  78  'asynchronous', along with 'blocking' and 'non-blocking' compared and
  79  contrasted. A synchronous I/O interface performs each I/O operation to
  80  completion before proceeding to the next. Synchronous interfaces are
  81  usually used in imperative style as a sequence of commands. An
  82  asynchronous interface allows multiple I/O requests to be issued
  83  simultaneously, without waiting for each to complete before proceeding
  84  to the next.
  85  
  86  Asynchronous interfaces are used to achieve 'non-blocking' I/O. In
  87  traditional single-threaded systems, performing a synchronous I/O
  88  operation means that the program stops all activity (it 'blocks')
  89  until the I/O is complete. Blocking is bad for performance when
  90  there are other computations that could be done.
  91  
  92  Asynchronous interfaces are most often associated with the callback
  93  (continuation-passing) style popularised by node.js. Such systems rely
  94  on all computations being run inside an event loop which maintains a
  95  list of all pending I/O events; when one completes the registered
  96  callback is run and the code that made the I/O request continues.
  97  Such interfaces achieve non-blocking at the expense of being more
  98  difficult to reason about.
  99  
 100  Rust's I/O interface is synchronous - easy to read - and non-blocking by default.
 101  
 102  Remember that Rust tasks are 'green threads', lightweight threads that
 103  are multiplexed onto a single operating system thread. If that system
 104  thread blocks then no other task may proceed. Rust tasks are
 105  relatively cheap to create, so as long as other tasks are free to
 106  execute then non-blocking code may be written by simply creating a new
 107  task.
 108  
 109  When discussing blocking in regards to Rust's I/O model, we are
 110  concerned with whether performing I/O blocks other Rust tasks from
 111  proceeding. In other words, when a task calls `read`, it must then
 112  wait (or 'sleep', or 'block') until the call to `read` is complete.
 113  During this time, other tasks may or may not be executed, depending on
 114  how `read` is implemented.
 115  
 116  
 117  Rust's default I/O implementation is non-blocking; by cooperating
 118  directly with the task scheduler it arranges to never block progress
 119  of *other* tasks. Under the hood, Rust uses asynchronous I/O via a
 120  per-scheduler (and hence per-thread) event loop. Synchronous I/O
 121  requests are implemented by descheduling the running task and
 122  performing an asynchronous request; the task is only resumed once the
 123  asynchronous request completes.
 124  
 125  For blocking (but possibly more efficient) implementations, look
 126  in the `io::native` module.
 127  
 128  # Error Handling
 129  
 130  I/O is an area where nearly every operation can result in unexpected
 131  errors. It should allow errors to be handled efficiently.
 132  It needs to be convenient to use I/O when you don't care
 133  about dealing with specific errors.
 134  
 135  Rust's I/O employs a combination of techniques to reduce boilerplate
 136  while still providing feedback about errors. The basic strategy:
 137  
 138  * Errors are fatal by default, resulting in task failure
 139  * Errors raise the `io_error` condition which provides an opportunity to inspect
 140    an IoError object containing details.
 141  * Return values must have a sensible null or zero value which is returned
 142    if a condition is handled successfully. This may be an `Option`, an empty
 143    vector, or other designated error value.
 144  * Common traits are implemented for `Option`, e.g. `impl<R: Reader> Reader for Option<R>`,
 145    so that nullable values do not have to be 'unwrapped' before use.
 146  
 147  These features combine in the API to allow for expressions like
 148  `File::new("diary.txt").write_line("met a girl")` without having to
 149  worry about whether "diary.txt" exists or whether the write
 150  succeeds. As written, if either `new` or `write_line` encounters
 151  an error the task will fail.
 152  
 153  If you wanted to handle the error though you might write
 154  
 155      let mut error = None;
 156      do io_error::cond(|e: IoError| {
 157          error = Some(e);
 158      }).in {
 159          File::new("diary.txt").write_line("met a girl");
 160      }
 161  
 162      if error.is_some() {
 163          println("failed to write my diary");
 164      }
 165  
 166  XXX: Need better condition handling syntax
 167  
 168  In this case the condition handler will have the opportunity to
 169  inspect the IoError raised by either the call to `new` or the call to
 170  `write_line`, but then execution will continue.
 171  
 172  So what actually happens if `new` encounters an error? To understand
 173  that it's important to know that what `new` returns is not a `File`
 174  but an `Option<File>`.  If the file does not open, and the condition
 175  is handled, then `new` will simply return `None`. Because there is an
 176  implementation of `Writer` (the trait required ultimately required for
 177  types to implement `write_line`) there is no need to inspect or unwrap
 178  the `Option<File>` and we simply call `write_line` on it.  If `new`
 179  returned a `None` then the followup call to `write_line` will also
 180  raise an error.
 181  
 182  ## Concerns about this strategy
 183  
 184  This structure will encourage a programming style that is prone
 185  to errors similar to null pointer dereferences.
 186  In particular code written to ignore errors and expect conditions to be unhandled
 187  will start passing around null or zero objects when wrapped in a condition handler.
 188  
 189  * XXX: How should we use condition handlers that return values?
 190  * XXX: Should EOF raise default conditions when EOF is not an error?
 191  
 192  # Issues with i/o scheduler affinity, work stealing, task pinning
 193  
 194  # Resource management
 195  
 196  * `close` vs. RAII
 197  
 198  # Paths, URLs and overloaded constructors
 199  
 200  
 201  
 202  # Scope
 203  
 204  In scope for core
 205  
 206  * Url?
 207  
 208  Some I/O things don't belong in core
 209  
 210    - url
 211    - net - `fn connect`
 212      - http
 213    - flate
 214  
 215  Out of scope
 216  
 217  * Async I/O. We'll probably want it eventually
 218  
 219  
 220  # XXX Questions and issues
 221  
 222  * Should default constructors take `Path` or `&str`? `Path` makes simple cases verbose.
 223    Overloading would be nice.
 224  * Add overloading for Path and &str and Url &str
 225  * stdin/err/out
 226  * print, println, etc.
 227  * fsync
 228  * relationship with filesystem querying, Directory, File types etc.
 229  * Rename Reader/Writer to ByteReader/Writer, make Reader/Writer generic?
 230  * Can Port and Chan be implementations of a generic Reader<T>/Writer<T>?
 231  * Trait for things that are both readers and writers, Stream?
 232  * How to handle newline conversion
 233  * String conversion
 234  * File vs. FileStream? File is shorter but could also be used for getting file info
 235    - maybe File is for general file querying and *also* has a static `open` method
 236  * open vs. connect for generic stream opening
 237  * Do we need `close` at all? dtors might be good enough
 238  * How does I/O relate to the Iterator trait?
 239  * std::base64 filters
 240  * Using conditions is a big unknown since we don't have much experience with them
 241  * Too many uses of OtherIoError
 242  
 243  */
 244  
 245  use prelude::*;
 246  use to_str::ToStr;
 247  use str::{StrSlice, OwnedStr};
 248  use path::Path;
 249  
 250  // Reexports
 251  pub use self::stdio::stdin;
 252  pub use self::stdio::stdout;
 253  pub use self::stdio::stderr;
 254  pub use self::stdio::print;
 255  pub use self::stdio::println;
 256  
 257  pub use self::file::FileStream;
 258  pub use self::timer::Timer;
 259  pub use self::net::ip::IpAddr;
 260  pub use self::net::tcp::TcpListener;
 261  pub use self::net::tcp::TcpStream;
 262  pub use self::net::udp::UdpStream;
 263  pub use self::pipe::PipeStream;
 264  pub use self::pipe::UnboundPipeStream;
 265  pub use self::process::Process;
 266  
 267  // Some extension traits that all Readers and Writers get.
 268  pub use self::extensions::ReaderUtil;
 269  pub use self::extensions::ReaderByteConversions;
 270  pub use self::extensions::WriterByteConversions;
 271  
 272  /// Synchronous, non-blocking file I/O.
 273  pub mod file;
 274  
 275  /// Synchronous, in-memory I/O.
 276  pub mod pipe;
 277  
 278  /// Child process management.
 279  pub mod process;
 280  
 281  /// Synchronous, non-blocking network I/O.
 282  pub mod net;
 283  
 284  /// Readers and Writers for memory buffers and strings.
 285  pub mod mem;
 286  
 287  /// Non-blocking access to stdin, stdout, stderr
 288  pub mod stdio;
 289  
 290  /// Implementations for Option
 291  mod option;
 292  
 293  /// Basic stream compression. XXX: Belongs with other flate code
 294  pub mod flate;
 295  
 296  /// Interop between byte streams and pipes. Not sure where it belongs
 297  pub mod comm_adapters;
 298  
 299  /// Extension traits
 300  pub mod extensions;
 301  
 302  /// Non-I/O things needed by the I/O module
 303  // XXX: shouldn this really be pub?
 304  pub mod support;
 305  
 306  /// Basic Timer
 307  pub mod timer;
 308  
 309  /// Buffered I/O wrappers
 310  pub mod buffered;
 311  
 312  /// Thread-blocking implementations
 313  pub mod native {
 314      /// Posix file I/O
 315      pub mod file;
 316      /// Process spawning and child management
 317      pub mod process;
 318      /// Posix stdio
 319      pub mod stdio;
 320  
 321      /// Sockets
 322      /// # XXX - implement this
 323      pub mod net {
 324          pub mod tcp { }
 325          pub mod udp { }
 326          #[cfg(unix)]
 327          pub mod unix { }
 328      }
 329  }
 330  
 331  /// Mock implementations for testing
 332  mod mock;
 333  
 334  /// The default buffer size for various I/O operations
 335  /// XXX: Not pub
 336  pub static DEFAULT_BUF_SIZE: uint = 1024 * 64;
 337  
 338  /// The type passed to I/O condition handlers to indicate error
 339  ///
 340  /// # XXX
 341  ///
 342  /// Is something like this sufficient? It's kind of archaic
 343  pub struct IoError {
 344      kind: IoErrorKind,
 345      desc: &'static str,
 346      detail: Option<~str>
 347  }
 348  
 349  // FIXME: #8242 implementing manually because deriving doesn't work for some reason
 350  impl ToStr for IoError {
 351      fn to_str(&self) -> ~str {
 352          let mut s = ~"IoError { kind: ";
 353          s.push_str(self.kind.to_str());
 354          s.push_str(", desc: ");
 355          s.push_str(self.desc);
 356          s.push_str(", detail: ");
 357          s.push_str(self.detail.to_str());
 358          s.push_str(}");
 359          s
 360      }
 361  }
 362  
 363  #[deriving(Eq)]
 364  pub enum IoErrorKind {
 365      PreviousIoError,
 366      OtherIoError,
 367      EndOfFile,
 368      FileNotFound,
 369      PermissionDenied,
 370      ConnectionFailed,
 371      Closed,
 372      ConnectionRefused,
 373      ConnectionReset,
 374      NotConnected,
 375      BrokenPipe,
 376      PathAlreadyExists,
 377      PathDoesntExist,
 378      MismatchedFileTypeForOperation
 379  }
 380  
 381  // FIXME: #8242 implementing manually because deriving doesn't work for some reason
 382  impl ToStr for IoErrorKind {
 383      fn to_str(&self) -> ~str {
 384          match *self {
 385              PreviousIoError => ~"PreviousIoError",
 386              OtherIoError => ~"OtherIoError",
 387              EndOfFile => ~"EndOfFile",
 388              FileNotFound => ~"FileNotFound",
 389              PermissionDenied => ~"PermissionDenied",
 390              ConnectionFailed => ~"ConnectionFailed",
 391              Closed => ~"Closed",
 392              ConnectionRefused => ~"ConnectionRefused",
 393              ConnectionReset => ~"ConnectionReset",
 394              NotConnected => ~"NotConnected",
 395              BrokenPipe => ~"BrokenPipe",
 396              PathAlreadyExists => ~"PathAlreadyExists",
 397              PathDoesntExist => ~"PathDoesntExist",
 398              MismatchedFileTypeForOperation => ~"MismatchedFileTypeForOperation"
 399          }
 400      }
 401  }
 402  
 403  // XXX: Can't put doc comments on macros
 404  // Raised by `I/O` operations on error.
 405  condition! {
 406      pub io_error: IoError -> ();
 407  }
 408  
 409  // XXX: Can't put doc comments on macros
 410  // Raised by `read` on error
 411  condition! {
 412      pub read_error: IoError -> ();
 413  }
 414  
 415  /// Helper for wrapper calls where you want to
 416  /// ignore any io_errors that might be raised
 417  pub fn ignore_io_error<T>(cb&fn() -> T) -> T {
 418      do io_error::cond.trap(|_| {
 419          // just swallow the error.. downstream users
 420          // who can make a decision based on a None result
 421          // won't care
 422      }).inside {
 423          cb()
 424      }
 425  }
 426  
 427  pub trait Reader {
 428      /// Read bytes, up to the length of `buf` and place them in `buf`.
 429      /// Returns the number of bytes read. The number of bytes read my
 430      /// be less than the number requested, even 0. Returns `None` on EOF.
 431      ///
 432      /// # Failure
 433      ///
 434      /// Raises the `read_error` condition on error. If the condition
 435      /// is handled then no guarantee is made about the number of bytes
 436      /// read and the contents of `buf`. If the condition is handled
 437      /// returns `None` (XXX see below).
 438      ///
 439      /// # XXX
 440      ///
 441      /// * Should raise_default error on eof?
 442      /// * If the condition is handled it should still return the bytes read,
 443      ///   in which case there's no need to return Option - but then you *have*
 444      ///   to install a handler to detect eof.
 445      ///
 446      /// This doesn't take a `len` argument like the old `read`.
 447      /// Will people often need to slice their vectors to call this
 448      /// and will that be annoying?
 449      /// Is it actually possible for 0 bytes to be read successfully?
 450      fn read(&mut self, buf: &mut [u8]) -> Option<uint>;
 451  
 452      /// Return whether the Reader has reached the end of the stream.
 453      ///
 454      /// # Example
 455      ///
 456      ///     let reader = FileStream::new()
 457      ///     while !reader.eof() {
 458      ///         println(reader.read_line());
 459      ///     }
 460      ///
 461      /// # Failure
 462      ///
 463      /// Returns `true` on failure.
 464      fn eof(&mut self) -> bool;
 465  }
 466  
 467  impl Reader for ~Reader {
 468      fn read(&mut self, buf&mut [u8]) -> Option<uint> { self.read(buf) }
 469      fn eof(&mut self) -> bool { self.eof() }
 470  }
 471  
 472  impl<'self> Reader for &'self mut Reader {
 473      fn read(&mut self, buf&mut [u8]) -> Option<uint> { self.read(buf) }
 474      fn eof(&mut self) -> bool { self.eof() }
 475  }
 476  
 477  pub trait Writer {
 478      /// Write the given buffer
 479      ///
 480      /// # Failure
 481      ///
 482      /// Raises the `io_error` condition on error
 483      fn write(&mut self, buf: &[u8]);
 484  
 485      /// Flush output
 486      fn flush(&mut self);
 487  }
 488  
 489  impl Writer for ~Writer {
 490      fn write(&mut self, buf&[u8]) { self.write(buf) }
 491      fn flush(&mut self) { self.flush() }
 492  }
 493  
 494  impl<'self> Writer for &'self mut Writer {
 495      fn write(&mut self, buf&[u8]) { self.write(buf) }
 496      fn flush(&mut self) { self.flush() }
 497  }
 498  
 499  pub trait Stream: Reader + Writer { }
 500  
 501  impl<T: Reader + Writer> Stream for T {}
 502  
 503  pub enum SeekStyle {
 504      /// Seek from the beginning of the stream
 505      SeekSet,
 506      /// Seek from the end of the stream
 507      SeekEnd,
 508      /// Seek from the current position
 509      SeekCur,
 510  }
 511  
 512  /// # XXX
 513  /// * Are `u64` and `i64` the right choices?
 514  pub trait Seek {
 515      /// Return position of file cursor in the stream
 516      fn tell(&self) -> u64;
 517  
 518      /// Seek to an offset in a stream
 519      ///
 520      /// A successful seek clears the EOF indicator.
 521      ///
 522      /// # XXX
 523      ///
 524      /// * What is the behavior when seeking past the end of a stream?
 525      fn seek(&mut self, pos: i64, style: SeekStyle);
 526  }
 527  
 528  /// A listener is a value that can consume itself to start listening for connections.
 529  /// Doing so produces some sort of Acceptor.
 530  pub trait Listener<T, A: Acceptor<T>> {
 531      /// Spin up the listener and start queueing incoming connections
 532      ///
 533      /// # Failure
 534      ///
 535      /// Raises `io_error` condition. If the condition is handled,
 536      /// then `listen` returns `None`.
 537      fn listen(self) -> Option<A>;
 538  }
 539  
 540  /// An acceptor is a value that presents incoming connections
 541  pub trait Acceptor<T> {
 542      /// Wait for and accept an incoming connection
 543      ///
 544      /// # Failure
 545      /// Raise `io_error` condition. If the condition is handled,
 546      /// then `accept` returns `None`.
 547      fn accept(&mut self) -> Option<T>;
 548  
 549      /// Create an iterator over incoming connection attempts
 550      fn incoming<'r>(&'r mut self) -> IncomingIterator<'r, Self> {
 551          IncomingIterator { inc: self }
 552      }
 553  }
 554  
 555  /// An infinite iterator over incoming connection attempts.
 556  /// Calling `next` will block the task until a connection is attempted.
 557  ///
 558  /// Since connection attempts can continue forever, this iterator always returns Some.
 559  /// The Some contains another Option representing whether the connection attempt was succesful.
 560  /// A successful connection will be wrapped in Some.
 561  /// A failed connection is represented as a None and raises a condition.
 562  struct IncomingIterator<'self, A> {
 563      priv inc: &'self mut A,
 564  }
 565  
 566  impl<'self, T, A: Acceptor<T>> Iterator<Option<T>> for IncomingIterator<'self, A> {
 567      fn next(&mut self) -> Option<Option<T>> {
 568          Some(self.inc.accept())
 569      }
 570  }
 571  
 572  /// Common trait for decorator types.
 573  ///
 574  /// Provides accessors to get the inner, 'decorated' values. The I/O library
 575  /// uses decorators to add functionality like compression and encryption to I/O
 576  /// streams.
 577  ///
 578  /// # XXX
 579  ///
 580  /// Is this worth having a trait for? May be overkill
 581  pub trait Decorator<T> {
 582      /// Destroy the decorator and extract the decorated value
 583      ///
 584      /// # XXX
 585      ///
 586      /// Because this takes `self' one could never 'undecorate' a Reader/Writer
 587      /// that has been boxed. Is that ok? This feature is mostly useful for
 588      /// extracting the buffer from MemWriter
 589      fn inner(self) -> T;
 590  
 591      /// Take an immutable reference to the decorated value
 592      fn inner_ref<'a>(&'a self) -> &'a T;
 593  
 594      /// Take a mutable reference to the decorated value
 595      fn inner_mut_ref<'a>(&'a mut self) -> &'a mut T;
 596  }
 597  
 598  pub fn standard_error(kindIoErrorKind) -> IoError {
 599      match kind {
 600          PreviousIoError => {
 601              IoError {
 602                  kind: PreviousIoError,
 603                  desc: "Failing due to a previous I/O error",
 604                  detail: None
 605              }
 606          }
 607          EndOfFile => {
 608              IoError {
 609                  kind: EndOfFile,
 610                  desc: "End of file",
 611                  detail: None
 612              }
 613          }
 614          _ => fail2!()
 615      }
 616  }
 617  
 618  pub fn placeholder_error() -> IoError {
 619      IoError {
 620          kind: OtherIoError,
 621          desc: "Placeholder error. You shouldn't be seeing this",
 622          detail: None
 623      }
 624  }
 625  
 626  /// Instructions on how to open a file and return a `FileStream`.
 627  pub enum FileMode {
 628      /// Opens an existing file. IoError if file does not exist.
 629      Open,
 630      /// Creates a file. IoError if file exists.
 631      Create,
 632      /// Opens an existing file or creates a new one.
 633      OpenOrCreate,
 634      /// Opens an existing file or creates a new one, positioned at EOF.
 635      Append,
 636      /// Opens an existing file, truncating it to 0 bytes.
 637      Truncate,
 638      /// Opens an existing file or creates a new one, truncating it to 0 bytes.
 639      CreateOrTruncate,
 640  }
 641  
 642  /// Access permissions with which the file should be opened.
 643  /// `FileStream`s opened with `Read` will raise an `io_error` condition if written to.
 644  pub enum FileAccess {
 645      Read,
 646      Write,
 647      ReadWrite
 648  }
 649  
 650  pub struct FileStat {
 651      /// A `Path` object containing information about the `PathInfo`'s location
 652      path: Path,
 653      /// `true` if the file pointed at by the `PathInfo` is a regular file
 654      is_file: bool,
 655      /// `true` if the file pointed at by the `PathInfo` is a directory
 656      is_dir: bool,
 657      /// The file pointed at by the `PathInfo`'s size in bytes
 658      size: u64,
 659      /// The file pointed at by the `PathInfo`'s creation time
 660      created: u64,
 661      /// The file pointed at by the `PathInfo`'s last-modification time in
 662      /// platform-dependent msecs
 663      modified: u64,
 664      /// The file pointed at by the `PathInfo`'s last-accessd time (e.g. read) in
 665      /// platform-dependent msecs
 666      accessed: u64,
 667  }

libstd/rt/io/mod.rs:363:16-363:16 -enum- definition:
#[deriving(Eq)]
pub enum IoErrorKind {
references:-
598: pub fn standard_error(kind: IoErrorKind) -> IoError {
382: impl ToStr for IoErrorKind {
363: #[deriving(Eq)]
344:     kind: IoErrorKind,
363: #[deriving(Eq)]
363: #[deriving(Eq)]


libstd/rt/io/mod.rs:502:1-502:1 -enum- definition:

pub enum SeekStyle {
references:-
525:     fn seek(&mut self, pos: i64, style: SeekStyle);
libstd/rt/io/file.rs:
347:     fn seek(&mut self, pos: i64, style: SeekStyle) {
320:     fn seek(&mut self, pos: i64, style: SeekStyle) {
429:     fn seek(&mut self, pos: i64, style: SeekStyle) {
libstd/rt/io/mem.rs:
196:     fn seek(&mut self, _pos: i64, _style: SeekStyle) { fail2!() }
105:     fn seek(&mut self, _pos: i64, _style: SeekStyle) { fail2!() }
43:     fn seek(&mut self, _pos: i64, _style: SeekStyle) { fail2!() }
154:     fn seek(&mut self, _pos: i64, _style: SeekStyle) { fail2!() }
libstd/rt/io/native/file.rs:
198:     fn seek(&mut self, pos: i64, style: SeekStyle) {
libstd/rt/rtio.rs:
142:     fn seek(&mut self, pos: i64, whence: SeekStyle) -> Result<u64, IoError>;
libstd/rt/uv/uvio.rs:
1512:     fn seek(&mut self, pos: i64, whence: SeekStyle) -> Result<u64, IoError> {


libstd/rt/io/mod.rs:649:1-649:1 -struct- definition:

pub struct FileStat {
references:-
libstd/rt/io/file.rs:
456:     fn stat(&self) -> Option<FileStat> {
241: pub fn stat<P: PathLike>(path: &P) -> Option<FileStat> {
libstd/rt/rtio.rs:
82:     fn fs_stat<P: PathLike>(&mut self, path: &P) -> Result<FileStat, IoError>;
libstd/rt/uv/uvio.rs:
616:     fn fs_stat<P: PathLike>(&mut self, path: &P) -> Result<FileStat, IoError> {
619:         let result_cell_ptr: *Cell<Result<FileStat,
634:                             Ok(FileStat {


libstd/rt/io/mod.rs:342:60-342:60 -struct- definition:
/// Is something like this sufficient? It's kind of archaic
pub struct IoError {
references:-
412:     pub read_error: IoError -> ();
618: pub fn placeholder_error() -> IoError {
406:     pub io_error: IoError -> ();
406:     pub io_error: IoError -> ();
350: impl ToStr for IoError {
619:     IoError {
598: pub fn standard_error(kind: IoErrorKind) -> IoError {
601:             IoError {
412:     pub read_error: IoError -> ();
608:             IoError {
libstd/rt/io/file.rs:
631:                 io_error::cond.raise(IoError {
660:                         let ioerr = IoError {
673:                 io_error::cond.raise(IoError {
libstd/rt/io/option.rs:
23: fn prev_io_error() -> IoError {
libstd/rt/io/native/file.rs:
27:     io_error::cond.raise(IoError {
libstd/rt/io/native/process.rs:
228:         unsafe fn killpid(pid: pid_t, signal: int) -> Result<(), io::IoError> {
195:     pub fn signal(&mut self, signum: int) -> Result<(), io::IoError> {
200:             Some(*) => return Err(io::IoError {
libstd/rt/rtio.rs:
82:     fn fs_stat<P: PathLike>(&mut self, path: &P) -> Result<FileStat, IoError>;
99:     fn dont_accept_simultaneously(&mut self) -> Result<(), IoError>;
154:     fn read(&mut self, buf: &mut [u8]) -> Result<uint, IoError>;
80:     fn fs_unlink<P: PathLike>(&mut self, path: &P) -> Result<(), IoError>;
76:     fn timer_init(&mut self) -> Result<~RtioTimerObject, IoError>;
106:     fn control_congestion(&mut self) -> Result<(), IoError>;
84:     fn fs_rmdir<P: PathLike>(&mut self, path: &P) -> Result<(), IoError>;
141:     fn pwrite(&mut self, buf: &[u8], offset: u64) -> Result<(), IoError>;
149:     fn kill(&mut self, signal: int) -> Result<(), IoError>;
103:     fn read(&mut self, buf: &mut [u8]) -> Result<uint, IoError>;
127:     fn time_to_live(&mut self, ttl: int) -> Result<(), IoError>;
138:     fn read(&mut self, buf: &mut [u8]) -> Result<int, IoError>;
(97)(98)(108)(130)(89)(87)(140)(74)(93)(121)(86)(105)(143)(79)(109)(126)(81)(123)(117)(124)(120)(83)(107)(142)(155)(73)(139)(129)(104)(75)(113)(118)(144)
libstd/rt/uv/mod.rs:
(279)(253)
libstd/rt/uv/uvio.rs:
(1128)(555)(1527)(750)(1506)(895)(658)(889)(616)(1420)(519)(449)(867)(1092)(1442)(744)(453)(1166)(1503)(833)(1521)(688)(1422)(1114)(1323)..44more..


libstd/rt/io/mod.rs:540:62-540:62 -trait- definition:
/// An acceptor is a value that presents incoming connections
pub trait Acceptor<T> {
references:-
566: impl<'self, T, A: Acceptor<T>> Iterator<Option<T>> for IncomingIterator<'self, A> {
550:     fn incoming<'r>(&'r mut self) -> IncomingIterator<'r, Self> {
530: pub trait Listener<T, A: Acceptor<T>> {
libstd/rt/io/net/tcp.rs:
148: impl Acceptor<TcpStream> for TcpAcceptor {
libstd/rt/io/net/unix.rs:
49: impl Acceptor<UnixStream> for UnixAcceptor {
libstd/rt/io/option.rs:
65: impl<T, A: Acceptor<T>, L: Listener<T, A>> Listener<T, A> for Option<L> {
77: impl<T, A: Acceptor<T>> Acceptor<T> for Option<A> {
77: impl<T, A: Acceptor<T>> Acceptor<T> for Option<A> {


libstd/rt/io/mod.rs:476:1-476:1 -trait- definition:

pub trait Writer {
references:-
499: pub trait Stream: Reader + Writer { }
489: impl Writer for ~Writer {
494: impl<'self> Writer for &'self mut Writer {
494: impl<'self> Writer for &'self mut Writer {
489: impl Writer for ~Writer {
501: impl<T: Reader + Writer> Stream for T {}
libstd/rt/io/file.rs:
331: impl Writer for FileWriter {
396: impl Writer for FileStream {
libstd/rt/io/pipe.rs:
70: impl Writer for PipeStream {
libstd/rt/io/net/tcp.rs:
90: impl Writer for TcpStream {
libstd/rt/io/net/udp.rs:
100: impl Writer for UdpStream {
libstd/rt/io/net/unix.rs:
29: impl Writer for UnixStream {
libstd/rt/io/mem.rs:
145: impl<'self> Writer for BufWriter<'self> {
32: impl Writer for MemWriter {
libstd/rt/io/stdio.rs:
95: impl Writer for StdWriter {
libstd/rt/io/option.rs:
27: impl<W: Writer> Writer for Option<W> {
27: impl<W: Writer> Writer for Option<W> {
libstd/rt/io/flate.rs:
31: impl<W: Writer> Writer for DeflateWriter<W> {
23: impl<W: Writer> DeflateWriter<W> {
37: impl<W: Writer> Decorator<W> for DeflateWriter<W> {
31: impl<W: Writer> Writer for DeflateWriter<W> {
libstd/rt/io/comm_adapters.rs:
53: impl<W: Writer> WriterChan<W> {
57: impl<W: Writer> GenericChan<~[u8]> for WriterChan<W> {
33: impl<C: GenericChan<~[u8]>> Writer for ChanWriter<C> {
libstd/rt/io/extensions.rs:
526: impl<T: Writer> WriterByteConversions for T {
libstd/rt/io/buffered.rs:
223: impl<W: Writer> Decorator<W> for BufferedWriter<W> {
199: impl<W: Writer> Writer for BufferedWriter<W> {
183: impl<W: Writer> BufferedWriter<W> {
199: impl<W: Writer> Writer for BufferedWriter<W> {
282: impl<S: Stream> Writer for BufferedStream<S> {
libstd/rt/io/native/file.rs:
(165)(103)
libstd/rt/io/native/process.rs:
(126)(165)(124)(164)
libstd/rt/io/native/stdio.rs:
(64)
libstd/rt/io/mock.rs:
(47)
libstd/rt/util.rs:
(76)
libstd/hash.rs:
(260)
libstd/run.rs:
(140)
libstd/sys.rs:
(99)
libstd/fmt/mod.rs:
(578)(547)(553)(447)(639)
libstd/repr.rs:
(55)(63)(609)(42)(108)(63)(63)(48)(63)(38)(63)(63)(82)(82)(63)(63)(63)(104)

libstd/rt/io/mod.rs:626:66-626:66 -enum- definition:
/// Instructions on how to open a file and return a `FileStream`.
pub enum FileMode {
references:-
libstd/rt/io/file.rs:
91:                          mode: FileMode,
537:     fn open_reader(&self, mode: FileMode) -> Option<FileReader> {
523:     fn open_stream(&self, mode: FileMode, access: FileAccess) -> Option<FileStream> {
548:     fn open_writer(&self, mode: FileMode) -> Option<FileWriter> {
libstd/rt/rtio.rs:
78:     fn fs_open<P: PathLike>(&mut self, path: &P, fm: FileMode, fa: FileAccess)
libstd/rt/uv/uvio.rs:
554:     fn fs_open<P: PathLike>(&mut self, path: &P, fm: FileMode, fa: FileAccess)


libstd/rt/io/mod.rs:416:46-416:46 -fn- definition:
/// ignore any io_errors that might be raised
pub fn ignore_io_error<T>(cb: &fn() -> T) -> T {
references:-
libstd/rt/io/file.rs:
654:         match ignore_io_error(|| self.stat()) {
612:         match ignore_io_error(|| self.stat()) {
513:         match ignore_io_error(|| self.stat()) {
628:         match ignore_io_error(|| self.stat()) {
466:         match ignore_io_error(|| self.stat()) {
524:         match ignore_io_error(|| self.stat()) {


libstd/rt/io/mod.rs:426:1-426:1 -trait- definition:

pub trait Reader {
references:-
467: impl Reader for ~Reader {
501: impl<T: Reader + Writer> Stream for T {}
467: impl Reader for ~Reader {
472: impl<'self> Reader for &'self mut Reader {
472: impl<'self> Reader for &'self mut Reader {
499: pub trait Stream: Reader + Writer { }
libstd/rt/io/file.rs:
304: impl Reader for FileReader {
370: impl Reader for FileStream {
libstd/rt/io/pipe.rs:
53: impl Reader for PipeStream {
libstd/rt/io/net/tcp.rs:
73: impl Reader for TcpStream {
libstd/rt/io/net/udp.rs:
85: impl Reader for UdpStream {
libstd/rt/io/net/unix.rs:
23: impl Reader for UnixStream {
libstd/rt/io/mem.rs:
173: impl<'self> Reader for BufReader<'self> {
82: impl Reader for MemReader {
libstd/rt/io/stdio.rs:
76: impl Reader for StdReader {
libstd/rt/io/option.rs:
43: impl<R: Reader> Reader for Option<R> {
43: impl<R: Reader> Reader for Option<R> {
libstd/rt/io/flate.rs:
70: impl<R: Reader> Reader for InflateReader<R> {
70: impl<R: Reader> Reader for InflateReader<R> {
76: impl<R: Reader> Decorator<R> for InflateReader<R> {
62: impl<R: Reader> InflateReader<R> {
libstd/rt/io/comm_adapters.rs:
41: impl<R: Reader> ReaderPort<R> {
21: impl<P: GenericPort<~[u8]>> Reader for PortReader<P> {
45: impl<R: Reader> GenericPort<~[u8]> for ReaderPort<R> {
libstd/rt/io/extensions.rs:
380: impl<'self, R: Reader> Iterator<u8> for ByteIterator<R> {
286: impl<T: Reader> ReaderUtil for T {
387: impl<T: Reader> ReaderByteConversions for T {
libstd/rt/io/buffered.rs:
140: impl<R: Reader> Reader for BufferedReader<R> {
239: impl<W: Reader> Reader for InternalBufferedWriter<W> {
272: impl<S: Stream> Reader for BufferedStream<S> {
(73)(140)(160)(239)
libstd/rt/io/native/file.rs:
(80)(140)
libstd/rt/io/native/process.rs:
(152)(138)(183)(140)(154)(182)(174)(173)
libstd/rt/io/native/stdio.rs:
(46)
libstd/rt/io/mock.rs:
(28)
libstd/rand/reader.rs:
(48)(39)
libstd/run.rs:
(156)(148)(194)

libstd/rt/io/mod.rs:529:45-529:45 -trait- definition:
/// Doing so produces some sort of Acceptor.
pub trait Listener<T, A: Acceptor<T>> {
references:-
libstd/rt/io/net/tcp.rs:
132: impl Listener<TcpStream, TcpAcceptor> for TcpListener {
libstd/rt/io/net/unix.rs:
43: impl Listener<UnixStream, UnixAcceptor> for UnixListener {
libstd/rt/io/option.rs:
65: impl<T, A: Acceptor<T>, L: Listener<T, A>> Listener<T, A> for Option<L> {
65: impl<T, A: Acceptor<T>, L: Listener<T, A>> Listener<T, A> for Option<L> {


libstd/rt/io/mod.rs:513:45-513:45 -trait- definition:
/// * Are `u64` and `i64` the right choices?
pub trait Seek {
references:-
libstd/rt/io/file.rs:
342: impl Seek for FileWriter {
315: impl Seek for FileReader {
417: impl Seek for FileStream {
libstd/rt/io/mem.rs:
40: impl Seek for MemWriter {
193: impl<'self> Seek for BufReader<'self> {
151: impl<'self> Seek for BufWriter<'self> {
102: impl Seek for MemReader {
libstd/rt/io/native/file.rs:
187: impl Seek for CFile {


libstd/rt/io/mod.rs:580:54-580:54 -trait- definition:
/// Is this worth having a trait for? May be overkill
pub trait Decorator<T> {
references:-
libstd/rt/io/mem.rs:
46: impl Decorator<~[u8]> for MemWriter {
108: impl Decorator<~[u8]> for MemReader {
libstd/rt/io/flate.rs:
37: impl<W: Writer> Decorator<W> for DeflateWriter<W> {
76: impl<R: Reader> Decorator<R> for InflateReader<R> {
libstd/rt/io/extensions.rs:
374: impl<R> Decorator<R> for ByteIterator<R> {
libstd/rt/io/buffered.rs:
160: impl<R: Reader> Decorator<R> for BufferedReader<R> {
292: impl<S: Stream> Decorator<S> for BufferedStream<S> {
223: impl<W: Writer> Decorator<W> for BufferedWriter<W> {


libstd/rt/io/mod.rs:643:87-643:87 -enum- definition:
/// `FileStream`s opened with `Read` will raise an `io_error` condition if written to.
pub enum FileAccess {
references:-
libstd/rt/io/file.rs:
523:     fn open_stream(&self, mode: FileMode, access: FileAccess) -> Option<FileStream> {
92:                          access: FileAccess
libstd/rt/rtio.rs:
78:     fn fs_open<P: PathLike>(&mut self, path: &P, fm: FileMode, fa: FileAccess)
libstd/rt/uv/uvio.rs:
554:     fn fs_open<P: PathLike>(&mut self, path: &P, fm: FileMode, fa: FileAccess)


libstd/rt/io/mod.rs:561:73-561:73 -struct- definition:
/// A failed connection is represented as a None and raises a condition.
struct IncomingIterator<'self, A> {
references:-
551:         IncomingIterator { inc: self }
566: impl<'self, T, A: Acceptor<T>> Iterator<Option<T>> for IncomingIterator<'self, A> {
550:     fn incoming<'r>(&'r mut self) -> IncomingIterator<'r, Self> {


libstd/rt/io/mod.rs:597:1-597:1 -fn- definition:

pub fn standard_error(kind: IoErrorKind) -> IoError {
references:-
libstd/rt/io/option.rs:
24:     standard_error(PreviousIoError)
libstd/rt/io/extensions.rs:
317:                             read_error::cond.raise(standard_error(EndOfFile));
libstd/rt/uv/uvio.rs:
848:                         Some(_) => Err(standard_error(OtherIoError)),


libstd/rt/io/mod.rs:498:1-498:1 -trait- definition:

pub trait Stream: Reader + Writer { }
references:-
501: impl<T: Reader + Writer> Stream for T {}
libstd/rt/io/buffered.rs:
272: impl<S: Stream> Reader for BufferedStream<S> {
256: impl<S: Stream> BufferedStream<S> {
282: impl<S: Stream> Writer for BufferedStream<S> {
292: impl<S: Stream> Decorator<S> for BufferedStream<S> {