[erlang-questions] Problem with io monitor - a bug?

Patrik Nyblom pan@REDACTED
Tue Dec 4 11:48:06 CET 2012


No, it's not a bug. It's a race in the calling code. The spawned process 
sends the first io-request and the shell sends the second. The first 
"read" will be overridden while the shell's request is served. They are 
so to say stacked. Having two processes (the shell and your newly 
spawned process) reading from the same io-device is generally not a good 
idea, they are competing for a single resource that is kind of hard to 
share... You have to keep other processes from tampering with your 
terminal while you're reading it, in this case by letting the shell wait 
for your process.

In fact, you actually get your prompt from the spawned process written, 
but the shell will override/overwrite it. Try sleeping the shell for a 
second and your prompt will temporarily be shown, but then the shell 
comes back and your prompt disappears again. If you sleep for a while in 
the child process before reading, the child will instead override the 
shell. There's no telling which one will be stacked upon the other. It's 
kind of impossible to determine which order is preferred by the 
caller... So, your program has to decide on the order by synchronizing 
it's activities.

1> Prompt = "Please enter data: ".
2> F = fun() -> try Result = io:read(Prompt), io:format("Res: 
~p~n",[Result]) catch A:B -> io:format("Read error: ~p:~p~n",[A,B]) end end.
3> {Pid,Ref} = spawn_monitor(F), receive after 1000 -> ok end.
%% "Please Enter data: " will be shown for a second, then disappears and 
the shell prompt comes back.
4> receive after 1000 -> ok end.
%% Please enter data will appear again, but disappears after a second again.
5> receive {'DOWN',Ref,process,Pid,_} -> ok end.
Please enter data: hi.
Res: {ok,hi}
%% Now try waiting a second to make the shell send the io-request before 
your spawned process
6> G = fun() -> try receive after 1000 -> ok end, Result = 
io:read(Prompt), io:format("Res: ~p~n",[Result]) catch A:B -> 
io:format("Read error: ~p:~p~n",[A,B]) end end.
7> spawn(G).
%% First you will see the shell prompt for ~ a second, then you will get:
Please enter data: hello.
Res: {ok,hello}

In other words, do not have two processes competing tor one terminal, it 
will only give confusing results :)

/Patrik, OTP

On 11/30/2012 01:57 PM, Álvaro wrote:
> Dear all,
> Every time I run this simple code, my program gets stuck:
> > Pid = spawn (moduleName,myread,["hello"]).
> where:
> myread(Prompt)->
>     try
>       Result = io:read(Prompt),
>       io:format("Res: ~p~n",[Result]),
>     catch
>     A:B->
>         io:format("Read error: ~p:~p~n",[A,B]),
>         false
>     end.
> if I check the status of the process:
> > erlang:process_info(Pid).
> [{current_function,{io,wait_io_mon_reply,2}},
>  {initial_call,{default_environment,myread,1}},
>  {status,waiting},
>  {message_queue_len,0},
>  {messages,[]},
>  {links,[]},
>  {dictionary,[]},
>  {trap_exit,false},
>  {error_handler,error_handler},
>  {priority,normal},
>  {group_leader,<0.25.0>},
>  {total_heap_size,233},
>  {heap_size,233},
>  {stack_size,7},
>  {reductions,28},
>  {garbage_collection,[{min_bin_vheap_size,46368},
>                       {min_heap_size,233},
>                       {fullsweep_after,65535},
>                       {minor_gcs,0}]},
>  {suspending,[]}]
> It seems to be stuck in the function io:wait_io_mon_reply/2 (surfing 
> through io.erl I found that this function waits for a response from 
> the  process managing the io ). This process is not answering, hence 
> my code stops working.
> I've checked that the "group_leader()" once I spawn the reading 
> process is the same used by my shell.
> Any ideas on how to deal with it?
> Regards,
> Álvaro
> _______________________________________________
> erlang-questions mailing list
> erlang-questions@REDACTED
> http://erlang.org/mailman/listinfo/erlang-questions

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20121204/cbeb5e99/attachment.htm>

More information about the erlang-questions mailing list