(index<- )        ./librustuv/file.rs

    git branch:    * master           5200215 auto merge of #14035 : alexcrichton/rust/experimental, r=huonw
    modified:    Fri May  9 13:02:28 2014
   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  use std::c_str::CString;
  12  use std::c_str;
  13  use std::cast::transmute;
  14  use std::cast;
  15  use libc::{c_int, c_char, c_void, ssize_t};
  16  use libc;
  17  use std::rt::task::BlockedTask;
  18  use std::io::{FileStat, IoError};
  19  use std::io;
  20  use std::rt::rtio;
  21  
  22  use homing::{HomingIO, HomeHandle};
  23  use super::{Loop, UvError, uv_error_to_io_error, wait_until_woken_after, wakeup};
  24  use uvio::UvIoFactory;
  25  use uvll;
  26  
  27  pub struct FsRequest {
  28      req: *uvll::uv_fs_t,
  29      fired: bool,
  30  }
  31  
  32  pub struct FileWatcher {
  33      loop_: Loop,
  34      fd: c_int,
  35      close: rtio::CloseBehavior,
  36      home: HomeHandle,
  37  }
  38  
  39  impl FsRequest {
  40      pub fn open(io&mut UvIoFactory, path&CString, flagsint, modeint)
  41          -> Result<FileWatcher, UvError>
  42      {
  43          execute(|req, cb| unsafe {
  44              uvll::uv_fs_open(io.uv_loop(),
  45                               req, path.with_ref(|p| p), flags as c_int,
  46                               mode as c_int, cb)
  47          }).map(|req|
  48              FileWatcher::new(io, req.get_result() as c_int,
  49                               rtio::CloseSynchronously)
  50          )
  51      }
  52  
  53      pub fn unlink(loop_&Loop, path&CString) -> Result<(), UvError> {
  54          execute_nop(|req, cb| unsafe {
  55              uvll::uv_fs_unlink(loop_.handle, req, path.with_ref(|p| p),
  56                                 cb)
  57          })
  58      }
  59  
  60      pub fn lstat(loop_&Loop, path&CString) -> Result<FileStat, UvError> {
  61          execute(|req, cb| unsafe {
  62              uvll::uv_fs_lstat(loop_.handle, req, path.with_ref(|p| p),
  63                                cb)
  64          }).map(|req| req.mkstat())
  65      }
  66  
  67      pub fn stat(loop_&Loop, path&CString) -> Result<FileStat, UvError> {
  68          execute(|req, cb| unsafe {
  69              uvll::uv_fs_stat(loop_.handle, req, path.with_ref(|p| p),
  70                               cb)
  71          }).map(|req| req.mkstat())
  72      }
  73  
  74      pub fn write(loop_&Loop, fdc_int, buf&[u8], offseti64)
  75          -> Result<(), UvError>
  76      {
  77          // In libuv, uv_fs_write is basically just shelling out to a write()
  78          // syscall at some point, with very little fluff around it. This means
  79          // that write() could actually be a short write, so we need to be sure
  80          // to call it continuously if we get a short write back. This method is
  81          // expected to write the full data if it returns success.
  82          let mut written = 0;
  83          while written < buf.len() {
  84              let offset = if offset == -1 {
  85                  offset
  86              } else {
  87                  offset + written as i64
  88              };
  89              let uvbuf = uvll::uv_buf_t {
  90                  base: buf.slice_from(written as uint).as_ptr(),
  91                  len: (buf.len() - written) as uvll::uv_buf_len_t,
  92              };
  93              match execute(|req, cb| unsafe {
  94                  uvll::uv_fs_write(loop_.handle, req, fd, &uvbuf, 1, offset, cb)
  95              }).map(|req| req.get_result()) {
  96                  Err(e) => return Err(e),
  97                  Ok(n) => { written += n as uint; }
  98              }
  99          }
 100          Ok(())
 101      }
 102  
 103      pub fn read(loop_&Loop, fdc_int, buf&mut [u8], offseti64)
 104          -> Result<int, UvError>
 105      {
 106          execute(|req, cb| unsafe {
 107              let uvbuf = uvll::uv_buf_t {
 108                  base: buf.as_ptr(),
 109                  len: buf.len() as uvll::uv_buf_len_t,
 110              };
 111              uvll::uv_fs_read(loop_.handle, req, fd, &uvbuf, 1, offset, cb)
 112          }).map(|req| {
 113              req.get_result() as int
 114          })
 115      }
 116  
 117      pub fn mkdir(loop_&Loop, path&CString, modec_int)
 118          -> Result<(), UvError>
 119      {
 120          execute_nop(|req, cb| unsafe {
 121              uvll::uv_fs_mkdir(loop_.handle, req, path.with_ref(|p| p),
 122                                mode, cb)
 123          })
 124      }
 125  
 126      pub fn rmdir(loop_&Loop, path&CString) -> Result<(), UvError> {
 127          execute_nop(|req, cb| unsafe {
 128              uvll::uv_fs_rmdir(loop_.handle, req, path.with_ref(|p| p),
 129                                cb)
 130          })
 131      }
 132  
 133      pub fn rename(loop_&Loop, path&CString, to&CString)
 134          -> Result<(), UvError>
 135      {
 136          execute_nop(|req, cb| unsafe {
 137              uvll::uv_fs_rename(loop_.handle,
 138                                 req,
 139                                 path.with_ref(|p| p),
 140                                 to.with_ref(|p| p),
 141                                 cb)
 142          })
 143      }
 144  
 145      pub fn chmod(loop_&Loop, path&CString, modec_int)
 146          -> Result<(), UvError>
 147      {
 148          execute_nop(|req, cb| unsafe {
 149              uvll::uv_fs_chmod(loop_.handle, req, path.with_ref(|p| p),
 150                                mode, cb)
 151          })
 152      }
 153  
 154      pub fn readdir(loop_&Loop, path&CString, flagsc_int)
 155          -> Result<Vec<Path>, UvError>
 156      {
 157          execute(|req, cb| unsafe {
 158              uvll::uv_fs_readdir(loop_.handle,
 159                                  req, path.with_ref(|p| p), flags, cb)
 160          }).map(|req| unsafe {
 161              let mut paths = vec!();
 162              let path = CString::new(path.with_ref(|p| p), false);
 163              let parent = Path::new(path);
 164              let _ = c_str::from_c_multistring(req.get_ptr() as *libc::c_char,
 165                                                Some(req.get_result() as uint),
 166                                                |rel| {
 167                  let p = rel.as_bytes();
 168                  paths.push(parent.join(p.slice_to(rel.len())));
 169              });
 170              paths
 171          })
 172      }
 173  
 174      pub fn readlink(loop_&Loop, path&CString) -> Result<Path, UvError> {
 175          execute(|req, cb| unsafe {
 176              uvll::uv_fs_readlink(loop_.handle, req,
 177                                   path.with_ref(|p| p), cb)
 178          }).map(|req| {
 179              Path::new(unsafe {
 180                  CString::new(req.get_ptr() as *libc::c_char, false)
 181              })
 182          })
 183      }
 184  
 185      pub fn chown(loop_&Loop, path&CString, uidint, gidint)
 186          -> Result<(), UvError>
 187      {
 188          execute_nop(|req, cb| unsafe {
 189              uvll::uv_fs_chown(loop_.handle,
 190                                req, path.with_ref(|p| p),
 191                                uid as uvll::uv_uid_t,
 192                                gid as uvll::uv_gid_t,
 193                                cb)
 194          })
 195      }
 196  
 197      pub fn truncate(loop_&Loop, filec_int, offseti64)
 198          -> Result<(), UvError>
 199      {
 200          execute_nop(|req, cb| unsafe {
 201              uvll::uv_fs_ftruncate(loop_.handle, req, file, offset, cb)
 202          })
 203      }
 204  
 205      pub fn link(loop_&Loop, src&CString, dst&CString)
 206          -> Result<(), UvError>
 207      {
 208          execute_nop(|req, cb| unsafe {
 209              uvll::uv_fs_link(loop_.handle, req,
 210                               src.with_ref(|p| p),
 211                               dst.with_ref(|p| p),
 212                               cb)
 213          })
 214      }
 215  
 216      pub fn symlink(loop_&Loop, src&CString, dst&CString)
 217          -> Result<(), UvError>
 218      {
 219          execute_nop(|req, cb| unsafe {
 220              uvll::uv_fs_symlink(loop_.handle, req,
 221                                  src.with_ref(|p| p),
 222                                  dst.with_ref(|p| p),
 223                                  0, cb)
 224          })
 225      }
 226  
 227      pub fn fsync(loop_&Loop, fdc_int) -> Result<(), UvError> {
 228          execute_nop(|req, cb| unsafe {
 229              uvll::uv_fs_fsync(loop_.handle, req, fd, cb)
 230          })
 231      }
 232  
 233      pub fn datasync(loop_&Loop, fdc_int) -> Result<(), UvError> {
 234          execute_nop(|req, cb| unsafe {
 235              uvll::uv_fs_fdatasync(loop_.handle, req, fd, cb)
 236          })
 237      }
 238  
 239      pub fn utime(loop_&Loop, path&CString, atimeu64, mtimeu64)
 240          -> Result<(), UvError>
 241      {
 242          // libuv takes seconds
 243          let atime = atime as libc::c_double / 1000.0;
 244          let mtime = mtime as libc::c_double / 1000.0;
 245          execute_nop(|req, cb| unsafe {
 246              uvll::uv_fs_utime(loop_.handle, req, path.with_ref(|p| p),
 247                                atime, mtime, cb)
 248          })
 249      }
 250  
 251      pub fn get_result(&self) -> ssize_t {
 252          unsafe { uvll::get_result_from_fs_req(self.req) }
 253      }
 254  
 255      pub fn get_stat(&self) -> uvll::uv_stat_t {
 256          let stat = uvll::uv_stat_t::new();
 257          unsafe { uvll::populate_stat(self.req, &stat); }
 258          stat
 259      }
 260  
 261      pub fn get_ptr(&self) -> *libc::c_void {
 262          unsafe { uvll::get_ptr_from_fs_req(self.req) }
 263      }
 264  
 265      pub fn mkstat(&self) -> FileStat {
 266          let path = unsafe { uvll::get_path_from_fs_req(self.req) };
 267          let path = unsafe { Path::new(CString::new(path, false)) };
 268          let stat = self.get_stat();
 269          fn to_msec(statuvll::uv_timespec_t) -> u64 {
 270              // Be sure to cast to u64 first to prevent overflowing if the tv_sec
 271              // field is a 32-bit integer.
 272              (stat.tv_sec as u64) * 1000 + (stat.tv_nsec as u64) / 1000000
 273          }
 274          let kind = match (stat.st_mode as c_int) & libc::S_IFMT {
 275              libc::S_IFREG => io::TypeFile,
 276              libc::S_IFDIR => io::TypeDirectory,
 277              libc::S_IFIFO => io::TypeNamedPipe,
 278              libc::S_IFBLK => io::TypeBlockSpecial,
 279              libc::S_IFLNK => io::TypeSymlink,
 280              _ => io::TypeUnknown,
 281          };
 282          FileStat {
 283              path: path,
 284              size: stat.st_size as u64,
 285              kind: kind,
 286              perm: unsafe {
 287                  io::FilePermission::from_bits(stat.st_mode as u32) & io::AllPermissions
 288              },
 289              created: to_msec(stat.st_birthtim),
 290              modified: to_msec(stat.st_mtim),
 291              accessed: to_msec(stat.st_atim),
 292              unstable: io::UnstableFileStat {
 293                  device: stat.st_dev as u64,
 294                  inode: stat.st_ino as u64,
 295                  rdev: stat.st_rdev as u64,
 296                  nlink: stat.st_nlink as u64,
 297                  uid: stat.st_uid as u64,
 298                  gid: stat.st_gid as u64,
 299                  blksize: stat.st_blksize as u64,
 300                  blocks: stat.st_blocks as u64,
 301                  flags: stat.st_flags as u64,
 302                  gen: stat.st_gen as u64,
 303              }
 304          }
 305      }
 306  }
 307  
 308  impl Drop for FsRequest {
 309      fn drop(&mut self) {
 310          unsafe {
 311              if self.fired {
 312                  uvll::uv_fs_req_cleanup(self.req);
 313              }
 314              uvll::free_req(self.req);
 315          }
 316      }
 317  }
 318  
 319  fn execute(f: |*uvll::uv_fs_t, uvll::uv_fs_cb-> c_int)
 320      -> Result<FsRequest, UvError>
 321  {
 322      let mut req = FsRequest {
 323          fired: false,
 324          req: unsafe { uvll::malloc_req(uvll::UV_FS) }
 325      };
 326      return match f(req.req, fs_cb) {
 327          0 => {
 328              req.fired = true;
 329              let mut slot = None;
 330              let loop_ = unsafe { uvll::get_loop_from_fs_req(req.req) };
 331              wait_until_woken_after(&mut slot, &Loop::wrap(loop_), || {
 332                  unsafe { uvll::set_data_for_req(req.req, &slot) }
 333              });
 334              match req.get_result() {
 335                  n if n < 0 => Err(UvError(n as i32)),
 336                  _ => Ok(req),
 337              }
 338          }
 339          n => Err(UvError(n))
 340      };
 341  
 342      extern fn fs_cb(req: *uvll::uv_fs_t) {
 343          let slot&mut Option<BlockedTask> = unsafe {
 344              cast::transmute(uvll::get_data_for_req(req))
 345          };
 346          wakeup(slot);
 347      }
 348  }
 349  
 350  fn execute_nop(f: |*uvll::uv_fs_t, uvll::uv_fs_cb-> c_int)
 351      -> Result<(), UvError> {
 352      execute(f).map(|_| {})
 353  }
 354  
 355  impl HomingIO for FileWatcher {
 356      fn home<'r>(&'r mut self) -> &'r mut HomeHandle { &mut self.home }
 357  }
 358  
 359  impl FileWatcher {
 360      pub fn new(io&mut UvIoFactory, fdc_int,
 361                 closertio::CloseBehavior) -> FileWatcher {
 362          FileWatcher {
 363              loop_: Loop::wrap(io.uv_loop()),
 364              fd: fd,
 365              close: close,
 366              home: io.make_handle(),
 367          }
 368      }
 369  
 370      fn base_read(&mut self, buf&mut [u8], offseti64) -> Result<int, IoError> {
 371          let _m = self.fire_homing_missile();
 372          let r = FsRequest::read(&self.loop_, self.fd, buf, offset);
 373          r.map_err(uv_error_to_io_error)
 374      }
 375      fn base_write(&mut self, buf&[u8], offseti64) -> Result<(), IoError> {
 376          let _m = self.fire_homing_missile();
 377          let r = FsRequest::write(&self.loop_, self.fd, buf, offset);
 378          r.map_err(uv_error_to_io_error)
 379      }
 380      fn seek_common(&mut self, posi64, whencec_int) ->
 381          Result<u64, IoError>{
 382          unsafe {
 383              match libc::lseek(self.fd, pos as libc::off_t, whence) {
 384                  -1 => {
 385                      Err(IoError {
 386                          kind: io::OtherIoError,
 387                          desc: "Failed to lseek.",
 388                          detail: None
 389                      })
 390                  },
 391                  n => Ok(n as u64)
 392              }
 393          }
 394      }
 395  }
 396  
 397  impl Drop for FileWatcher {
 398      fn drop(&mut self) {
 399          let _m = self.fire_homing_missile();
 400          match self.close {
 401              rtio::DontClose => {}
 402              rtio::CloseAsynchronously => {
 403                  unsafe {
 404                      let req = uvll::malloc_req(uvll::UV_FS);
 405                      assert_eq!(uvll::uv_fs_close(self.loop_.handle, req,
 406                                                   self.fd, close_cb), 0);
 407                  }
 408  
 409                  extern fn close_cb(req*uvll::uv_fs_t) {
 410                      unsafe {
 411                          uvll::uv_fs_req_cleanup(req);
 412                          uvll::free_req(req);
 413                      }
 414                  }
 415              }
 416              rtio::CloseSynchronously => {
 417                  let _ = execute_nop(|req, cb| unsafe {
 418                      uvll::uv_fs_close(self.loop_.handle, req, self.fd, cb)
 419                  });
 420              }
 421          }
 422      }
 423  }
 424  
 425  impl rtio::RtioFileStream for FileWatcher {
 426      fn read(&mut self, buf&mut [u8]) -> Result<int, IoError> {
 427          self.base_read(buf, -1)
 428      }
 429      fn write(&mut self, buf&[u8]) -> Result<(), IoError> {
 430          self.base_write(buf, -1)
 431      }
 432      fn pread(&mut self, buf&mut [u8], offsetu64) -> Result<int, IoError> {
 433          self.base_read(buf, offset as i64)
 434      }
 435      fn pwrite(&mut self, buf&[u8], offsetu64) -> Result<(), IoError> {
 436          self.base_write(buf, offset as i64)
 437      }
 438      fn seek(&mut self, posi64, whenceio::SeekStyle) -> Result<u64, IoError> {
 439          use libc::{SEEK_SET, SEEK_CUR, SEEK_END};
 440          let whence = match whence {
 441              io::SeekSet => SEEK_SET,
 442              io::SeekCur => SEEK_CUR,
 443              io::SeekEnd => SEEK_END
 444          };
 445          self.seek_common(pos, whence)
 446      }
 447      fn tell(&self) -> Result<u64, IoError> {
 448          use libc::SEEK_CUR;
 449          // this is temporary
 450          // FIXME #13933: Remove/justify all `&T` to `&mut T` transmutes
 451          let self_ = unsafe { cast::transmute::<&_, &mut FileWatcher>(self) };
 452          self_.seek_common(0, SEEK_CUR)
 453      }
 454      fn fsync(&mut self) -> Result<(), IoError> {
 455          let _m = self.fire_homing_missile();
 456          FsRequest::fsync(&self.loop_, self.fd).map_err(uv_error_to_io_error)
 457      }
 458      fn datasync(&mut self) -> Result<(), IoError> {
 459          let _m = self.fire_homing_missile();
 460          FsRequest::datasync(&self.loop_, self.fd).map_err(uv_error_to_io_error)
 461      }
 462      fn truncate(&mut self, offseti64) -> Result<(), IoError> {
 463          let _m = self.fire_homing_missile();
 464          let r = FsRequest::truncate(&self.loop_, self.fd, offset);
 465          r.map_err(uv_error_to_io_error)
 466      }
 467  }
 468  
 469  #[cfg(test)]
 470  mod test {
 471      use libc::c_int;
 472      use libc::{O_CREAT, O_RDWR, O_RDONLY, S_IWUSR, S_IRUSR};
 473      use std::io;
 474      use std::str;
 475      use super::FsRequest;
 476      use super::super::Loop;
 477      use super::super::local_loop;
 478  
 479      fn l() -> &mut Loop { &mut local_loop().loop_ }
 480  
 481      #[test]
 482      fn file_test_full_simple_sync() {
 483          let create_flags = O_RDWR | O_CREAT;
 484          let read_flags = O_RDONLY;
 485          let mode = S_IWUSR | S_IRUSR;
 486          let path_str = "./tmp/file_full_simple_sync.txt";
 487  
 488          {
 489              // open/create
 490              let result = FsRequest::open(local_loop(), &path_str.to_c_str(),
 491                                           create_flags as int, mode as int);
 492              assert!(result.is_ok());
 493              let result = result.unwrap();
 494              let fd = result.fd;
 495  
 496              // write
 497              let result = FsRequest::write(l(), fd, "hello".as_bytes(), -1);
 498              assert!(result.is_ok());
 499          }
 500  
 501          {
 502              // re-open
 503              let result = FsRequest::open(local_loop(), &path_str.to_c_str(),
 504                                           read_flags as int, 0);
 505              assert!(result.is_ok());
 506              let result = result.unwrap();
 507              let fd = result.fd;
 508  
 509              // read
 510              let mut read_mem = Vec::from_elem(1000, 0u8);
 511              let result = FsRequest::read(l(), fd, read_mem.as_mut_slice(), 0);
 512              assert!(result.is_ok());
 513  
 514              let nread = result.unwrap();
 515              assert!(nread > 0);
 516              let read_str = str::from_utf8(read_mem.slice_to(nread as uint)).unwrap();
 517              assert_eq!(read_str, "hello");
 518          }
 519          // unlink
 520          let result = FsRequest::unlink(l(), &path_str.to_c_str());
 521          assert!(result.is_ok());
 522      }
 523  
 524      #[test]
 525      fn file_test_stat() {
 526          let path = &"./tmp/file_test_stat_simple".to_c_str();
 527          let create_flags = (O_RDWR | O_CREAT) as int;
 528          let mode = (S_IWUSR | S_IRUSR) as int;
 529  
 530          let result = FsRequest::open(local_loop(), path, create_flags, mode);
 531          assert!(result.is_ok());
 532          let file = result.unwrap();
 533  
 534          let result = FsRequest::write(l(), file.fd, "hello".as_bytes(), 0);
 535          assert!(result.is_ok());
 536  
 537          let result = FsRequest::stat(l(), path);
 538          assert!(result.is_ok());
 539          assert_eq!(result.unwrap().size, 5);
 540  
 541          fn free<T>(_: T) {}
 542          free(file);
 543  
 544          let result = FsRequest::unlink(l(), path);
 545          assert!(result.is_ok());
 546      }
 547  
 548      #[test]
 549      fn file_test_mk_rm_dir() {
 550          let path = &"./tmp/mk_rm_dir".to_c_str();
 551          let mode = S_IWUSR | S_IRUSR;
 552  
 553          let result = FsRequest::mkdir(l(), path, mode);
 554          assert!(result.is_ok());
 555  
 556          let result = FsRequest::stat(l(), path);
 557          assert!(result.is_ok());
 558          assert!(result.unwrap().kind == io::TypeDirectory);
 559  
 560          let result = FsRequest::rmdir(l(), path);
 561          assert!(result.is_ok());
 562  
 563          let result = FsRequest::stat(l(), path);
 564          assert!(result.is_err());
 565      }
 566  
 567      #[test]
 568      fn file_test_mkdir_chokes_on_double_create() {
 569          let path = &"./tmp/double_create_dir".to_c_str();
 570          let mode = S_IWUSR | S_IRUSR;
 571  
 572          let result = FsRequest::stat(l(), path);
 573          assert!(result.is_err(), "{:?}", result);
 574          let result = FsRequest::mkdir(l(), path, mode as c_int);
 575          assert!(result.is_ok(), "{:?}", result);
 576          let result = FsRequest::mkdir(l(), path, mode as c_int);
 577          assert!(result.is_err(), "{:?}", result);
 578          let result = FsRequest::rmdir(l(), path);
 579          assert!(result.is_ok(), "{:?}", result);
 580      }
 581  
 582      #[test]
 583      fn file_test_rmdir_chokes_on_nonexistant_path() {
 584          let path = &"./tmp/never_existed_dir".to_c_str();
 585          let result = FsRequest::rmdir(l(), path);
 586          assert!(result.is_err());
 587      }
 588  }


librustuv/file.rs:31:1-31:1 -struct- definition:
pub struct FileWatcher {
    loop_: Loop,
    fd: c_int,
references:- 8
361:                close: rtio::CloseBehavior) -> FileWatcher {
362:         FileWatcher {
363:             loop_: Loop::wrap(io.uv_loop()),
--
397: impl Drop for FileWatcher {
398:     fn drop(&mut self) {
--
425: impl rtio::RtioFileStream for FileWatcher {
426:     fn read(&mut self, buf: &mut [u8]) -> Result<int, IoError> {
--
450:         // FIXME #13933: Remove/justify all `&T` to `&mut T` transmutes
451:         let self_ = unsafe { cast::transmute::<&_, &mut FileWatcher>(self) };
452:         self_.seek_common(0, SEEK_CUR)


librustuv/file.rs:26:1-26:1 -struct- definition:
pub struct FsRequest {
    req: *uvll::uv_fs_t,
    fired: bool,
references:- 4
321: {
322:     let mut req = FsRequest {
323:         fired: false,


librustuv/file.rs:349:1-349:1 -fn- definition:
fn execute_nop(f: |*uvll::uv_fs_t, uvll::uv_fs_cb| -> c_int)
    -> Result<(), UvError> {
    execute(f).map(|_| {})
references:- 13
416:             rtio::CloseSynchronously => {
417:                 let _ = execute_nop(|req, cb| unsafe {
418:                     uvll::uv_fs_close(self.loop_.handle, req, self.fd, cb)


librustuv/file.rs:318:1-318:1 -fn- definition:
fn execute(f: |*uvll::uv_fs_t, uvll::uv_fs_cb| -> c_int)
    -> Result<FsRequest, UvError>
{
references:- 8
351:     -> Result<(), UvError> {
352:     execute(f).map(|_| {})
353: }


librustuv/file.rs:269:8-269:8 -fn- definition:
        fn to_msec(stat: uvll::uv_timespec_t) -> u64 {
            // Be sure to cast to u64 first to prevent overflowing if the tv_sec
            // field is a 32-bit integer.
references:- 3
288:             },
289:             created: to_msec(stat.st_birthtim),
290:             modified: to_msec(stat.st_mtim),
291:             accessed: to_msec(stat.st_atim),
292:             unstable: io::UnstableFileStat {