[SSI] openssi/kernel/cluster/ssi/vproc dvp_move.c,1.17,1.18
Roger Tsang <[email protected]> Tue, 04 May 2010 04:42:28 +0000
| Newsgroups | gmane.linux.cluster.ssic.cvs |
|---|---|
| Message-ID | <[email protected]> |
Update of /cvsroot/ssic-linux/openssi/kernel/cluster/ssi/vproc
In directory sfp-cvsdas-3.v30.ch3.sourceforge.com:/tmp/cvs-serv16722/cluster/ssi/vproc
Modified Files:
Tag: OPENSSI-FC
dvp_move.c
Log Message:
VPROC (#ifdef VPROC_RCU_MOVEMENT_LIST):
- Fix move_data struct leak in move_out_nodedown(). Bug introduced in OPENSSI-FC-1-9-6-PRE39.
- No need to acquire mh_lock in put_move_data(); there is no race. move_data struct is removed from mh_datalist before final put_move_data().
VPROC:
- Remove unnecessary memory barriers.
Index: dvp_move.c
===================================================================
RCS file: /cvsroot/ssic-linux/openssi/kernel/cluster/ssi/vproc/dvp_move.c,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -d -r1.17 -r1.18
--- dvp_move.c 3 May 2010 06:18:14 -0000 1.17
+++ dvp_move.c 4 May 2010 04:42:26 -0000 1.18
@@ -263,6 +263,7 @@
return h;
}
+/* Might acquire movement_list_lock */
void
put_move_header(struct move_header *h)
{
@@ -352,14 +353,10 @@
}
#endif /* !VPROC_RCU_MOVEMENT_LIST */
-/* Might acquire movement_list_lock, mh_lock */
+/* Might acquire movement_list_lock */
static void
put_move_data(struct move_data *d)
{
-#ifdef VPROC_RCU_MOVEMENT_LIST
- struct move_header *h;
-#endif
-
#ifdef DEBUG
if (unlikely(d->m_magic != ((u_long)&d->m_magic) + 1)) {
panic("%s:move_data %p has invalid magic number %p\n",
@@ -368,15 +365,13 @@
#endif
BUG_ON(atomic_read(&d->m_refcnt) < 1);
#ifdef VPROC_RCU_MOVEMENT_LIST
- h = d->m_mhp;
-
- if (!atomic_dec_and_lock(&d->m_refcnt, &h->mh_lock))
+ if (!atomic_dec_and_test(&d->m_refcnt))
return;
#ifdef DEBUG
d->m_magic = 0;
#endif
- d->m_mhp = NULL;
- spin_unlock(&h->mh_lock);
+ /* NB: already removed from mh_datalist in drop_move_data() */
+ put_move_header(d->m_mhp);
if (unlikely(d->m_taskp))
panic("%s:move_data %p freed with m_taskp %p set\n",
@@ -384,7 +379,6 @@
if (unlikely(atomic_read(&d->m_hashed)))
panic("%s:move_data %p still hashed\n", __FUNCTION__, d);
- put_move_header(h); /* for d->m_mhp */
call_rcu(&d->m_rcu, free_move_data);
#else /* VPROC_RCU_MOVEMENT_LIST */
if (!atomic_dec_and_lock(&d->m_refcnt, &movement_list_lock))
@@ -627,8 +621,6 @@
{
struct move_data *d;
- smp_mb(); /* ensure all CPU's see new state */
-
rcu_read_lock();
list_for_each_entry_rcu(d, &h->mh_datalist, m_list) {
if (!__get_move_data(d))
@@ -740,6 +732,7 @@
list_for_each_entry(d, &h->mh_datalist, m_list) {
d->m_state = state;
}
+ smp_mb(); /* ensure all CPU's see new state */
}
@@ -851,9 +844,7 @@
#ifdef VPROC_RCU_MOVEMENT_LIST
if (aborting)
free_move_datalist(h);
- else
#endif
- smp_mb(); /* ensure all CPU's see new state */
wake_up_all(&h->mh_wqh);
@@ -1992,7 +1983,7 @@
state);
goto out;
}
- l->m_state = PM_MIGRATE_IN_THREAD;
+ set_mb(l->m_state, PM_MIGRATE_IN_THREAD);
get_move_data(d); /* for l->m_threadlist */
list_add_tail(&d->m_threadlist, &l->m_threadlist);
@@ -2000,10 +1991,9 @@
d->m_migargs = args;
spin_unlock(&h->mh_lock);
- if (state == PM_MIGRATE_IN_DONE) {
- smp_mb(); /* ensure CPU's see new state */
+ if (state == PM_MIGRATE_IN_DONE)
wake_up_all(&l->m_wqh);
- }
+
(void)move_data_wait_for_state_change(d, PM_MIGRATE_IN_START);
spin_lock(&h->mh_lock);
@@ -2349,6 +2339,7 @@
move_data_wait_for_state_change(d,
PM_MIGRATE_OUT_START);
+ put_move_data(d);
goto again;
} else if (d->m_state == PM_MIGRATE_OUT) {
spin_lock(&h->mh_lock);
------------------------------------------------------------------------------