private static StashTableEntry <T>[] ReadStashTable <T>( this RuntimeBase runtime, IntPtr pointer, Func <IntPtr, T> callback) { if (pointer == IntPtr.Zero) { return(new StashTableEntry <T> [0]); } StashTableHeader header; if (runtime.Is32Bit == false) { header = runtime.ReadStructure <StashTableHeader>(pointer); } else { header = runtime.ReadStructure <x32.StashTableHeader>(pointer).Upgrade(); } if (header.AllocatedCount == 0) { return(new StashTableEntry <T> [0]); } StashTableEntry[] entries; if (runtime.Is32Bit == false) { entries = runtime.ReadStructureArray <StashTableEntry>(header.EntriesPointer, header.AllocatedCount); } else { var entries32 = runtime.ReadStructureArray <x32.StashTableEntry>(header.EntriesPointer, header.AllocatedCount); entries = new StashTableEntry[header.AllocatedCount]; for (int i = 0; i < header.AllocatedCount; i++) { entries[i] = entries32[i].Upgrade(); } } var items = new StashTableEntry <T> [header.AllocatedCount]; int o = 0; for (int i = 0; i < header.AllocatedCount; i++) { var entry = entries[i]; if (entry.NamePointer == default && entry.ValuePointer == default) { continue; } var name = runtime.ReadStringZ(entry.NamePointer, Encoding.ASCII); var value = callback(entry.ValuePointer); items[o] = new StashTableEntry <T>(name, value); o++; } Array.Resize(ref items, o); return(items); }
private static uint HashTable(RuntimeBase runtime, IntPtr address, uint hash) { throw new NotImplementedException(); var columns = new List <KeyValuePair <ParseColumn, string> >(); var currentAddress = address; while (true) { var column = runtime.ReadStructure <ParseColumn>(currentAddress); currentAddress += 40; var name = runtime.ReadStringZ(column.NamePointer, Encoding.ASCII); if (column.Type == 0) { if (string.IsNullOrEmpty(name) == true) { break; } } columns.Add(new KeyValuePair <ParseColumn, string>(column, name)); } foreach (var kv in columns) { var column = kv.Key; if (column.Flags.HasAny(Parse.ColumnFlags.REDUNDANTNAME | Parse.ColumnFlags.UNOWNED) == true) { continue; } var name = kv.Value; if (string.IsNullOrEmpty(name) == false) { hash = Adler32.Hash(name, hash); } hash = Adler32.Hash(column.Type, hash); var token = Parse.GlobalTokens.GetToken(column.Token); switch (token.GetParameter(column.Flags, 0)) { case Parse.ColumnParameter.NumberOfElements: case Parse.ColumnParameter.Default: case Parse.ColumnParameter.StringLength: case Parse.ColumnParameter.Size: { hash = Adler32.Hash(column.Parameter0.Int32, hash); break; } case Parse.ColumnParameter.BitOffset: { hash = Adler32.Hash(column.Parameter0.Int32 >> 16, hash); break; } case Parse.ColumnParameter.DefaultString: case Parse.ColumnParameter.CommandString: { if (column.Parameter0.Pointer != default) { hash = Adler32.Hash(runtime.ReadStringZ(column.Parameter0.Pointer, Encoding.ASCII), hash); } break; } } var param1 = token.GetParameter(column.Flags, 1); if (column.Parameter1.Pointer != default && (column.Token == 20 || column.Token == 21) && address != column.Parameter1.Pointer && column.Flags.HasAny(Parse.ColumnFlags.STRUCT_NORECURSE) == false) { hash = HashTable(runtime, column.Parameter1.Pointer, hash); } if (column.Parameter1.Pointer != default && param1 == Parse.ColumnParameter.StaticDefineList) { hash = HashStaticDefineList(runtime, column.Parameter1.Pointer, hash); } if (column.Token == 23) { var formatString = runtime.ReadStringZ(column.FormatStringPointer, Encoding.ASCII); if (string.IsNullOrEmpty(formatString) == false) { hash = Adler32.Hash(formatString, hash); } } } return(hash); }