algolejos
algolejos

Reputation: 139

Blocking sockets

I'm programing a small c linux local server. I've read a lot of documentation about threads, select function, nonblocking options, etc. But I can't find any documentation about how to deal with client-side failures.

More specifically, working with threads and blocking sockets (not the best idea, I know, but I'm just running some tests), what happens when the client connection goes too slow? or what happens when the client doesn't close the connection properly (or not closing it at all)? Will my socket remain blocked? or the thread will never finish?

How to deal with this situations?

Upvotes: 2

Views: 230

Answers (2)

nneonneo
nneonneo

Reputation: 179392

Typically, sockets have some timeout value which can be controlled by the client. If a connection runs too slowly, or the connection dies for some reason (e.g. poor internet connectivity), the socket operation might continue to block until the timeout expires. With Linux sockets, when the timeout expires, you'll get an ETIMEDOUT errno that you can then handle later.

Typical values for the timeout are on the order of 60-300 seconds, but you can set them lower if you want to know about timeouts sooner. You can also set it to infinite, but this isn't recommended if you're using direct blocking calls since you could hang your thread forever.

On Linux (and any other system using the BSD socket API), you may change the socket timeouts using

struct timeval timeout;
timeout.tv_sec = 60;
timeout.tv_usec = 0;

setsockopt(socket, SOL_SOCK, SO_RCVTIMEO, &timeout, sizeof(struct timeval));

Upvotes: 1

missimer
missimer

Reputation: 4079

When using blocking sockets you have a couple of options.

One is to have one thread per client such that when you wait for information it doesn't matter how long you block. Note that when a connection is closed, the blocked operation will terminate. You can read a much more detailed description of this here.

An alternative to multiple threads is to use select. This allows you to wait on multiple file descriptors until some subset of the file descriptors are ready in the sense that they will not block. So basically instead of blocking on a single file descriptor during a read or write, you instead block on select and then you know you won't later block on the read/write.

Finally, you can use the asynchronous I/O functions, aio_read and aio_write which will perform the read/write asynchronously from the calling thread of execution.

Upvotes: 2

Related Questions