private void LoadFile(string fullName) { var reader = new FileReader(fullName); LoadFile(reader); }
private void LoadBlkFile(FileReader reader, Guid?targetId = null) { if (targetId == null) { Logger.Info("Loading " + reader.FileName); } else { Logger.Info("Loading " + reader.FileName + " with target ID " + targetId.Value.ToString()); } try { var blkFile = new BlkFile(reader); bool targetFound = false; for (int i = 0; i < blkFile.Files.Count; i++) { //Console.WriteLine(blkFile.Files[i].ID); if (targetId.HasValue && targetId.Value != blkFile.Files[i].ID) { continue; } targetFound = true; // TODO: proper dummyPath var dummyPath = Path.Combine(Path.GetDirectoryName(reader.FullPath), string.Format("{0}_{1}", reader.FileName, blkFile.Files[i].ID.ToString())); var subReader = new FileReader(dummyPath, new MemoryStream(blkFile.Files[i].Data)); var asset = LoadAssetsFromMemory(subReader, dummyPath); if (asset == null) { //Logger.Error("what"); continue; } foreach (var sharedFile in asset.m_Externals) { var sharedFileName = sharedFile.fileName; var sharedFileNameWithID = string.Format("{0}_{1}", sharedFileName, sharedFile.cabId.ToString()); if (!sharedFileName.EndsWith(".blk")) { // this will directly load .blk files, so anything that isn't one is not supported Logger.Warning(String.Format("attempted to load non-blk shared file ({0})", sharedFileName)); continue; } if (!importFilesHash.Contains(sharedFileNameWithID)) { var sharedFilePath = Path.Combine(Path.GetDirectoryName(reader.FullPath), sharedFileName); if (!File.Exists(sharedFilePath)) { var findFiles = Directory.GetFiles(Path.GetDirectoryName(reader.FullPath), sharedFileName, SearchOption.AllDirectories); if (findFiles.Length > 0) { sharedFilePath = findFiles[0]; } } if (File.Exists(sharedFilePath)) { // TODO: proper integration with the loading bar LoadBlkFile(new FileReader(sharedFilePath), sharedFile.cabId); //importFiles.Add(sharedFilePath); importFilesHash.Add(sharedFileNameWithID); } } } } if (blkFile.Files.Count > 0 && !targetFound) { Logger.Warning("failed to find target mhy0"); } } catch (Exception e) { Logger.Error($"Error while reading blk file {reader.FileName}", e); } finally { reader.Dispose(); } }
public SerializedFile(FileReader reader, AssetsManager assetsManager) { this.assetsManager = assetsManager; this.reader = reader; fullName = reader.FullPath; fileName = reader.FileName; // ReadHeader header = new SerializedFileHeader(); header.m_MetadataSize = reader.ReadUInt32(); header.m_FileSize = reader.ReadUInt32(); header.m_Version = (SerializedFileFormatVersion)reader.ReadUInt32(); header.m_DataOffset = reader.ReadUInt32(); if (header.m_Version >= SerializedFileFormatVersion.Unknown_9) { header.m_Endianess = reader.ReadByte(); header.m_Reserved = reader.ReadBytes(3); m_FileEndianess = header.m_Endianess; } else { reader.Position = header.m_FileSize - header.m_MetadataSize; m_FileEndianess = reader.ReadByte(); } if (header.m_Version >= SerializedFileFormatVersion.LargeFilesSupport) { header.m_MetadataSize = reader.ReadUInt32(); header.m_FileSize = reader.ReadInt64(); header.m_DataOffset = reader.ReadInt64(); reader.ReadInt64(); // unknown } // ReadMetadata if (m_FileEndianess == 0) { reader.Endian = EndianType.LittleEndian; } if (header.m_Version >= SerializedFileFormatVersion.Unknown_7) { unityVersion = reader.ReadStringToNull(); SetVersion(unityVersion); } if (header.m_Version >= SerializedFileFormatVersion.Unknown_8) { m_TargetPlatform = (BuildTarget)reader.ReadInt32(); if (!Enum.IsDefined(typeof(BuildTarget), m_TargetPlatform)) { m_TargetPlatform = BuildTarget.UnknownPlatform; } } if (header.m_Version >= SerializedFileFormatVersion.HasTypeTreeHashes) { m_EnableTypeTree = reader.ReadBoolean(); } // Read Types int typeCount = reader.ReadInt32(); m_Types = new List <SerializedType>(typeCount); for (int i = 0; i < typeCount; i++) { m_Types.Add(ReadSerializedType(false)); } if (header.m_Version >= SerializedFileFormatVersion.Unknown_7 && header.m_Version < SerializedFileFormatVersion.Unknown_14) { bigIDEnabled = reader.ReadInt32(); } // Read Objects int objectCount = reader.ReadInt32(); m_Objects = new List <ObjectInfo>(objectCount); Objects = new List <Object>(objectCount); ObjectsDic = new Dictionary <long, Object>(objectCount); for (int i = 0; i < objectCount; i++) { var objectInfo = new ObjectInfo(); if (bigIDEnabled != 0) { objectInfo.m_PathID = reader.ReadInt64(); } else if (header.m_Version < SerializedFileFormatVersion.Unknown_14) { objectInfo.m_PathID = reader.ReadInt32(); } else { reader.AlignStream(); objectInfo.m_PathID = reader.ReadInt64(); } if (header.m_Version >= SerializedFileFormatVersion.LargeFilesSupport) { objectInfo.byteStart = reader.ReadInt64(); } else { objectInfo.byteStart = reader.ReadUInt32(); } objectInfo.byteStart += header.m_DataOffset; objectInfo.byteSize = reader.ReadUInt32(); objectInfo.typeID = reader.ReadInt32(); if (header.m_Version < SerializedFileFormatVersion.RefactoredClassId) { objectInfo.classID = reader.ReadUInt16(); objectInfo.serializedType = m_Types.Find(x => x.classID == objectInfo.typeID); } else { var type = m_Types[objectInfo.typeID]; objectInfo.serializedType = type; objectInfo.classID = type.classID; } if (header.m_Version < SerializedFileFormatVersion.HasScriptTypeIndex) { objectInfo.isDestroyed = reader.ReadUInt16(); } if (header.m_Version >= SerializedFileFormatVersion.HasScriptTypeIndex && header.m_Version < SerializedFileFormatVersion.RefactorTypeData) { var m_ScriptTypeIndex = reader.ReadInt16(); if (objectInfo.serializedType != null) { objectInfo.serializedType.m_ScriptTypeIndex = m_ScriptTypeIndex; } } if (header.m_Version == SerializedFileFormatVersion.SupportsStrippedObject || header.m_Version == SerializedFileFormatVersion.RefactoredClassId) { objectInfo.stripped = reader.ReadByte(); } m_Objects.Add(objectInfo); } if (header.m_Version >= SerializedFileFormatVersion.HasScriptTypeIndex) { int scriptCount = reader.ReadInt32(); m_ScriptTypes = new List <LocalSerializedObjectIdentifier>(scriptCount); for (int i = 0; i < scriptCount; i++) { var m_ScriptType = new LocalSerializedObjectIdentifier(); m_ScriptType.localSerializedFileIndex = reader.ReadInt32(); if (header.m_Version < SerializedFileFormatVersion.Unknown_14) { m_ScriptType.localIdentifierInFile = reader.ReadInt32(); } else { reader.AlignStream(); m_ScriptType.localIdentifierInFile = reader.ReadInt64(); } m_ScriptTypes.Add(m_ScriptType); } } int externalsCount = reader.ReadInt32(); m_Externals = new List <FileIdentifier>(externalsCount); for (int i = 0; i < externalsCount; i++) { var m_External = new FileIdentifier(); if (header.m_Version >= SerializedFileFormatVersion.Unknown_6) { var tempEmpty = reader.ReadStringToNull(); } if (header.m_Version >= SerializedFileFormatVersion.Unknown_5) { m_External.guid = new Guid(reader.ReadBytes(16)); m_External.type = reader.ReadInt32(); } m_External.pathName = reader.ReadStringToNull(); m_External.fileName = Path.GetFileName(m_External.pathName); m_Externals.Add(m_External); } if (header.m_Version >= SerializedFileFormatVersion.SupportsRefObject) { int refTypesCount = reader.ReadInt32(); m_RefTypes = new List <SerializedType>(refTypesCount); for (int i = 0; i < refTypesCount; i++) { m_RefTypes.Add(ReadSerializedType(true)); } } if (header.m_Version >= SerializedFileFormatVersion.Unknown_5) { userInformation = reader.ReadStringToNull(); } //reader.AlignStream(16); }
private void LoadZipFile(FileReader reader) { Logger.Info("Loading " + reader.FileName); try { using (ZipArchive archive = new ZipArchive(reader.BaseStream, ZipArchiveMode.Read)) { List <string> splitFiles = new List <string>(); // register all files before parsing the assets so that the external references can be found // and find split files foreach (ZipArchiveEntry entry in archive.Entries) { if (entry.Name.Contains(".split")) { string baseName = Path.GetFileNameWithoutExtension(entry.Name); string basePath = Path.Combine(Path.GetDirectoryName(entry.FullName), baseName); if (!splitFiles.Contains(basePath)) { splitFiles.Add(basePath); importFilesHash.Add(baseName); } } else { importFilesHash.Add(entry.Name); } } // merge split files and load the result foreach (string basePath in splitFiles) { try { Stream splitStream = new MemoryStream(); int i = 0; while (true) { string path = $"{basePath}.split{i++}"; ZipArchiveEntry entry = archive.GetEntry(path); if (entry == null) { break; } using (Stream entryStream = entry.Open()) { entryStream.CopyTo(splitStream); } } splitStream.Seek(0, SeekOrigin.Begin); FileReader entryReader = new FileReader(basePath, splitStream); LoadFile(entryReader); } catch (Exception e) { Logger.Error($"Error while reading zip split file {basePath}", e); } } // load all entries foreach (ZipArchiveEntry entry in archive.Entries) { try { string dummyPath = Path.Combine(Path.GetDirectoryName(reader.FullPath), reader.FileName, entry.FullName); // create a new stream // - to store the deflated stream in // - to keep the data for later extraction Stream streamReader = new MemoryStream(); using (Stream entryStream = entry.Open()) { entryStream.CopyTo(streamReader); } streamReader.Position = 0; FileReader entryReader = new FileReader(dummyPath, streamReader); LoadFile(entryReader); if (entryReader.FileType == FileType.ResourceFile) { entryReader.Position = 0; if (!resourceFileReaders.ContainsKey(entry.Name)) { resourceFileReaders.Add(entry.Name, entryReader); } } } catch (Exception e) { Logger.Error($"Error while reading zip entry {entry.FullName}", e); } } } } catch (Exception e) { Logger.Error($"Error while reading zip file {reader.FileName}", e); } finally { reader.Dispose(); } }