Author: thebeing
Date: Fri Jul 17 22:08:38 2015
New Revision: 38814

URL: http://svn.gna.org/viewcvs/gnustep?rev=38814&view=rev
Log:
Optionally allow the caller to specify the time it wants to block on an
empty FIFO. This supplements the existing method of having a timeout on
the FIFO, and does not raise an excepion when the wait time is too long.

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

Modified: libs/performance/trunk/ChangeLog
URL: 
http://svn.gna.org/viewcvs/gnustep/libs/performance/trunk/ChangeLog?rev=38814&r1=38813&r2=38814&view=diff
==============================================================================
--- libs/performance/trunk/ChangeLog    (original)
+++ libs/performance/trunk/ChangeLog    Fri Jul 17 22:08:38 2015
@@ -1,3 +1,9 @@
+2015-07-17 Niels Grewe <[email protected]>
+
+       * GSFIFO.m: Implement methods that allow waiting on an empty
+       FIFO for an arbitrary period of time, without raising an
+       exception.
+
 2015-07-16 Niels Grewe <[email protected]>
 
        * GSFIFO.m: Implement -sizeInBytesExcluding:

Modified: libs/performance/trunk/GSFIFO.h
URL: 
http://svn.gna.org/viewcvs/gnustep/libs/performance/trunk/GSFIFO.h?rev=38814&r1=38813&r2=38814&view=diff
==============================================================================
--- libs/performance/trunk/GSFIFO.h     (original)
+++ libs/performance/trunk/GSFIFO.h     Fri Jul 17 22:08:38 2015
@@ -118,6 +118,17 @@
  */
 - (unsigned) get: (void**)buf  count: (unsigned)count  shouldBlock: 
(BOOL)block;
 
+/**
+ * Reads up to count items from the FIFO into the buf. If blocking is requested
+ * and a before date is specified, the operation blocks until the specified 
time
+ * and returns 0 if it could not read any items. The timeout configured for 
the 
+ * FIFO still takes precedence.
+ */
+- (unsigned) get: (void**)buf
+           count: (unsigned)count
+     shouldBlock: (BOOL)block
+          before: (NSDate*)date;
+
 /** Reads up to count objects from the FIFO (which must contain objects
  * or nil items) into buf and autoreleases them.<br />
  * If block is YES, this blocks if necessary until at least one object
@@ -128,6 +139,18 @@
 - (unsigned) getObjects: (NSObject**)buf
                   count: (unsigned)count
             shouldBlock: (BOOL)block;
+
+
+/**
+ * Reads up to count autoreleased objects from the FIFO into the buf. If 
blocking
+ * is requested and a before date is specified, the operation blocks until the
+ * specified time and returns 0 if it could not read any items. The timeout
+ * configured for the FIFO still takes precedence.
+ */
+- (unsigned) getObjects: (NSObject**)buf
+                  count: (unsigned)count
+            shouldBlock: (BOOL)block
+                 before: (NSDate*)date;
 
 /** Gets the next item from the FIFO, blocking if necessary until an
  * item is available.  Raises an exception if the FIFO is configured

Modified: libs/performance/trunk/GSFIFO.m
URL: 
http://svn.gna.org/viewcvs/gnustep/libs/performance/trunk/GSFIFO.m?rev=38814&r1=38813&r2=38814&view=diff
==============================================================================
--- libs/performance/trunk/GSFIFO.m     (original)
+++ libs/performance/trunk/GSFIFO.m     Fri Jul 17 22:08:38 2015
@@ -128,6 +128,7 @@
 - (unsigned) _cooperatingGet: (void**)buf
                       count: (unsigned)count
                 shouldBlock: (BOOL)block
+                      before: (NSDate*)before
 {
   NSTimeInterval       ti;
   unsigned             index;
@@ -145,7 +146,7 @@
        }
 
       START
-      if (0 == timeout)
+      if ((0 == timeout) && (before == nil))
        {
          while (_head - _tail == 0)
            {
@@ -155,22 +156,47 @@
       else
        {
          NSDate        *d;
-
-         d = [[NSDateClass alloc]
-           initWithTimeIntervalSinceNow: timeout / 1000.0f];
+          NSDate        *effective;
+          [before retain];
+          if (timeout != 0)
+            {
+              d = [[NSDateClass alloc]
+               initWithTimeIntervalSinceNow: timeout / 1000.0f];
+            }
+          if ((d != nil) && (before != nil))
+            {
+              effective = [d earlierDate: before];
+            }
+          else if (d != nil)
+            {
+              effective = d;
+            }
+          else
+            {
+              effective = before;
+            }
          while (_head - _tail == 0)
            {
-             if (NO == [condition waitUntilDate: d])
+             if (NO == [condition waitUntilDate: effective])
                {
                  [d release];
+                  [before release];
                  ENDGET
                  [condition broadcast];
                  [condition unlock];
-                 [NSException raise: NSGenericException
-                             format: @"Timeout waiting for new data in FIFO"];
+                  if (before != effective)
+                    {
+                      [NSException raise: NSGenericException
+                                  format: @"Timeout waiting for new data in 
FIFO"];
+                    }
+                  else
+                    {
+                      return 0;
+                    }
                }
            }
          [d release];
+          [before release];
          ENDGET
        }
     }
@@ -383,21 +409,28 @@
     fullCount];
 }
 
-- (unsigned) get: (void**)buf count: (unsigned)count shouldBlock: (BOOL)block
+- (unsigned) get: (void**)buf
+           count: (unsigned)count
+     shouldBlock: (BOOL)block
+          before: (NSDate*)date
+
 {
   unsigned             index;
   NSTimeInterval       ti;
   NSTimeInterval       sum;
+  NSTimeInterval        waitLength;
   uint32_t             old;
-  uint32_t             fib;
-  
+  uint32_t             fib; 
   if (0 == count) return 0;
 
   if (nil != condition)
     {
-      return [self _cooperatingGet: buf count: count shouldBlock: block];
-    }
-
+      return [self _cooperatingGet: buf 
+                             count: count 
+                       shouldBlock: block
+                            before: date];
+    }
+  waitLength = [date timeIntervalSinceNow];
   if (nil == getThread)
     {
       getThread = [NSThread currentThread];
@@ -434,6 +467,11 @@
          [NSException raise: NSGenericException
                      format: @"Timeout waiting for new data in FIFO"];
        }
+      else if (date != nil && sum > waitLength)
+        {
+          ENDGET
+          return 0;
+        }
       tmp = fib + old;
       old = fib;
       fib = tmp;
@@ -454,19 +492,41 @@
   return index;
 }
 
+
+- (unsigned) get: (void**)buf count: (unsigned)count shouldBlock: (BOOL)block
+{
+  return [self get: buf count: count shouldBlock: block before: nil];
+}
+
+
+
 - (unsigned) getObjects: (NSObject**)buf
                   count: (unsigned)count
             shouldBlock: (BOOL)block
+                 before: (NSDate*)date
 {
   unsigned      result;
   unsigned      index;
 
-  index = result = [self get: (void**)buf count: count shouldBlock: block];
+  index = result = [self get: (void**)buf
+                       count: count 
+                 shouldBlock: block 
+                      before: date];
   while (index-- > 0)
     {
       [buf[index] autorelease];
     }
   return result;
+}
+
+- (unsigned) getObjects: (NSObject**)buf
+                  count: (unsigned)count
+            shouldBlock: (BOOL)block
+{
+  return [self getObjects: buf
+                    count: count
+              shouldBlock: block
+                   before: nil];
 }
 
 - (void*) get


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

Reply via email to