From 8d2a2cd5de40e2b94ef5007c32832ed9a063dc40 Mon Sep 17 00:00:00 2001
From: chai <215380520@qq.com>
Date: Thu, 12 Oct 2023 22:09:49 +0800
Subject: +hazel-networking
---
 Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs | 131 +++++++++++++++++++++
 1 file changed, 131 insertions(+)
 create mode 100644 Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs
(limited to 'Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs')
diff --git a/Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs b/Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs
new file mode 100644
index 0000000..3a9d1ac
--- /dev/null
+++ b/Tools/Hazel-Networking/Hazel/ByteSpanExtensions.cs
@@ -0,0 +1,131 @@
+namespace Hazel
+{
+    /// 
+    /// Extension functions for (en/de)coding integer values
+    /// 
+    public static class ByteSpanBigEndianExtensions
+    {
+        // Write a 16-bit integer in big-endian format to output[0..2)
+        public static void WriteBigEndian16(this ByteSpan output, ushort value, int offset = 0)
+        {
+            output[offset + 0] = (byte)(value >> 8);
+            output[offset + 1] = (byte)(value >> 0);
+        }
+
+        // Write a 24-bit integer in big-endian format to output[0..3)
+        public static void WriteBigEndian24(this ByteSpan output, uint value, int offset = 0)
+        {
+            output[offset + 0] = (byte)(value >> 16);
+            output[offset + 1] = (byte)(value >> 8);
+            output[offset + 2] = (byte)(value >> 0);
+        }
+
+        // Write a 32-bit integer in big-endian format to output[0..4)
+        public static void WriteBigEndian32(this ByteSpan output, uint value, int offset)
+        {
+            output[offset + 0] = (byte)(value >> 24);
+            output[offset + 1] = (byte)(value >> 16);
+            output[offset + 2] = (byte)(value >> 8);
+            output[offset + 3] = (byte)(value >> 0);
+        }
+
+        // Write a 48-bit integer in big-endian format to output[0..6)
+        public static void WriteBigEndian48(this ByteSpan output, ulong value, int offset = 0)
+        {
+            output[offset + 0] = (byte)(value >> 40);
+            output[offset + 1] = (byte)(value >> 32);
+            output[offset + 2] = (byte)(value >> 24);
+            output[offset + 3] = (byte)(value >> 16);
+            output[offset + 4] = (byte)(value >> 8);
+            output[offset + 5] = (byte)(value >> 0);
+        }
+
+        // Write a 64-bit integer in big-endian format to output[0..8)
+        public static void WriteBigEndian64(this ByteSpan output, ulong value, int offset = 0)
+        {
+            output[offset + 0] = (byte)(value >> 56);
+            output[offset + 1] = (byte)(value >> 48);
+            output[offset + 2] = (byte)(value >> 40);
+            output[offset + 3] = (byte)(value >> 32);
+            output[offset + 4] = (byte)(value >> 24);
+            output[offset + 5] = (byte)(value >> 16);
+            output[offset + 6] = (byte)(value >> 8);
+            output[offset + 7] = (byte)(value >> 0);
+        }
+
+        // Read a 16-bit integer in big-endian format from input[0..2)
+        public static ushort ReadBigEndian16(this ByteSpan input, int offset = 0)
+        {
+            ushort value = 0;
+            value |= (ushort)(input[offset + 0] << 8);
+            value |= (ushort)(input[offset + 1] << 0);
+            return value;
+        }
+
+        // Read a 24-bit integer in big-endian format from input[0..3)
+        public static uint ReadBigEndian24(this ByteSpan input, int offset = 0)
+        {
+            uint value = 0;
+            value |= (uint)input[offset + 0] << 16;
+            value |= (uint)input[offset + 1] <<  8;
+            value |= (uint)input[offset + 2] <<  0;
+            return value;
+        }
+
+        // Read a 48-bit integer in big-endian format from input[0..3)
+        public static ulong ReadBigEndian48(this ByteSpan input, int offset = 0)
+        {
+            ulong value = 0;
+            value |= (ulong)input[offset + 0] << 40;
+            value |= (ulong)input[offset + 1] << 32;
+            value |= (ulong)input[offset + 2] << 24;
+            value |= (ulong)input[offset + 3] << 16;
+            value |= (ulong)input[offset + 4] <<  8;
+            value |= (ulong)input[offset + 5] <<  0;
+            return value;
+        }
+    }
+
+    public static class ByteSpanLittleEndianExtensions
+    {
+        // Read a 24-bit integer in little-endian format from input[0..3)
+        public static uint ReadLittleEndian24(this ByteSpan input, int offset = 0)
+        {
+            uint value = 0;
+            value |= (uint)input[offset + 0];
+            value |= (uint)input[offset + 1] << 8;
+            value |= (uint)input[offset + 2] << 16;
+            return value;
+        }
+
+        // Read a 24-bit integer in little-endian format from input[0..4)
+        public static uint ReadLittleEndian32(this ByteSpan input, int offset = 0)
+        {
+            uint value = 0;
+            value |= (uint)input[offset + 0];
+            value |= (uint)input[offset + 1] << 8;
+            value |= (uint)input[offset + 2] << 16;
+            value |= (uint)input[offset + 3] << 24;
+            return value;
+        }
+
+        /// 
+        /// Reuse an existing span if there is enough space,
+        /// otherwise allocate new storage
+        /// 
+        /// 
+        /// Source span we should attempt to reuse
+        /// 
+        /// Required size (bytes)
+        public static ByteSpan ReuseSpanIfPossible(this ByteSpan source, int requiredSize)
+        {
+            if (source.Length >= requiredSize)
+            {
+                return source.Slice(0, requiredSize);
+            }
+
+            return new byte[requiredSize];
+        }
+
+    }
+}
-- 
cgit v1.1-26-g67d0