creating a socket connection timeout in "C" linux - Unix

This is a discussion on creating a socket connection timeout in "C" linux - Unix ; How can I open a socket connection with a timeout? Currently when I make a call like "var = socket(" if the internet is down or there is a problem reaching the destination computer, my programs behaves like it is ...

+ Reply to Thread
Results 1 to 7 of 7

Thread: creating a socket connection timeout in "C" linux

  1. creating a socket connection timeout in "C" linux

    How can I open a socket connection with a timeout? Currently when I
    make a call like "var = socket(" if the internet is down or there is
    a problem reaching the destination computer, my programs behaves like
    it is freezing. It here a way to control this behavior via a timeout
    or any other method so that if the destination cannot then my program
    will not hang?

  2. Re: creating a socket connection timeout in "C" linux

    On Jun 6, 7:43 am, d-fan wrote:
    > How can I open a socket connection with a timeout? Currently when I
    > make a call like "var = socket(" if the internet is down or there is
    > a problem reaching the destination computer, my programs behaves like
    > it is freezing. It here a way to control this behavior via a timeout
    > or any other method so that if the destination cannot then my program
    > will not hang?


    The socket() call should never hang. If it does it means either the OS
    is very busy or theres something wierd happening.

    I assume you're writing a client and mean connect() hangs? In which
    case you can either spawn a seperate thread or process to run the
    connect in , or you can set the socket to non blocking which means
    connect() will return immediately and then you wait in a select() for
    the write descriptor to be set. This can be quite tricky to code so
    its probably best you buy a book such as Unix Network Programming or
    similar. However some example code would be:

    iif ((sock = socket(AF_INET,SOCK_STREAM,0)) == -1)
    {
    do something
    }
    flags = fcntl(sock,F_GETFL,0);
    fcntl(sock,F_SETFL, flags | O_NONBLOCK)

    if (!connect(sock,....))
    {
    got immediate connect
    }

    if (errno != EINPROGRESS)
    {
    perror("connect"); exit(1);
    }
    FD_ZERO(&wset);
    FD_SET(sock,&wset);
    timeout.tv_sec=1;
    timeout.tv_usec=0;

    /* Wait for write bit to be set */
    switch (select(FD_SETSIZE,0,&wset,0,&timeout))
    {
    }

    Obviously you'll need to fill in lots of code above but thats the
    general idea of how to write a single threaded non blocking connect.

    B2003

  3. Re: creating a socket connection timeout in "C" linux

    d-fan writes:
    > How can I open a socket connection with a timeout? Currently when I
    > make a call like "var = socket(" if the internet is down or there is
    > a problem reaching the destination computer, my programs behaves like
    > it is freezing. It here a way to control this behavior via a timeout


    This is already done by the kernel. According to RFC1122 4.2.3.5 a SYN
    (TCP connection initiation request) must be retransmitted for at least
    three minutes before establishing the connection is considered to have
    failed. Assuming that you (like your countless predecessors) really
    believe that the cross sum of the bust size of your girl friend is a
    number you just happen to like a lot more, the easy, unreliable way
    to enforce a shorter timeout is alarm(3).


  4. Re: creating a socket connection timeout in "C" linux

    Rainer Weikusat wrote:
    > d-fan writes:
    >> How can I open a socket connection with a timeout? Currently when I
    >> make a call like "var = socket(" if the internet is down or there is
    >> a problem reaching the destination computer, my programs behaves like
    >> it is freezing. It here a way to control this behavior via a timeout

    >
    > This is already done by the kernel. According to RFC1122 4.2.3.5 a SYN
    > (TCP connection initiation request) must be retransmitted for at least
    > three minutes before establishing the connection is considered to have
    > failed. Assuming that you (like your countless predecessors) really
    > believe that the cross sum of the bust size of your girl friend is a
    > number you just happen to like a lot more, the easy, unreliable way
    > to enforce a shorter timeout is alarm(3).


    What makes alarm() unreliable?

    Alex

  5. Re: creating a socket connection timeout in "C" linux

    Alex Fraser writes:
    > Rainer Weikusat wrote:
    >> d-fan writes:
    >>> How can I open a socket connection with a timeout?


    [...]

    >> the easy, unreliable way to enforce a shorter timeout is alarm(3).

    >
    > What makes alarm() unreliable?


    I was being too imprecise. The 'easy, unreliable timeout' is setting
    up a no-op handler for SIGALRM and relying on the alarm signal to
    interrupt the connect. The problem is that 'setting up an alarm' and
    'starting to connect' are two operations instead of one atomic
    operation and their can be a near arbitrary delay between them because
    other processes could be scheduled. This means there is a chance that
    the SIGALRM may actually be posted to the process before the connect
    ever blocks.

  6. Re: creating a socket connection timeout in "C" linux

    Rainer Weikusat wrote:
    > Alex Fraser writes:
    >> Rainer Weikusat wrote:
    >>> d-fan writes:
    >>>> How can I open a socket connection with a timeout?

    >
    > [...]
    >
    >>> the easy, unreliable way to enforce a shorter timeout is alarm(3).

    >> What makes alarm() unreliable?

    >
    > I was being too imprecise. The 'easy, unreliable timeout' is setting
    > up a no-op handler for SIGALRM and relying on the alarm signal to
    > interrupt the connect. The problem is that 'setting up an alarm' and
    > 'starting to connect' are two operations instead of one atomic
    > operation and their can be a near arbitrary delay between them because
    > other processes could be scheduled. This means there is a chance that
    > the SIGALRM may actually be posted to the process before the connect
    > ever blocks.


    But you'd have the same "near arbitrary delay" even if there was an
    atomic "connect() with timeout" call, between timeout/connect success
    and the thread being scheduled again. So are you any worse off?

    Alex

  7. Re: creating a socket connection timeout in "C" linux

    Alex Fraser writes:
    > Rainer Weikusat wrote:
    >> Alex Fraser writes:
    >>> Rainer Weikusat wrote:
    >>>> d-fan writes:
    >>>>> How can I open a socket connection with a timeout?

    >> [...]
    >>
    >>>> the easy, unreliable way to enforce a shorter timeout is alarm(3).
    >>> What makes alarm() unreliable?

    >> I was being too imprecise. The 'easy, unreliable timeout' is setting
    >> up a no-op handler for SIGALRM and relying on the alarm signal to
    >> interrupt the connect. The problem is that 'setting up an alarm' and
    >> 'starting to connect' are two operations instead of one atomic
    >> operation and their can be a near arbitrary delay between them because
    >> other processes could be scheduled. This means there is a chance that
    >> the SIGALRM may actually be posted to the process before the connect
    >> ever blocks.

    >
    > But you'd have the same "near arbitrary delay" even if there was an
    > atomic "connect() with timeout" call, between timeout/connect success
    > and the thread being scheduled again. So are you any worse off?


    "Well, a piece of orbital junk could smash the building you are living
    in at any time so it would clearly be useless to prevent it from
    burning down by not making a large fire in the living room before
    leaving for a three week holiday trip."

    Relying on (a single) SIGALRM to interrupt a blocked system call could
    lead to a lost wakeup in particular circumstances. This potential
    problem can be avoided by suitable code, ie by longjumping from the
    handler instead. This still doesn't mean that connect was ever
    actually called, but that the program has done every possible thing to
    regain control after the timeout expired. Which in no way implies that
    some other problem could not cause a similar effect.



+ Reply to Thread