Two-way pipe on an awk process

  • Follow


[This started as a call for help, but now is for discussion.]

Using two-way pipes in Gawk with the separate program being an Awk program
(Gawk process) one will get buffering problems.  The result is that
currently Gawk needs pseydo-ttys (ptys) for two-communication to another
Awk program.

Here's a simple example involving an Awk version of cat(1) called cat.awk,
which is used in a simple two-way i/o example script called 2way-io.awk,
which really just functions as a simple unix cat(1), also.

$ cat cat.awk
{
  print $0
}

$ cat 2way-io.awk
BEGIN {
  prog = "gawk -f ./cat.awk"; ## pseudo-ttys not needed when /bin/cat
  PROCINFO[prog, "pty"] = 1; ## use pseydo-ttys
}

{
  print $0 |& prog
  prog |& getline result;
  print result;
}

END {
  close(prog);
}

Usage

$ gawk -f cat.awk
> foo
-| foo

$ gawk -f 2way-io.awk
> foo
-| foo

Here's the documentation I read on Two-way pipes in the GNU Awk User
Manual:
<http://www.gnu.org/software/gawk/manual/html_node/Two_002dway-I_002fO.html>

/a
0
Reply Aaron 1/7/2005 5:43:23 PM

In article <Pine.A41.4.58.0501071121001.106090@elk.uvm.edu>,
Aaron S. Hawley <Aaron.Hawley@uvm.edu> wrote:
>[This started as a call for help, but now is for discussion.]
>
>Using two-way pipes in Gawk with the separate program being an Awk program
>(Gawk process) one will get buffering problems.  The result is that
>currently Gawk needs pseydo-ttys (ptys) for two-communication to another
>Awk program.

You can generalize this to "using pipes with any program that uses stdio-style
buffering with no way to control that buffering is liable to result in
buffering problems".  A gawk program, at least, can eliminate its problems by
fflush()ing prints to pipes.  If you add "fflush()" after the print in cat.awk,
it'll work without needing the pty in 2way-io.awk.  In many other awks you can 
also flush the standard output, though it is clumsier - print to "/dev/stdout",
and then close("/dev/stdout") after each print:

{
  print $0 > "/dev/stdout"
  close("/dev/stdout")
}

	John
-- 
John DuBois  spcecdt@armory.com  KC6QKZ/AE  http://www.armory.com/~spcecdt/
0
Reply spcecdt 1/7/2005 9:47:16 PM


On Fri, 7 Jan 2005, John DuBois wrote:

> You can generalize this to "using pipes with any program that uses
> stdio-style buffering with no way to control that buffering is liable to
> result in buffering problems".  A gawk program, at least, can eliminate
> its problems by fflush()ing prints to pipes.  If you add "fflush()"
> after the print in cat.awk, it'll work without needing the pty in
> 2way-io.awk. [...]

Thanks.  I guess you learn something new about standard output, everday.

My motivation was trying to write a simple checkerboard in Awk: so simple
that it's only function is taking from single-line text moves on stdout
(understood by a valid command-line player) from one player and
communicating them on stdin to the other player who then responds with
it's counter move on stdout.  The players themselves verify the rules are
being followed and decide who wins (making this Awk checkerboard no more
intelligent then the real thing).

For example, included below is a checker board playing a computer player
against itself.  The necessary function calls to fflush() are made by the
player programs themselves.

Thanks again,
/a

BEGIN {
  player1 = "./checker_player";
  player2 = "./checker_player";
  player1black = player1 " 1"; #play first
  player2white = player2 " 2"; #play second
  do {
    player1black |& getline play1;
    print "black played: " play1;
    print play1 |& player2white;
    player2white |& getline play2;
    print "white played: " play2;
    print play2 |& player1black;
  } while (play1 != "" && play1 > 0 \
	   && play2 != "" && play2 > 0);
  close(player1black);
  close(player2white);
}
## TODO: check if a player program has exited.
0
Reply Aaron 1/11/2005 9:33:10 PM

2 Replies
484 Views

(page loaded in 0.067 seconds)

Similiar Articles:













7/22/2012 7:35:10 AM


Reply: