public static bool IsByteOrder(ref Binary.Binary.ByteOrder byteOrder) { var bitOrder = Binary.Binary.BitOrder.Unknown; var testByteOrder = Binary.Binary.ByteOrder.Unknown; ProbeBitOrderAndByteOrder(ref bitOrder, ref testByteOrder); return(byteOrder == testByteOrder); }
public static bool IsByteOrder(Binary.Binary.ByteOrder byteOrder) { return(IsByteOrder(ref byteOrder)); }
public static void ProbeBitOrderAndByteOrder(ref Binary.Binary.BitOrder bitOrder, ref Binary.Binary.ByteOrder byteOrder) { //Don't use unsafe code because eventually .Net MF will be completely supported. //Not because you can't but because of the implications //If Unsafe is used then only the Non - Generic Subset will be supported although you could just as well have Generics too... //Todo, Ensure integer, short and byte ... #if false == NATIVE //Use 128 as a value and get the memory associated with the integer representation of the value byte[] memoryOf = System.BitConverter.GetBytes((int)Binary.Binary.SedecimBitSize); //Use ByteOrder #endif //Iterate the memory looking for a non 0 value for (int offset = 0, endOffset = Binary.Binary.BytesPerInteger; offset < endOffset; ++offset) { //Read a single byte from memory out of the constant value of 128 (0x00000080) at offset 0 in memory (This constant was chosen because it should only have one bit set) //Take a copy of the byte at the offset in memory #if false == NATIVE byte atOffset = memoryOf[offset]; #else byte atOffset = System.Runtime.InteropServices.Marshal.ReadByte(Binary.SedecimBitSize, offset); #endif //If the value is 0 continue if (atOffset == Binary.Binary.Nihil) { continue; } //Assign the result and determine the bit order when the value is not 0. bitOrder = ((Oragon.Classes.Binary.Binary.BitOrder)atOffset); //Determine the ByteOrder using the offset where the value was found switch (offset) { case Binary.Binary.Zero: byteOrder = Binary.Binary.ByteOrder.Little; break; case Binary.Binary.One: byteOrder = Binary.Binary.ByteOrder.MiddleLittle; break; case Binary.Binary.Two: byteOrder = Binary.Binary.ByteOrder.MiddleBig; break; case Binary.Binary.Three: byteOrder = Binary.Binary.ByteOrder.Big; break; } //This check is engineered by the fact that the enumeration of ByteOrder is defined by how the value should be laid on in memory accordingly. //Since BigEndian is reversed then little should be equal to big when read integer is called without reversing the bytes. #if false == NATIVE //If the result of reading an integer of the native bytes of ByteOrder.Little does not match the expected value throw an exception. if ((int)byteOrder != Binary.Binary.ReadInteger(System.BitConverter.GetBytes((int)Binary.Binary.ByteOrder.Little), Binary.Binary.Nihil, Binary.Binary.BytesPerInteger, false)) { throw new System.InvalidOperationException("Did not correctly detect ByteOrder"); } #else //If the native read of the value of m_SystemByteOrder from memory does not match the value expected throw an exception. if ((int)byteOrder != System.Runtime.InteropServices.Marshal.ReadInt32((int)byteOrder, 0)) { throw new System.InvalidOperationException("Did not correctly detect ByteOrder"); } #endif //Could also determine if the Binary Representation is One or Twos Complement.. #if false == NATIVE //This allocation will be removed memoryOf = null; #endif //Stop detection break; } }