/// <summary>Get the "main" <see cref="GroupTagCollection"/> property value from a group tag container</summary> /// <param name="container">Type which acts as a <see cref="GroupTagCollection"/> container</param> /// <returns></returns> public static GroupTagCollection GetCollection(Type container) { Contract.Requires(container != null); Contract.Ensures(Contract.Result <GroupTagCollection>() != null); var attr = container.GetCustomAttributes(typeof(GroupTagContainerAttribute), false); if (attr.Length != 1) { throw new ArgumentException(string.Format(Util.InvariantCultureInfo, "[{0}] doesn't have a ", container.FullName), nameof(container)); } return((attr[0] as GroupTagContainerAttribute).TagCollection); }
public ulong[] ReadFixedArray(ulong[] array, int startIndex, int length) { Contract.Requires(array != null); Contract.Requires(startIndex >= 0); Contract.Requires(length >= 0); Contract.Ensures(Contract.Result <ulong[]>() != null); for (int x = startIndex, end = startIndex + length; x < end; x++) { array[x] = ReadUInt64(); } return(array); }
public static byte[] DecompressFromStream(IO.EndianStream blockStream) { Contract.Requires <ArgumentNullException>(blockStream != null); Contract.Ensures(Contract.Result <byte[]>() != null); byte[] buffer; using (var cs = new CompressedStream()) { cs.Serialize(blockStream); cs.Decompress(); buffer = cs.UncompressedData; } return(buffer); }
public static EndianStream UsingWriter(EndianWriter writer) { Contract.Requires <ArgumentNullException>(writer != null); Contract.Ensures(Contract.Result <EndianStream>() != null); var s = new EndianStream { BaseStream = writer.BaseStream, StreamPermissions = FileAccess.Write, StreamMode = FileAccess.Write, Writer = writer }; return(s); }
/// <summary>Converts a string containing hex values into a byte array</summary> /// <param name="data">String of hex digits to convert</param> /// <param name="startIndex">Character index in <paramref name="data"/> to start the conversion at</param> /// <returns></returns> public static byte[] ByteStringToArray(string data , int startIndex = 0) { Contract.Requires <ArgumentNullException>(!string.IsNullOrEmpty(data)); Contract.Requires(startIndex >= 0); Contract.Requires(startIndex < data.Length); Contract.Requires( ((data.Length - startIndex) % 2) == 0, "Can't byte-ify a string that's not even!" ); Contract.Ensures(Contract.Result <byte[]>() != null); return(ByteStringToArray(data, startIndex, data.Length - startIndex)); }
/// <summary>Generate a specific static field setter for a specific reference type</summary> /// <typeparam name="T">The type which contains the member</typeparam> /// <typeparam name="TValue">The static member's actual type</typeparam> /// <param name="memberName">The member's name as defined in <typeparamref name="T"/></param> /// <returns>A compiled lambda which can access (set) the member</returns> /// <exception cref="MemberAccessException"><paramref name="memberName"/> is readonly</exception> /// <remarks>Generates a method similar to this: /// <code> /// void SetMethod(TValue value) /// { /// T.memberName = value; /// } /// </code> /// </remarks> public static Action <TValue> GenerateStaticFieldSetter <T, TValue>(string memberName) where T : class { Contract.Requires <ArgumentException>(!string.IsNullOrEmpty(memberName)); Contract.Ensures(Contract.Result <Action <TValue> >() != null); var param_value = Expr.Parameter(typeof(TValue), kValueName); // the member's new value var member = Expr.Field(null, typeof(T), memberName); // i.e., 'T.memberName' ValidateMemberForGenerateSetter(member.Member); var assign = Expr.Assign(member, param_value); // i.e., 'T.memberName = value' var lambda = Expr.Lambda <Action <TValue> >(assign, param_value); return(lambda.Compile()); }
/// <summary>Takes a four character code and performs a dword byte swap on it, storing the result in a new four character code</summary> /// <param name="tag">value to be byte swapped</param> /// <returns>dword byte swapped four character code</returns> public static char[] Swap(char[] tag) { Contract.Requires(tag != null); Contract.Requires <ArgumentOutOfRangeException>(tag.Length >= kExpectedTagLength); Contract.Ensures(Contract.Result <char[]>() != null); Contract.Ensures(Contract.Result <char[]>().Length == kExpectedTagLength); char[] swap = new char[kExpectedTagLength]; swap[0] = tag[3]; swap[1] = tag[2]; swap[2] = tag[1]; swap[3] = tag[0]; return(swap); }
public static int GetBitCount(Shell.ProcessorSize value) { Contract.Ensures(Contract.Result <int>() >= -1); switch (value) { case Shell.ProcessorSize.x32: return(Bits.kInt32BitCount); case Shell.ProcessorSize.x64: return(Bits.kInt64BitCount); default: return(-1); } }
public static BitVectorUserInterfaceData ForExplicitData(IEnumerable <BitUserInterfaceData> bitInfos) { Contract.Ensures(Contract.Result <BitVectorUserInterfaceData>() != null); var info = new BitVectorUserInterfaceData(); if (bitInfos != null) { info.mBitInfo = bitInfos.ToArray(); if (info.mBitInfo.Length == 0 || Array.TrueForAll(info.mBitInfo, CanNotBeRendered)) { info.mBitInfo = null; } } return(info); }
/// <summary>Convert a byte digit character pair to the byte they represent</summary> /// <param name="radix">The base we're converting from</param> /// <param name="c2">Character in the 2nd position (when reading right to left)</param> /// <param name="c1">Character in the 1st position (when reading right to left)</param> /// <returns></returns> /// <remarks>Upper ('A') and lower ('a') case char digits map to the same int values</remarks> /// <example> /// int b = CharsToByte(NumeralBase.Hex, '3', 'F'); /// b == 63; /// </example> public static int CharsToByte(NumeralBase radix, char c2, char c1) { Contract.Ensures(Contract.Result <int>() >= byte.MinValue); Contract.Ensures(Contract.Result <int>() <= byte.MaxValue); int value = 0; if (CharIsAnyDigit(c2) && CharIsAnyDigit(c1)) { value = CharToInt(c2, radix, 1) + CharToInt(c1, radix, 0); } // Someone could supply a radix value that isn't technically a member of NumeralBase (eg, 36) // So we clamp it to a byte here return(value > byte.MaxValue ? 0 : value); }
public static byte TrailingZerosCount(uint value) { Contract.Ensures(Contract.Result <byte>() <= kInt32BitCount); if (value == 0) { return(kInt32BitCount); } // instead of (value & -value), where the op result is a long, we do this to keep it all 32-bit uint ls1b = (~value) + 1; // two's complement ls1b = value & ls1b; // least significant 1 bit uint index = (ls1b * 0x077CB531U) >> 27; return(kMultiplyDeBruijnBitPositionTrailingZeros32[index]); }
public static int GetByteCount(Shell.ProcessorSize value) { Contract.Ensures(Contract.Result <int>() >= -1); switch (value) { case Shell.ProcessorSize.x32: return(sizeof(int)); case Shell.ProcessorSize.x64: return(sizeof(long)); default: return(-1); } }
public static byte[] LowLevelDecompress(byte[] bytes, int uncompressedSize, int skipHeaderLength = sizeof(uint)) { Contract.Requires <ArgumentNullException>(bytes != null); Contract.Requires <ArgumentOutOfRangeException>(uncompressedSize >= 0); Contract.Requires <ArgumentOutOfRangeException>(skipHeaderLength >= 0); Contract.Ensures(Contract.Result <byte[]>() != null); byte[] result = new byte[uncompressedSize]; var zip = new ICSharpCode.SharpZipLib.Zip.Compression.Inflater(); { zip.SetInput(bytes, skipHeaderLength, bytes.Length - skipHeaderLength); // skip the decompressed size header zip.Inflate(result); } return(result); }
/// <summary>Converts a string containing hex values into a byte array</summary> /// <param name="data">String of hex digits to convert</param> /// <param name="startIndex">Character index in <paramref name="data"/> to start the conversion at</param> /// <param name="count">Number of characters to convert</param> /// <returns></returns> public static byte[] ByteStringToArray(string data, int startIndex, int count) { Contract.Requires <ArgumentNullException>(!string.IsNullOrEmpty(data)); Contract.Requires(startIndex >= 0); Contract.Requires(startIndex < data.Length); Contract.Requires(count > 0); Contract.Requires((startIndex + count) <= data.Length); Contract.Requires( (((data.Length - startIndex) - count) % 2) == 0, "Can't byte-ify a string that's not even!" ); Contract.Ensures(Contract.Result <byte[]>() != null); byte[] bytes = new byte[count / 2]; return(ByteStringToArray(bytes, data, startIndex, count)); }
/// <summary>Creates a string of the build component name ids separated by periods</summary> /// <returns></returns> /// <remarks>If the <see cref="Branch"/>'s display name is the same as <see cref="Engine"/>, the former isn't included in the output</remarks> public string ToDisplayString() { Contract.Ensures(Contract.Result <string>() != null); if (IsNone) { return(TypeExtensions.kNoneDisplayString); } var sb = new System.Text.StringBuilder(); int engine_index = EngineIndex; int branch_index = BranchIndex; int revisn_index = RevisionIndex; if (engine_index.IsNotNone()) { var engine = EngineRegistry.Engines[engine_index]; sb.Append(engine); #region Branch if (branch_index.IsNotNone()) { var branch = engine.BuildRepository.Branches[branch_index]; // only include the branch display name if it isn't the same as the engine's if (branch.ToString() != engine.ToString()) { sb.AppendFormat(Util.InvariantCultureInfo, ".{0}", branch); } #region Revision if (revisn_index.IsNotNone()) { var revisn = branch.Revisions[revisn_index]; sb.AppendFormat(Util.InvariantCultureInfo, ".{0}", revisn.Version.ToString(Util.InvariantCultureInfo)); } #endregion } #endregion } return(sb.ToString()); }
/// <summary>Generate a specific member setter for a specific reference type</summary> /// <typeparam name="T">The type which contains the member</typeparam> /// <typeparam name="TValue">The member's actual type</typeparam> /// <param name="memberName">The member's name as defined in <typeparamref name="T"/></param> /// <returns>A compiled lambda which can access (set) the member</returns> /// <exception cref="MemberAccessException"><paramref name="memberName"/> is readonly</exception> /// <remarks>Generates a method similar to this: /// <code> /// void SetMethod(T @this, TValue value) /// { /// @this.memberName = value; /// } /// </code> /// </remarks> public static ReferenceTypeMemberSetterDelegate <T, TValue> GenerateReferenceTypeMemberSetter <T, TValue>(string memberName) where T : class { Contract.Requires <ArgumentException>(!string.IsNullOrEmpty(memberName)); Contract.Ensures(Contract.Result <ReferenceTypeMemberSetterDelegate <T, TValue> >() != null); var param_this = Expr.Parameter(typeof(T), kThisName); var param_value = Expr.Parameter(typeof(TValue), kValueName); // the member's new value var member = Expr.PropertyOrField(param_this, memberName); // i.e., 'this.memberName' ValidateMemberForGenerateSetter(member.Member); var assign = Expr.Assign(member, param_value); // i.e., 'this.memberName = value' var lambda = Expr.Lambda <ReferenceTypeMemberSetterDelegate <T, TValue> >( assign, param_this, param_value); return(lambda.Compile()); }
public static Encoding GetEncoding(this MS.StringStorageWidthType type) { Contract.Ensures(Contract.Result <Encoding>() != null); switch (type) { case MS.StringStorageWidthType.Ascii: return(Encoding.ASCII); case MS.StringStorageWidthType.Unicode: return(Encoding.Unicode); case MS.StringStorageWidthType.UTF7: return(Encoding.UTF7); case MS.StringStorageWidthType.UTF8: return(Encoding.UTF8); case MS.StringStorageWidthType.UTF32: return(Encoding.UTF32); default: throw new Debug.UnreachableException(type.ToString()); } }
public static byte LeadingZerosCount(uint value) { Contract.Ensures(Contract.Result <byte>() <= kInt32BitCount); if (value == 0) { return(kInt32BitCount); } value |= value >> 1; // first round down to one less than a power of 2 value |= value >> 2; value |= value >> 4; value |= value >> 8; value |= value >> 16; // subtract the log base 2 from the number of bits in the integer uint index = (value * 0x07C4ACDDU) >> 27; return((byte)(kInt32BitCount - kMultiplyDeBruijnBitPositionLeadingZeros32[index])); }
public static byte IndexOfHighestBitSet(ulong value) { Contract.Ensures(Contract.Result <byte>() < kInt64BitCount); int index = 0; uint high = GetHighBits(value); if (high != 0) { index = IndexOfHighestBitSet(high) + kInt32BitCount; } else { index = IndexOfHighestBitSet(GetLowBits(value)); } Contract.Assume(index >= 0); return((byte)index); }
/// <summary>Takes a (unsigned) integer and converts it into its eight-cc value</summary> /// <param name="groupTag"></param> /// <param name="tag">optional result buffer</param> /// <param name="isBigEndian">endian order override</param> /// <returns>big-endian ordered eight-cc if <paramref name="isBigEndian"/> is true, little-endian if false</returns> public static char[] FromULong(TagWord groupTag, char[] tag = null, bool isBigEndian = true) { Contract.Requires(tag == null || tag.Length >= 8); Contract.Ensures(Contract.Result <char[]>() != null); Contract.Ensures(Contract.Result <char[]>().Length >= kExpectedTagLength); if (tag == null) { tag = new char[kExpectedTagLength]; } if (isBigEndian) { // high bits tag[0] = (char)((groupTag & 0xFF000000) >> 24); tag[1] = (char)((groupTag & 0x00FF0000) >> 16); tag[2] = (char)((groupTag & 0x0000FF00) >> 8); tag[3] = (char)(groupTag & 0x000000FF); // low bits groupTag >>= 32; tag[4 + 0] = (char)((groupTag & 0xFF000000) >> 24); tag[4 + 1] = (char)((groupTag & 0x00FF0000) >> 16); tag[4 + 2] = (char)((groupTag & 0x0000FF00) >> 8); tag[4 + 3] = (char)(groupTag & 0x000000FF); } else { // high bits tag[3] = (char)((groupTag & 0xFF000000) >> 24); tag[2] = (char)((groupTag & 0x00FF0000) >> 16); tag[1] = (char)((groupTag & 0x0000FF00) >> 8); tag[0] = (char)(groupTag & 0x000000FF); // low bits groupTag >>= 32; tag[4 + 3] = (char)((groupTag & 0xFF000000) >> 24); tag[4 + 2] = (char)((groupTag & 0x00FF0000) >> 16); tag[4 + 1] = (char)((groupTag & 0x0000FF00) >> 8); tag[4 + 0] = (char)(groupTag & 0x000000FF); } return(tag); }
// #REVIEW: Instead of doing byte.ToString("X2") we could just have a lookup table... #region ByteArrayToString (byte[] to string) /// <summary>Converts an array of bytes to a hex string</summary> /// <param name="data">Buffer of bytes to convert</param> /// <param name="startIndex">Index in <paramref name="data"/> to start the conversion</param> /// <param name="count">Number of bytes to convert</param> /// <example>"1337BEEF"</example> /// <returns></returns> public static string ByteArrayToString(byte[] data, int startIndex, int count) { Contract.Requires <ArgumentNullException>(data != null); Contract.Requires(startIndex >= 0); Contract.Requires(startIndex < data.Length); Contract.Requires(count > 0); Contract.Requires((startIndex + count) <= data.Length); Contract.Ensures(Contract.Result <string>() != null); StringBuilder sb = new StringBuilder(count * 2); for (int x = startIndex; x < (startIndex + count); x++) { sb.Append(data[x].ToString("X2", KSoft.Util.InvariantCultureInfo)); } return(sb.ToString()); }
/// <summary>Get a human readable display string for debugging system references from a GUID</summary> /// <param name="systemGuid"></param> /// <returns>Non-null or empty string, no matter the input</returns> public static string GetSystemDebugDisplayString(Values.KGuid systemGuid) { Contract.Ensures(Contract.Result <string>().IsNotNullOrEmpty()); EngineSystemAttribute system_attribute = null; if (systemGuid.IsNotEmpty) { system_attribute = TryGetRegisteredSystem(systemGuid); } string display_string = string.Format("{{{0}}}={1}", systemGuid.ToString(Values.KGuid.kFormatHyphenated), system_attribute != null ? system_attribute.EngineSystemType.ToString() : "UNDEFINED_SYSTEM"); return(display_string); }
public static TFunc GenerateObjectMethodProxy <T, TFunc, TSig>( string methodName, Reflect.BindingFlags bindingAttr = Reflect.BindingFlags.NonPublic | Reflect.BindingFlags.Instance) where TFunc : class where TSig : class { Contract.Requires <ArgumentException>(!string.IsNullOrEmpty(methodName)); Contract.Requires <ArgumentException>(typeof(TSig).IsSubclassOf(typeof(Delegate))); Contract.Requires <ArgumentException>(typeof(TFunc).IsSubclassOf(typeof(Delegate))); Contract.Ensures(Contract.Result <TFunc>() != null); var type = typeof(T); var sig_method_info = typeof(TSig).GetMethod(kDelegateInvokeMethodName); var method_params = sig_method_info.GetParameters().Select(p => p.ParameterType).ToArray(); var method = type.GetMethod(methodName, bindingAttr, null, method_params, null); if (method == null) { throw new InvalidOperationException(string.Format(KSoft.Util.InvariantCultureInfo, "Couldn't find a method in {0} named '{1}' ({2})", type, methodName, bindingAttr)); } var param_this = Expr.Parameter(type, kThisName); // have to convert it to a collection, else a different set of Parameter objects will be created for Call and the Lambda var @params = (from param_type in method_params select Expr.Parameter(param_type)).ToArray(); var call = Expr.Call(param_this, method, @params); var params_lamda = new System.Linq.Expressions.ParameterExpression[method_params.Length + 1]; { params_lamda[0] = param_this; int i = 1; foreach (var param in @params) { params_lamda[i++] = param; } } return(Expr.Lambda <TFunc>(call, params_lamda).Compile()); }
public static List <FieldInfo> GetEnumFields(Type enumType) { Contract.Requires <ArgumentNullException>(enumType != null); Contract.Requires <ArgumentException>(enumType.IsEnum); Contract.Ensures(Contract.Result <List <FieldInfo> >() != null); var fields = enumType.GetFields(); var results = new List <FieldInfo>(fields.Length - 1); foreach (var field in fields) { if (field.Name == kMemberName) { continue; } results.Add(field); } return(results); }
public static byte[] BufferFromStream(MemoryStream ms, int offset = TypeExtensions.kNoneInt32, int length = TypeExtensions.kNoneInt32, bool skipHeader = true) { Contract.Requires <ArgumentNullException>(ms != null); Contract.Ensures(Contract.Result <byte[]>() != null); if (offset.IsNone()) { offset = 0; } if (length.IsNone()) { length = (int)ms.Length; } using (var dec = new DeflateStream(ms, CompressionMode.Decompress, true)) { return(BufferFromStream(dec, offset, length, skipHeader)); } }
/// <summary>Generate a specific member setter for a specific reference type</summary> /// <typeparam name="TValue">The member's actual type</typeparam> /// <param name="type">The type which contains the member</param> /// <param name="memberName">The member's name as defined in <paramref name="type"/></param> /// <returns>A compiled lambda which can access (set) the member</returns> /// <exception cref="MemberAccessException"><paramref name="memberName"/> is readonly</exception> /// <remarks>Generates a method similar to this: /// <code> /// void SetMethod(object @this, TValue value) /// { /// ((type)@this).memberName = value; /// } /// </code> /// </remarks> public static ReferenceTypeMemberSetterDelegate <object, TValue> GenerateReferenceTypeMemberSetter <TValue>(Type type, string memberName) { Contract.Requires <ArgumentNullException>(type != null); Contract.Requires <ArgumentException>(!type.IsGenericTypeDefinition); Contract.Requires <ArgumentException>(!string.IsNullOrEmpty(memberName)); Contract.Requires <ArgumentException>(!type.IsValueType, "Type must be a reference type"); Contract.Ensures(Contract.Result <ReferenceTypeMemberSetterDelegate <object, TValue> >() != null); var param_this = Expr.Parameter(typeof(object), kThisName); var param_value = Expr.Parameter(typeof(TValue), kValueName); // the member's new value var cast_this = Expr.Convert(param_this, type); // i.e., '((type)this)' var member = Expr.PropertyOrField(cast_this, memberName); // i.e., 'this.memberName' ValidateMemberForGenerateSetter(member.Member); var assign = Expr.Assign(member, param_value); // i.e., 'this.memberName = value' var lambda = Expr.Lambda <ReferenceTypeMemberSetterDelegate <object, TValue> >( assign, param_this, param_value); return(lambda.Compile()); }
/// <summary>Reads a tag id (four character code)</summary> /// <param name="tag">Array to populate</param> /// <returns>Big-endian ordered tag id</returns> public char[] ReadTag32(char[] tag) { Contract.Requires(tag != null); Contract.Requires(tag.Length >= 4); Contract.Ensures(Contract.Result <char[]>() != null); Contract.Ensures(Contract.Result <char[]>().Length >= 4); tag[0] = (char)base.ReadByte(); tag[1] = (char)base.ReadByte(); tag[2] = (char)base.ReadByte(); tag[3] = (char)base.ReadByte(); // Explicitly check for Little endian since this is // a character array and not a primitive integer if (ByteOrder == Shell.EndianFormat.Little) { Array.Reverse(tag, 0, 4); return(tag); } return(tag); }
/// <summary>Generate a specific member setter for a specific value type</summary> /// <typeparam name="T">The type which contains the member</typeparam> /// <typeparam name="TValue">The member's actual type</typeparam> /// <param name="memberName">The member's name as defined in <typeparamref name="T"/></param> /// <returns>A compiled lambda which can access (set) the member</returns> /// <remarks>Generates a method similar to this: /// <code> /// void SetMethod(ref T @this, TValue value) /// { /// @this.memberName = value; /// } /// </code> /// </remarks> public static ValueTypeMemberSetterDelegate <T, TValue> GenerateValueTypeMemberSetter <T, TValue>(string memberName) where T : struct { Contract.Requires <ArgumentException>(!string.IsNullOrEmpty(memberName)); Contract.Ensures(Contract.Result <ValueTypeMemberSetterDelegate <T, TValue> >() != null); // Get a "ref type" of the value-type we're dealing with // Eg: Guid => "System.Guid&" var this_ref = typeof(T).MakeByRefType(); var param_this = Expr.Parameter(this_ref, kThisName); var param_value = Expr.Parameter(typeof(TValue), kValueName); // the member's new value var member = Expr.PropertyOrField(param_this, memberName); // i.e., 'this.memberName' ValidateMemberForGenerateSetter(member.Member); var assign = Expr.Assign(member, param_value); // i.e., 'this.memberName = value' var lambda = Expr.Lambda <ValueTypeMemberSetterDelegate <T, TValue> >( assign, param_this, param_value); return(lambda.Compile()); }
/// <summary>Convert an array of bytes into a formatted hex string</summary> /// <param name="data">Buffer of bytes to convert</param> /// <param name="padding">Padding string to appear before each line of hex characters</param> /// <param name="digitsPerLine">Number of hex characters per line</param> /// <returns></returns> /// <remarks>Uses <see cref="System.Environment.NewLine"/> for line termination</remarks> public static string ByteArrayToAlignedString(byte[] data , string padding = "" , int digitsPerLine = kDefaultHexDigitsPerLine) { Contract.Requires <ArgumentNullException>(data != null); Contract.Requires <ArgumentNullException>(padding != null); Contract.Requires(digitsPerLine >= 2); Contract.Requires((digitsPerLine % 2) == 0); Contract.Ensures(Contract.Result <string>() != null); string new_line = Environment.NewLine; int blocks = data.Length / digitsPerLine; int leftovers = data.Length % digitsPerLine; StringBuilder sb = new StringBuilder( (data.Length * 2) + (new_line.Length * blocks) + // calculate how many new line characters we'll need (padding.Length * (leftovers == 0 ? blocks : blocks + 1)) // calculate how many characters the padding on each line will take ); int index = 0; for (int b = 0; b < blocks; b++, index += digitsPerLine) { sb.AppendFormat(KSoft.Util.InvariantCultureInfo, "{0}{1}{2}", padding, ByteArrayToString(data, index, digitsPerLine), new_line); } if (leftovers > 0) { sb.AppendFormat(KSoft.Util.InvariantCultureInfo, "{0}{1}{2}", padding, ByteArrayToString(data, index), new_line); } return(sb.ToString()); }
/// <summary>Returns <see cref="BuildString"/></summary> /// <returns></returns> public override string ToString() { Contract.Ensures(Contract.Result <string>() != null); return(BuildString); }