OpenOptions::custom_flags with O_NONBLOCK on pipe


I fail to create and open a pipe with O_NONBLOCK as shown by this program:

#![allow(dead_code, unused_macros, unused_variables, unused_assignments, unreachable_code)]

extern crate libc;
use std::fs::OpenOptions;
use std::os::unix::fs::OpenOptionsExt;

use std::fs::File;
use std::error::Error;
use std::path::{Path,PathBuf};

type Result<T> = std::result::Result<T, Box<Error>>;

fn mkfifo(path: &PathBuf) -> Result<()> {
    let path_name = path.to_str().unwrap();
    let c_path = std::ffi::CString::new(path_name).unwrap();
    // Safe because c_path points to a valid C string.
    let status = unsafe { libc::mkfifo(c_path.as_ptr(), 0o644) };
    if status < 0 {
    } else {

fn new(fifo_path: PathBuf) -> Result<File> {
    println!("{:?}", fifo_path);
    let fifo_in = OpenOptions::new()
    println!("{:?}", fifo_in);
    let fifo_out = OpenOptions::new()

fn main() {
    let p = PathBuf::from("x");
    mkfifo(&p).expect("bad mkfifo");
    let f = new(p);
    println!("{:?}", f);

This is the output:

semenzato@luigi:~/src/rust$ ./target/debug/main
Err(Os { code: 22, kind: InvalidInput, message: "Invalid argument" })

strace shows that open() is not even called so the failure cause isn’t immediately clear. I did the equivalent operation (minus any errors) in previous programs in C, and that seems to work. Any suggestions on debugging this? Thanks!


Are you missing read(true) for fifo_in?


Thank you vitalyd. This works fine with .read(true). Sorry for the spam!