Fill out the remaining functionality in io::file
This adds bindings to the remaining functions provided by libuv, all of which are useful operations on files which need to get exposed somehow. Some highlights: * Dropped `FileReader` and `FileWriter` and `FileStream` for one `File` type * Moved all file-related methods to be static methods under `File` * All directory related methods are still top-level functions * Created `io::FilePermission` types (backed by u32) that are what you'd expect * Created `io::FileType` and refactored `FileStat` to use FileType and FilePermission * Removed the expanding matrix of `FileMode` operations. The mode of reading a file will not have the O_CREAT flag, but a write mode will always have the O_CREAT flag. Closes #10130 Closes #10131 Closes #10121
This commit is contained in:
parent
9c1851019f
commit
f19d083362
38 changed files with 1381 additions and 1030 deletions
|
@ -9,7 +9,7 @@
|
||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
use std::rt::io::buffered::BufferedReader;
|
use std::rt::io::buffered::BufferedReader;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
|
|
||||||
pub struct ExpectedError { line: uint, kind: ~str, msg: ~str }
|
pub struct ExpectedError { line: uint, kind: ~str, msg: ~str }
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@ pub struct ExpectedError { line: uint, kind: ~str, msg: ~str }
|
||||||
pub fn load_errors(testfile: &Path) -> ~[ExpectedError] {
|
pub fn load_errors(testfile: &Path) -> ~[ExpectedError] {
|
||||||
|
|
||||||
let mut error_patterns = ~[];
|
let mut error_patterns = ~[];
|
||||||
let mut rdr = BufferedReader::new(file::open(testfile).unwrap());
|
let mut rdr = BufferedReader::new(File::open(testfile).unwrap());
|
||||||
let mut line_num = 1u;
|
let mut line_num = 1u;
|
||||||
loop {
|
loop {
|
||||||
let ln = match rdr.read_line() {
|
let ln = match rdr.read_line() {
|
||||||
|
|
|
@ -104,9 +104,9 @@ pub fn is_test_ignored(config: &config, testfile: &Path) -> bool {
|
||||||
|
|
||||||
fn iter_header(testfile: &Path, it: &fn(&str) -> bool) -> bool {
|
fn iter_header(testfile: &Path, it: &fn(&str) -> bool) -> bool {
|
||||||
use std::rt::io::buffered::BufferedReader;
|
use std::rt::io::buffered::BufferedReader;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
|
|
||||||
let mut rdr = BufferedReader::new(file::open(testfile).unwrap());
|
let mut rdr = BufferedReader::new(File::open(testfile).unwrap());
|
||||||
loop {
|
loop {
|
||||||
let ln = match rdr.read_line() {
|
let ln = match rdr.read_line() {
|
||||||
Some(ln) => ln, None => break
|
Some(ln) => ln, None => break
|
||||||
|
|
|
@ -23,6 +23,7 @@ use util::logv;
|
||||||
use std::cell::Cell;
|
use std::cell::Cell;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::task::{spawn_sched, SingleThreaded};
|
use std::task::{spawn_sched, SingleThreaded};
|
||||||
|
@ -171,7 +172,7 @@ fn run_pretty_test(config: &config, props: &TestProps, testfile: &Path) {
|
||||||
let rounds =
|
let rounds =
|
||||||
match props.pp_exact { Some(_) => 1, None => 2 };
|
match props.pp_exact { Some(_) => 1, None => 2 };
|
||||||
|
|
||||||
let src = file::open(testfile).read_to_end();
|
let src = File::open(testfile).read_to_end();
|
||||||
let src = str::from_utf8_owned(src);
|
let src = str::from_utf8_owned(src);
|
||||||
let mut srcs = ~[src];
|
let mut srcs = ~[src];
|
||||||
|
|
||||||
|
@ -193,7 +194,7 @@ fn run_pretty_test(config: &config, props: &TestProps, testfile: &Path) {
|
||||||
let mut expected = match props.pp_exact {
|
let mut expected = match props.pp_exact {
|
||||||
Some(ref file) => {
|
Some(ref file) => {
|
||||||
let filepath = testfile.dir_path().join(file);
|
let filepath = testfile.dir_path().join(file);
|
||||||
let s = file::open(&filepath).read_to_end();
|
let s = File::open(&filepath).read_to_end();
|
||||||
str::from_utf8_owned(s)
|
str::from_utf8_owned(s)
|
||||||
}
|
}
|
||||||
None => { srcs[srcs.len() - 2u].clone() }
|
None => { srcs[srcs.len() - 2u].clone() }
|
||||||
|
@ -764,7 +765,7 @@ fn dump_output(config: &config, testfile: &Path, out: &str, err: &str) {
|
||||||
fn dump_output_file(config: &config, testfile: &Path,
|
fn dump_output_file(config: &config, testfile: &Path,
|
||||||
out: &str, extension: &str) {
|
out: &str, extension: &str) {
|
||||||
let outfile = make_out_name(config, testfile, extension);
|
let outfile = make_out_name(config, testfile, extension);
|
||||||
file::create(&outfile).write(out.as_bytes());
|
File::create(&outfile).write(out.as_bytes());
|
||||||
}
|
}
|
||||||
|
|
||||||
fn make_out_name(config: &config, testfile: &Path, extension: &str) -> Path {
|
fn make_out_name(config: &config, testfile: &Path, extension: &str) -> Path {
|
||||||
|
@ -1015,7 +1016,7 @@ fn disassemble_extract(config: &config, _props: &TestProps,
|
||||||
|
|
||||||
|
|
||||||
fn count_extracted_lines(p: &Path) -> uint {
|
fn count_extracted_lines(p: &Path) -> uint {
|
||||||
let x = file::open(&p.with_extension("ll")).read_to_end();
|
let x = File::open(&p.with_extension("ll")).read_to_end();
|
||||||
let x = str::from_utf8_owned(x);
|
let x = str::from_utf8_owned(x);
|
||||||
x.line_iter().len()
|
x.line_iter().len()
|
||||||
}
|
}
|
||||||
|
|
|
@ -143,6 +143,7 @@ void posix88_consts() {
|
||||||
put_const(S_IFBLK, int);
|
put_const(S_IFBLK, int);
|
||||||
put_const(S_IFDIR, int);
|
put_const(S_IFDIR, int);
|
||||||
put_const(S_IFREG, int);
|
put_const(S_IFREG, int);
|
||||||
|
put_const(S_IFLNK, int);
|
||||||
put_const(S_IFMT, int);
|
put_const(S_IFMT, int);
|
||||||
|
|
||||||
put_const(S_IEXEC, int);
|
put_const(S_IEXEC, int);
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
use std::{os, str};
|
use std::{os, str};
|
||||||
use std::os::getenv;
|
use std::os::getenv;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
|
|
||||||
/// Return path to database entry for `term`
|
/// Return path to database entry for `term`
|
||||||
pub fn get_dbpath_for_term(term: &str) -> Option<~Path> {
|
pub fn get_dbpath_for_term(term: &str) -> Option<~Path> {
|
||||||
|
@ -76,7 +76,7 @@ pub fn get_dbpath_for_term(term: &str) -> Option<~Path> {
|
||||||
/// Return open file for `term`
|
/// Return open file for `term`
|
||||||
pub fn open(term: &str) -> Result<@mut io::Reader, ~str> {
|
pub fn open(term: &str) -> Result<@mut io::Reader, ~str> {
|
||||||
match get_dbpath_for_term(term) {
|
match get_dbpath_for_term(term) {
|
||||||
Some(x) => Ok(@mut file::open(x) as @mut io::Reader),
|
Some(x) => Ok(@mut File::open(x) as @mut io::Reader),
|
||||||
None => Err(format!("could not find terminfo entry for {}", term))
|
None => Err(format!("could not find terminfo entry for {}", term))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,7 +31,7 @@ use treemap::TreeMap;
|
||||||
use std::clone::Clone;
|
use std::clone::Clone;
|
||||||
use std::comm::{stream, SharedChan, GenericPort, GenericChan};
|
use std::comm::{stream, SharedChan, GenericPort, GenericChan};
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::task;
|
use std::task;
|
||||||
use std::to_str::ToStr;
|
use std::to_str::ToStr;
|
||||||
use std::f64;
|
use std::f64;
|
||||||
|
@ -353,7 +353,7 @@ struct ConsoleTestState {
|
||||||
impl ConsoleTestState {
|
impl ConsoleTestState {
|
||||||
pub fn new(opts: &TestOpts) -> ConsoleTestState {
|
pub fn new(opts: &TestOpts) -> ConsoleTestState {
|
||||||
let log_out = match opts.logfile {
|
let log_out = match opts.logfile {
|
||||||
Some(ref path) => Some(@mut file::create(path) as @mut io::Writer),
|
Some(ref path) => Some(@mut File::create(path) as @mut io::Writer),
|
||||||
None => None
|
None => None
|
||||||
};
|
};
|
||||||
let out = @mut io::stdio::stdout() as @mut io::Writer;
|
let out = @mut io::stdio::stdout() as @mut io::Writer;
|
||||||
|
@ -936,14 +936,14 @@ impl MetricMap {
|
||||||
/// Load MetricDiff from a file.
|
/// Load MetricDiff from a file.
|
||||||
pub fn load(p: &Path) -> MetricMap {
|
pub fn load(p: &Path) -> MetricMap {
|
||||||
assert!(p.exists());
|
assert!(p.exists());
|
||||||
let f = @mut file::open(p) as @mut io::Reader;
|
let f = @mut File::open(p) as @mut io::Reader;
|
||||||
let mut decoder = json::Decoder(json::from_reader(f).unwrap());
|
let mut decoder = json::Decoder(json::from_reader(f).unwrap());
|
||||||
MetricMap(Decodable::decode(&mut decoder))
|
MetricMap(Decodable::decode(&mut decoder))
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Write MetricDiff to a file.
|
/// Write MetricDiff to a file.
|
||||||
pub fn save(&self, p: &Path) {
|
pub fn save(&self, p: &Path) {
|
||||||
self.to_json().to_pretty_writer(@mut file::create(p) as @mut io::Writer);
|
self.to_json().to_pretty_writer(@mut File::create(p) as @mut io::Writer);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Compare against another MetricMap. Optionally compare all
|
/// Compare against another MetricMap. Optionally compare all
|
||||||
|
|
|
@ -19,7 +19,7 @@ use std::cell::Cell;
|
||||||
use std::comm::{PortOne, oneshot};
|
use std::comm::{PortOne, oneshot};
|
||||||
use std::{str, task};
|
use std::{str, task};
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::rt::io::Decorator;
|
use std::rt::io::Decorator;
|
||||||
use std::rt::io::mem::MemWriter;
|
use std::rt::io::mem::MemWriter;
|
||||||
|
|
||||||
|
@ -176,14 +176,14 @@ impl Database {
|
||||||
|
|
||||||
// FIXME #4330: This should have &mut self and should set self.db_dirty to false.
|
// FIXME #4330: This should have &mut self and should set self.db_dirty to false.
|
||||||
fn save(&self) {
|
fn save(&self) {
|
||||||
let f = @mut file::create(&self.db_filename);
|
let f = @mut File::create(&self.db_filename);
|
||||||
self.db_cache.to_json().to_pretty_writer(f as @mut io::Writer);
|
self.db_cache.to_json().to_pretty_writer(f as @mut io::Writer);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn load(&mut self) {
|
fn load(&mut self) {
|
||||||
assert!(!self.db_dirty);
|
assert!(!self.db_dirty);
|
||||||
assert!(self.db_filename.exists());
|
assert!(self.db_filename.exists());
|
||||||
match io::result(|| file::open(&self.db_filename)) {
|
match io::result(|| File::open(&self.db_filename)) {
|
||||||
Err(e) => fail!("Couldn't load workcache database {}: {}",
|
Err(e) => fail!("Couldn't load workcache database {}: {}",
|
||||||
self.db_filename.display(),
|
self.db_filename.display(),
|
||||||
e.desc),
|
e.desc),
|
||||||
|
@ -480,7 +480,6 @@ impl<'self, T:Send +
|
||||||
#[test]
|
#[test]
|
||||||
fn test() {
|
fn test() {
|
||||||
use std::{os, run};
|
use std::{os, run};
|
||||||
use std::rt::io::file;
|
|
||||||
use std::str::from_utf8_owned;
|
use std::str::from_utf8_owned;
|
||||||
|
|
||||||
// Create a path to a new file 'filename' in the directory in which
|
// Create a path to a new file 'filename' in the directory in which
|
||||||
|
@ -488,13 +487,13 @@ fn test() {
|
||||||
fn make_path(filename: ~str) -> Path {
|
fn make_path(filename: ~str) -> Path {
|
||||||
let pth = os::self_exe_path().expect("workcache::test failed").with_filename(filename);
|
let pth = os::self_exe_path().expect("workcache::test failed").with_filename(filename);
|
||||||
if pth.exists() {
|
if pth.exists() {
|
||||||
file::unlink(&pth);
|
File::unlink(&pth);
|
||||||
}
|
}
|
||||||
return pth;
|
return pth;
|
||||||
}
|
}
|
||||||
|
|
||||||
let pth = make_path(~"foo.c");
|
let pth = make_path(~"foo.c");
|
||||||
file::create(&pth).write(bytes!("int main() { return 0; }"));
|
File::create(&pth).write(bytes!("int main() { return 0; }"));
|
||||||
|
|
||||||
let db_path = make_path(~"db.json");
|
let db_path = make_path(~"db.json");
|
||||||
|
|
||||||
|
@ -507,7 +506,7 @@ fn test() {
|
||||||
let subcx = cx.clone();
|
let subcx = cx.clone();
|
||||||
let pth = pth.clone();
|
let pth = pth.clone();
|
||||||
|
|
||||||
let file_content = from_utf8_owned(file::open(&pth).read_to_end());
|
let file_content = from_utf8_owned(File::open(&pth).read_to_end());
|
||||||
|
|
||||||
// FIXME (#9639): This needs to handle non-utf8 paths
|
// FIXME (#9639): This needs to handle non-utf8 paths
|
||||||
prep.declare_input("file", pth.as_str().unwrap(), file_content);
|
prep.declare_input("file", pth.as_str().unwrap(), file_content);
|
||||||
|
|
|
@ -31,7 +31,7 @@ use std::ptr;
|
||||||
use std::run;
|
use std::run;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::vec;
|
use std::vec;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use syntax::ast;
|
use syntax::ast;
|
||||||
use syntax::ast_map::{path, path_mod, path_name, path_pretty_name};
|
use syntax::ast_map::{path, path_mod, path_name, path_pretty_name};
|
||||||
use syntax::attr;
|
use syntax::attr;
|
||||||
|
@ -950,18 +950,17 @@ pub fn link_binary(sess: Session,
|
||||||
|
|
||||||
// Remove the temporary object file if we aren't saving temps
|
// Remove the temporary object file if we aren't saving temps
|
||||||
if !sess.opts.save_temps {
|
if !sess.opts.save_temps {
|
||||||
file::unlink(obj_filename);
|
File::unlink(obj_filename);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn is_writeable(p: &Path) -> bool {
|
fn is_writeable(p: &Path) -> bool {
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::libc::consts::os::posix88::S_IWUSR;
|
|
||||||
|
|
||||||
!p.exists() ||
|
!p.exists() ||
|
||||||
(match io::result(|| p.stat()) {
|
(match io::result(|| p.stat()) {
|
||||||
Err(*) => false,
|
Err(*) => false,
|
||||||
Ok(m) => (m.mode as uint) & S_IWUSR as uint == S_IWUSR as uint
|
Ok(m) => m.perm & io::UserWrite == io::UserWrite
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -27,7 +27,7 @@ use util::ppaux;
|
||||||
|
|
||||||
use std::hashmap::{HashMap,HashSet};
|
use std::hashmap::{HashMap,HashSet};
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::rt::io::mem::MemReader;
|
use std::rt::io::mem::MemReader;
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::vec;
|
use std::vec;
|
||||||
|
@ -370,7 +370,7 @@ pub fn phase_5_run_llvm_passes(sess: Session,
|
||||||
|
|
||||||
// Remove assembly source unless --save-temps was specified
|
// Remove assembly source unless --save-temps was specified
|
||||||
if !sess.opts.save_temps {
|
if !sess.opts.save_temps {
|
||||||
file::unlink(&asm_filename);
|
File::unlink(&asm_filename);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
time(sess.time_passes(), "LLVM passes", (), |_|
|
time(sess.time_passes(), "LLVM passes", (), |_|
|
||||||
|
|
|
@ -42,6 +42,7 @@ use std::local_data;
|
||||||
use std::rt::io::buffered::BufferedWriter;
|
use std::rt::io::buffered::BufferedWriter;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::task;
|
use std::task;
|
||||||
|
@ -263,7 +264,7 @@ pub fn run(mut crate: clean::Crate, dst: Path) {
|
||||||
// Publish the search index
|
// Publish the search index
|
||||||
{
|
{
|
||||||
dst.push("search-index.js");
|
dst.push("search-index.js");
|
||||||
let mut w = BufferedWriter::new(file::create(&dst).unwrap());
|
let mut w = BufferedWriter::new(File::create(&dst).unwrap());
|
||||||
let w = &mut w as &mut Writer;
|
let w = &mut w as &mut Writer;
|
||||||
write!(w, "var searchIndex = [");
|
write!(w, "var searchIndex = [");
|
||||||
for (i, item) in cache.search_index.iter().enumerate() {
|
for (i, item) in cache.search_index.iter().enumerate() {
|
||||||
|
@ -313,7 +314,7 @@ pub fn run(mut crate: clean::Crate, dst: Path) {
|
||||||
/// Writes the entire contents of a string to a destination, not attempting to
|
/// Writes the entire contents of a string to a destination, not attempting to
|
||||||
/// catch any errors.
|
/// catch any errors.
|
||||||
fn write(dst: Path, contents: &str) {
|
fn write(dst: Path, contents: &str) {
|
||||||
file::create(&dst).write(contents.as_bytes());
|
File::create(&dst).write(contents.as_bytes());
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Makes a directory on the filesystem, failing the task if an error occurs and
|
/// Makes a directory on the filesystem, failing the task if an error occurs and
|
||||||
|
@ -419,7 +420,7 @@ impl<'self> SourceCollector<'self> {
|
||||||
// If we couldn't open this file, then just returns because it
|
// If we couldn't open this file, then just returns because it
|
||||||
// probably means that it's some standard library macro thing and we
|
// probably means that it's some standard library macro thing and we
|
||||||
// can't have the source to it anyway.
|
// can't have the source to it anyway.
|
||||||
let mut r = match io::result(|| file::open(&p)) {
|
let mut r = match io::result(|| File::open(&p)) {
|
||||||
Ok(r) => r,
|
Ok(r) => r,
|
||||||
// eew macro hacks
|
// eew macro hacks
|
||||||
Err(*) => return filename == "<std-macros>"
|
Err(*) => return filename == "<std-macros>"
|
||||||
|
@ -445,7 +446,7 @@ impl<'self> SourceCollector<'self> {
|
||||||
}
|
}
|
||||||
|
|
||||||
cur.push(p.filename().expect("source has no filename") + bytes!(".html"));
|
cur.push(p.filename().expect("source has no filename") + bytes!(".html"));
|
||||||
let mut w = BufferedWriter::new(file::create(&cur).unwrap());
|
let mut w = BufferedWriter::new(File::create(&cur).unwrap());
|
||||||
|
|
||||||
let title = cur.filename_display().with_str(|s| format!("{} -- source", s));
|
let title = cur.filename_display().with_str(|s| format!("{} -- source", s));
|
||||||
let page = layout::Page {
|
let page = layout::Page {
|
||||||
|
@ -767,7 +768,7 @@ impl Context {
|
||||||
///
|
///
|
||||||
/// The rendering driver uses this closure to queue up more work.
|
/// The rendering driver uses this closure to queue up more work.
|
||||||
fn item(&mut self, item: clean::Item, f: &fn(&mut Context, clean::Item)) {
|
fn item(&mut self, item: clean::Item, f: &fn(&mut Context, clean::Item)) {
|
||||||
fn render(w: file::FileWriter, cx: &mut Context, it: &clean::Item,
|
fn render(w: io::File, cx: &mut Context, it: &clean::Item,
|
||||||
pushname: bool) {
|
pushname: bool) {
|
||||||
// A little unfortunate that this is done like this, but it sure
|
// A little unfortunate that this is done like this, but it sure
|
||||||
// does make formatting *a lot* nicer.
|
// does make formatting *a lot* nicer.
|
||||||
|
@ -804,7 +805,7 @@ impl Context {
|
||||||
do self.recurse(name) |this| {
|
do self.recurse(name) |this| {
|
||||||
let item = item.take();
|
let item = item.take();
|
||||||
let dst = this.dst.join("index.html");
|
let dst = this.dst.join("index.html");
|
||||||
render(file::create(&dst).unwrap(), this, &item, false);
|
render(File::create(&dst).unwrap(), this, &item, false);
|
||||||
|
|
||||||
let m = match item.inner {
|
let m = match item.inner {
|
||||||
clean::ModuleItem(m) => m,
|
clean::ModuleItem(m) => m,
|
||||||
|
@ -821,7 +822,7 @@ impl Context {
|
||||||
// pages dedicated to them.
|
// pages dedicated to them.
|
||||||
_ if item.name.is_some() => {
|
_ if item.name.is_some() => {
|
||||||
let dst = self.dst.join(item_path(&item));
|
let dst = self.dst.join(item_path(&item));
|
||||||
render(file::create(&dst).unwrap(), self, &item, true);
|
render(File::create(&dst).unwrap(), self, &item, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
_ => {}
|
_ => {}
|
||||||
|
|
|
@ -26,7 +26,7 @@ extern mod extra;
|
||||||
use std::cell::Cell;
|
use std::cell::Cell;
|
||||||
use std::local_data;
|
use std::local_data;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::rt::io::mem::MemWriter;
|
use std::rt::io::mem::MemWriter;
|
||||||
use std::rt::io::Decorator;
|
use std::rt::io::Decorator;
|
||||||
use std::str;
|
use std::str;
|
||||||
|
@ -259,7 +259,7 @@ fn rust_input(cratefile: &str, matches: &getopts::Matches) -> Output {
|
||||||
/// This input format purely deserializes the json output file. No passes are
|
/// This input format purely deserializes the json output file. No passes are
|
||||||
/// run over the deserialized output.
|
/// run over the deserialized output.
|
||||||
fn json_input(input: &str) -> Result<Output, ~str> {
|
fn json_input(input: &str) -> Result<Output, ~str> {
|
||||||
let input = match file::open(&Path::new(input)) {
|
let input = match File::open(&Path::new(input)) {
|
||||||
Some(f) => f,
|
Some(f) => f,
|
||||||
None => return Err(format!("couldn't open {} for reading", input)),
|
None => return Err(format!("couldn't open {} for reading", input)),
|
||||||
};
|
};
|
||||||
|
@ -321,7 +321,7 @@ fn json_output(crate: clean::Crate, res: ~[plugins::PluginJson], dst: Path) {
|
||||||
json.insert(~"crate", crate_json);
|
json.insert(~"crate", crate_json);
|
||||||
json.insert(~"plugins", json::Object(plugins_json));
|
json.insert(~"plugins", json::Object(plugins_json));
|
||||||
|
|
||||||
let mut file = file::create(&dst).unwrap();
|
let mut file = File::create(&dst).unwrap();
|
||||||
let output = json::Object(json).to_str();
|
let output = json::Object(json).to_str();
|
||||||
file.write(output.as_bytes());
|
file.write(output.as_bytes());
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,6 +28,7 @@ use std::{os, result, run, str, task};
|
||||||
use std::hashmap::HashSet;
|
use std::hashmap::HashSet;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
pub use std::path::Path;
|
pub use std::path::Path;
|
||||||
|
|
||||||
use extra::workcache;
|
use extra::workcache;
|
||||||
|
@ -661,7 +662,7 @@ impl CtxMethods for BuildContext {
|
||||||
for exec in subex.iter() {
|
for exec in subex.iter() {
|
||||||
debug!("Copying: {} -> {}", exec.display(), sub_target_ex.display());
|
debug!("Copying: {} -> {}", exec.display(), sub_target_ex.display());
|
||||||
file::mkdir_recursive(&sub_target_ex.dir_path(), io::UserRWX);
|
file::mkdir_recursive(&sub_target_ex.dir_path(), io::UserRWX);
|
||||||
file::copy(exec, &sub_target_ex);
|
File::copy(exec, &sub_target_ex);
|
||||||
// FIXME (#9639): This needs to handle non-utf8 paths
|
// FIXME (#9639): This needs to handle non-utf8 paths
|
||||||
exe_thing.discover_output("binary",
|
exe_thing.discover_output("binary",
|
||||||
sub_target_ex.as_str().unwrap(),
|
sub_target_ex.as_str().unwrap(),
|
||||||
|
@ -674,7 +675,7 @@ impl CtxMethods for BuildContext {
|
||||||
didn't install it!", lib.display()));
|
didn't install it!", lib.display()));
|
||||||
target_lib.set_filename(lib.filename().expect("weird target lib"));
|
target_lib.set_filename(lib.filename().expect("weird target lib"));
|
||||||
file::mkdir_recursive(&target_lib.dir_path(), io::UserRWX);
|
file::mkdir_recursive(&target_lib.dir_path(), io::UserRWX);
|
||||||
file::copy(lib, &target_lib);
|
File::copy(lib, &target_lib);
|
||||||
debug!("3. discovering output {}", target_lib.display());
|
debug!("3. discovering output {}", target_lib.display());
|
||||||
exe_thing.discover_output("binary",
|
exe_thing.discover_output("binary",
|
||||||
target_lib.as_str().unwrap(),
|
target_lib.as_str().unwrap(),
|
||||||
|
|
|
@ -14,6 +14,7 @@ use target::*;
|
||||||
use package_id::PkgId;
|
use package_id::PkgId;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
use std::os;
|
use std::os;
|
||||||
use context::*;
|
use context::*;
|
||||||
use crate::Crate;
|
use crate::Crate;
|
||||||
|
@ -301,7 +302,7 @@ impl PkgSrc {
|
||||||
// Move clone_target to local.
|
// Move clone_target to local.
|
||||||
// First, create all ancestor directories.
|
// First, create all ancestor directories.
|
||||||
let moved = make_dir_rwx_recursive(&local.dir_path())
|
let moved = make_dir_rwx_recursive(&local.dir_path())
|
||||||
&& io::result(|| file::rename(&clone_target, local)).is_ok();
|
&& io::result(|| File::rename(&clone_target, local)).is_ok();
|
||||||
if moved { Some(local.clone()) }
|
if moved { Some(local.clone()) }
|
||||||
else { None }
|
else { None }
|
||||||
}
|
}
|
||||||
|
@ -350,7 +351,7 @@ impl PkgSrc {
|
||||||
|
|
||||||
let prefix = self.start_dir.component_iter().len();
|
let prefix = self.start_dir.component_iter().len();
|
||||||
debug!("Matching against {}", self.id.short_name);
|
debug!("Matching against {}", self.id.short_name);
|
||||||
do file::walk_dir(&self.start_dir) |pth| {
|
for pth in file::walk_dir(&self.start_dir) {
|
||||||
let maybe_known_crate_set = match pth.filename_str() {
|
let maybe_known_crate_set = match pth.filename_str() {
|
||||||
Some(filename) if filter(filename) => match filename {
|
Some(filename) if filter(filename) => match filename {
|
||||||
"lib.rs" => Some(&mut self.libs),
|
"lib.rs" => Some(&mut self.libs),
|
||||||
|
@ -363,11 +364,10 @@ impl PkgSrc {
|
||||||
};
|
};
|
||||||
|
|
||||||
match maybe_known_crate_set {
|
match maybe_known_crate_set {
|
||||||
Some(crate_set) => PkgSrc::push_crate(crate_set, prefix, pth),
|
Some(crate_set) => PkgSrc::push_crate(crate_set, prefix, &pth),
|
||||||
None => ()
|
None => ()
|
||||||
}
|
}
|
||||||
true
|
}
|
||||||
};
|
|
||||||
|
|
||||||
let crate_sets = [&self.libs, &self.mains, &self.tests, &self.benchs];
|
let crate_sets = [&self.libs, &self.mains, &self.tests, &self.benchs];
|
||||||
if crate_sets.iter().all(|crate_set| crate_set.is_empty()) {
|
if crate_sets.iter().all(|crate_set| crate_set.is_empty()) {
|
||||||
|
|
|
@ -21,6 +21,7 @@ use std::libc::consts::os::posix88::{S_IRUSR, S_IWUSR, S_IXUSR};
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
use messages::*;
|
use messages::*;
|
||||||
|
|
||||||
pub fn default_workspace() -> Path {
|
pub fn default_workspace() -> Path {
|
||||||
|
@ -72,9 +73,9 @@ pub fn workspace_contains_package_id_(pkgid: &PkgId, workspace: &Path,
|
||||||
if !src_dir.is_dir() { return None }
|
if !src_dir.is_dir() { return None }
|
||||||
|
|
||||||
let mut found = None;
|
let mut found = None;
|
||||||
do file::walk_dir(&src_dir) |p| {
|
for p in file::walk_dir(&src_dir) {
|
||||||
if p.is_dir() {
|
if p.is_dir() {
|
||||||
if *p == src_dir.join(&pkgid.path) || {
|
if p == src_dir.join(&pkgid.path) || {
|
||||||
let pf = p.filename_str();
|
let pf = p.filename_str();
|
||||||
do pf.iter().any |&g| {
|
do pf.iter().any |&g| {
|
||||||
match split_version_general(g, '-') {
|
match split_version_general(g, '-') {
|
||||||
|
@ -89,9 +90,8 @@ pub fn workspace_contains_package_id_(pkgid: &PkgId, workspace: &Path,
|
||||||
found = Some(p.clone());
|
found = Some(p.clone());
|
||||||
}
|
}
|
||||||
|
|
||||||
};
|
}
|
||||||
true
|
}
|
||||||
};
|
|
||||||
|
|
||||||
if found.is_some() {
|
if found.is_some() {
|
||||||
debug!("Found {} in {}", pkgid.to_str(), workspace.display());
|
debug!("Found {} in {}", pkgid.to_str(), workspace.display());
|
||||||
|
@ -399,12 +399,12 @@ pub fn uninstall_package_from(workspace: &Path, pkgid: &PkgId) {
|
||||||
let mut did_something = false;
|
let mut did_something = false;
|
||||||
let installed_bin = target_executable_in_workspace(pkgid, workspace);
|
let installed_bin = target_executable_in_workspace(pkgid, workspace);
|
||||||
if installed_bin.exists() {
|
if installed_bin.exists() {
|
||||||
file::unlink(&installed_bin);
|
File::unlink(&installed_bin);
|
||||||
did_something = true;
|
did_something = true;
|
||||||
}
|
}
|
||||||
let installed_lib = target_library_in_workspace(pkgid, workspace);
|
let installed_lib = target_library_in_workspace(pkgid, workspace);
|
||||||
if installed_lib.exists() {
|
if installed_lib.exists() {
|
||||||
file::unlink(&installed_lib);
|
File::unlink(&installed_lib);
|
||||||
did_something = true;
|
did_something = true;
|
||||||
}
|
}
|
||||||
if !did_something {
|
if !did_something {
|
||||||
|
|
|
@ -96,12 +96,11 @@ pub enum CloneResult {
|
||||||
|
|
||||||
pub fn make_read_only(target: &Path) {
|
pub fn make_read_only(target: &Path) {
|
||||||
// Now, make all the files in the target dir read-only
|
// Now, make all the files in the target dir read-only
|
||||||
do file::walk_dir(target) |p| {
|
for p in file::walk_dir(target) {
|
||||||
if !p.is_dir() {
|
if !p.is_dir() {
|
||||||
assert!(chmod_read_only(p));
|
assert!(chmod_read_only(&p));
|
||||||
};
|
}
|
||||||
true
|
}
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Source can be either a URL or a local file path.
|
/// Source can be either a URL or a local file path.
|
||||||
|
|
|
@ -14,6 +14,7 @@ use context::{BuildContext, Context, RustcFlags};
|
||||||
use std::{os, run, str, task};
|
use std::{os, run, str, task};
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
use extra::arc::Arc;
|
use extra::arc::Arc;
|
||||||
use extra::arc::RWArc;
|
use extra::arc::RWArc;
|
||||||
use extra::tempfile::TempDir;
|
use extra::tempfile::TempDir;
|
||||||
|
@ -83,7 +84,7 @@ fn git_repo_pkg_with_tag(a_tag: ~str) -> PkgId {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn writeFile(file_path: &Path, contents: &str) {
|
fn writeFile(file_path: &Path, contents: &str) {
|
||||||
let mut out = file::create(file_path);
|
let mut out = File::create(file_path);
|
||||||
out.write(contents.as_bytes());
|
out.write(contents.as_bytes());
|
||||||
out.write(['\n' as u8]);
|
out.write(['\n' as u8]);
|
||||||
}
|
}
|
||||||
|
@ -196,23 +197,13 @@ fn add_git_tag(repo: &Path, tag: ~str) {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn is_rwx(p: &Path) -> bool {
|
fn is_rwx(p: &Path) -> bool {
|
||||||
use std::libc::consts::os::posix88::{S_IRUSR, S_IWUSR, S_IXUSR};
|
|
||||||
|
|
||||||
if !p.exists() { return false }
|
if !p.exists() { return false }
|
||||||
let m = p.stat().mode;
|
p.stat().perm & io::UserRWX == io::UserRWX
|
||||||
(m & S_IRUSR as u64) == S_IRUSR as u64
|
|
||||||
&& (m & S_IWUSR as u64) == S_IWUSR as u64
|
|
||||||
&& (m & S_IXUSR as u64) == S_IXUSR as u64
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn is_read_only(p: &Path) -> bool {
|
fn is_read_only(p: &Path) -> bool {
|
||||||
use std::libc::consts::os::posix88::{S_IRUSR, S_IWUSR, S_IXUSR};
|
|
||||||
|
|
||||||
if !p.exists() { return false }
|
if !p.exists() { return false }
|
||||||
let m = p.stat().mode;
|
p.stat().perm & io::UserRWX == io::UserRead
|
||||||
(m & S_IRUSR as u64) == S_IRUSR as u64
|
|
||||||
&& (m & S_IWUSR as u64) == 0 as u64
|
|
||||||
&& (m & S_IXUSR as u64) == 0 as u64
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn test_sysroot() -> Path {
|
fn test_sysroot() -> Path {
|
||||||
|
@ -398,7 +389,7 @@ fn test_executable_exists(repo: &Path, short_name: &str) -> bool {
|
||||||
fn remove_executable_file(p: &PkgId, workspace: &Path) {
|
fn remove_executable_file(p: &PkgId, workspace: &Path) {
|
||||||
let exec = target_executable_in_workspace(&PkgId::new(p.short_name), workspace);
|
let exec = target_executable_in_workspace(&PkgId::new(p.short_name), workspace);
|
||||||
if exec.exists() {
|
if exec.exists() {
|
||||||
file::unlink(&exec);
|
File::unlink(&exec);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -419,7 +410,7 @@ fn built_executable_exists(repo: &Path, short_name: &str) -> bool {
|
||||||
fn remove_built_executable_file(p: &PkgId, workspace: &Path) {
|
fn remove_built_executable_file(p: &PkgId, workspace: &Path) {
|
||||||
let exec = built_executable_in_workspace(&PkgId::new(p.short_name), workspace);
|
let exec = built_executable_in_workspace(&PkgId::new(p.short_name), workspace);
|
||||||
match exec {
|
match exec {
|
||||||
Some(r) => file::unlink(&r),
|
Some(r) => File::unlink(&r),
|
||||||
None => ()
|
None => ()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -553,7 +544,7 @@ fn frob_source_file(workspace: &Path, pkgid: &PkgId, filename: &str) {
|
||||||
do io::io_error::cond.trap(|e| {
|
do io::io_error::cond.trap(|e| {
|
||||||
cond.raise((p.clone(), format!("Bad path: {}", e.desc)));
|
cond.raise((p.clone(), format!("Bad path: {}", e.desc)));
|
||||||
}).inside {
|
}).inside {
|
||||||
let mut w = file::open_stream(p, io::Append, io::Write);
|
let mut w = File::open_mode(p, io::Append, io::Write);
|
||||||
w.write(bytes!("/* hi */\n"));
|
w.write(bytes!("/* hi */\n"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -902,7 +893,7 @@ fn package_script_with_default_build() {
|
||||||
let source = Path::new(file!()).dir_path().join_many(
|
let source = Path::new(file!()).dir_path().join_many(
|
||||||
[~"testsuite", ~"pass", ~"src", ~"fancy-lib", ~"pkg.rs"]);
|
[~"testsuite", ~"pass", ~"src", ~"fancy-lib", ~"pkg.rs"]);
|
||||||
debug!("package_script_with_default_build: {}", source.display());
|
debug!("package_script_with_default_build: {}", source.display());
|
||||||
file::copy(&source, &dir.join_many(["src", "fancy-lib-0.1", "pkg.rs"]));
|
File::copy(&source, &dir.join_many(["src", "fancy-lib-0.1", "pkg.rs"]));
|
||||||
command_line_test([~"install", ~"fancy-lib"], dir);
|
command_line_test([~"install", ~"fancy-lib"], dir);
|
||||||
assert_lib_exists(dir, &Path::new("fancy-lib"), NoVersion);
|
assert_lib_exists(dir, &Path::new("fancy-lib"), NoVersion);
|
||||||
assert!(target_build_dir(dir).join_many([~"fancy-lib", ~"generated.rs"]).exists());
|
assert!(target_build_dir(dir).join_many([~"fancy-lib", ~"generated.rs"]).exists());
|
||||||
|
@ -2288,7 +2279,7 @@ fn test_c_dependency_ok() {
|
||||||
debug!("dir = {}", dir.display());
|
debug!("dir = {}", dir.display());
|
||||||
let source = Path::new(file!()).dir_path().join_many(
|
let source = Path::new(file!()).dir_path().join_many(
|
||||||
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
||||||
file::copy(&source, &dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]));
|
File::copy(&source, &dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]));
|
||||||
command_line_test([~"build", ~"cdep"], dir);
|
command_line_test([~"build", ~"cdep"], dir);
|
||||||
assert_executable_exists(dir, "cdep");
|
assert_executable_exists(dir, "cdep");
|
||||||
let out_dir = target_build_dir(dir).join("cdep");
|
let out_dir = target_build_dir(dir).join("cdep");
|
||||||
|
@ -2309,7 +2300,7 @@ fn test_c_dependency_no_rebuilding() {
|
||||||
debug!("dir = {}", dir.display());
|
debug!("dir = {}", dir.display());
|
||||||
let source = Path::new(file!()).dir_path().join_many(
|
let source = Path::new(file!()).dir_path().join_many(
|
||||||
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
||||||
file::copy(&source, &dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]));
|
File::copy(&source, &dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]));
|
||||||
command_line_test([~"build", ~"cdep"], dir);
|
command_line_test([~"build", ~"cdep"], dir);
|
||||||
assert_executable_exists(dir, "cdep");
|
assert_executable_exists(dir, "cdep");
|
||||||
let out_dir = target_build_dir(dir).join("cdep");
|
let out_dir = target_build_dir(dir).join("cdep");
|
||||||
|
@ -2342,7 +2333,7 @@ fn test_c_dependency_yes_rebuilding() {
|
||||||
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
[~"testsuite", ~"pass", ~"src", ~"c-dependencies", ~"pkg.rs"]);
|
||||||
let target = dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]);
|
let target = dir.join_many([~"src", ~"cdep-0.1", ~"pkg.rs"]);
|
||||||
debug!("Copying {} -> {}", source.display(), target.display());
|
debug!("Copying {} -> {}", source.display(), target.display());
|
||||||
file::copy(&source, &target);
|
File::copy(&source, &target);
|
||||||
command_line_test([~"build", ~"cdep"], dir);
|
command_line_test([~"build", ~"cdep"], dir);
|
||||||
assert_executable_exists(dir, "cdep");
|
assert_executable_exists(dir, "cdep");
|
||||||
let out_dir = target_build_dir(dir).join("cdep");
|
let out_dir = target_build_dir(dir).join("cdep");
|
||||||
|
@ -2366,7 +2357,5 @@ fn test_c_dependency_yes_rebuilding() {
|
||||||
|
|
||||||
/// Returns true if p exists and is executable
|
/// Returns true if p exists and is executable
|
||||||
fn is_executable(p: &Path) -> bool {
|
fn is_executable(p: &Path) -> bool {
|
||||||
use std::libc::consts::os::posix88::{S_IXUSR};
|
p.exists() && p.stat().perm & io::UserExec == io::UserExec
|
||||||
|
|
||||||
p.exists() && p.stat().mode & S_IXUSR as u64 == S_IXUSR as u64
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,7 +12,7 @@ extern mod rustpkg;
|
||||||
extern mod rustc;
|
extern mod rustc;
|
||||||
|
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use rustpkg::api;
|
use rustpkg::api;
|
||||||
use rustpkg::version::NoVersion;
|
use rustpkg::version::NoVersion;
|
||||||
|
|
||||||
|
@ -43,7 +43,7 @@ pub fn main() {
|
||||||
let out_path = os::self_exe_path().expect("Couldn't get self_exe path");
|
let out_path = os::self_exe_path().expect("Couldn't get self_exe path");
|
||||||
|
|
||||||
debug!("Writing file");
|
debug!("Writing file");
|
||||||
let mut file = file::create(&out_path.join("generated.rs"));
|
let mut file = File::create(&out_path.join("generated.rs"));
|
||||||
file.write("pub fn wheeeee() { let xs = [1, 2, 3]; \
|
file.write("pub fn wheeeee() { let xs = [1, 2, 3]; \
|
||||||
for _ in xs.iter() { assert!(true); } }".as_bytes());
|
for _ in xs.iter() { assert!(true); } }".as_bytes());
|
||||||
|
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use extra::workcache;
|
use extra::workcache;
|
||||||
use sha1::{Digest, Sha1};
|
use sha1::{Digest, Sha1};
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@ use sha1::{Digest, Sha1};
|
||||||
pub fn digest_file_with_date(path: &Path) -> ~str {
|
pub fn digest_file_with_date(path: &Path) -> ~str {
|
||||||
use conditions::bad_path::cond;
|
use conditions::bad_path::cond;
|
||||||
|
|
||||||
match io::result(|| file::open(path).read_to_end()) {
|
match io::result(|| File::open(path).read_to_end()) {
|
||||||
Ok(bytes) => {
|
Ok(bytes) => {
|
||||||
let mut sha = Sha1::new();
|
let mut sha = Sha1::new();
|
||||||
sha.input(bytes);
|
sha.input(bytes);
|
||||||
|
|
|
@ -11,10 +11,9 @@
|
||||||
use std::ptr::null;
|
use std::ptr::null;
|
||||||
use std::c_str;
|
use std::c_str;
|
||||||
use std::c_str::CString;
|
use std::c_str::CString;
|
||||||
use std::libc::c_void;
|
|
||||||
use std::cast::transmute;
|
use std::cast::transmute;
|
||||||
use std::libc;
|
use std::libc;
|
||||||
use std::libc::{c_int};
|
use std::libc::{c_int, c_char, c_void};
|
||||||
|
|
||||||
use super::{Request, NativeHandle, Loop, FsCallback, Buf,
|
use super::{Request, NativeHandle, Loop, FsCallback, Buf,
|
||||||
status_to_maybe_uv_error, UvError};
|
status_to_maybe_uv_error, UvError};
|
||||||
|
@ -49,12 +48,9 @@ impl FsRequest {
|
||||||
assert_eq!(ret, 0);
|
assert_eq!(ret, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn open_sync(self, loop_: &Loop, path: &CString,
|
pub fn open_sync(mut self, loop_: &Loop, path: &CString,
|
||||||
flags: int, mode: int) -> Result<c_int, UvError> {
|
flags: int, mode: int) -> Result<c_int, UvError> {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(None);
|
||||||
let mut me = self;
|
|
||||||
me.req_boilerplate(None)
|
|
||||||
};
|
|
||||||
let result = path.with_ref(|p| unsafe {
|
let result = path.with_ref(|p| unsafe {
|
||||||
uvll::fs_open(loop_.native_handle(),
|
uvll::fs_open(loop_.native_handle(),
|
||||||
self.native_handle(), p, flags, mode, complete_cb_ptr)
|
self.native_handle(), p, flags, mode, complete_cb_ptr)
|
||||||
|
@ -62,11 +58,8 @@ impl FsRequest {
|
||||||
self.sync_cleanup(result)
|
self.sync_cleanup(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn unlink(self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
pub fn unlink(mut self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let mut me = self;
|
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let ret = path.with_ref(|p| unsafe {
|
let ret = path.with_ref(|p| unsafe {
|
||||||
uvll::fs_unlink(loop_.native_handle(),
|
uvll::fs_unlink(loop_.native_handle(),
|
||||||
self.native_handle(), p, complete_cb_ptr)
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
|
@ -74,12 +67,9 @@ impl FsRequest {
|
||||||
assert_eq!(ret, 0);
|
assert_eq!(ret, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn unlink_sync(self, loop_: &Loop, path: &CString)
|
pub fn unlink_sync(mut self, loop_: &Loop, path: &CString)
|
||||||
-> Result<c_int, UvError> {
|
-> Result<c_int, UvError> {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(None);
|
||||||
let mut me = self;
|
|
||||||
me.req_boilerplate(None)
|
|
||||||
};
|
|
||||||
let result = path.with_ref(|p| unsafe {
|
let result = path.with_ref(|p| unsafe {
|
||||||
uvll::fs_unlink(loop_.native_handle(),
|
uvll::fs_unlink(loop_.native_handle(),
|
||||||
self.native_handle(), p, complete_cb_ptr)
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
|
@ -87,11 +77,17 @@ impl FsRequest {
|
||||||
self.sync_cleanup(result)
|
self.sync_cleanup(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn stat(self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
pub fn lstat(mut self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let mut me = self;
|
let ret = path.with_ref(|p| unsafe {
|
||||||
me.req_boilerplate(Some(cb))
|
uvll::uv_fs_lstat(loop_.native_handle(),
|
||||||
};
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
|
});
|
||||||
|
assert_eq!(ret, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn stat(mut self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let ret = path.with_ref(|p| unsafe {
|
let ret = path.with_ref(|p| unsafe {
|
||||||
uvll::fs_stat(loop_.native_handle(),
|
uvll::fs_stat(loop_.native_handle(),
|
||||||
self.native_handle(), p, complete_cb_ptr)
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
|
@ -99,11 +95,9 @@ impl FsRequest {
|
||||||
assert_eq!(ret, 0);
|
assert_eq!(ret, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn write(self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64, cb: FsCallback) {
|
pub fn write(mut self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64,
|
||||||
let complete_cb_ptr = {
|
cb: FsCallback) {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let base_ptr = buf.base as *c_void;
|
let base_ptr = buf.base as *c_void;
|
||||||
let len = buf.len as uint;
|
let len = buf.len as uint;
|
||||||
let ret = unsafe {
|
let ret = unsafe {
|
||||||
|
@ -113,12 +107,9 @@ impl FsRequest {
|
||||||
};
|
};
|
||||||
assert_eq!(ret, 0);
|
assert_eq!(ret, 0);
|
||||||
}
|
}
|
||||||
pub fn write_sync(self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64)
|
pub fn write_sync(mut self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64)
|
||||||
-> Result<c_int, UvError> {
|
-> Result<c_int, UvError> {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(None);
|
||||||
let mut me = self;
|
|
||||||
me.req_boilerplate(None)
|
|
||||||
};
|
|
||||||
let base_ptr = buf.base as *c_void;
|
let base_ptr = buf.base as *c_void;
|
||||||
let len = buf.len as uint;
|
let len = buf.len as uint;
|
||||||
let result = unsafe {
|
let result = unsafe {
|
||||||
|
@ -129,11 +120,9 @@ impl FsRequest {
|
||||||
self.sync_cleanup(result)
|
self.sync_cleanup(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn read(self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64, cb: FsCallback) {
|
pub fn read(mut self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64,
|
||||||
let complete_cb_ptr = {
|
cb: FsCallback) {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let buf_ptr = buf.base as *c_void;
|
let buf_ptr = buf.base as *c_void;
|
||||||
let len = buf.len as uint;
|
let len = buf.len as uint;
|
||||||
let ret = unsafe {
|
let ret = unsafe {
|
||||||
|
@ -143,12 +132,9 @@ impl FsRequest {
|
||||||
};
|
};
|
||||||
assert_eq!(ret, 0);
|
assert_eq!(ret, 0);
|
||||||
}
|
}
|
||||||
pub fn read_sync(self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64)
|
pub fn read_sync(mut self, loop_: &Loop, fd: c_int, buf: Buf, offset: i64)
|
||||||
-> Result<c_int, UvError> {
|
-> Result<c_int, UvError> {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(None);
|
||||||
let mut me = self;
|
|
||||||
me.req_boilerplate(None)
|
|
||||||
};
|
|
||||||
let buf_ptr = buf.base as *c_void;
|
let buf_ptr = buf.base as *c_void;
|
||||||
let len = buf.len as uint;
|
let len = buf.len as uint;
|
||||||
let result = unsafe {
|
let result = unsafe {
|
||||||
|
@ -159,22 +145,16 @@ impl FsRequest {
|
||||||
self.sync_cleanup(result)
|
self.sync_cleanup(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn close(self, loop_: &Loop, fd: c_int, cb: FsCallback) {
|
pub fn close(mut self, loop_: &Loop, fd: c_int, cb: FsCallback) {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let mut me = self;
|
assert_eq!(unsafe {
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let ret = unsafe {
|
|
||||||
uvll::fs_close(loop_.native_handle(), self.native_handle(),
|
uvll::fs_close(loop_.native_handle(), self.native_handle(),
|
||||||
fd, complete_cb_ptr)
|
fd, complete_cb_ptr)
|
||||||
};
|
}, 0);
|
||||||
assert_eq!(ret, 0);
|
|
||||||
}
|
}
|
||||||
pub fn close_sync(self, loop_: &Loop, fd: c_int) -> Result<c_int, UvError> {
|
pub fn close_sync(mut self, loop_: &Loop,
|
||||||
let complete_cb_ptr = {
|
fd: c_int) -> Result<c_int, UvError> {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(None);
|
||||||
me.req_boilerplate(None)
|
|
||||||
};
|
|
||||||
let result = unsafe {
|
let result = unsafe {
|
||||||
uvll::fs_close(loop_.native_handle(), self.native_handle(),
|
uvll::fs_close(loop_.native_handle(), self.native_handle(),
|
||||||
fd, complete_cb_ptr)
|
fd, complete_cb_ptr)
|
||||||
|
@ -182,68 +162,119 @@ impl FsRequest {
|
||||||
self.sync_cleanup(result)
|
self.sync_cleanup(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn mkdir(self, loop_: &Loop, path: &CString, mode: c_int, cb: FsCallback) {
|
pub fn mkdir(mut self, loop_: &Loop, path: &CString, mode: c_int,
|
||||||
let complete_cb_ptr = {
|
cb: FsCallback) {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
me.req_boilerplate(Some(cb))
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
};
|
|
||||||
let ret = path.with_ref(|p| unsafe {
|
|
||||||
uvll::fs_mkdir(loop_.native_handle(),
|
uvll::fs_mkdir(loop_.native_handle(),
|
||||||
self.native_handle(), p, mode, complete_cb_ptr)
|
self.native_handle(), p, mode, complete_cb_ptr)
|
||||||
});
|
}), 0);
|
||||||
assert_eq!(ret, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn rmdir(self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
pub fn rmdir(mut self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let mut me = self;
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let ret = path.with_ref(|p| unsafe {
|
|
||||||
uvll::fs_rmdir(loop_.native_handle(),
|
uvll::fs_rmdir(loop_.native_handle(),
|
||||||
self.native_handle(), p, complete_cb_ptr)
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
});
|
}), 0);
|
||||||
assert_eq!(ret, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn rename(self, loop_: &Loop, path: &CString, to: &CString, cb: FsCallback) {
|
pub fn rename(mut self, loop_: &Loop, path: &CString, to: &CString,
|
||||||
let complete_cb_ptr = {
|
cb: FsCallback) {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
me.req_boilerplate(Some(cb))
|
assert_eq!(unsafe {
|
||||||
};
|
|
||||||
let ret = unsafe {
|
|
||||||
uvll::fs_rename(loop_.native_handle(),
|
uvll::fs_rename(loop_.native_handle(),
|
||||||
self.native_handle(),
|
self.native_handle(),
|
||||||
path.with_ref(|p| p),
|
path.with_ref(|p| p),
|
||||||
to.with_ref(|p| p),
|
to.with_ref(|p| p),
|
||||||
complete_cb_ptr)
|
complete_cb_ptr)
|
||||||
};
|
}, 0);
|
||||||
assert_eq!(ret, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn chmod(self, loop_: &Loop, path: &CString, mode: c_int, cb: FsCallback) {
|
pub fn chmod(mut self, loop_: &Loop, path: &CString, mode: c_int,
|
||||||
let complete_cb_ptr = {
|
cb: FsCallback) {
|
||||||
let mut me = self;
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
me.req_boilerplate(Some(cb))
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
};
|
|
||||||
let ret = path.with_ref(|p| unsafe {
|
|
||||||
uvll::fs_chmod(loop_.native_handle(), self.native_handle(), p, mode,
|
uvll::fs_chmod(loop_.native_handle(), self.native_handle(), p, mode,
|
||||||
complete_cb_ptr)
|
complete_cb_ptr)
|
||||||
});
|
}), 0);
|
||||||
assert_eq!(ret, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn readdir(self, loop_: &Loop, path: &CString,
|
pub fn readdir(mut self, loop_: &Loop, path: &CString,
|
||||||
flags: c_int, cb: FsCallback) {
|
flags: c_int, cb: FsCallback) {
|
||||||
let complete_cb_ptr = {
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
let mut me = self;
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
me.req_boilerplate(Some(cb))
|
|
||||||
};
|
|
||||||
let ret = path.with_ref(|p| unsafe {
|
|
||||||
uvll::fs_readdir(loop_.native_handle(),
|
uvll::fs_readdir(loop_.native_handle(),
|
||||||
self.native_handle(), p, flags, complete_cb_ptr)
|
self.native_handle(), p, flags, complete_cb_ptr)
|
||||||
});
|
}), 0);
|
||||||
assert_eq!(ret, 0);
|
}
|
||||||
|
|
||||||
|
pub fn readlink(mut self, loop_: &Loop, path: &CString, cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
|
uvll::uv_fs_readlink(loop_.native_handle(),
|
||||||
|
self.native_handle(), p, complete_cb_ptr)
|
||||||
|
}), 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn chown(mut self, loop_: &Loop, path: &CString, uid: int, gid: int,
|
||||||
|
cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(path.with_ref(|p| unsafe {
|
||||||
|
uvll::uv_fs_chown(loop_.native_handle(),
|
||||||
|
self.native_handle(), p,
|
||||||
|
uid as uvll::uv_uid_t,
|
||||||
|
gid as uvll::uv_gid_t,
|
||||||
|
complete_cb_ptr)
|
||||||
|
}), 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn truncate(mut self, loop_: &Loop, file: c_int, offset: i64,
|
||||||
|
cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(unsafe {
|
||||||
|
uvll::uv_fs_ftruncate(loop_.native_handle(),
|
||||||
|
self.native_handle(), file, offset,
|
||||||
|
complete_cb_ptr)
|
||||||
|
}, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn link(mut self, loop_: &Loop, src: &CString, dst: &CString,
|
||||||
|
cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(unsafe {
|
||||||
|
uvll::uv_fs_link(loop_.native_handle(), self.native_handle(),
|
||||||
|
src.with_ref(|p| p),
|
||||||
|
dst.with_ref(|p| p),
|
||||||
|
complete_cb_ptr)
|
||||||
|
}, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn symlink(mut self, loop_: &Loop, src: &CString, dst: &CString,
|
||||||
|
cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(unsafe {
|
||||||
|
uvll::uv_fs_symlink(loop_.native_handle(), self.native_handle(),
|
||||||
|
src.with_ref(|p| p),
|
||||||
|
dst.with_ref(|p| p),
|
||||||
|
complete_cb_ptr)
|
||||||
|
}, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn fsync(mut self, loop_: &Loop, fd: c_int, cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(unsafe {
|
||||||
|
uvll::uv_fs_fsync(loop_.native_handle(), self.native_handle(), fd,
|
||||||
|
complete_cb_ptr)
|
||||||
|
}, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn datasync(mut self, loop_: &Loop, fd: c_int, cb: FsCallback) {
|
||||||
|
let complete_cb_ptr = self.req_boilerplate(Some(cb));
|
||||||
|
assert_eq!(unsafe {
|
||||||
|
uvll::uv_fs_fdatasync(loop_.native_handle(), self.native_handle(), fd,
|
||||||
|
complete_cb_ptr)
|
||||||
|
}, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// accessors/utility funcs
|
// accessors/utility funcs
|
||||||
|
@ -284,10 +315,12 @@ impl FsRequest {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_result(&mut self) -> c_int {
|
pub fn get_path(&self) -> *c_char {
|
||||||
unsafe {
|
unsafe { uvll::get_path_from_fs_req(self.native_handle()) }
|
||||||
uvll::get_result_from_fs_req(self.native_handle())
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn get_result(&self) -> c_int {
|
||||||
|
unsafe { uvll::get_result_from_fs_req(self.native_handle()) }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_loop(&self) -> Loop {
|
pub fn get_loop(&self) -> Loop {
|
||||||
|
@ -380,7 +413,7 @@ extern fn compl_cb(req: *uv_fs_t) {
|
||||||
mod test {
|
mod test {
|
||||||
use super::*;
|
use super::*;
|
||||||
//use std::rt::test::*;
|
//use std::rt::test::*;
|
||||||
use std::libc::{STDOUT_FILENO};
|
use std::libc::{STDOUT_FILENO, c_int};
|
||||||
use std::vec;
|
use std::vec;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::unstable::run_in_bare_thread;
|
use std::unstable::run_in_bare_thread;
|
||||||
|
|
|
@ -8,18 +8,15 @@
|
||||||
// option. This file may not be copied, modified, or distributed
|
// option. This file may not be copied, modified, or distributed
|
||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
use std::c_str::{ToCStr, CString};
|
use std::c_str::CString;
|
||||||
use std::cast::transmute;
|
use std::cast::transmute;
|
||||||
use std::cast;
|
use std::cast;
|
||||||
use std::cell::Cell;
|
use std::cell::Cell;
|
||||||
use std::clone::Clone;
|
|
||||||
use std::comm::{SendDeferred, SharedChan, Port, PortOne, GenericChan};
|
use std::comm::{SendDeferred, SharedChan, Port, PortOne, GenericChan};
|
||||||
|
use std::libc;
|
||||||
use std::libc::{c_int, c_uint, c_void, pid_t};
|
use std::libc::{c_int, c_uint, c_void, pid_t};
|
||||||
use std::ops::Drop;
|
|
||||||
use std::option::*;
|
|
||||||
use std::ptr;
|
use std::ptr;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::result::*;
|
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::IoError;
|
use std::rt::io::IoError;
|
||||||
use std::rt::io::net::ip::{SocketAddr, IpAddr};
|
use std::rt::io::net::ip::{SocketAddr, IpAddr};
|
||||||
|
@ -33,22 +30,16 @@ use std::rt::sched::{Scheduler, SchedHandle};
|
||||||
use std::rt::tube::Tube;
|
use std::rt::tube::Tube;
|
||||||
use std::rt::task::Task;
|
use std::rt::task::Task;
|
||||||
use std::unstable::sync::Exclusive;
|
use std::unstable::sync::Exclusive;
|
||||||
use std::path::{GenericPath, Path};
|
use std::libc::{lseek, off_t};
|
||||||
use std::libc::{lseek, off_t, O_CREAT, O_APPEND, O_TRUNC, O_RDWR, O_RDONLY,
|
use std::rt::io::{FileMode, FileAccess, FileStat};
|
||||||
O_WRONLY, S_IRUSR, S_IWUSR};
|
|
||||||
use std::rt::io::{FileMode, FileAccess, OpenOrCreate, Open, Create,
|
|
||||||
CreateOrTruncate, Append, Truncate, Read, Write, ReadWrite,
|
|
||||||
FileStat};
|
|
||||||
use std::rt::io::signal::Signum;
|
use std::rt::io::signal::Signum;
|
||||||
use std::task;
|
use std::task;
|
||||||
use ai = std::rt::io::net::addrinfo;
|
use ai = std::rt::io::net::addrinfo;
|
||||||
|
|
||||||
#[cfg(test)] use std::container::Container;
|
|
||||||
#[cfg(test)] use std::unstable::run_in_bare_thread;
|
#[cfg(test)] use std::unstable::run_in_bare_thread;
|
||||||
#[cfg(test)] use std::rt::test::{spawntask,
|
#[cfg(test)] use std::rt::test::{spawntask,
|
||||||
next_test_ip4,
|
next_test_ip4,
|
||||||
run_in_mt_newsched_task};
|
run_in_mt_newsched_task};
|
||||||
#[cfg(test)] use std::iter::{Iterator, range};
|
|
||||||
#[cfg(test)] use std::rt::comm::oneshot;
|
#[cfg(test)] use std::rt::comm::oneshot;
|
||||||
|
|
||||||
use super::*;
|
use super::*;
|
||||||
|
@ -418,24 +409,25 @@ impl UvIoFactory {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Helper for a variety of simple uv_fs_* functions that
|
/// Helper for a variety of simple uv_fs_* functions that have no ret val. This
|
||||||
/// have no ret val
|
/// function takes the loop that it will act on, and then invokes the specified
|
||||||
fn uv_fs_helper(loop_: &mut Loop, path: &CString,
|
/// callback in a situation where the task wil be immediately blocked
|
||||||
cb: ~fn(&mut FsRequest, &mut Loop, &CString,
|
/// afterwards. The `FsCallback` yielded must be invoked to reschedule the task
|
||||||
~fn(&FsRequest, Option<UvError>)))
|
/// (once the result of the operation is known).
|
||||||
-> Result<(), IoError> {
|
fn uv_fs_helper<T>(loop_: &mut Loop,
|
||||||
|
retfn: extern "Rust" fn(&mut FsRequest) -> T,
|
||||||
|
cb: &fn(&mut FsRequest, &mut Loop, FsCallback))
|
||||||
|
-> Result<T, IoError> {
|
||||||
let result_cell = Cell::new_empty();
|
let result_cell = Cell::new_empty();
|
||||||
let result_cell_ptr: *Cell<Result<(), IoError>> = &result_cell;
|
let result_cell_ptr: *Cell<Result<T, IoError>> = &result_cell;
|
||||||
let path_cell = Cell::new(path);
|
|
||||||
do task::unkillable { // FIXME(#8674)
|
do task::unkillable { // FIXME(#8674)
|
||||||
let scheduler: ~Scheduler = Local::take();
|
let scheduler: ~Scheduler = Local::take();
|
||||||
let mut new_req = FsRequest::new();
|
let mut new_req = FsRequest::new();
|
||||||
do scheduler.deschedule_running_task_and_then |_, task| {
|
do scheduler.deschedule_running_task_and_then |_, task| {
|
||||||
let task_cell = Cell::new(task);
|
let task_cell = Cell::new(task);
|
||||||
let path = path_cell.take();
|
do cb(&mut new_req, loop_) |req, err| {
|
||||||
do cb(&mut new_req, loop_, path) |_, err| {
|
|
||||||
let res = match err {
|
let res = match err {
|
||||||
None => Ok(()),
|
None => Ok(retfn(req)),
|
||||||
Some(err) => Err(uv_error_to_io_error(err))
|
Some(err) => Err(uv_error_to_io_error(err))
|
||||||
};
|
};
|
||||||
unsafe { (*result_cell_ptr).put_back(res); }
|
unsafe { (*result_cell_ptr).put_back(res); }
|
||||||
|
@ -448,6 +440,43 @@ fn uv_fs_helper(loop_: &mut Loop, path: &CString,
|
||||||
return result_cell.take();
|
return result_cell.take();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn unit(_: &mut FsRequest) {}
|
||||||
|
|
||||||
|
fn fs_mkstat(f: &mut FsRequest) -> FileStat {
|
||||||
|
let path = unsafe { Path::new(CString::new(f.get_path(), false)) };
|
||||||
|
let stat = f.get_stat();
|
||||||
|
fn to_msec(stat: uvll::uv_timespec_t) -> u64 {
|
||||||
|
(stat.tv_sec * 1000 + stat.tv_nsec / 1000000) as u64
|
||||||
|
}
|
||||||
|
let kind = match (stat.st_mode as c_int) & libc::S_IFMT {
|
||||||
|
libc::S_IFREG => io::TypeFile,
|
||||||
|
libc::S_IFDIR => io::TypeDirectory,
|
||||||
|
libc::S_IFIFO => io::TypeNamedPipe,
|
||||||
|
libc::S_IFBLK => io::TypeBlockSpecial,
|
||||||
|
libc::S_IFLNK => io::TypeSymlink,
|
||||||
|
_ => io::TypeUnknown,
|
||||||
|
};
|
||||||
|
FileStat {
|
||||||
|
path: path,
|
||||||
|
size: stat.st_size as u64,
|
||||||
|
kind: kind,
|
||||||
|
perm: (stat.st_mode as io::FilePermission) & io::AllPermissions,
|
||||||
|
created: to_msec(stat.st_birthtim),
|
||||||
|
modified: to_msec(stat.st_mtim),
|
||||||
|
accessed: to_msec(stat.st_atim),
|
||||||
|
device: stat.st_dev as u64,
|
||||||
|
inode: stat.st_ino as u64,
|
||||||
|
rdev: stat.st_rdev as u64,
|
||||||
|
nlink: stat.st_nlink as u64,
|
||||||
|
uid: stat.st_uid as u64,
|
||||||
|
gid: stat.st_gid as u64,
|
||||||
|
blksize: stat.st_blksize as u64,
|
||||||
|
blocks: stat.st_blocks as u64,
|
||||||
|
flags: stat.st_flags as u64,
|
||||||
|
gen: stat.st_gen as u64,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl IoFactory for UvIoFactory {
|
impl IoFactory for UvIoFactory {
|
||||||
// Connect to an address and return a new stream
|
// Connect to an address and return a new stream
|
||||||
// NB: This blocks the task waiting on the connection.
|
// NB: This blocks the task waiting on the connection.
|
||||||
|
@ -552,120 +581,6 @@ impl IoFactory for UvIoFactory {
|
||||||
Ok(~UvTimer::new(watcher, home) as ~RtioTimer)
|
Ok(~UvTimer::new(watcher, home) as ~RtioTimer)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fs_from_raw_fd(&mut self, fd: c_int, close: CloseBehavior) -> ~RtioFileStream {
|
|
||||||
let loop_ = Loop {handle: self.uv_loop().native_handle()};
|
|
||||||
let home = get_handle_to_current_scheduler!();
|
|
||||||
~UvFileStream::new(loop_, fd, close, home) as ~RtioFileStream
|
|
||||||
}
|
|
||||||
|
|
||||||
fn fs_open(&mut self, path: &CString, fm: FileMode, fa: FileAccess)
|
|
||||||
-> Result<~RtioFileStream, IoError> {
|
|
||||||
let mut flags = match fm {
|
|
||||||
Open => 0,
|
|
||||||
Create => O_CREAT,
|
|
||||||
OpenOrCreate => O_CREAT,
|
|
||||||
Append => O_APPEND,
|
|
||||||
Truncate => O_TRUNC,
|
|
||||||
CreateOrTruncate => O_TRUNC | O_CREAT
|
|
||||||
};
|
|
||||||
flags = match fa {
|
|
||||||
Read => flags | O_RDONLY,
|
|
||||||
Write => flags | O_WRONLY,
|
|
||||||
ReadWrite => flags | O_RDWR
|
|
||||||
};
|
|
||||||
let create_mode = match fm {
|
|
||||||
Create|OpenOrCreate|CreateOrTruncate =>
|
|
||||||
S_IRUSR | S_IWUSR,
|
|
||||||
_ => 0
|
|
||||||
};
|
|
||||||
let result_cell = Cell::new_empty();
|
|
||||||
let result_cell_ptr: *Cell<Result<~RtioFileStream,
|
|
||||||
IoError>> = &result_cell;
|
|
||||||
let path_cell = Cell::new(path);
|
|
||||||
do task::unkillable { // FIXME(#8674)
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
let open_req = file::FsRequest::new();
|
|
||||||
do scheduler.deschedule_running_task_and_then |_, task| {
|
|
||||||
let task_cell = Cell::new(task);
|
|
||||||
let path = path_cell.take();
|
|
||||||
do open_req.open(self.uv_loop(), path, flags as int, create_mode as int)
|
|
||||||
|req,err| {
|
|
||||||
if err.is_none() {
|
|
||||||
let loop_ = Loop {handle: req.get_loop().native_handle()};
|
|
||||||
let home = get_handle_to_current_scheduler!();
|
|
||||||
let fd = req.get_result() as c_int;
|
|
||||||
let fs = ~UvFileStream::new(
|
|
||||||
loop_, fd, CloseSynchronously, home) as ~RtioFileStream;
|
|
||||||
let res = Ok(fs);
|
|
||||||
unsafe { (*result_cell_ptr).put_back(res); }
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
scheduler.resume_blocked_task_immediately(task_cell.take());
|
|
||||||
} else {
|
|
||||||
let res = Err(uv_error_to_io_error(err.unwrap()));
|
|
||||||
unsafe { (*result_cell_ptr).put_back(res); }
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
scheduler.resume_blocked_task_immediately(task_cell.take());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
assert!(!result_cell.is_empty());
|
|
||||||
return result_cell.take();
|
|
||||||
}
|
|
||||||
|
|
||||||
fn fs_unlink(&mut self, path: &CString) -> Result<(), IoError> {
|
|
||||||
do uv_fs_helper(self.uv_loop(), path) |unlink_req, l, p, cb| {
|
|
||||||
do unlink_req.unlink(l, p) |req, err| {
|
|
||||||
cb(req, err)
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fn fs_stat(&mut self, path: &CString) -> Result<FileStat, IoError> {
|
|
||||||
use str::StrSlice;
|
|
||||||
let result_cell = Cell::new_empty();
|
|
||||||
let result_cell_ptr: *Cell<Result<FileStat,
|
|
||||||
IoError>> = &result_cell;
|
|
||||||
let path_cell = Cell::new(path);
|
|
||||||
do task::unkillable { // FIXME(#8674)
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
let stat_req = file::FsRequest::new();
|
|
||||||
do scheduler.deschedule_running_task_and_then |_, task| {
|
|
||||||
let task_cell = Cell::new(task);
|
|
||||||
let path = path_cell.take();
|
|
||||||
// Don't pick up the null byte
|
|
||||||
let slice = path.as_bytes().slice(0, path.len());
|
|
||||||
let path_instance = Cell::new(Path::new(slice));
|
|
||||||
do stat_req.stat(self.uv_loop(), path) |req,err| {
|
|
||||||
let res = match err {
|
|
||||||
None => {
|
|
||||||
let stat = req.get_stat();
|
|
||||||
Ok(FileStat {
|
|
||||||
path: path_instance.take(),
|
|
||||||
is_file: stat.is_file(),
|
|
||||||
is_dir: stat.is_dir(),
|
|
||||||
device: stat.st_dev,
|
|
||||||
mode: stat.st_mode,
|
|
||||||
inode: stat.st_ino,
|
|
||||||
size: stat.st_size,
|
|
||||||
created: stat.st_ctim.tv_sec as u64,
|
|
||||||
modified: stat.st_mtim.tv_sec as u64,
|
|
||||||
accessed: stat.st_atim.tv_sec as u64
|
|
||||||
})
|
|
||||||
},
|
|
||||||
Some(e) => {
|
|
||||||
Err(uv_error_to_io_error(e))
|
|
||||||
}
|
|
||||||
};
|
|
||||||
unsafe { (*result_cell_ptr).put_back(res); }
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
scheduler.resume_blocked_task_immediately(task_cell.take());
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
assert!(!result_cell.is_empty());
|
|
||||||
return result_cell.take();
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_host_addresses(&mut self, host: Option<&str>, servname: Option<&str>,
|
fn get_host_addresses(&mut self, host: Option<&str>, servname: Option<&str>,
|
||||||
hint: Option<ai::Hint>) -> Result<~[ai::Info], IoError> {
|
hint: Option<ai::Hint>) -> Result<~[ai::Info], IoError> {
|
||||||
let result_cell = Cell::new_empty();
|
let result_cell = Cell::new_empty();
|
||||||
|
@ -700,39 +615,98 @@ impl IoFactory for UvIoFactory {
|
||||||
assert!(!result_cell.is_empty());
|
assert!(!result_cell.is_empty());
|
||||||
return result_cell.take();
|
return result_cell.take();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn fs_from_raw_fd(&mut self, fd: c_int, close: CloseBehavior) -> ~RtioFileStream {
|
||||||
|
let loop_ = Loop {handle: self.uv_loop().native_handle()};
|
||||||
|
let home = get_handle_to_current_scheduler!();
|
||||||
|
~UvFileStream::new(loop_, fd, close, home) as ~RtioFileStream
|
||||||
|
}
|
||||||
|
|
||||||
|
fn fs_open(&mut self, path: &CString, fm: FileMode, fa: FileAccess)
|
||||||
|
-> Result<~RtioFileStream, IoError> {
|
||||||
|
let flags = match fm {
|
||||||
|
io::Open => 0,
|
||||||
|
io::Append => libc::O_APPEND,
|
||||||
|
io::Truncate => libc::O_TRUNC,
|
||||||
|
};
|
||||||
|
// Opening with a write permission must silently create the file.
|
||||||
|
let (flags, mode) = match fa {
|
||||||
|
io::Read => (flags | libc::O_RDONLY, 0),
|
||||||
|
io::Write => (flags | libc::O_WRONLY | libc::O_CREAT,
|
||||||
|
libc::S_IRUSR | libc::S_IWUSR),
|
||||||
|
io::ReadWrite => (flags | libc::O_RDWR | libc::O_CREAT,
|
||||||
|
libc::S_IRUSR | libc::S_IWUSR),
|
||||||
|
};
|
||||||
|
let result_cell = Cell::new_empty();
|
||||||
|
let result_cell_ptr: *Cell<Result<~RtioFileStream,
|
||||||
|
IoError>> = &result_cell;
|
||||||
|
do task::unkillable { // FIXME(#8674)
|
||||||
|
let scheduler: ~Scheduler = Local::take();
|
||||||
|
let open_req = file::FsRequest::new();
|
||||||
|
do scheduler.deschedule_running_task_and_then |_, task| {
|
||||||
|
let task_cell = Cell::new(task);
|
||||||
|
do open_req.open(self.uv_loop(), path, flags as int, mode as int)
|
||||||
|
|req,err| {
|
||||||
|
if err.is_none() {
|
||||||
|
let loop_ = Loop {handle: req.get_loop().native_handle()};
|
||||||
|
let home = get_handle_to_current_scheduler!();
|
||||||
|
let fd = req.get_result() as c_int;
|
||||||
|
let fs = ~UvFileStream::new(
|
||||||
|
loop_, fd, CloseSynchronously, home) as ~RtioFileStream;
|
||||||
|
let res = Ok(fs);
|
||||||
|
unsafe { (*result_cell_ptr).put_back(res); }
|
||||||
|
let scheduler: ~Scheduler = Local::take();
|
||||||
|
scheduler.resume_blocked_task_immediately(task_cell.take());
|
||||||
|
} else {
|
||||||
|
let res = Err(uv_error_to_io_error(err.unwrap()));
|
||||||
|
unsafe { (*result_cell_ptr).put_back(res); }
|
||||||
|
let scheduler: ~Scheduler = Local::take();
|
||||||
|
scheduler.resume_blocked_task_immediately(task_cell.take());
|
||||||
|
}
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
assert!(!result_cell.is_empty());
|
||||||
|
return result_cell.take();
|
||||||
|
}
|
||||||
|
|
||||||
|
fn fs_unlink(&mut self, path: &CString) -> Result<(), IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
|
req.unlink(l, path, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn fs_lstat(&mut self, path: &CString) -> Result<FileStat, IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), fs_mkstat) |req, l, cb| {
|
||||||
|
req.lstat(l, path, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn fs_stat(&mut self, path: &CString) -> Result<FileStat, IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), fs_mkstat) |req, l, cb| {
|
||||||
|
req.stat(l, path, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
fn fs_mkdir(&mut self, path: &CString,
|
fn fs_mkdir(&mut self, path: &CString,
|
||||||
perm: io::FilePermission) -> Result<(), IoError> {
|
perm: io::FilePermission) -> Result<(), IoError> {
|
||||||
do uv_fs_helper(self.uv_loop(), path) |mkdir_req, l, p, cb| {
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
do mkdir_req.mkdir(l, p, perm as c_int) |req, err| {
|
req.mkdir(l, path, perm as c_int, cb)
|
||||||
cb(req, err)
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fn fs_rmdir(&mut self, path: &CString) -> Result<(), IoError> {
|
fn fs_rmdir(&mut self, path: &CString) -> Result<(), IoError> {
|
||||||
do uv_fs_helper(self.uv_loop(), path) |rmdir_req, l, p, cb| {
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
do rmdir_req.rmdir(l, p) |req, err| {
|
req.rmdir(l, path, cb)
|
||||||
cb(req, err)
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fn fs_rename(&mut self, path: &CString, to: &CString) -> Result<(), IoError> {
|
fn fs_rename(&mut self, path: &CString, to: &CString) -> Result<(), IoError> {
|
||||||
let to = to.with_ref(|p| p);
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
do uv_fs_helper(self.uv_loop(), path) |rename_req, l, p, cb| {
|
req.rename(l, path, to, cb)
|
||||||
let to = unsafe { CString::new(to, false) };
|
|
||||||
do rename_req.rename(l, p, &to) |req, err| {
|
|
||||||
cb(req, err)
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fn fs_chmod(&mut self, path: &CString,
|
fn fs_chmod(&mut self, path: &CString,
|
||||||
perm: io::FilePermission) -> Result<(), IoError> {
|
perm: io::FilePermission) -> Result<(), IoError> {
|
||||||
do uv_fs_helper(self.uv_loop(), path) |chmod_req, l, p, cb| {
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
do chmod_req.chmod(l, p, perm as c_int) |req, err| {
|
req.chmod(l, path, perm as c_int, cb)
|
||||||
cb(req, err)
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
>>>>>>> Remove all blocking std::os blocking functions
|
|
||||||
fn fs_readdir(&mut self, path: &CString, flags: c_int) ->
|
fn fs_readdir(&mut self, path: &CString, flags: c_int) ->
|
||||||
Result<~[Path], IoError> {
|
Result<~[Path], IoError> {
|
||||||
use str::StrSlice;
|
use str::StrSlice;
|
||||||
|
@ -773,6 +747,29 @@ impl IoFactory for UvIoFactory {
|
||||||
assert!(!result_cell.is_empty());
|
assert!(!result_cell.is_empty());
|
||||||
return result_cell.take();
|
return result_cell.take();
|
||||||
}
|
}
|
||||||
|
fn fs_link(&mut self, src: &CString, dst: &CString) -> Result<(), IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
|
req.link(l, src, dst, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn fs_symlink(&mut self, src: &CString, dst: &CString) -> Result<(), IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
|
req.symlink(l, src, dst, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn fs_chown(&mut self, path: &CString, uid: int, gid: int) -> Result<(), IoError> {
|
||||||
|
do uv_fs_helper(self.uv_loop(), unit) |req, l, cb| {
|
||||||
|
req.chown(l, path, uid, gid, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn fs_readlink(&mut self, path: &CString) -> Result<Path, IoError> {
|
||||||
|
fn getlink(f: &mut FsRequest) -> Path {
|
||||||
|
Path::new(unsafe { CString::new(f.get_path(), false) })
|
||||||
|
}
|
||||||
|
do uv_fs_helper(self.uv_loop(), getlink) |req, l, cb| {
|
||||||
|
req.readlink(l, path, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn spawn(&mut self, config: ProcessConfig)
|
fn spawn(&mut self, config: ProcessConfig)
|
||||||
-> Result<(~RtioProcess, ~[Option<~RtioPipe>]), IoError>
|
-> Result<(~RtioProcess, ~[Option<~RtioPipe>]), IoError>
|
||||||
|
@ -1581,27 +1578,10 @@ impl UvFileStream {
|
||||||
result_cell.take()
|
result_cell.take()
|
||||||
}
|
}
|
||||||
fn base_write(&mut self, buf: &[u8], offset: i64) -> Result<(), IoError> {
|
fn base_write(&mut self, buf: &[u8], offset: i64) -> Result<(), IoError> {
|
||||||
let result_cell = Cell::new_empty();
|
do self.nop_req |self_, req, cb| {
|
||||||
let result_cell_ptr: *Cell<Result<(), IoError>> = &result_cell;
|
req.write(&self_.loop_, self_.fd, slice_to_uv_buf(buf), offset, cb)
|
||||||
let buf_ptr: *&[u8] = &buf;
|
|
||||||
do self.home_for_io_with_sched |self_, scheduler| {
|
|
||||||
do scheduler.deschedule_running_task_and_then |_, task| {
|
|
||||||
let buf = unsafe { slice_to_uv_buf(*buf_ptr) };
|
|
||||||
let task_cell = Cell::new(task);
|
|
||||||
let write_req = file::FsRequest::new();
|
|
||||||
do write_req.write(&self_.loop_, self_.fd, buf, offset) |_, uverr| {
|
|
||||||
let res = match uverr {
|
|
||||||
None => Ok(()),
|
|
||||||
Some(err) => Err(uv_error_to_io_error(err))
|
|
||||||
};
|
|
||||||
unsafe { (*result_cell_ptr).put_back(res); }
|
|
||||||
let scheduler: ~Scheduler = Local::take();
|
|
||||||
scheduler.resume_blocked_task_immediately(task_cell.take());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
result_cell.take()
|
|
||||||
}
|
|
||||||
fn seek_common(&mut self, pos: i64, whence: c_int) ->
|
fn seek_common(&mut self, pos: i64, whence: c_int) ->
|
||||||
Result<u64, IoError>{
|
Result<u64, IoError>{
|
||||||
#[fixed_stack_segment]; #[inline(never)];
|
#[fixed_stack_segment]; #[inline(never)];
|
||||||
|
@ -1618,6 +1598,27 @@ impl UvFileStream {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
fn nop_req(&mut self, f: &fn(&mut UvFileStream, file::FsRequest, FsCallback))
|
||||||
|
-> Result<(), IoError> {
|
||||||
|
let result_cell = Cell::new_empty();
|
||||||
|
let result_cell_ptr: *Cell<Result<(), IoError>> = &result_cell;
|
||||||
|
do self.home_for_io_with_sched |self_, sched| {
|
||||||
|
do sched.deschedule_running_task_and_then |_, task| {
|
||||||
|
let task = Cell::new(task);
|
||||||
|
let req = file::FsRequest::new();
|
||||||
|
do f(self_, req) |_, uverr| {
|
||||||
|
let res = match uverr {
|
||||||
|
None => Ok(()),
|
||||||
|
Some(err) => Err(uv_error_to_io_error(err))
|
||||||
|
};
|
||||||
|
unsafe { (*result_cell_ptr).put_back(res); }
|
||||||
|
let scheduler: ~Scheduler = Local::take();
|
||||||
|
scheduler.resume_blocked_task_immediately(task.take());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
result_cell.take()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Drop for UvFileStream {
|
impl Drop for UvFileStream {
|
||||||
|
@ -1672,6 +1673,21 @@ impl RtioFileStream for UvFileStream {
|
||||||
let self_ = unsafe { cast::transmute::<&UvFileStream, &mut UvFileStream>(self) };
|
let self_ = unsafe { cast::transmute::<&UvFileStream, &mut UvFileStream>(self) };
|
||||||
self_.seek_common(0, SEEK_CUR)
|
self_.seek_common(0, SEEK_CUR)
|
||||||
}
|
}
|
||||||
|
fn fsync(&mut self) -> Result<(), IoError> {
|
||||||
|
do self.nop_req |self_, req, cb| {
|
||||||
|
req.fsync(&self_.loop_, self_.fd, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn datasync(&mut self) -> Result<(), IoError> {
|
||||||
|
do self.nop_req |self_, req, cb| {
|
||||||
|
req.datasync(&self_.loop_, self_.fd, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn truncate(&mut self, offset: i64) -> Result<(), IoError> {
|
||||||
|
do self.nop_req |self_, req, cb| {
|
||||||
|
req.truncate(&self_.loop_, self_.fd, offset, cb)
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct UvProcess {
|
pub struct UvProcess {
|
||||||
|
@ -2489,13 +2505,13 @@ fn test_timer_sleep_simple() {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn file_test_uvio_full_simple_impl() {
|
fn file_test_uvio_full_simple_impl() {
|
||||||
use std::rt::io::{Open, Create, ReadWrite, Read};
|
use std::rt::io::{Open, ReadWrite, Read};
|
||||||
unsafe {
|
unsafe {
|
||||||
let io = local_io();
|
let io = local_io();
|
||||||
let write_val = "hello uvio!";
|
let write_val = "hello uvio!";
|
||||||
let path = "./tmp/file_test_uvio_full.txt";
|
let path = "./tmp/file_test_uvio_full.txt";
|
||||||
{
|
{
|
||||||
let create_fm = Create;
|
let create_fm = Open;
|
||||||
let create_fa = ReadWrite;
|
let create_fa = ReadWrite;
|
||||||
let mut fd = io.fs_open(&path.to_c_str(), create_fm, create_fa).unwrap();
|
let mut fd = io.fs_open(&path.to_c_str(), create_fm, create_fa).unwrap();
|
||||||
let write_buf = write_val.as_bytes();
|
let write_buf = write_val.as_bytes();
|
||||||
|
|
|
@ -222,6 +222,7 @@ pub type uv_exit_cb = extern "C" fn(handle: *uv_process_t,
|
||||||
term_signal: c_int);
|
term_signal: c_int);
|
||||||
pub type uv_signal_cb = extern "C" fn(handle: *uv_signal_t,
|
pub type uv_signal_cb = extern "C" fn(handle: *uv_signal_t,
|
||||||
signum: c_int);
|
signum: c_int);
|
||||||
|
pub type uv_fs_cb = extern "C" fn(req: *uv_fs_t);
|
||||||
|
|
||||||
pub type sockaddr = c_void;
|
pub type sockaddr = c_void;
|
||||||
pub type sockaddr_in = c_void;
|
pub type sockaddr_in = c_void;
|
||||||
|
@ -886,6 +887,11 @@ pub unsafe fn get_ptr_from_fs_req(req: *uv_fs_t) -> *libc::c_void {
|
||||||
|
|
||||||
rust_uv_get_ptr_from_fs_req(req)
|
rust_uv_get_ptr_from_fs_req(req)
|
||||||
}
|
}
|
||||||
|
pub unsafe fn get_path_from_fs_req(req: *uv_fs_t) -> *c_char {
|
||||||
|
#[fixed_stack_segment]; #[inline(never)];
|
||||||
|
|
||||||
|
rust_uv_get_path_from_fs_req(req)
|
||||||
|
}
|
||||||
pub unsafe fn get_loop_from_fs_req(req: *uv_fs_t) -> *uv_loop_t {
|
pub unsafe fn get_loop_from_fs_req(req: *uv_fs_t) -> *uv_loop_t {
|
||||||
#[fixed_stack_segment]; #[inline(never)];
|
#[fixed_stack_segment]; #[inline(never)];
|
||||||
|
|
||||||
|
@ -1129,6 +1135,7 @@ extern {
|
||||||
fn rust_uv_populate_uv_stat(req_in: *uv_fs_t, stat_out: *uv_stat_t);
|
fn rust_uv_populate_uv_stat(req_in: *uv_fs_t, stat_out: *uv_stat_t);
|
||||||
fn rust_uv_get_result_from_fs_req(req: *uv_fs_t) -> c_int;
|
fn rust_uv_get_result_from_fs_req(req: *uv_fs_t) -> c_int;
|
||||||
fn rust_uv_get_ptr_from_fs_req(req: *uv_fs_t) -> *libc::c_void;
|
fn rust_uv_get_ptr_from_fs_req(req: *uv_fs_t) -> *libc::c_void;
|
||||||
|
fn rust_uv_get_path_from_fs_req(req: *uv_fs_t) -> *c_char;
|
||||||
fn rust_uv_get_loop_from_fs_req(req: *uv_fs_t) -> *uv_loop_t;
|
fn rust_uv_get_loop_from_fs_req(req: *uv_fs_t) -> *uv_loop_t;
|
||||||
fn rust_uv_get_loop_from_getaddrinfo_req(req: *uv_fs_t) -> *uv_loop_t;
|
fn rust_uv_get_loop_from_getaddrinfo_req(req: *uv_fs_t) -> *uv_loop_t;
|
||||||
|
|
||||||
|
@ -1189,7 +1196,24 @@ extern {
|
||||||
signal_cb: uv_signal_cb,
|
signal_cb: uv_signal_cb,
|
||||||
signum: c_int) -> c_int;
|
signum: c_int) -> c_int;
|
||||||
fn rust_uv_signal_stop(handle: *uv_signal_t) -> c_int;
|
fn rust_uv_signal_stop(handle: *uv_signal_t) -> c_int;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
externfn!(fn uv_fs_fsync(handle: *uv_loop_t, req: *uv_fs_t, file: c_int,
|
||||||
|
cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_fdatasync(handle: *uv_loop_t, req: *uv_fs_t, file: c_int,
|
||||||
|
cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_ftruncate(handle: *uv_loop_t, req: *uv_fs_t, file: c_int,
|
||||||
|
offset: i64, cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_readlink(handle: *uv_loop_t, req: *uv_fs_t, file: *c_char,
|
||||||
|
cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_symlink(handle: *uv_loop_t, req: *uv_fs_t, src: *c_char,
|
||||||
|
dst: *c_char, cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_link(handle: *uv_loop_t, req: *uv_fs_t, src: *c_char,
|
||||||
|
dst: *c_char, cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_chown(handle: *uv_loop_t, req: *uv_fs_t, src: *c_char,
|
||||||
|
uid: uv_uid_t, gid: uv_gid_t, cb: *u8) -> c_int)
|
||||||
|
externfn!(fn uv_fs_lstat(handle: *uv_loop_t, req: *uv_fs_t, file: *c_char,
|
||||||
|
cb: *u8) -> c_int)
|
||||||
|
|
||||||
// libuv requires various system libraries to successfully link on some
|
// libuv requires various system libraries to successfully link on some
|
||||||
// platforms
|
// platforms
|
||||||
|
|
|
@ -142,7 +142,7 @@ pub use libc::consts::os::c95::{SEEK_SET, TMP_MAX};
|
||||||
pub use libc::consts::os::posix88::{F_OK, O_APPEND, O_CREAT, O_EXCL};
|
pub use libc::consts::os::posix88::{F_OK, O_APPEND, O_CREAT, O_EXCL};
|
||||||
pub use libc::consts::os::posix88::{O_RDONLY, O_RDWR, O_TRUNC, O_WRONLY};
|
pub use libc::consts::os::posix88::{O_RDONLY, O_RDWR, O_TRUNC, O_WRONLY};
|
||||||
pub use libc::consts::os::posix88::{R_OK, S_IEXEC, S_IFBLK, S_IFCHR};
|
pub use libc::consts::os::posix88::{R_OK, S_IEXEC, S_IFBLK, S_IFCHR};
|
||||||
pub use libc::consts::os::posix88::{S_IFDIR, S_IFIFO, S_IFMT, S_IFREG};
|
pub use libc::consts::os::posix88::{S_IFDIR, S_IFIFO, S_IFMT, S_IFREG, S_IFLNK};
|
||||||
pub use libc::consts::os::posix88::{S_IREAD, S_IRUSR, S_IRWXU, S_IWUSR};
|
pub use libc::consts::os::posix88::{S_IREAD, S_IRUSR, S_IRWXU, S_IWUSR};
|
||||||
pub use libc::consts::os::posix88::{STDERR_FILENO, STDIN_FILENO};
|
pub use libc::consts::os::posix88::{STDERR_FILENO, STDIN_FILENO};
|
||||||
pub use libc::consts::os::posix88::{STDOUT_FILENO, W_OK, X_OK};
|
pub use libc::consts::os::posix88::{STDOUT_FILENO, W_OK, X_OK};
|
||||||
|
@ -1168,6 +1168,7 @@ pub mod consts {
|
||||||
pub static S_IFBLK : c_int = 12288;
|
pub static S_IFBLK : c_int = 12288;
|
||||||
pub static S_IFDIR : c_int = 16384;
|
pub static S_IFDIR : c_int = 16384;
|
||||||
pub static S_IFREG : c_int = 32768;
|
pub static S_IFREG : c_int = 32768;
|
||||||
|
pub static S_IFLNK : c_int = 40960;
|
||||||
pub static S_IFMT : c_int = 61440;
|
pub static S_IFMT : c_int = 61440;
|
||||||
pub static S_IEXEC : c_int = 64;
|
pub static S_IEXEC : c_int = 64;
|
||||||
pub static S_IWRITE : c_int = 128;
|
pub static S_IWRITE : c_int = 128;
|
||||||
|
@ -1345,6 +1346,7 @@ pub mod consts {
|
||||||
pub static S_IFBLK : c_int = 24576;
|
pub static S_IFBLK : c_int = 24576;
|
||||||
pub static S_IFDIR : c_int = 16384;
|
pub static S_IFDIR : c_int = 16384;
|
||||||
pub static S_IFREG : c_int = 32768;
|
pub static S_IFREG : c_int = 32768;
|
||||||
|
pub static S_IFLNK : c_int = 40960;
|
||||||
pub static S_IFMT : c_int = 61440;
|
pub static S_IFMT : c_int = 61440;
|
||||||
pub static S_IEXEC : c_int = 64;
|
pub static S_IEXEC : c_int = 64;
|
||||||
pub static S_IWRITE : c_int = 128;
|
pub static S_IWRITE : c_int = 128;
|
||||||
|
@ -1555,6 +1557,7 @@ pub mod consts {
|
||||||
pub static S_IFBLK : c_int = 24576;
|
pub static S_IFBLK : c_int = 24576;
|
||||||
pub static S_IFDIR : c_int = 16384;
|
pub static S_IFDIR : c_int = 16384;
|
||||||
pub static S_IFREG : c_int = 32768;
|
pub static S_IFREG : c_int = 32768;
|
||||||
|
pub static S_IFLNK : c_int = 40960;
|
||||||
pub static S_IFMT : c_int = 61440;
|
pub static S_IFMT : c_int = 61440;
|
||||||
pub static S_IEXEC : c_int = 64;
|
pub static S_IEXEC : c_int = 64;
|
||||||
pub static S_IWRITE : c_int = 128;
|
pub static S_IWRITE : c_int = 128;
|
||||||
|
@ -1999,6 +2002,7 @@ pub mod consts {
|
||||||
pub static S_IFBLK : c_int = 24576;
|
pub static S_IFBLK : c_int = 24576;
|
||||||
pub static S_IFDIR : c_int = 16384;
|
pub static S_IFDIR : c_int = 16384;
|
||||||
pub static S_IFREG : c_int = 32768;
|
pub static S_IFREG : c_int = 32768;
|
||||||
|
pub static S_IFLNK : c_int = 40960;
|
||||||
pub static S_IFMT : c_int = 61440;
|
pub static S_IFMT : c_int = 61440;
|
||||||
pub static S_IEXEC : c_int = 64;
|
pub static S_IEXEC : c_int = 64;
|
||||||
pub static S_IWRITE : c_int = 128;
|
pub static S_IWRITE : c_int = 128;
|
||||||
|
@ -2341,6 +2345,7 @@ pub mod consts {
|
||||||
pub static S_IFBLK : c_int = 24576;
|
pub static S_IFBLK : c_int = 24576;
|
||||||
pub static S_IFDIR : c_int = 16384;
|
pub static S_IFDIR : c_int = 16384;
|
||||||
pub static S_IFREG : c_int = 32768;
|
pub static S_IFREG : c_int = 32768;
|
||||||
|
pub static S_IFLNK : c_int = 40960;
|
||||||
pub static S_IFMT : c_int = 61440;
|
pub static S_IFMT : c_int = 61440;
|
||||||
pub static S_IEXEC : c_int = 64;
|
pub static S_IEXEC : c_int = 64;
|
||||||
pub static S_IWRITE : c_int = 128;
|
pub static S_IWRITE : c_int = 128;
|
||||||
|
|
|
@ -1495,7 +1495,7 @@ mod tests {
|
||||||
use result::{Ok, Err};
|
use result::{Ok, Err};
|
||||||
use os::*;
|
use os::*;
|
||||||
use libc::*;
|
use libc::*;
|
||||||
use rt::io::file;
|
use rt::io::File;
|
||||||
|
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
#[fixed_stack_segment]
|
#[fixed_stack_segment]
|
||||||
|
@ -1544,7 +1544,7 @@ mod tests {
|
||||||
assert!(*chunk.data == 0xbe);
|
assert!(*chunk.data == 0xbe);
|
||||||
close(fd);
|
close(fd);
|
||||||
}
|
}
|
||||||
file::unlink(&path);
|
File::unlink(&path);
|
||||||
}
|
}
|
||||||
|
|
||||||
// More recursive_mkdir tests are in extra::tempfile
|
// More recursive_mkdir tests are in extra::tempfile
|
||||||
|
|
|
@ -23,9 +23,6 @@ use to_bytes::IterBytes;
|
||||||
use vec::Vector;
|
use vec::Vector;
|
||||||
use super::{contains_nul, BytesContainer, GenericPath, GenericPathUnsafe};
|
use super::{contains_nul, BytesContainer, GenericPath, GenericPathUnsafe};
|
||||||
|
|
||||||
#[cfg(target_os = "win32")]
|
|
||||||
use rt::io::{FileStat, file, io_error};
|
|
||||||
|
|
||||||
/// Iterator that yields successive components of a Path as &str
|
/// Iterator that yields successive components of a Path as &str
|
||||||
///
|
///
|
||||||
/// Each component is yielded as Option<&str> for compatibility with PosixPath, but
|
/// Each component is yielded as Option<&str> for compatibility with PosixPath, but
|
||||||
|
@ -1056,67 +1053,6 @@ fn prefix_is_sep(p: Option<PathPrefix>, c: u8) -> bool {
|
||||||
else { is_sep_verbatim(c as char) }
|
else { is_sep_verbatim(c as char) }
|
||||||
}
|
}
|
||||||
|
|
||||||
// Stat support
|
|
||||||
#[cfg(target_os = "win32")]
|
|
||||||
impl Path {
|
|
||||||
/// Calls stat() on the represented file and returns the resulting rt::io::FileStat
|
|
||||||
pub fn stat(&self) -> Option<FileStat> {
|
|
||||||
let mut file_stat: Option<FileStat> = None;
|
|
||||||
do io_error::cond.trap(|_| { /* Ignore error, will return None */ }).inside {
|
|
||||||
file_stat = file::stat(self);
|
|
||||||
}
|
|
||||||
file_stat
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns whether the represented file exists
|
|
||||||
pub fn exists(&self) -> bool {
|
|
||||||
match self.stat() {
|
|
||||||
None => false,
|
|
||||||
Some(_) => true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the filesize of the represented file
|
|
||||||
pub fn get_size(&self) -> Option<u64> {
|
|
||||||
match self.stat() {
|
|
||||||
None => None,
|
|
||||||
Some(st) => Some(st.size)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the mode of the represented file
|
|
||||||
pub fn get_mode(&self) -> Option<uint> {
|
|
||||||
match self.stat() {
|
|
||||||
None => None,
|
|
||||||
Some(st) => Some(st.mode as uint)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the atime of the represented file, as msecs
|
|
||||||
pub fn get_atime(&self) -> Option<u64> {
|
|
||||||
match self.stat() {
|
|
||||||
None => None,
|
|
||||||
Some(st) => Some(st.accessed)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the mtime of the represented file, as msecs
|
|
||||||
pub fn get_mtime(&self) -> Option<u64> {
|
|
||||||
match self.stat() {
|
|
||||||
None => None,
|
|
||||||
Some(st) => Some(st.modified)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the ctime of the represented file, as msecs
|
|
||||||
pub fn get_ctime(&self) -> Option<u64> {
|
|
||||||
match self.stat() {
|
|
||||||
None => None,
|
|
||||||
Some(st) => Some(st.created)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|
|
@ -13,12 +13,11 @@
|
||||||
|
|
||||||
use rand::Rng;
|
use rand::Rng;
|
||||||
use ops::Drop;
|
use ops::Drop;
|
||||||
use path::Path;
|
|
||||||
|
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
use rand::reader::ReaderRng;
|
use rand::reader::ReaderRng;
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
use rt::io::file;
|
use rt::io::File;
|
||||||
|
|
||||||
#[cfg(windows)]
|
#[cfg(windows)]
|
||||||
use cast;
|
use cast;
|
||||||
|
@ -41,7 +40,7 @@ type HCRYPTPROV = c_long;
|
||||||
/// This does not block.
|
/// This does not block.
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
pub struct OSRng {
|
pub struct OSRng {
|
||||||
priv inner: ReaderRng<file::FileReader>
|
priv inner: ReaderRng<File>
|
||||||
}
|
}
|
||||||
/// A random number generator that retrieves randomness straight from
|
/// A random number generator that retrieves randomness straight from
|
||||||
/// the operating system. Platform sources:
|
/// the operating system. Platform sources:
|
||||||
|
@ -61,7 +60,8 @@ impl OSRng {
|
||||||
/// Create a new `OSRng`.
|
/// Create a new `OSRng`.
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
pub fn new() -> OSRng {
|
pub fn new() -> OSRng {
|
||||||
let reader = file::open(&Path::new("/dev/urandom"));
|
use path::Path;
|
||||||
|
let reader = File::open(&Path::new("/dev/urandom"));
|
||||||
let reader = reader.expect("Error opening /dev/urandom");
|
let reader = reader.expect("Error opening /dev/urandom");
|
||||||
let reader_rng = ReaderRng::new(reader);
|
let reader_rng = ReaderRng::new(reader);
|
||||||
|
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -231,8 +231,6 @@ Out of scope
|
||||||
* Trait for things that are both readers and writers, Stream?
|
* Trait for things that are both readers and writers, Stream?
|
||||||
* How to handle newline conversion
|
* How to handle newline conversion
|
||||||
* String conversion
|
* String conversion
|
||||||
* File vs. FileStream? File is shorter but could also be used for getting file info
|
|
||||||
- maybe File is for general file querying and *also* has a static `open` method
|
|
||||||
* open vs. connect for generic stream opening
|
* open vs. connect for generic stream opening
|
||||||
* Do we need `close` at all? dtors might be good enough
|
* Do we need `close` at all? dtors might be good enough
|
||||||
* How does I/O relate to the Iterator trait?
|
* How does I/O relate to the Iterator trait?
|
||||||
|
@ -244,7 +242,6 @@ Out of scope
|
||||||
|
|
||||||
use cast;
|
use cast;
|
||||||
use int;
|
use int;
|
||||||
use libc;
|
|
||||||
use path::Path;
|
use path::Path;
|
||||||
use str::{StrSlice, OwnedStr};
|
use str::{StrSlice, OwnedStr};
|
||||||
use option::{Option, Some, None};
|
use option::{Option, Some, None};
|
||||||
|
@ -262,7 +259,7 @@ pub use self::stdio::stderr;
|
||||||
pub use self::stdio::print;
|
pub use self::stdio::print;
|
||||||
pub use self::stdio::println;
|
pub use self::stdio::println;
|
||||||
|
|
||||||
pub use self::file::FileStream;
|
pub use self::file::File;
|
||||||
pub use self::timer::Timer;
|
pub use self::timer::Timer;
|
||||||
pub use self::net::ip::IpAddr;
|
pub use self::net::ip::IpAddr;
|
||||||
pub use self::net::tcp::TcpListener;
|
pub use self::net::tcp::TcpListener;
|
||||||
|
@ -465,7 +462,7 @@ pub trait Reader {
|
||||||
///
|
///
|
||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// let reader = FileStream::new()
|
/// let reader = File::open(&Path::new("foo.txt"))
|
||||||
/// while !reader.eof() {
|
/// while !reader.eof() {
|
||||||
/// println(reader.read_line());
|
/// println(reader.read_line());
|
||||||
/// }
|
/// }
|
||||||
|
@ -1104,55 +1101,103 @@ pub fn placeholder_error() -> IoError {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Instructions on how to open a file and return a `FileStream`.
|
/// A mode specifies how a file should be opened or created. These modes are
|
||||||
|
/// passed to `File::open_mode` and are used to control where the file is
|
||||||
|
/// positioned when it is initially opened.
|
||||||
pub enum FileMode {
|
pub enum FileMode {
|
||||||
/// Opens an existing file. IoError if file does not exist.
|
/// Opens a file positioned at the beginning.
|
||||||
Open,
|
Open,
|
||||||
/// Creates a file. IoError if file exists.
|
/// Opens a file positioned at EOF.
|
||||||
Create,
|
|
||||||
/// Opens an existing file or creates a new one.
|
|
||||||
OpenOrCreate,
|
|
||||||
/// Opens an existing file or creates a new one, positioned at EOF.
|
|
||||||
Append,
|
Append,
|
||||||
/// Opens an existing file, truncating it to 0 bytes.
|
/// Opens a file, truncating it if it already exists.
|
||||||
Truncate,
|
Truncate,
|
||||||
/// Opens an existing file or creates a new one, truncating it to 0 bytes.
|
|
||||||
CreateOrTruncate,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Access permissions with which the file should be opened.
|
/// Access permissions with which the file should be opened. `File`s
|
||||||
/// `FileStream`s opened with `Read` will raise an `io_error` condition if written to.
|
/// opened with `Read` will raise an `io_error` condition if written to.
|
||||||
pub enum FileAccess {
|
pub enum FileAccess {
|
||||||
Read,
|
Read,
|
||||||
Write,
|
Write,
|
||||||
ReadWrite
|
ReadWrite,
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Different kinds of files which can be identified by a call to stat
|
||||||
|
#[deriving(Eq)]
|
||||||
|
pub enum FileType {
|
||||||
|
TypeFile,
|
||||||
|
TypeDirectory,
|
||||||
|
TypeNamedPipe,
|
||||||
|
TypeBlockSpecial,
|
||||||
|
TypeSymlink,
|
||||||
|
TypeUnknown,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct FileStat {
|
pub struct FileStat {
|
||||||
/// A `Path` object containing information about the `PathInfo`'s location
|
/// The path that this stat structure is describing
|
||||||
path: Path,
|
path: Path,
|
||||||
/// `true` if the file pointed at by the `PathInfo` is a regular file
|
/// The size of the file, in bytes
|
||||||
is_file: bool,
|
|
||||||
/// `true` if the file pointed at by the `PathInfo` is a directory
|
|
||||||
is_dir: bool,
|
|
||||||
/// The file pointed at by the `PathInfo`'s device
|
|
||||||
device: u64,
|
|
||||||
/// The file pointed at by the `PathInfo`'s mode
|
|
||||||
mode: u64,
|
|
||||||
/// The file pointed at by the `PathInfo`'s inode
|
|
||||||
inode: u64,
|
|
||||||
/// The file pointed at by the `PathInfo`'s size in bytes
|
|
||||||
size: u64,
|
size: u64,
|
||||||
/// The file pointed at by the `PathInfo`'s creation time
|
/// The kind of file this path points to (directory, file, pipe, etc.)
|
||||||
|
kind: FileType,
|
||||||
|
/// The file permissions currently on the file
|
||||||
|
perm: FilePermission,
|
||||||
|
|
||||||
|
// XXX: These time fields are pretty useless without an actual time
|
||||||
|
// representation, what are the milliseconds relative to?
|
||||||
|
|
||||||
|
/// The time that the file was created at, in platform-dependent
|
||||||
|
/// milliseconds
|
||||||
created: u64,
|
created: u64,
|
||||||
/// The file pointed at by the `PathInfo`'s last-modification time in
|
/// The time that this file was last modified, in platform-dependent
|
||||||
/// platform-dependent msecs
|
/// milliseconds
|
||||||
modified: u64,
|
modified: u64,
|
||||||
/// The file pointed at by the `PathInfo`'s last-accessd time (e.g. read) in
|
/// The time that this file was last accessed, in platform-dependent
|
||||||
/// platform-dependent msecs
|
/// milliseconds
|
||||||
accessed: u64,
|
accessed: u64,
|
||||||
|
|
||||||
|
// Various filesytem info
|
||||||
|
device: u64,
|
||||||
|
inode: u64,
|
||||||
|
rdev: u64,
|
||||||
|
nlink: u64,
|
||||||
|
uid: u64,
|
||||||
|
gid: u64,
|
||||||
|
blksize: u64,
|
||||||
|
blocks: u64,
|
||||||
|
flags: u64,
|
||||||
|
gen: u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME(#10131): this needs to get designed for real
|
/// A set of permissions for a file or directory is represented by a set of
|
||||||
|
/// flags which are or'd together.
|
||||||
pub type FilePermission = u32;
|
pub type FilePermission = u32;
|
||||||
pub static UserRWX: FilePermission = libc::S_IRWXU as FilePermission;
|
|
||||||
|
// Each permission bit
|
||||||
|
pub static UserRead: FilePermission = 0x100;
|
||||||
|
pub static UserWrite: FilePermission = 0x080;
|
||||||
|
pub static UserExecute: FilePermission = 0x040;
|
||||||
|
pub static GroupRead: FilePermission = 0x020;
|
||||||
|
pub static GroupWrite: FilePermission = 0x010;
|
||||||
|
pub static GroupExecute: FilePermission = 0x008;
|
||||||
|
pub static OtherRead: FilePermission = 0x004;
|
||||||
|
pub static OtherWrite: FilePermission = 0x002;
|
||||||
|
pub static OtherExecute: FilePermission = 0x001;
|
||||||
|
|
||||||
|
// Common combinations of these bits
|
||||||
|
pub static UserRWX: FilePermission = UserRead | UserWrite | UserExecute;
|
||||||
|
pub static GroupRWX: FilePermission = GroupRead | GroupWrite | GroupExecute;
|
||||||
|
pub static OtherRWX: FilePermission = OtherRead | OtherWrite | OtherExecute;
|
||||||
|
|
||||||
|
/// A set of permissions for user owned files, this is equivalent to 0644 on
|
||||||
|
/// unix-like systems.
|
||||||
|
pub static UserFile: FilePermission = UserRead | UserWrite | GroupRead | OtherRead;
|
||||||
|
/// A set of permissions for user owned directories, this is equivalent to 0755
|
||||||
|
/// on unix-like systems.
|
||||||
|
pub static UserDir: FilePermission = UserRWX | GroupRead | GroupExecute |
|
||||||
|
OtherRead | OtherExecute;
|
||||||
|
/// A set of permissions for user owned executables, this is equivalent to 0755
|
||||||
|
/// on unix-like systems.
|
||||||
|
pub static UserExec: FilePermission = UserDir;
|
||||||
|
|
||||||
|
/// A mask for all possible permission bits
|
||||||
|
pub static AllPermissions: FilePermission = 0x1ff;
|
||||||
|
|
|
@ -309,14 +309,16 @@ mod tests {
|
||||||
// get bitrotted instantaneously.
|
// get bitrotted instantaneously.
|
||||||
mod old_os {
|
mod old_os {
|
||||||
use prelude::*;
|
use prelude::*;
|
||||||
use c_str::CString;
|
|
||||||
use libc::fclose;
|
|
||||||
use libc::{size_t, c_void, c_int};
|
use libc::{size_t, c_void, c_int};
|
||||||
use libc;
|
use libc;
|
||||||
use vec;
|
use vec;
|
||||||
|
|
||||||
#[cfg(test)] use os;
|
#[cfg(not(windows))] use c_str::CString;
|
||||||
|
#[cfg(not(windows))] use libc::fclose;
|
||||||
|
#[cfg(test)] #[cfg(windows)] use os;
|
||||||
#[cfg(test)] use rand;
|
#[cfg(test)] use rand;
|
||||||
|
#[cfg(windows)] use str;
|
||||||
|
#[cfg(windows)] use ptr;
|
||||||
|
|
||||||
// On Windows, wide character version of function must be used to support
|
// On Windows, wide character version of function must be used to support
|
||||||
// unicode, so functions should be split into at least two versions,
|
// unicode, so functions should be split into at least two versions,
|
||||||
|
@ -651,7 +653,7 @@ mod old_os {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// Preserve permissions
|
// Preserve permissions
|
||||||
let from_mode = from.stat().mode;
|
let from_mode = from.stat().perm;
|
||||||
|
|
||||||
let ostream = do to.with_c_str |top| {
|
let ostream = do to.with_c_str |top| {
|
||||||
do "w+b".with_c_str |modebuf| {
|
do "w+b".with_c_str |modebuf| {
|
||||||
|
@ -735,8 +737,8 @@ mod old_os {
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_path_is_dir() {
|
fn test_path_is_dir() {
|
||||||
use rt::io::file::{open_stream, mkdir_recursive};
|
use rt::io::file::{mkdir_recursive};
|
||||||
use rt::io::{OpenOrCreate, Read, UserRWX};
|
use rt::io::{File, UserRWX};
|
||||||
|
|
||||||
assert!((path_is_dir(&Path::new("."))));
|
assert!((path_is_dir(&Path::new("."))));
|
||||||
assert!((!path_is_dir(&Path::new("test/stdtest/fs.rs"))));
|
assert!((!path_is_dir(&Path::new("test/stdtest/fs.rs"))));
|
||||||
|
@ -754,7 +756,7 @@ mod old_os {
|
||||||
filepath.push("unicode-file-\uac00\u4e00\u30fc\u4f60\u597d.rs");
|
filepath.push("unicode-file-\uac00\u4e00\u30fc\u4f60\u597d.rs");
|
||||||
debug!("path_is_dir filepath: {}", filepath.display());
|
debug!("path_is_dir filepath: {}", filepath.display());
|
||||||
|
|
||||||
open_stream(&filepath, OpenOrCreate, Read); // ignore return; touch only
|
File::create(&filepath); // ignore return; touch only
|
||||||
assert!((!path_is_dir(&filepath)));
|
assert!((!path_is_dir(&filepath)));
|
||||||
|
|
||||||
assert!((!path_is_dir(&Path::new(
|
assert!((!path_is_dir(&Path::new(
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
//! Implementations of I/O traits for the Option type
|
//! Implementations of I/O traits for the Option type
|
||||||
//!
|
//!
|
||||||
//! I/O constructors return option types to allow errors to be handled.
|
//! I/O constructors return option types to allow errors to be handled.
|
||||||
//! These implementations allow e.g. `Option<FileStream>` to be used
|
//! These implementations allow e.g. `Option<File>` to be used
|
||||||
//! as a `Reader` without unwrapping the option first.
|
//! as a `Reader` without unwrapping the option first.
|
||||||
|
|
||||||
use option::*;
|
use option::*;
|
||||||
|
|
|
@ -91,12 +91,17 @@ pub fn with_local_io<T>(f: &fn(&mut IoFactory) -> Option<T>) -> Option<T> {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub trait IoFactory {
|
pub trait IoFactory {
|
||||||
|
// networking
|
||||||
fn tcp_connect(&mut self, addr: SocketAddr) -> Result<~RtioTcpStream, IoError>;
|
fn tcp_connect(&mut self, addr: SocketAddr) -> Result<~RtioTcpStream, IoError>;
|
||||||
fn tcp_bind(&mut self, addr: SocketAddr) -> Result<~RtioTcpListener, IoError>;
|
fn tcp_bind(&mut self, addr: SocketAddr) -> Result<~RtioTcpListener, IoError>;
|
||||||
fn udp_bind(&mut self, addr: SocketAddr) -> Result<~RtioUdpSocket, IoError>;
|
fn udp_bind(&mut self, addr: SocketAddr) -> Result<~RtioUdpSocket, IoError>;
|
||||||
|
fn unix_bind(&mut self, path: &CString) ->
|
||||||
|
Result<~RtioUnixListener, IoError>;
|
||||||
|
fn unix_connect(&mut self, path: &CString) -> Result<~RtioPipe, IoError>;
|
||||||
fn get_host_addresses(&mut self, host: Option<&str>, servname: Option<&str>,
|
fn get_host_addresses(&mut self, host: Option<&str>, servname: Option<&str>,
|
||||||
hint: Option<ai::Hint>) -> Result<~[ai::Info], IoError>;
|
hint: Option<ai::Hint>) -> Result<~[ai::Info], IoError>;
|
||||||
fn timer_init(&mut self) -> Result<~RtioTimer, IoError>;
|
|
||||||
|
// filesystem operations
|
||||||
fn fs_from_raw_fd(&mut self, fd: c_int, close: CloseBehavior) -> ~RtioFileStream;
|
fn fs_from_raw_fd(&mut self, fd: c_int, close: CloseBehavior) -> ~RtioFileStream;
|
||||||
fn fs_open(&mut self, path: &CString, fm: FileMode, fa: FileAccess)
|
fn fs_open(&mut self, path: &CString, fm: FileMode, fa: FileAccess)
|
||||||
-> Result<~RtioFileStream, IoError>;
|
-> Result<~RtioFileStream, IoError>;
|
||||||
|
@ -110,13 +115,18 @@ pub trait IoFactory {
|
||||||
fn fs_rename(&mut self, path: &CString, to: &CString) -> Result<(), IoError>;
|
fn fs_rename(&mut self, path: &CString, to: &CString) -> Result<(), IoError>;
|
||||||
fn fs_readdir(&mut self, path: &CString, flags: c_int) ->
|
fn fs_readdir(&mut self, path: &CString, flags: c_int) ->
|
||||||
Result<~[Path], IoError>;
|
Result<~[Path], IoError>;
|
||||||
|
fn fs_lstat(&mut self, path: &CString) -> Result<FileStat, IoError>;
|
||||||
|
fn fs_chown(&mut self, path: &CString, uid: int, gid: int) ->
|
||||||
|
Result<(), IoError>;
|
||||||
|
fn fs_readlink(&mut self, path: &CString) -> Result<Path, IoError>;
|
||||||
|
fn fs_symlink(&mut self, src: &CString, dst: &CString) -> Result<(), IoError>;
|
||||||
|
fn fs_link(&mut self, src: &CString, dst: &CString) -> Result<(), IoError>;
|
||||||
|
|
||||||
|
// misc
|
||||||
|
fn timer_init(&mut self) -> Result<~RtioTimer, IoError>;
|
||||||
fn spawn(&mut self, config: ProcessConfig)
|
fn spawn(&mut self, config: ProcessConfig)
|
||||||
-> Result<(~RtioProcess, ~[Option<~RtioPipe>]), IoError>;
|
-> Result<(~RtioProcess, ~[Option<~RtioPipe>]), IoError>;
|
||||||
|
|
||||||
fn pipe_open(&mut self, fd: c_int) -> Result<~RtioPipe, IoError>;
|
fn pipe_open(&mut self, fd: c_int) -> Result<~RtioPipe, IoError>;
|
||||||
fn unix_bind(&mut self, path: &CString) ->
|
|
||||||
Result<~RtioUnixListener, IoError>;
|
|
||||||
fn unix_connect(&mut self, path: &CString) -> Result<~RtioPipe, IoError>;
|
|
||||||
fn tty_open(&mut self, fd: c_int, readable: bool)
|
fn tty_open(&mut self, fd: c_int, readable: bool)
|
||||||
-> Result<~RtioTTY, IoError>;
|
-> Result<~RtioTTY, IoError>;
|
||||||
fn signal(&mut self, signal: Signum, channel: SharedChan<Signum>)
|
fn signal(&mut self, signal: Signum, channel: SharedChan<Signum>)
|
||||||
|
@ -177,6 +187,9 @@ pub trait RtioFileStream {
|
||||||
fn pwrite(&mut self, buf: &[u8], offset: u64) -> Result<(), IoError>;
|
fn pwrite(&mut self, buf: &[u8], offset: u64) -> Result<(), IoError>;
|
||||||
fn seek(&mut self, pos: i64, whence: SeekStyle) -> Result<u64, IoError>;
|
fn seek(&mut self, pos: i64, whence: SeekStyle) -> Result<u64, IoError>;
|
||||||
fn tell(&self) -> Result<u64, IoError>;
|
fn tell(&self) -> Result<u64, IoError>;
|
||||||
|
fn fsync(&mut self) -> Result<(), IoError>;
|
||||||
|
fn datasync(&mut self) -> Result<(), IoError>;
|
||||||
|
fn truncate(&mut self, offset: i64) -> Result<(), IoError>;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub trait RtioProcess {
|
pub trait RtioProcess {
|
||||||
|
|
|
@ -20,8 +20,7 @@ use parse::token::{get_ident_interner};
|
||||||
use print::pprust;
|
use print::pprust;
|
||||||
|
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::Reader;
|
use std::rt::io::File;
|
||||||
use std::rt::io::file;
|
|
||||||
use std::str;
|
use std::str;
|
||||||
|
|
||||||
// These macros all relate to the file system; they either return
|
// These macros all relate to the file system; they either return
|
||||||
|
@ -92,7 +91,7 @@ pub fn expand_include_str(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
|
||||||
-> base::MacResult {
|
-> base::MacResult {
|
||||||
let file = get_single_str_from_tts(cx, sp, tts, "include_str!");
|
let file = get_single_str_from_tts(cx, sp, tts, "include_str!");
|
||||||
let file = res_rel_file(cx, sp, &Path::new(file));
|
let file = res_rel_file(cx, sp, &Path::new(file));
|
||||||
let bytes = match io::result(|| file::open(&file).read_to_end()) {
|
let bytes = match io::result(|| File::open(&file).read_to_end()) {
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
cx.span_fatal(sp, format!("couldn't read {}: {}",
|
cx.span_fatal(sp, format!("couldn't read {}: {}",
|
||||||
file.display(), e.desc));
|
file.display(), e.desc));
|
||||||
|
@ -114,7 +113,7 @@ pub fn expand_include_bin(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
|
||||||
|
|
||||||
let file = get_single_str_from_tts(cx, sp, tts, "include_bin!");
|
let file = get_single_str_from_tts(cx, sp, tts, "include_bin!");
|
||||||
let file = res_rel_file(cx, sp, &Path::new(file));
|
let file = res_rel_file(cx, sp, &Path::new(file));
|
||||||
match io::result(|| file::open(&file).read_to_end()) {
|
match io::result(|| File::open(&file).read_to_end()) {
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
cx.span_fatal(sp, format!("couldn't read {}: {}",
|
cx.span_fatal(sp, format!("couldn't read {}: {}",
|
||||||
file.display(), e.desc));
|
file.display(), e.desc));
|
||||||
|
|
|
@ -19,9 +19,8 @@ use parse::attr::parser_attr;
|
||||||
use parse::lexer::reader;
|
use parse::lexer::reader;
|
||||||
use parse::parser::Parser;
|
use parse::parser::Parser;
|
||||||
|
|
||||||
use std::path::Path;
|
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::str;
|
use std::str;
|
||||||
|
|
||||||
pub mod lexer;
|
pub mod lexer;
|
||||||
|
@ -268,7 +267,7 @@ pub fn file_to_filemap(sess: @mut ParseSess, path: &Path, spanopt: Option<Span>)
|
||||||
None => sess.span_diagnostic.handler().fatal(msg),
|
None => sess.span_diagnostic.handler().fatal(msg),
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
let bytes = match io::result(|| file::open(path).read_to_end()) {
|
let bytes = match io::result(|| File::open(path).read_to_end()) {
|
||||||
Ok(bytes) => bytes,
|
Ok(bytes) => bytes,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
err(format!("couldn't read {}: {}", path.display(), e.desc));
|
err(format!("couldn't read {}: {}", path.display(), e.desc));
|
||||||
|
|
|
@ -532,6 +532,10 @@ extern "C" int
|
||||||
rust_uv_get_result_from_fs_req(uv_fs_t* req) {
|
rust_uv_get_result_from_fs_req(uv_fs_t* req) {
|
||||||
return req->result;
|
return req->result;
|
||||||
}
|
}
|
||||||
|
extern "C" const char*
|
||||||
|
rust_uv_get_path_from_fs_req(uv_fs_t* req) {
|
||||||
|
return req->path;
|
||||||
|
}
|
||||||
extern "C" void*
|
extern "C" void*
|
||||||
rust_uv_get_ptr_from_fs_req(uv_fs_t* req) {
|
rust_uv_get_ptr_from_fs_req(uv_fs_t* req) {
|
||||||
return req->ptr;
|
return req->ptr;
|
||||||
|
|
|
@ -21,7 +21,7 @@ use std::rand;
|
||||||
use std::str;
|
use std::str;
|
||||||
use std::util;
|
use std::util;
|
||||||
use std::vec;
|
use std::vec;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
|
|
||||||
macro_rules! bench (
|
macro_rules! bench (
|
||||||
($argv:expr, $id:ident) => (maybe_run_test($argv, stringify!($id).to_owned(), $id))
|
($argv:expr, $id:ident) => (maybe_run_test($argv, stringify!($id).to_owned(), $id))
|
||||||
|
@ -76,7 +76,7 @@ fn read_line() {
|
||||||
path.push("src/test/bench/shootout-k-nucleotide.data");
|
path.push("src/test/bench/shootout-k-nucleotide.data");
|
||||||
|
|
||||||
for _ in range(0, 3) {
|
for _ in range(0, 3) {
|
||||||
let mut reader = BufferedReader::new(file::open(&path).unwrap());
|
let mut reader = BufferedReader::new(File::open(&path).unwrap());
|
||||||
while !reader.eof() {
|
while !reader.eof() {
|
||||||
reader.read_line();
|
reader.read_line();
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,7 +19,7 @@ extern mod extra;
|
||||||
|
|
||||||
use std::int;
|
use std::int;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
use std::os;
|
use std::os;
|
||||||
use std::rand::Rng;
|
use std::rand::Rng;
|
||||||
use std::rand;
|
use std::rand;
|
||||||
|
@ -123,7 +123,7 @@ fn main() {
|
||||||
};
|
};
|
||||||
|
|
||||||
let writer = if os::getenv("RUST_BENCH").is_some() {
|
let writer = if os::getenv("RUST_BENCH").is_some() {
|
||||||
let file = file::create(&Path::new("./shootout-fasta.data"));
|
let file = File::create(&Path::new("./shootout-fasta.data"));
|
||||||
@mut file as @mut io::Writer
|
@mut file as @mut io::Writer
|
||||||
} else {
|
} else {
|
||||||
@mut io::stdout() as @mut io::Writer
|
@mut io::stdout() as @mut io::Writer
|
||||||
|
|
|
@ -23,7 +23,7 @@ pub fn main() {
|
||||||
if directory {
|
if directory {
|
||||||
io::file::mkdir(&Path::new(path), io::UserRWX);
|
io::file::mkdir(&Path::new(path), io::UserRWX);
|
||||||
} else {
|
} else {
|
||||||
io::file::create(&Path::new(path));
|
io::File::create(&Path::new(path));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -19,6 +19,7 @@ use std::os;
|
||||||
use std::libc;
|
use std::libc;
|
||||||
use std::rt::io;
|
use std::rt::io;
|
||||||
use std::rt::io::file;
|
use std::rt::io::file;
|
||||||
|
use std::rt::io::File;
|
||||||
|
|
||||||
fn rename_directory() {
|
fn rename_directory() {
|
||||||
#[fixed_stack_segment];
|
#[fixed_stack_segment];
|
||||||
|
@ -50,7 +51,7 @@ fn rename_directory() {
|
||||||
|
|
||||||
let new_path = tmpdir.join_many(["quux", "blat"]);
|
let new_path = tmpdir.join_many(["quux", "blat"]);
|
||||||
file::mkdir_recursive(&new_path, io::UserRWX);
|
file::mkdir_recursive(&new_path, io::UserRWX);
|
||||||
file::rename(&old_path, &new_path.join("newdir"));
|
File::rename(&old_path, &new_path.join("newdir"));
|
||||||
assert!(new_path.join("newdir").is_dir());
|
assert!(new_path.join("newdir").is_dir());
|
||||||
assert!(new_path.join_many(["newdir", "temp.txt"]).exists());
|
assert!(new_path.join_many(["newdir", "temp.txt"]).exists());
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,14 +13,14 @@
|
||||||
extern mod extra;
|
extern mod extra;
|
||||||
|
|
||||||
use extra::tempfile;
|
use extra::tempfile;
|
||||||
use std::rt::io::file;
|
use std::rt::io::File;
|
||||||
|
|
||||||
pub fn main() {
|
pub fn main() {
|
||||||
let dir = tempfile::TempDir::new_in(&Path::new("."), "").unwrap();
|
let dir = tempfile::TempDir::new_in(&Path::new("."), "").unwrap();
|
||||||
let path = dir.path().join("file");
|
let path = dir.path().join("file");
|
||||||
|
|
||||||
{
|
{
|
||||||
match file::create(&path) {
|
match File::create(&path) {
|
||||||
None => unreachable!(),
|
None => unreachable!(),
|
||||||
Some(f) => {
|
Some(f) => {
|
||||||
let mut f = f;
|
let mut f = f;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue