public String ReadStringTable(int offset) { if (_stringBuffer == null || offset > _stringBuffer.Length - 1) { return(null); } if (offset < -1) { return(null); // -1 is an expected value, but less isn't } return((offset == -1) ? String.Empty : FileTools.ByteArrayToStringASCII(_stringBuffer, offset)); }
private void _ParseDataType(byte[] buffer) { int offset = 0; // header FileHeader fileHeader = FileTools.ByteArrayToStructure <FileHeader>(buffer, ref offset); if (fileHeader.FileToken != Token.Head) { throw new Exceptions.UnexpectedTokenException("Expected Head token but got 0x" + fileHeader.FileToken.ToString("X8")); } if (fileHeader.FileVersion != RequiredVersion) { throw new Exceptions.NotSupportedFileVersionException(RequiredVersion, fileHeader.FileVersion); } // Read the strings section StringsHeader stringsHeader = FileTools.ByteArrayToStructure <StringsHeader>(buffer, ref offset); if (stringsHeader.StringsToken != Token.Sect) { throw new Exceptions.UnexpectedTokenException(Token.Sect, stringsHeader.StringsToken); } List <String> strings = new List <String>(); for (int i = 0; i < stringsHeader.StringsCount; i++) { strings.Add(FileTools.ByteArrayToStringASCII(buffer, offset)); offset += strings[i].Length + 1; // +1 for \0 } // String Details UInt32 stringsDetailsToken = FileTools.ByteArrayToUInt32(buffer, ref offset); if (stringsDetailsToken != Token.Sect) { throw new Exceptions.UnexpectedTokenException(Token.Sect, stringsDetailsToken); } // Skip over the details struct because we don't need it. offset += stringsHeader.StringsCount * Marshal.SizeOf(typeof(StringDetailsStruct)); // Files Structure details UInt32 filesToken = FileTools.ByteArrayToUInt32(buffer, ref offset); if (filesToken != Token.Sect) { throw new Exceptions.UnexpectedTokenException(Token.Sect, stringsDetailsToken); } FileDetails.AddRange(FileTools.ByteArrayToArray <FileEntryStruct>(buffer, ref offset, fileHeader.FileCount)); // The Files list is the public interface for (int i = 0; i < fileHeader.FileCount; i++) { PackFileEntry fileEntry = new FileEntry(FileDetails[i]) { Pack = this, Path = System.IO.Path.Combine(strings[FileDetails[i].DirectoryIndex], strings[FileDetails[i].NameIndex]), }; Files.Add(fileEntry); } HasIntegrity = true; }
private static bool _ParsePropertiesScript(byte[] data, ref int offset, ref ExcelFunction excelScript) { ExcelFunction.Parameter parameter = new ExcelFunction.Parameter(); // token and version checks if (!_CheckToken(data, ref offset, Token.mysh)) { return(false); } UInt32 version = FileTools.ByteArrayToUInt32(data, ref offset); if (version != Token.MyshVersion) { return(false); } // general parameter values int charCount = FileTools.ByteArrayToInt32(data, ref offset); if (charCount >= 0x1000) { return(false); } parameter.Name = FileTools.ByteArrayToStringASCII(data, ref offset, charCount); parameter.Unknown = FileTools.ByteArrayToUInt32(data, ref offset); // what kind of parameter is it parameter.TypeId = FileTools.ByteArrayToUInt32(data, ref offset); int paramLength; switch (parameter.TypeId) { case 0x38: // 56 // "nPowerChange" from TCv4 Skills paramLength = 4; break; case 0x39: // 57 // oldstats, x, sel, dmgtype, ? paramLength = 4; break; case 0x3C: // 60 // dam, ? paramLength = 5; break; case 0x41: // 65 // dmg_elec, dmg_fire, etc paramLength = 8; break; default: Debug.Assert(false, "Unknown MYSH TypeId = " + parameter.TypeId); return(false); } parameter.TypeValues = FileTools.ByteArrayToInt32Array(data, ref offset, paramLength); excelScript.Parameters.Add(parameter); if (parameter.TypeId != 0x41) { return(true); // only 0x41 has paramaters and a script values block following it } // get remaining parameters int paramCount = parameter.TypeValues[5]; for (int i = 0; i < paramCount; i++) { if (!_ParsePropertiesScript(data, ref offset, ref excelScript)) { return(false); } } // the actual script values int valuesByteCount = FileTools.ByteArrayToInt32(data, ref offset); if (valuesByteCount <= 0) { return(false); } excelScript.ScriptByteCode = new byte[valuesByteCount]; Buffer.BlockCopy(data, offset, excelScript.ScriptByteCode, 0, valuesByteCount); offset += valuesByteCount; return(true); }
public override sealed bool ParseData(byte[] buffer) { if ((buffer == null)) { return(false); } int offset = 0; StringsHeader stringsHeader = FileTools.ByteArrayToStructure <StringsHeader>(buffer, ref offset); for (int i = 0; i < stringsHeader.Count; i++) { StringBlock stringBlock = new StringBlock { ReferenceId = FileTools.ByteArrayToInt32(buffer, ref offset), Unknown = FileTools.ByteArrayToInt32(buffer, ref offset) }; int count = FileTools.ByteArrayToInt32(buffer, ref offset); stringBlock.StringId = FileTools.ByteArrayToStringASCII(buffer, offset); offset += count + 1; stringBlock.Reserved = FileTools.ByteArrayToInt32(buffer, ref offset); count = FileTools.ByteArrayToInt32(buffer, ref offset); stringBlock.String = FileTools.ByteArrayToStringUnicode(buffer, offset, count); offset += count; int attributeCount = FileTools.ByteArrayToInt32(buffer, ref offset); for (int j = 0; j < attributeCount; j++) { count = FileTools.ByteArrayToInt32(buffer, ref offset); int byteCount = (count + 1) * 2; switch (j) { case 0: stringBlock.Attribute1 = FileTools.ByteArrayToStringUnicode(buffer, offset, byteCount); break; case 1: stringBlock.Attribute2 = FileTools.ByteArrayToStringUnicode(buffer, offset, byteCount); break; case 2: stringBlock.Attribute3 = FileTools.ByteArrayToStringUnicode(buffer, offset, byteCount); break; case 3: stringBlock.Attribute4 = FileTools.ByteArrayToStringUnicode(buffer, offset, byteCount); break; } offset += byteCount; } Rows.Add(stringBlock); } return(HasIntegrity = ((offset == buffer.Length)) ? true : false); }