[bcl] Replace more long fields with int to make them CAS friendly on 32 bits systems.
authorRodrigo Kumpera <kumpera@gmail.com>
Wed, 4 Sep 2013 18:47:27 +0000 (14:47 -0400)
committerRodrigo Kumpera <kumpera@gmail.com>
Wed, 4 Sep 2013 18:47:27 +0000 (14:47 -0400)
mcs/class/corlib/System.Threading.Tasks/CyclicDeque.cs
mcs/class/corlib/System.Threading.Tasks/Parallel.cs
mcs/class/corlib/System.Threading/ManualResetEventSlim.cs

index 907dad29fac44e62a122c24ce1e81d5c333389dd..d0b723d285ed4dbd9d5800d7e1a95bce6fa9bee8 100644 (file)
@@ -43,23 +43,20 @@ namespace System.Threading.Tasks
        {
                const int BaseSize = 11;
                
-               long bottom;
-               long top;
-               long upperBound;
+               int bottom;
+               int top;
+               int upperBound;
                CircularArray<T> array = new CircularArray<T> (BaseSize);
                
                public void PushBottom (T obj)
                {
-                       /* Read is implemented as a simple load operation on 64bits
-                        * so no need to make the distinction ourselves
-                        */
-                       long b = Interlocked.Read (ref bottom);
+                       int b = bottom;
                        var a = array;
                        
                        // Take care of growing
                        var size = b - top - upperBound;
                        if (size > a.Size) {
-                               upperBound = Interlocked.Read (ref top);
+                               upperBound = top;
                                a = a.Grow (b, upperBound);
                                array = a;
                        }
@@ -73,10 +70,10 @@ namespace System.Threading.Tasks
                {
                        obj = default (T);
                        
-                       long b = Interlocked.Decrement (ref bottom);
+                       int b = Interlocked.Decrement (ref bottom);
                        var a = array;
-                       long t = Interlocked.Read (ref top);
-                       long size = b - t;
+                       int t = top;
+                       int size = b - t;
                        
                        if (size < 0) {
                                // Set bottom to t
@@ -99,10 +96,10 @@ namespace System.Threading.Tasks
                {
                        obj = default (T);
 
-                       long b = Interlocked.Decrement (ref bottom);
+                       int b = Interlocked.Decrement (ref bottom);
                        var a = array;
-                       long t = Interlocked.Read (ref top);
-                       long size = b - t;
+                       int t = top;
+                       int size = b - t;
 
                        if (size < 0)
                                return false;
@@ -115,8 +112,8 @@ namespace System.Threading.Tasks
                {
                        obj = default (T);
                        
-                       long t = Interlocked.Read (ref top);
-                       long b = Interlocked.Read (ref bottom);
+                       int t = top;
+                       int b = bottom;
                        
                        if (b - t <= 0)
                                return PopResult.Empty;
@@ -134,8 +131,8 @@ namespace System.Threading.Tasks
                {
                        obj = default (T);
 
-                       long t = Interlocked.Read (ref top);
-                       long b = Interlocked.Read (ref bottom);
+                       int t = top;
+                       int b = bottom;
 
                        if (b - t <= 0)
                                return false;
@@ -154,8 +151,8 @@ namespace System.Threading.Tasks
 
                public bool IsEmpty {
                        get {
-                               long t = Interlocked.Read (ref top);
-                               long b = Interlocked.Read (ref bottom);
+                               int t = top;
+                               int b = bottom;
                                return b - t <= 0;
                        }
                }
@@ -174,13 +171,13 @@ namespace System.Threading.Tasks
                        this.segment = new T[size];
                }
                
-               public long Size {
+               public int Size {
                        get {
                                return size;
                        }
                }
                
-               public T this[long index] {
+               public T this[int index] {
                        get {
                                return segment[index % size];
                        }
@@ -189,32 +186,32 @@ namespace System.Threading.Tasks
                        }
                }
                
-               public CircularArray<T> Grow (long bottom, long top)
+               public CircularArray<T> Grow (int bottom, int top)
                {
                        var grow = new CircularArray<T> (baseSize + 1);
                        
-                       for (long i = top; i < bottom; i++) {
+                       for (int i = top; i < bottom; i++) {
                                grow.segment[i] = segment[i % size];
                        }
                        
                        return grow;
                }
                
-               public IEnumerable<T> GetEnumerable (long bottom, ref long top)
+               public IEnumerable<T> GetEnumerable (int bottom, ref int top)
                {
-                       long instantTop = top;
+                       int instantTop = top;
                        T[] slice = new T[bottom - instantTop];
                        int destIndex = -1;
-                       for (long i = instantTop; i < bottom; i++)
+                       for (int i = instantTop; i < bottom; i++)
                                slice[++destIndex] = segment[i % size];
 
                        return RealGetEnumerable (slice, bottom, top, instantTop);
                }
 
-               IEnumerable<T> RealGetEnumerable (T[] slice, long bottom, long realTop, long initialTop)
+               IEnumerable<T> RealGetEnumerable (T[] slice, int bottom, int realTop, int initialTop)
                {
                        int destIndex = (int)(realTop - initialTop - 1);
-                       for (long i = realTop; i < bottom; ++i)
+                       for (int i = realTop; i < bottom; ++i)
                                yield return slice[++destIndex];
                }
        }
index c175441792c521064986ec87fc5ba2deb0da36ab..d62df9a7e68f98237ca537dce7d41da4df0b4a0c 100644 (file)
@@ -203,7 +203,7 @@ namespace System.Threading.Tasks
                                                                long old;
                                                                StealValue64 val = new StealValue64 ();
 
-                                                               old = sixtyfour ? range.V64.Value : Interlocked.CompareExchange (ref range.V64.Value, 0, 0);
+                                                               old = Thread.VolatileRead (ref range.V64.Value);
                                                                val.Value = old;
 
                                                                if (val.Actual >= stopIndex - val.Stolen - 2)
index baaa25ca4bb19e4fa86f9c59b612cdd357033513..a34370d460be051bbdaf54315d093cb8f573b037 100644 (file)
@@ -38,7 +38,7 @@ namespace System.Threading
                ManualResetEvent handle;
                internal AtomicBooleanValue disposed;
                int used;
-               long state;
+               int state;
 
                public ManualResetEventSlim ()
                        : this (false, 10)
@@ -89,10 +89,10 @@ namespace System.Threading
 
                long UpdateStateWithOp (bool set)
                {
-                       long oldValue, newValue;
+                       int oldValue, newValue;
                        do {
                                oldValue = state;
-                               newValue = (long)(((oldValue >> 1) + 1) << 1) | (set ? 1u : 0u);
+                               newValue = (int)(((oldValue >> 1) + 1) << 1) | (set ? 1 : 0);
                        } while (Interlocked.CompareExchange (ref state, newValue, oldValue) != oldValue);
                        return newValue;
                }
@@ -119,7 +119,7 @@ namespace System.Threading
                                 * we have a mismatch between S and H at the end because the last operations done were
                                 * S3/H1. We thus need to repeat H3 to get to the desired final state.
                                 */
-                               long currentState;
+                               int currentState;
                                do {
                                        currentState = state;
                                        if (currentState != stamp && (stamp & 1) != (currentState & 1)) {