Advanced search
Log In | New Account   
Home My Page Project Tree Code Snippets Project Openings Batteries : Revised Standard Library
Summary Activity Forums Tracker Lists Tasks Docs News Files

Bugs: Browse | Download .csv

[#227] close_out does not close_out ??

Date:
2009-06-19 06:04
Priority:
3
State:
Open
Submitted by:
Assigned to:
David Teller (yoric)
Summary:
close_out does not close_out ??

Detailed description
According to the docs

> some IO.outputs are built on top of other IO.outputs for the same
> purpose (e.g. on-the-fly compression of a file or network
> information). In this case, closing the "outer" IO.input/IO.output
> (e.g. the decompressor/compressor) will not close the "inner"
> IO.input/IO.output (e.g. access to the file or to the network). You
> will need to close the "inner" IO.input/IO.output, which will
> automatically flush the outer IO.input/IO.output and close it.

It seems to me that this is happening with the following code:

let r,w = Unix.open_process "cat";;
Printf.fprintf w "hello world\n";;
close_out w;;
try
while true do
  print_char (input_char r)
done with _ -> ();;

Compiled in batteries the result hangs.  Compiled with straight ocamlc
it prints "hello world".  Most likely culprit is the close_out not
operating correctly.

However I don't see in the docs a way close the underlying IO.output.
Either the docs are buggy or something else is wrong.

File attached, compile with

    ocamlc unix.cma t.ml -o t

or

    ocamlfind batteries/ocamlc t.ml -o t

and run with

    ./t

Followup

Message
Date: 2009-06-20 15:32
Sender: David Teller

Yes, we should probably get [cleanup] to be true by default.
Date: 2009-06-20 06:24
Sender: Trevor Jim

Well, I was misled because I was used to the ocaml version, and
I looked back at the ocaml documentation, and at various examples
people have posted over some years.

I think, therefore, that changing the behavior wrt the ocaml
version has downsides :-).

Also, Unix and networking books (e.g., Stevens) will tell you
to close the file descriptor in this case.  Of course, this is
not a file descriptor but still, I'm likely to be looking at
a networking book when doing this sort of thing.

I'm not even sure what "[close_out] closes the output
but not the underlying process" means.  How is the output
closed if the underlying **file descriptor** is not closed? 
And closing the file descriptor does not kill the process, if
that's what you mean by "closing" a process.

So I'm voting to restore the original behavior :-)
Date: 2009-06-19 22:02
Sender: David Teller

After a complex sequence of debugging, I took the time to read
my own documentation and realized that this was actually the
documented behavior: by default, [close_out] closes the output
but not the underlying process.

If you want the process to close when [close_out] is invoked,
you should create it with [~cleanup:true].

Now, the question is: should we change the behavior?
Date: 2009-06-19 17:26
Sender: David Teller

I have just added a test for this bug to the testsuite. Strangely,
the test seems to work. It uses IO.read_line which might be the
reason for difference. This is puzzling.
Date: 2009-06-19 16:23
Sender: Trevor Jim

Here is a workaround:

let r,w = Unix.open_process "cat";;
Printf.fprintf w "hello world\n";;
flush w;;
close_out w;;
try let fd = Unix.descr_of_out_channel w in Unix.close fd with
_ -> ();;
try
while true do
  print_char (input_char r)
done with _ -> ();;

I have added a flush and a Unix.close.  The Unix.close is necessary,
the batteries version hangs without it.
Date: 2009-06-19 16:15
Sender: Trevor Jim

I don't think it is a flushing problem, or, if so, that's an
additional issue.  (I have tried explicitly flushing and that
doesn't help, and looking at the source it seems to flush.)

Furthermore I have run strace on both versions.  In the batteries
version I can see that "hello world\n" is written and
also read.  Then there is another read that hangs.  The cat process
is waiting for the EOF before it prints anything.

I also see a close in the non-batteries version and no close
in the batteries version.
Date: 2009-06-19 07:55
Sender: David Teller

Indeed, there seems to be a problem with flushing.

Related Tasks:

No Related Tasks

Attached Files:

Name Download
t.ml Download

Changes:

Field Old Value Date By
ResolutionAccepted As Bug2009-06-19 22:02yoric
assigned_tonone2009-06-19 17:26yoric
ResolutionNone2009-06-19 07:55yoric
File Added41: t.ml2009-06-19 06:04trevor

Powered By GForge Collaborative Development Environment