diff --git a/Makefile b/Makefile index 17ed29197..a5f4de24f 100644 --- a/Makefile +++ b/Makefile @@ -53,6 +53,7 @@ UNIX_PROGS := \ id \ kill \ logname \ + mkfifo \ sync \ tty \ uname \ diff --git a/mkfifo/mkfifo.rs b/mkfifo/mkfifo.rs new file mode 100644 index 000000000..b35d3bd10 --- /dev/null +++ b/mkfifo/mkfifo.rs @@ -0,0 +1,82 @@ +#![crate_id(name="mkfifo", vers="1.0.0", author="Michael Gehring")] +#![feature(macro_rules)] + +/* + * This file is part of the uutils coreutils package. + * + * (c) Michael Gehring + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +extern crate getopts; +extern crate libc; + +use std::num::FromStrRadix; +use std::os; +use libc::funcs::posix88::stat_::mkfifo; + +#[path = "../common/util.rs"] +mod util; + +static NAME : &'static str = "mkfifo"; +static VERSION : &'static str = "1.0.0"; + +#[allow(dead_code)] +fn main() { os::set_exit_status(uumain(os::args())); } + +pub fn uumain(args: Vec) -> int { + let opts = [ + getopts::optopt("m", "mode", "file permissions for the fifo", "(default 0666)"), + getopts::optflag("h", "help", "display this help and exit"), + getopts::optflag("V", "version", "output version information and exit"), + ]; + + let matches = match getopts::getopts(args.tail(), opts) { + Ok(m) => m, + Err(err) => fail!("{}", err), + }; + + if matches.opt_present("version") { + println!("{} {}", NAME, VERSION); + return 0; + } + + if matches.opt_present("help") || matches.free.is_empty() { + println!("{} {}", NAME, VERSION); + println!(""); + println!("Usage:"); + println!(" {} [OPTIONS] NAME...", NAME); + println!(""); + print!("{}", getopts::usage("Create a FIFO with the given name.", opts.as_slice()).as_slice()); + if matches.free.is_empty() { + return 1; + } + return 0; + } + + let mode = match matches.opt_str("m") { + Some(m) => match FromStrRadix::from_str_radix(m.as_slice(), 8) { + Some(m) => m, + None => { + show_error!("invalid mode"); + return 1; + } + }, + None => 0o666, + }; + + let mut exit_status = 0; + for f in matches.free.iter() { + f.with_c_str(|name| { + let err = unsafe { mkfifo(name, mode) }; + if err == -1 { + show_error!("creating '{}': {}", f, os::error_string(os::errno() as uint)); + exit_status = 1; + } + }); + } + + exit_status +} diff --git a/uutils/uutils.rs b/uutils/uutils.rs index a3221054b..0615edcab 100644 --- a/uutils/uutils.rs +++ b/uutils/uutils.rs @@ -34,6 +34,7 @@ extern crate kill; extern crate logname; extern crate md5sum; extern crate mkdir; +extern crate mkfifo; extern crate nl; extern crate paste; extern crate printenv; @@ -94,6 +95,7 @@ fn util_map() -> HashMap<&str, fn(Vec) -> int> { map.insert("logname", logname::uumain); map.insert("md5sum", md5sum::uumain); map.insert("mkdir", mkdir::uumain); + map.insert("mkfifo", mkfifo::uumain); map.insert("nl", nl::uumain); map.insert("paste", paste::uumain); map.insert("printenv", printenv::uumain);