[CRIU] [PATCH 1/2] futex: Make raw value being s32

Cyrill Gorcunov gorcunov at openvz.org
Mon Apr 2 02:20:47 EDT 2012


In case of error we do set futex value to
be negative one, this breaks waiting loops
and allow us to exit from program.

But during the futex conversion futex_wait_while_gt
was occasionally changed to u32 type making
error conditions to yield endless wait loop.

Change futex raw value to s32 to fix this.

Reported-by: Andrey Vagin <avagin at openvz.org>
Signed-off-by: Cyrill Gorcunov <gorcunov at openvz.org>
---
 include/lock.h |   22 +++++++++++-----------
 1 files changed, 11 insertions(+), 11 deletions(-)

diff --git a/include/lock.h b/include/lock.h
index 6f77bfd..9d06da2 100644
--- a/include/lock.h
+++ b/include/lock.h
@@ -12,7 +12,7 @@
 #include "util.h"
 
 typedef struct {
-	u32	raw;
+	s32	raw;
 } futex_t;
 
 /* Get current futex @f value */
@@ -22,7 +22,7 @@ static inline u32 futex_get(futex_t *f)
 }
 
 /* Set futex @f value to @v */
-static inline void futex_set(futex_t *f, u32 v)
+static inline void futex_set(futex_t *f, s32 v)
 {
 	atomic_set(&f->raw, v);
 }
@@ -33,30 +33,30 @@ static inline void futex_set(futex_t *f, u32 v)
 #define futex_wait_if_cond(__f, __v, __cond)			\
 	do {							\
 		int ret;					\
-		u32 tmp;					\
+		s32 tmp;					\
 								\
 		while (1) {					\
 			tmp = (__f)->raw;			\
 			if (tmp __cond (__v))			\
 				break;				\
-			ret = sys_futex(&(__f)->raw, FUTEX_WAIT,\
+			ret = sys_futex((u32 *)&(__f)->raw, FUTEX_WAIT,\
 					tmp, NULL, NULL, 0);	\
 			BUG_ON(ret < 0 && ret != -EWOULDBLOCK);	\
 		}						\
 	} while (0)
 
 /* Set futex @f to @v and wake up all waiters */
-static inline void futex_set_and_wake(futex_t *f, u32 v)
+static inline void futex_set_and_wake(futex_t *f, s32 v)
 {
 	atomic_set(&f->raw, v);
-	BUG_ON(sys_futex(&f->raw, FUTEX_WAKE, INT_MAX, NULL, NULL, 0) < 0);
+	BUG_ON(sys_futex((u32 *)&f->raw, FUTEX_WAKE, INT_MAX, NULL, NULL, 0) < 0);
 }
 
 /* Decrement futex @f value and wake up all waiters */
 static inline void futex_dec_and_wake(futex_t *f)
 {
 	atomic_dec(&f->raw);
-	BUG_ON(sys_futex(&f->raw, FUTEX_WAKE, INT_MAX, NULL, NULL, 0) < 0);
+	BUG_ON(sys_futex((u32 *)&f->raw, FUTEX_WAKE, INT_MAX, NULL, NULL, 0) < 0);
 }
 
 /* Plain increment futex @f value */
@@ -66,18 +66,18 @@ static inline void futex_inc(futex_t *f) { f->raw++; }
 static inline void futex_dec(futex_t *f) { f->raw--; }
 
 /* Wait until futex @f value become @v */
-static inline void futex_wait_until(futex_t *f, u32 v)
+static inline void futex_wait_until(futex_t *f, s32 v)
 { futex_wait_if_cond(f, v, ==); }
 
 /* Wait while futex @f value is greater than @v */
-static inline void futex_wait_while_gt(futex_t *f, u32 v)
+static inline void futex_wait_while_gt(futex_t *f, s32 v)
 { futex_wait_if_cond(f, v, <=); }
 
 /* Wait while futex @f value is @v */
-static inline void futex_wait_while(futex_t *f, u32 v)
+static inline void futex_wait_while(futex_t *f, s32 v)
 {
 	while (f->raw == v) {
-		int ret = sys_futex(&f->raw, FUTEX_WAIT, v, NULL, NULL, 0);
+		int ret = sys_futex((u32 *)&f->raw, FUTEX_WAIT, v, NULL, NULL, 0);
 		BUG_ON(ret < 0 && ret != -EWOULDBLOCK);
 	}
 }
-- 
1.7.7.6



More information about the CRIU mailing list