aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/eventpoll.c23
1 files changed, 12 insertions, 11 deletions
diff --git a/fs/eventpoll.c b/fs/eventpoll.c
index 4284cd31eba6..f5d69f46ba9b 100644
--- a/fs/eventpoll.c
+++ b/fs/eventpoll.c
@@ -34,6 +34,7 @@
34#include <linux/eventpoll.h> 34#include <linux/eventpoll.h>
35#include <linux/mount.h> 35#include <linux/mount.h>
36#include <linux/bitops.h> 36#include <linux/bitops.h>
37#include <linux/mutex.h>
37#include <asm/uaccess.h> 38#include <asm/uaccess.h>
38#include <asm/system.h> 39#include <asm/system.h>
39#include <asm/io.h> 40#include <asm/io.h>
@@ -46,7 +47,7 @@
46 * LOCKING: 47 * LOCKING:
47 * There are three level of locking required by epoll : 48 * There are three level of locking required by epoll :
48 * 49 *
49 * 1) epsem (semaphore) 50 * 1) epmutex (mutex)
50 * 2) ep->sem (rw_semaphore) 51 * 2) ep->sem (rw_semaphore)
51 * 3) ep->lock (rw_lock) 52 * 3) ep->lock (rw_lock)
52 * 53 *
@@ -67,9 +68,9 @@
67 * if a file has been pushed inside an epoll set and it is then 68 * if a file has been pushed inside an epoll set and it is then
68 * close()d without a previous call toepoll_ctl(EPOLL_CTL_DEL). 69 * close()d without a previous call toepoll_ctl(EPOLL_CTL_DEL).
69 * It is possible to drop the "ep->sem" and to use the global 70 * It is possible to drop the "ep->sem" and to use the global
70 * semaphore "epsem" (together with "ep->lock") to have it working, 71 * semaphore "epmutex" (together with "ep->lock") to have it working,
71 * but having "ep->sem" will make the interface more scalable. 72 * but having "ep->sem" will make the interface more scalable.
72 * Events that require holding "epsem" are very rare, while for 73 * Events that require holding "epmutex" are very rare, while for
73 * normal operations the epoll private "ep->sem" will guarantee 74 * normal operations the epoll private "ep->sem" will guarantee
74 * a greater scalability. 75 * a greater scalability.
75 */ 76 */
@@ -274,7 +275,7 @@ static struct super_block *eventpollfs_get_sb(struct file_system_type *fs_type,
274/* 275/*
275 * This semaphore is used to serialize ep_free() and eventpoll_release_file(). 276 * This semaphore is used to serialize ep_free() and eventpoll_release_file().
276 */ 277 */
277static struct semaphore epsem; 278static struct mutex epmutex;
278 279
279/* Safe wake up implementation */ 280/* Safe wake up implementation */
280static struct poll_safewake psw; 281static struct poll_safewake psw;
@@ -477,10 +478,10 @@ void eventpoll_release_file(struct file *file)
477 * cleanup path, and this means that noone is using this file anymore. 478 * cleanup path, and this means that noone is using this file anymore.
478 * The only hit might come from ep_free() but by holding the semaphore 479 * The only hit might come from ep_free() but by holding the semaphore
479 * will correctly serialize the operation. We do need to acquire 480 * will correctly serialize the operation. We do need to acquire
480 * "ep->sem" after "epsem" because ep_remove() requires it when called 481 * "ep->sem" after "epmutex" because ep_remove() requires it when called
481 * from anywhere but ep_free(). 482 * from anywhere but ep_free().
482 */ 483 */
483 down(&epsem); 484 mutex_lock(&epmutex);
484 485
485 while (!list_empty(lsthead)) { 486 while (!list_empty(lsthead)) {
486 epi = list_entry(lsthead->next, struct epitem, fllink); 487 epi = list_entry(lsthead->next, struct epitem, fllink);
@@ -492,7 +493,7 @@ void eventpoll_release_file(struct file *file)
492 up_write(&ep->sem); 493 up_write(&ep->sem);
493 } 494 }
494 495
495 up(&epsem); 496 mutex_unlock(&epmutex);
496} 497}
497 498
498 499
@@ -819,9 +820,9 @@ static void ep_free(struct eventpoll *ep)
819 * We do not need to hold "ep->sem" here because the epoll file 820 * We do not need to hold "ep->sem" here because the epoll file
820 * is on the way to be removed and no one has references to it 821 * is on the way to be removed and no one has references to it
821 * anymore. The only hit might come from eventpoll_release_file() but 822 * anymore. The only hit might come from eventpoll_release_file() but
822 * holding "epsem" is sufficent here. 823 * holding "epmutex" is sufficent here.
823 */ 824 */
824 down(&epsem); 825 mutex_lock(&epmutex);
825 826
826 /* 827 /*
827 * Walks through the whole tree by unregistering poll callbacks. 828 * Walks through the whole tree by unregistering poll callbacks.
@@ -843,7 +844,7 @@ static void ep_free(struct eventpoll *ep)
843 ep_remove(ep, epi); 844 ep_remove(ep, epi);
844 } 845 }
845 846
846 up(&epsem); 847 mutex_unlock(&epmutex);
847} 848}
848 849
849 850
@@ -1615,7 +1616,7 @@ static int __init eventpoll_init(void)
1615{ 1616{
1616 int error; 1617 int error;
1617 1618
1618 init_MUTEX(&epsem); 1619 mutex_init(&epmutex);
1619 1620
1620 /* Initialize the structure used to perform safe poll wait head wake ups */ 1621 /* Initialize the structure used to perform safe poll wait head wake ups */
1621 ep_poll_safewake_init(&psw); 1622 ep_poll_safewake_init(&psw);