2008-10-29 Rodrigo Kumpera <rkumpera@novell.com>
[mono.git] / mcs / class / Mono.Simd / Mono.Simd / Vector16b.cs
index 1aba2107e95aa0874cbd07643900e91600066426..1ae0831bb50b1f541ab0d2a49e26005f8d2a81bc 100644 (file)
@@ -1,4 +1,4 @@
-// Vector4u.cs
+// Vector16b.cs
 //
 // Author:
 //   Rodrigo Kumpera (rkumpera@novell.com)
@@ -29,8 +29,7 @@ using System.Runtime.InteropServices;
 \r
 namespace Mono.Simd\r
 {\r
-       [StructLayout(LayoutKind.Sequential, Pack = 0, Size = 16)]
-       [CLSCompliant(false)]\r
+       [StructLayout(LayoutKind.Sequential, Pack = 0, Size = 16)]\r
        public struct Vector16b\r
        {\r
                private byte v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15;\r\r
@@ -92,42 +91,6 @@ namespace Mono.Simd
                        return res;\r
                }
 
-               /*
-                * NOTE: Thou pmullw states it does signed multiplication, it works for unsigned numbers
-                * if only the lower part is considered and the flags disregarded.
-                */
-               public static unsafe Vector16b operator * (Vector16b va, Vector16b vb)\r
-               {\r
-                       Vector16b res = new Vector16b ();
-                       byte *a = &va.v0;
-                       byte *b = &vb.v0;
-                       byte *c = &res.v0;
-                       for (int i = 0; i < 16; ++i)
-                               *c++ = (byte)(*a++ * (*b++));
-                       return res;\r
-               }
-
-               public static unsafe Vector16b operator >> (Vector16b va, int amount)\r
-               {\r
-                       Vector16b res = new Vector16b ();
-                       byte *a = &va.v0;
-                       byte *b = &res.v0;
-                       for (int i = 0; i < 16; ++i)
-                               *b++ = (byte)(*a++ >> amount);
-                       return res;\r
-               }
-
-
-               public static unsafe Vector16b operator << (Vector16b va, int amount)\r
-               {\r
-                       Vector16b res = new Vector16b ();
-                       byte *a = &va.v0;
-                       byte *b = &res.v0;
-                       for (int i = 0; i < 16; ++i)
-                               *b++ = (byte)(*a++ << amount);
-                       return res;\r
-               }
-
                public static unsafe Vector16b operator & (Vector16b va, Vector16b vb)\r
                {\r
                        Vector16b res = new Vector16b ();
@@ -171,20 +134,6 @@ namespace Mono.Simd
                        return new Vector16b (va.v8, vb.v8, va.v9, vb.v9, va.v10, vb.v10, va.v11, vb.v11, va.v12, vb.v12, va.v13, vb.v13, va.v14, vb.v14, va.v15, vb.v15);
                }
 
-               /*
-                * XXX Maybe this method doesn't make sense.
-                * C# doesn't support explicit shifting mode, it is defined by the signed of the type.
-                */
-               public static unsafe Vector16b ShiftRightArithmetic (Vector16b va, int amount)\r
-               {\r
-                       Vector16b res = new Vector16b ();
-                       byte *a = &va.v0;
-                       byte *b = &res.v0;
-                       for (int i = 0; i < 16; ++i)
-                               *b++ = (byte)(((uint)(*a++)) >> amount);
-                       return res;\r
-               }
-
                public static unsafe Vector16b AddWithSaturation (Vector16b va, Vector16b vb) {
                        Vector16b res = new Vector16b ();
                        byte *a = &va.v0;
@@ -205,15 +154,91 @@ namespace Mono.Simd
                        return res;
                }
 
-               public static unsafe explicit operator Vector16b(Vector4f v)\r
+               public static unsafe Vector16b Average (Vector16b va, Vector16b vb) {
+                       Vector16b res = new Vector16b ();
+                       byte *a = &va.v0;
+                       byte *b = &vb.v0;
+                       byte *c = &res.v0;
+                       for (int i = 0; i < 16; ++i)
+                               *c++ = (byte) ((*a++ + *b++ + 1) >> 1);
+                       return res;
+               }
+
+               public static unsafe Vector16b Max (Vector16b va, Vector16b vb) {
+                       Vector16b res = new Vector16b ();
+                       byte *a = &va.v0;
+                       byte *b = &vb.v0;
+                       byte *c = &res.v0;
+                       for (int i = 0; i < 16; ++i)
+                               *c++ = (byte) System.Math.Max(*a++, *b++);
+                       return res;
+               }
+
+
+               public static unsafe Vector16b Min (Vector16b va, Vector16b vb) {
+                       Vector16b res = new Vector16b ();
+                       byte *a = &va.v0;
+                       byte *b = &vb.v0;
+                       byte *c = &res.v0;
+                       for (int i = 0; i < 16; ++i)
+                               *c++ = (byte) System.Math.Min(*a++, *b++);
+                       return res;
+               }
+
+               public static unsafe int ExtractByteMask (Vector16b va) {
+                       int res = 0;
+                       byte *a = (byte*)&va;
+                       for (int i = 0; i < 16; ++i)
+                               res |= (*a++ & 0x80) >> 7 << i;
+                       return res;
+               }
+
+               [CLSCompliant(false)]\r
+               public static unsafe Vector8us SumOfAbsoluteDifferences (Vector16b va, Vector16sb vb) {
+                       Vector8us res = new Vector8us ();
+                       byte *a = &va.v0;
+                       sbyte *b = (sbyte*)&vb;
+
+                       int tmp = 0;
+                       for (int i = 0; i < 8; ++i)
+                               tmp += System.Math.Abs ((int)*a++ - (int)*b++);
+                       res.V0 = (ushort)tmp;
+
+                       tmp = 0;
+                       for (int i = 0; i < 8; ++i)
+                               tmp += System.Math.Abs ((int)*a++ - (int)*b++);
+                       res.V4 = (ushort)tmp;
+
+                       return res;
+               }
+
+               public static unsafe Vector16b CompareEqual (Vector16b va, Vector16b vb) {
+                       Vector16b res = new Vector16b ();
+                       byte *a = &va.v0;
+                       byte *b = &vb.v0;
+                       byte *c = &res.v0;
+                       for (int i = 0; i < 16; ++i)
+                               *c++ = (byte) (*a++ == *b++ ? -1 : 0);
+                       return res;
+               }
+
+               public static unsafe explicit operator Vector4f(Vector16b v)\r
                {\r
-                       Vector16b* p = (Vector16b*)&v;\r
+                       Vector4f* p = (Vector4f*)&v;\r
                        return *p;\r
                }\r
 
-               public static unsafe explicit operator Vector16b(Vector8us v)\r
+               [CLSCompliant(false)]\r
+               public static unsafe explicit operator Vector4ui(Vector16b v)\r
                {\r
-                       Vector16b* p = (Vector16b*)&v;\r
+                       Vector4ui* p = (Vector4ui*)&v;\r
+                       return *p;\r
+               }
+
+               [CLSCompliant(false)]\r
+               public static unsafe explicit operator Vector8us(Vector16b v)\r
+               {\r
+                       Vector8us* p = (Vector8us*)&v;\r
                        return *p;\r
                }
 
@@ -226,5 +251,17 @@ namespace Mono.Simd
                {\r
                        res = val;\r
                }
+
+               [CLSCompliant(false)]\r
+               public static unsafe Vector16b LoadAligned (Vector16b *v)\r
+               {\r
+                       return *v;\r
+               }\r
+\r
+               [CLSCompliant(false)]\r
+               public static unsafe void StoreAligned (Vector16b *res, Vector16b val)\r
+               {\r
+                       *res = val;\r
+               }
        }\r
 }\r