diff options
-rw-r--r-- | net/tipc/socket.c | 78 |
1 files changed, 36 insertions, 42 deletions
diff --git a/net/tipc/socket.c b/net/tipc/socket.c index ae45df060e3a..1b5fb6103ded 100644 --- a/net/tipc/socket.c +++ b/net/tipc/socket.c | |||
@@ -102,44 +102,6 @@ static void sock_unlock(struct tipc_sock* tsock) | |||
102 | } | 102 | } |
103 | 103 | ||
104 | /** | 104 | /** |
105 | * pollmask - determine the current set of poll() events for a socket | ||
106 | * @sock: socket structure | ||
107 | * | ||
108 | * TIPC sets the returned events as follows: | ||
109 | * a) POLLRDNORM and POLLIN are set if the socket's receive queue is non-empty | ||
110 | * or if a connection-oriented socket is does not have an active connection | ||
111 | * (i.e. a read operation will not block). | ||
112 | * b) POLLOUT is set except when a socket's connection has been terminated | ||
113 | * (i.e. a write operation will not block). | ||
114 | * c) POLLHUP is set when a socket's connection has been terminated. | ||
115 | * | ||
116 | * IMPORTANT: The fact that a read or write operation will not block does NOT | ||
117 | * imply that the operation will succeed! | ||
118 | * | ||
119 | * Returns pollmask value | ||
120 | */ | ||
121 | |||
122 | static u32 pollmask(struct socket *sock) | ||
123 | { | ||
124 | u32 mask; | ||
125 | |||
126 | if ((skb_queue_len(&sock->sk->sk_receive_queue) != 0) || | ||
127 | (sock->state == SS_UNCONNECTED) || | ||
128 | (sock->state == SS_DISCONNECTING)) | ||
129 | mask = (POLLRDNORM | POLLIN); | ||
130 | else | ||
131 | mask = 0; | ||
132 | |||
133 | if (sock->state == SS_DISCONNECTING) | ||
134 | mask |= POLLHUP; | ||
135 | else | ||
136 | mask |= POLLOUT; | ||
137 | |||
138 | return mask; | ||
139 | } | ||
140 | |||
141 | |||
142 | /** | ||
143 | * advance_queue - discard first buffer in queue | 105 | * advance_queue - discard first buffer in queue |
144 | * @tsock: TIPC socket | 106 | * @tsock: TIPC socket |
145 | */ | 107 | */ |
@@ -390,15 +352,47 @@ static int get_name(struct socket *sock, struct sockaddr *uaddr, | |||
390 | * @sock: socket for which to calculate the poll bits | 352 | * @sock: socket for which to calculate the poll bits |
391 | * @wait: ??? | 353 | * @wait: ??? |
392 | * | 354 | * |
393 | * Returns the pollmask | 355 | * Returns pollmask value |
356 | * | ||
357 | * COMMENTARY: | ||
358 | * It appears that the usual socket locking mechanisms are not useful here | ||
359 | * since the pollmask info is potentially out-of-date the moment this routine | ||
360 | * exits. TCP and other protocols seem to rely on higher level poll routines | ||
361 | * to handle any preventable race conditions, so TIPC will do the same ... | ||
362 | * | ||
363 | * TIPC sets the returned events as follows: | ||
364 | * a) POLLRDNORM and POLLIN are set if the socket's receive queue is non-empty | ||
365 | * or if a connection-oriented socket is does not have an active connection | ||
366 | * (i.e. a read operation will not block). | ||
367 | * b) POLLOUT is set except when a socket's connection has been terminated | ||
368 | * (i.e. a write operation will not block). | ||
369 | * c) POLLHUP is set when a socket's connection has been terminated. | ||
370 | * | ||
371 | * IMPORTANT: The fact that a read or write operation will not block does NOT | ||
372 | * imply that the operation will succeed! | ||
394 | */ | 373 | */ |
395 | 374 | ||
396 | static unsigned int poll(struct file *file, struct socket *sock, | 375 | static unsigned int poll(struct file *file, struct socket *sock, |
397 | poll_table *wait) | 376 | poll_table *wait) |
398 | { | 377 | { |
399 | poll_wait(file, sock->sk->sk_sleep, wait); | 378 | struct sock *sk = sock->sk; |
400 | /* NEED LOCK HERE? */ | 379 | u32 mask; |
401 | return pollmask(sock); | 380 | |
381 | poll_wait(file, sk->sk_sleep, wait); | ||
382 | |||
383 | if (!skb_queue_empty(&sk->sk_receive_queue) || | ||
384 | (sock->state == SS_UNCONNECTED) || | ||
385 | (sock->state == SS_DISCONNECTING)) | ||
386 | mask = (POLLRDNORM | POLLIN); | ||
387 | else | ||
388 | mask = 0; | ||
389 | |||
390 | if (sock->state == SS_DISCONNECTING) | ||
391 | mask |= POLLHUP; | ||
392 | else | ||
393 | mask |= POLLOUT; | ||
394 | |||
395 | return mask; | ||
402 | } | 396 | } |
403 | 397 | ||
404 | /** | 398 | /** |