Author: thebeing
Date: Tue May  5 13:32:38 2015
New Revision: 38475

URL: http://svn.gna.org/viewcvs/gnustep?rev=38475&view=rev
Log:
Fix potential race condition when getting the top object without
removing it. (previously, we had a window between returning a peeked
pointer and retaining it where another thread might have been able to
pop and release the object).

Modified:
    libs/performance/trunk/ChangeLog
    libs/performance/trunk/GSFIFO.m

Modified: libs/performance/trunk/ChangeLog
URL: 
http://svn.gna.org/viewcvs/gnustep/libs/performance/trunk/ChangeLog?rev=38475&r1=38474&r2=38475&view=diff
==============================================================================
--- libs/performance/trunk/ChangeLog    (original)
+++ libs/performance/trunk/ChangeLog    Tue May  5 13:32:38 2015
@@ -1,3 +1,7 @@
+2015-05-05 Niels Grewe <[email protected]>
+
+       * GSFIFO.m: Fix a potential race condition in -peekObject.
+
 2015-05-05 Niels Grewe <[email protected]>
 
        * GSFIFO.[hm]: Add methods to peek at the top/front object in the

Modified: libs/performance/trunk/GSFIFO.m
URL: 
http://svn.gna.org/viewcvs/gnustep/libs/performance/trunk/GSFIFO.m?rev=38475&r1=38474&r2=38475&view=diff
==============================================================================
--- libs/performance/trunk/GSFIFO.m     (original)
+++ libs/performance/trunk/GSFIFO.m     Tue May  5 13:32:38 2015
@@ -216,6 +216,23 @@
   return ptr;
 }
 
+- (id) _cooperatingPeekObject
+{
+  [condition lock];
+  if ((_head - _tail) == 0)
+    {
+      // We do not need to signal the condition because
+      // nothing about the qeuue did change
+      [condition unlock];
+      return nil;
+    }
+  id obj =
+    [[(id<NSObject>)_items[_tail % _capacity] retain] autorelease];
+  [condition unlock];
+  return obj;
+}
+
+
 - (void*) peek
 {
   if (condition != nil)
@@ -231,7 +248,15 @@
 
 - (NSObject*) peekObject
 {
-  return [[(id<NSObject>)[self peek] retain] autorelease];
+  if (condition != nil)
+    {
+      return [self _cooperatingPeekObject];
+    }
+  if (_head - _tail == 0)
+    {
+      return nil;
+    }
+  return [[(id<NSObject>)_items[_tail % _capacity] retain] autorelease];
 }
 
 - (unsigned) _cooperatingPut: (void**)buf


_______________________________________________
Gnustep-cvs mailing list
[email protected]
https://mail.gna.org/listinfo/gnustep-cvs

Reply via email to