simple socket client-server interaction works on C, but the analogouscode does not work with Perl

Discussion in 'Perl Misc' started by Mark_Galeck, Aug 16, 2009.

  1. Mark_Galeck

    Mark_Galeck Guest

    Hello,

    here is a simplest possible (I think), socket client-server code in
    Perl. You start the server first, it listens, client starts, sends
    the server a message, server replies back, that's it. The exact
    analogous code to this, written in C, works as expected, but here in
    Perl, not (both run under the latest Ubuntu). So I think, I
    understand how the sockets work, I just don't understand how Perl
    works.

    Under Perl, the server just prints "accepted", but never gets any
    messages from the client. Curiously, if I comment out the client
    reading from server after sending, then everything else is fine, the
    server gets the message and both exit.

    What is going on?? Thank you for your insights! Mark


    serv.pl:

    use Socket;



    socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));

    bind(SERVER, sockaddr_in(3000, inet_aton("127.0.0.1")));

    listen(SERVER, 1);

    accept(CLIENT, SERVER);

    print "accepted\n";



    $_ = <CLIENT>;

    print "read from client:\n";

    print ;

    print CLIENT "foobar\n";



    close(CLIENT);

    close(SERVER);



    client.pl:

    use Socket;



    socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));


    connect(SERVER, sockaddr_in(3000, inet_aton("127.0.0.1")))

    or die "WHOA! could not connect";



    print SERVER "foo\n";

    $_ = <SERVER>; #only if I comment this line out, does the server get
    the above message!!

    print "read from server:\n";

    print ;


    close(SERVER);
    Mark_Galeck, Aug 16, 2009
    #1
    1. Advertising

  2. Re: simple socket client-server interaction works on C, but theanalogous code does not work with Perl

    Mark_Galeck wrote:
    > [...]
    > Under Perl, the server just prints "accepted", but never gets any
    > messages from the client. Curiously, if I comment out the client
    > reading from server after sending, then everything else is fine, the
    > server gets the message and both exit.
    >
    > What is going on?? Thank you for your insights! Mark


    You are using buffered I/O without explicit flush.

    http://perldoc.perl.org/perlfaq5.ht...er-an-output-filehandle?--Why-must-I-do-this?

    The simplies fix of your program (measured in lines of code) is
    this line:

    binmode(SERVER, ":unix");

    --
    Brüder, in die Tonne die Freiheit,
    Brüder, ein Stoppschild davor.
    Egal was die Schwarzen Verlangen
    Rufen wir: Ja! Brav im Chor.
    Alexander Bartolich, Aug 16, 2009
    #2
    1. Advertising

  3. Re: simple socket client-server interaction works on C, but theanalogous code does not work with Perl

    On 2009-08-16 14:50, Mark_Galeck <> wrote:
    > here is a simplest possible (I think), socket client-server code in
    > Perl. You start the server first, it listens, client starts, sends
    > the server a message, server replies back, that's it. The exact
    > analogous code to this, written in C, works as expected, but here in
    > Perl, not (both run under the latest Ubuntu). So I think, I
    > understand how the sockets work, I just don't understand how Perl
    > works.
    >
    > Under Perl, the server just prints "accepted", but never gets any
    > messages from the client. Curiously, if I comment out the client
    > reading from server after sending, then everything else is fine, the
    > server gets the message and both exit.
    >
    > What is going on?? Thank you for your insights! Mark
    >

    [...]
    > client.pl:
    >
    > use Socket;
    >
    >
    >
    > socket(SERVER, PF_INET, SOCK_STREAM, getprotobyname('tcp'));
    >
    >
    > connect(SERVER, sockaddr_in(3000, inet_aton("127.0.0.1")))
    >
    > or die "WHOA! could not connect";


    At this point, the file handle SERVER is buffered, so ...

    > print SERVER "foo\n";


    This will *not* send "foo\n" to the server, it will only put it into the
    buffer.


    > $_ = <SERVER>; #only if I comment this line out, does the server get
    > the above message!!


    Now you wait for a message from the server. But you haven't sent a
    message to the server yet, so the server is waiting for the client, too.

    This is called a deadlock.


    > print "read from server:\n";
    >
    > print ;
    >
    >
    > close(SERVER);


    The close would flush the buffer (and send everything in it to the
    server), but that line is never reached.

    See the question "How do I flush/unbuffer an output filehandle? Why
    must I do this?" in the FAQ for a solution.

    Or just use IO::Socket objects instead of plain file handles. They have
    autoflush turned on by default (the FAQ is out-of-date in this respect).

    hp
    Peter J. Holzer, Aug 16, 2009
    #3
  4. Mark_Galeck

    Mark_Galeck Guest

    Re: simple socket client-server interaction works on C, but theanalogous code does not work with Perl

    thank you Peter and Alexander, this makes perfect sense
    Mark_Galeck, Aug 16, 2009
    #4
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. stan k.
    Replies:
    3
    Views:
    6,635
    Gordon Beaton
    Sep 27, 2003
  2. John fabiani
    Replies:
    14
    Views:
    498
    Donn Cave
    Jul 2, 2004
  3. Tim
    Replies:
    7
    Views:
    586
    Nobody
    Feb 18, 2011
  4. Phi!
    Replies:
    1
    Views:
    168
  5. Andrzej
    Replies:
    0
    Views:
    67
    Andrzej
    Oct 6, 2003
Loading...

Share This Page