caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
* Strange buffering interaction: stdout / file_descr
@ 2009-05-23 21:17 Alexander Fuchs
  2009-05-24 10:55 ` [Caml-list] " Gerd Stolpmann
  0 siblings, 1 reply; 2+ messages in thread
From: Alexander Fuchs @ 2009-05-23 21:17 UTC (permalink / raw)
  To: caml-list

Hi,

I am trying to use Unix.create_process to create a process and redirect
its input/output channels. Actually, as a first step I want to determine
if process creation succeeded. I couldn't find any straightforward way
to figure this out, so I am just making the program output its version,
and them I am trying to read from its output channel. If the output
channel is ready according to Unix.select, but returns 0 bytes with
Unix.read, I can conclude that process creation failed (e.g. the wrong
path was given). I hope I am just missing something obvious here and
someone can point me to a better solution.

Anyway, when doing this, I get some strange behavior. First the main
program outputs something on stdout, without flushing stdout. Then a
process is created, with redirecting it input/output channels to new
socket pairs, but process creation fails (intentionally). But now
reading from the process' stdout, which should be completely independent
from the main program's stdout, yields what was previously output on the
main program's stdout. If instead I flush stdout before calling
Unix.create_process, this doesn't happen, and nothing can be read from
the failed process' stdout, as expected.

Is this a bug in the interaction of channels / file_descr, or should
this be make sense? 

For illustration I attached a sample program, compile with ocamlc
unix.cma <file_name>. It first outputs "main" on its stdout, then tries
to create a process, fails, reads "main" from the process' stdout, and
prints it.

Tested with ocaml 3.11.0 native and byte code, on x86_64 GNU/Linux.


Thanks,
	Alex




let () =
  print_string "main";

  let (stdout_r, stdout_w) = Unix.socketpair Unix.PF_UNIX
Unix.SOCK_STREAM 0 in
  let (stdin_r, stdin_w) = Unix.socketpair Unix.PF_UNIX Unix.SOCK_STREAM
0 in

  let cmd = "none" in

  (* without flush reading from stdout_r yields "main" *)
  (* flush stdout; *)
  let pid = Unix.create_process cmd [| cmd; "-version" |] stdin_r
stdout_w stdout_w in

  Unix.close stdin_r;
  Unix.close stdout_w;

  begin

    let (outs, _, _) = Unix.select [stdout_r] [] [] (-1.0) in

    match outs with
    | [out] ->
        let buffer = String.make 100 ' ' in
        let size =  Unix.read out buffer 0 100 in

        if size > 0 then begin
          print_endline (buffer)
        end

        else begin
          print_endline "create_process failed"
        end

    | _ ->
        assert false;
  end;

  Unix.close stdout_r;
  Unix.close stdin_w;
  Unix.kill pid Sys.sigkill;
  let (_, _status) = Unix.waitpid [] pid in
  ()



^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2009-05-24 10:53 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2009-05-23 21:17 Strange buffering interaction: stdout / file_descr Alexander Fuchs
2009-05-24 10:55 ` [Caml-list] " Gerd Stolpmann

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).