Merge pull request #2545 from ermshiperete/Xamarin-24974
[mono.git] / mcs / class / Mono.Simd / Mono.Simd / Vector4ui.cs
index 929b252074c971629bcc8202057fe12d55c435fd..c62365c61a3337906905f93b8f3ee23b9c04d23d 100644 (file)
@@ -29,20 +29,34 @@ using System.Runtime.InteropServices;
 
 namespace Mono.Simd
 {
-       [StructLayout(LayoutKind.Sequential, Pack = 0, Size = 16)]
+       [StructLayout(LayoutKind.Explicit, Pack = 0, Size = 16)]
        [CLSCompliant(false)]
        public struct Vector4ui
        {
-               private uint x;
-               private uint y;
-               private uint z;
-               private uint w;
+               [ FieldOffset(0) ]
+               internal uint x;
+               [ FieldOffset(4) ]
+               internal uint y;
+               [ FieldOffset(8) ]
+               internal uint z;
+               [ FieldOffset(12) ]
+               internal uint w;
 
                public uint X { get { return x; } set { x = value; } }
                public uint Y { get { return y; } set { y = value; } }
                public uint Z { get { return z; } set { z = value; } }
                public uint W { get { return w; } set { w = value; } }
 
+               public static Vector4ui Identity
+               {
+                       get { return  new Vector4ui (1); }
+               }
+
+               public static Vector4ui Zero
+               {
+                       get { return  new Vector4ui (0); }
+               }
+
                [System.Runtime.CompilerServices.IndexerName ("Component")]
                public unsafe uint this [int index]
                {
@@ -69,6 +83,14 @@ namespace Mono.Simd
                        this.z = z;
                        this.w = w;
                }
+               
+               public Vector4ui (uint ui)
+               {
+                       this.x = ui;
+                       this.y = ui;
+                       this.z = ui;
+                       this.w = ui;
+               }
 
                [Acceleration (AccelMode.SSE2)]
                public static Vector4ui operator + (Vector4ui v1, Vector4ui v2)
@@ -101,125 +123,33 @@ namespace Mono.Simd
                }
 
                [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui operator & (Vector4ui v1, Vector4ui v2)
+               public static Vector4ui operator & (Vector4ui v1, Vector4ui v2)
                {
-                       Vector4ui res = new Vector4ui ();
-                       ulong *a = (ulong*) &v1.x;
-                       ulong *b = (ulong*) &v2.x;
-                       ulong *c = (ulong*) &res.x;
-                       *c++ = (ulong)(*a++ & *b++);
-                       *c = (ulong)(*a & *b);
-                       return res;
+                       return new Vector4ui (v1.x & v2.x, v1.y & v2.y, v1.z & v2.z, v1.w & v2.w);
                }
 
                [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui operator | (Vector4ui v1, Vector4ui v2)
+               public static Vector4ui operator | (Vector4ui v1, Vector4ui v2)
                {
-                       Vector4ui res = new Vector4ui ();
-                       ulong *a = (ulong*) &v1.x;
-                       ulong *b = (ulong*) &v2.x;
-                       ulong *c = (ulong*) &res.x;
-                       *c++ = (ulong)(*a++ | *b++);
-                       *c = (ulong)(*a | *b);
-                       return res;
+                       return new Vector4ui (v1.x | v2.x, v1.y | v2.y, v1.z | v2.z, v1.w | v2.w);
                }
 
                [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui operator ^ (Vector4ui v1, Vector4ui v2)
+               public static Vector4ui operator ^ (Vector4ui v1, Vector4ui v2)
                {
-                       Vector4ui res = new Vector4ui ();
-                       ulong *a = (ulong*) &v1.x;
-                       ulong *b = (ulong*) &v2.x;
-                       ulong *c = (ulong*) &res.x;
-                       *c++ = (ulong)(*a++ ^ *b++);
-                       *c = (ulong)(*a ^ *b);
-                       return res;
+                       return new Vector4ui (v1.x ^ v2.x, v1.y ^ v2.y, v1.z ^ v2.z, v1.w ^ v2.w);
                }
 
                [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui UnpackLow (Vector4ui v1, Vector4ui v2)
+               public static bool operator ==(Vector4ui v1, Vector4ui v2)
                {
-                       return new Vector4ui (v1.x, v2.x, v1.y, v2.y);
+                       return v1.x == v2.x && v1.y == v2.y && v1.z == v2.z && v1.w == v2.w;
                }
 
                [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui UnpackHigh (Vector4ui v1, Vector4ui v2)
+               public static bool operator !=(Vector4ui v1, Vector4ui v2)
                {
-                       return new Vector4ui (v1.z, v2.z, v1.w, v2.w);
-               }
-
-               [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui ShiftRightArithmetic (Vector4ui v1, int amount)
-               {
-                       Vector4ui res = new Vector4ui ();
-                       uint *a = &v1.x;
-                       uint *b = &res.x;
-                       for (int i = 0; i < 4; ++i)
-                               *b++ = (uint)((int)(*a++) >> amount);
-                       return res;
-               }
-
-               [Acceleration (AccelMode.SSE41)]
-               public static unsafe Vector4ui Max (Vector4ui v1, Vector4ui v2)
-               {
-                       return new Vector4ui (System.Math.Max (v1.x, v2.x), System.Math.Max (v1.y, v2.y), System.Math.Max (v1.z, v2.z), System.Math.Max (v1.w, v2.w));
-               }
-
-               [Acceleration (AccelMode.SSE41)]
-               public static unsafe Vector4ui Min (Vector4ui v1, Vector4ui v2)
-               {
-                       return new Vector4ui (System.Math.Min (v1.x, v2.x), System.Math.Min (v1.y, v2.y), System.Math.Min (v1.z, v2.z), System.Math.Min (v1.w, v2.w));
-               }
-
-               [Acceleration (AccelMode.SSE2)]
-               public static unsafe int ExtractByteMask (Vector4ui va) {
-                       int res = 0;
-                       byte *a = (byte*)&va;
-                       for (int i = 0; i < 16; ++i)
-                               res |= (*a++ & 0x80) >> 7 << i;
-                       return res;
-               }
-
-               [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui Shuffle (Vector4ui v1, ShuffleSel sel)
-               {
-                       uint *ptr = (uint*)&v1;
-                       int idx = (int)sel;
-                       return new Vector4ui (*(ptr + ((idx >> 0) & 0x3)),*(ptr + ((idx >> 2) & 0x3)),*(ptr + ((idx >> 4) & 0x3)),*(ptr + ((idx >> 6) & 0x3)));
-               }
-
-               [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector4ui CompareEqual (Vector4ui v1, Vector4ui v2)
-               {
-                       return new Vector4ui ((uint)(v1.x ==  v2.x ? -1 : 0), (uint)(v1.y ==  v2.y ? -1 : 0), (uint)(v1.z ==  v2.z ? -1 : 0), (uint)(v1.w ==  v2.w ? -1 : 0));
-               }
-
-               /* This function performs a packusdw, which treats the source as a signed value */
-               [Acceleration (AccelMode.SSE41)]
-               public static unsafe Vector8us SignedPackWithUnsignedSaturation (Vector4ui va, Vector4ui vb) {
-                       Vector8us res = new Vector8us ();
-                       int *a = (int*)&va;
-                       int *b = (int*)&vb;
-                       ushort *c = (ushort*)&res;
-                       for (int i = 0; i < 4; ++i)
-                               *c++ = (ushort)System.Math.Max (0, System.Math.Min (*a++, ushort.MaxValue));
-                       for (int i = 0; i < 4; ++i)
-                               *c++ = (ushort)System.Math.Max (0, System.Math.Min (*b++, ushort.MaxValue));
-                       return res;
-               }
-
-               /* This function performs a packssdw, which treats the source as a signed value*/
-               [Acceleration (AccelMode.SSE2)]
-               public static unsafe Vector8s SignedPackWithSignedSaturation (Vector4ui va, Vector4ui vb) {
-                       Vector8s res = new Vector8s ();
-                       int *a = (int*)&va;
-                       int *b = (int*)&vb;
-                       short *c = (short*)&res;
-                       for (int i = 0; i < 4; ++i)
-                               *c++ = (short)System.Math.Max (System.Math.Min ((int)*a++, short.MaxValue), short.MinValue);
-                       for (int i = 0; i < 4; ++i)
-                               *c++ = (short)System.Math.Max (System.Math.Min ((int)*b++, short.MaxValue), short.MinValue);
-                       return res;
+                       return v1.x != v2.x || v1.y != v2.y || v1.z != v2.z || v1.w != v2.w;
                }
 
                [Acceleration (AccelMode.SSE1)]
@@ -356,5 +286,10 @@ namespace Mono.Simd
                public static unsafe void PrefetchNonTemporal (Vector4ui *res)
                {
                }
+               
+               public override string ToString()
+               {
+                       return "<" + x + ", " + y + ", " + z + ", " + w + ">"; 
+               }
        }
 }