Unix Programming - Select system call

This is Interesting: Free IT Magazines  
Home > Archive > Unix Programming > February 2006 > Select system call





You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

Author Select system call
Vijairaj R

2006-02-22, 6:04 pm

Hi All,
I have a problem using select multiple times on the same file
descriptor. There are two threads waiting for an event on a file
descriptor. some times only one thread is notified of the input and the
other is not notified.

Is it legitimate to use select multiple times on the same file
descriptor?

--
Thanks,
Vijairaj

Pascal Bourguignon

2006-02-22, 6:04 pm

"Vijairaj R" <Vijairaj.R@gmail.com> writes:

> Hi All,
> I have a problem using select multiple times on the same file
> descriptor. There are two threads waiting for an event on a file
> descriptor. some times only one thread is notified of the input and the
> other is not notified.
>
> Is it legitimate to use select multiple times on the same file
> descriptor?


Yes, if you put the same fd in different sets. If one threads waits
to write to the file, and the other waits to read.

If both threads wait to read, or both wait to write, it could lead to
a deadlock if both select calls would notify the same fd.

--
__Pascal Bourguignon__ http://www.informatimago.com/

Pour moi, la grande question n'a jamais été: «Qui suis-je? Où vais-je?»
comme l'a formulé si adroitement notre ami Pascal, mais plutôt:
«Comment vais-je m'en tirer?» -- Jean Yanne
Chris McDonald

2006-02-22, 6:04 pm

"Vijairaj R" <Vijairaj.R@gmail.com> writes:

>Hi All,
>I have a problem using select multiple times on the same file
>descriptor. There are two threads waiting for an event on a file
>descriptor. some times only one thread is notified of the input and the
>other is not notified.


>Is it legitimate to use select multiple times on the same file
>descriptor?


Yes, of course.
Do you re-initialize your FDSETs before *every* call to select()?
The contents of the FDSETs are (may be) modified as a result of calling
select().

--
Chris.
David Schwartz

2006-02-22, 6:04 pm


"Pascal Bourguignon" <usenet@informatimago.com> wrote in message
news:87u0arrzgp.fsf@thalassa.informatimago.com...

> If both threads wait to read, or both wait to write, it could lead to
> a deadlock if both select calls would notify the same fd.


I don't see how. Though I can't imagine how this could be useful, I
can't imagine how it would cause a deadlock either.

DS


Pascal Bourguignon

2006-02-22, 6:04 pm

"David Schwartz" <davids@webmaster.com> writes:

> "Pascal Bourguignon" <usenet@informatimago.com> wrote in message
> news:87u0arrzgp.fsf@thalassa.informatimago.com...
>
>
> I don't see how. Though I can't imagine how this could be useful, I
> can't imagine how it would cause a deadlock either.


Of course, you'd need help from the threads.

After a select for reading, a thread may assume it can read (at least
one byte) without blocking. If only one byte is available and two
threads do read, one of them may block, and may not release another
ressouce needed by the other thread.

--
__Pascal Bourguignon__ http://www.informatimago.com/
Small brave carnivores
Kill pine cones and mosquitoes
Fear vacuum cleaner
skylazart@gmail.com

2006-02-22, 6:04 pm

the same descriptor and the same operation (read or write)?
didn't it could lead a race condition?

i think you need a semaphore or a mutex.

Chris Friesen

2006-02-22, 6:04 pm

Pascal Bourguignon wrote:
> "David Schwartz" <davids@webmaster.com> writes:


> After a select for reading, a thread may assume it can read (at least
> one byte) without blocking.


Actually, this is not a reliable assumption, at least on some linux systems.

Some kernel versions delay UDP checksum scans until the read()/recv()
call. If the checksum is corrupt, it then throws away the packet.
There is no valid data to read, but the app has issued a blocking read().

The reason this is done is for performance reasons...by delaying it
until the read, the checksum operation is nearly free. If you do the
checksum earlier, then you get suboptimal caching.

There was a heated discussion on the linux networking list a while back
on this topic. Its fixed in current versions, but older ones are affected.

It's safer to use a nonblocking read, even if select() says that the
socket is readable.

Chris
David Schwartz

2006-02-22, 6:04 pm


"Pascal Bourguignon" <usenet@informatimago.com> wrote in message
news:87fymbrsf9.fsf@thalassa.informatimago.com...

> After a select for reading, a thread may assume it can read (at least
> one byte) without blocking.


It might assume that, but its assumption might be incorrect. Nowhere
does it say that the 'select' function call guarantees anything about the
future.

> If only one byte is available and two
> threads do read, one of them may block, and may not release another
> ressouce needed by the other thread.


Sure, but if no bytes are available and one does a read, it may block.

Imagine, for example, an network protocol that allows one side to
"revoke" message before they're received by the other side. The 'select'
function is protocol neutral.

Like every other status function, the 'select' function tells you
something that *was* true at some time in the past. There is no assurance
it's still true. Assuming that it must still be so is *bad* programming.

DS


David Schwartz

2006-02-22, 6:04 pm


"Chris Friesen" <cbf123@mail.usask.ca> wrote in message
news:11vpn12a9oi8o16@corp.supernews.com...

> It's safer to use a nonblocking read, even if select() says that the
> socket is readable.


You mean "even if select() says that the socket *WAS* readable". The
'select' call makes no attempt or promise to predict the future.

DS


Chris Friesen

2006-02-22, 8:51 pm

David Schwartz wrote:
> "Chris Friesen" <cbf123@mail.usask.ca> wrote in message


[vbcol=seagreen]
> You mean "even if select() says that the socket *WAS* readable". The
> 'select' call makes no attempt or promise to predict the future.


Actually it does...the spec reads like this:

"A descriptor shall be considered ready for reading when a call to an
input function with O_NONBLOCK clear would not block, whether or not the
function would transfer data successfully. (The function might return
data, an end-of-file indication, or an error other than one indicating
that it is blocked, and in each of these cases the descriptor shall be
considered ready for reading.)"

According to that, if select() returns readable, the next blocking read
on that socket must not block. If you read in another thread, then the
spec refers to the read in that other thread. If you are a single
threaded app though...

This was the eventual interpretation of the networking guys, and a patch
was added to solve the issue (at a performance cost for blocking sockets).

Chris
David Schwartz

2006-02-22, 8:51 pm


"Chris Friesen" <cbf123@mail.usask.ca> wrote in message
news:11vq0p8kecunv1c@corp.supernews.com...

> David Schwartz wrote:


[vbcol=seagreen]
[vbcol=seagreen]
[vbcol=seagreen]
> Actually it does...the spec reads like this:


No, it does not.

> "A descriptor shall be considered ready for reading when a call to an
> input function with O_NONBLOCK clear would not block, whether or not the
> function would transfer data successfully. (The function might return
> data, an end-of-file indication, or an error other than one indicating
> that it is blocked, and in each of these cases the descriptor shall be
> considered ready for reading.)"


Notice it says *WOULD* not block.

> According to that, if select() returns readable, the next blocking read on
> that socket must not block. If you read in another thread, then the spec
> refers to the read in that other thread. If you are a single threaded app
> though...


No, it doesn't say a *subsequent* operation *will* not block. It says a
hypothetical *concurrent* operation *would* not block.

> This was the eventual interpretation of the networking guys, and a patch
> was added to solve the issue (at a performance cost for blocking sockets).


You are confusing two different issues. In their case, a concurrent read
operation would have blocked, which the specification does prohibit. (So
they were correct.)

However, this doesn't mean that a future operation cannot block. For
example, it is perfectly legal for an implementation to choose to discard a
UDP datagram even though it has given a read indication in a call to
'select'. This will make the next 'recv' block. However, had their been a
read operation during the select, it would not have blocked, which is what
'select' is supposed to tell you.

DS


David Schwartz

2006-02-22, 8:51 pm


"David Schwartz" <davids@webmaster.com> wrote in message
news:dtj0p2$tug$1@nntp.webmaster.com...

> You are confusing two different issues. In their case, a concurrent
> read operation would have blocked, which the specification does prohibit.
> (So they were correct.)


Actually, they are incorrect, but it would be too long and complicated
to explain why here and would take us deep into territory not related to
this issue. (Hint: Think about the as-if rule.)

DS


Vijairaj R

2006-02-23, 2:54 am

Chris McDonald wrote:
> "Vijairaj R" <Vijairaj.R@gmail.com> writes:
>
>
>
> Yes, of course.
> Do you re-initialize your FDSETs before *every* call to select()?
> The contents of the FDSETs are (may be) modified as a result of calling
> select().


In my case the select calls are issued by two different threads but on
the same file descriptor. Both of the select calls are waiting for
input on the descriptor. Some times this problem occurs where only one
of the select call returns when there is data available for reading.

Vijairaj R

2006-02-23, 2:54 am

Pascal Bourguignon wrote:
> After a select for reading, a thread may assume it can read (at least
> one byte) without blocking. If only one byte is available and two
> threads do read, one of them may block, and may not release another
> ressouce needed by the other thread.


It only happens when the select call in both the threads return when
there is data available for reading. But in my case only one of the
select call returns and the other thread doesnot even know that data
has arrived and the select call in that thread is still waiting for
data.

Sponsored Links






Free braindumps | Software forum | Database administration forum

Copyright 2003 - 2008 webservertalk.com