private static Hed.Entry AddFile(string inputFolder, string filename, FileStream hedStream, FileStream pkgStream, bool shouldCompressData = false, bool shouldEncryptData = false) { var completeFilePath = Path.Combine(inputFolder, ORIGINAL_FILES_FOLDER_NAME, filename); var offset = pkgStream.Position; #region Data using var newFileStream = File.OpenRead(completeFilePath); var header = new EgsHdAsset.Header() { // CompressedLenght => -2: no compression and encryption, -1: no compression CompressedLength = !shouldCompressData ? !shouldEncryptData ? -2 : -1 : 0, DecompressedLength = (int)newFileStream.Length, RemasteredAssetCount = 0, CreationDate = -1 }; var decompressedData = newFileStream.ReadAllBytes(); var compressedData = decompressedData.ToArray(); if (shouldCompressData) { compressedData = Helpers.CompressData(decompressedData); header.CompressedLength = compressedData.Length; } // Encrypt and write current file data in the PKG stream // The seed used for encryption is the original data header var seed = new MemoryStream(); BinaryMapping.WriteObject <EgsHdAsset.Header>(seed, header); var encryptionSeed = seed.ReadAllBytes(); var encryptedData = header.CompressedLength > -2 ? EgsEncryption.Encrypt(compressedData, encryptionSeed) : compressedData; // Write original file header BinaryMapping.WriteObject <EgsHdAsset.Header>(pkgStream, header); // Make sure to write the original file after remastered assets headers pkgStream.Write(encryptedData); #endregion // Write a new entry in the HED stream var hedHeader = new Hed.Entry() { MD5 = Helpers.ToBytes(Helpers.CreateMD5(filename)), ActualLength = (int)newFileStream.Length, DataLength = (int)(pkgStream.Position - offset), Offset = offset }; BinaryMapping.WriteObject <Hed.Entry>(hedStream, hedHeader); return(hedHeader); }
private static Hed.Entry ReplaceFile( string inputFolder, string filename, FileStream hedStream, FileStream pkgStream, EgsHdAsset asset, Hed.Entry originalHedHeader = null) { var completeFilePath = Path.Combine(inputFolder, ORIGINAL_FILES_FOLDER_NAME, filename); var offset = pkgStream.Position; var originalHeader = asset.OriginalAssetHeader; // Clone the original asset header var header = new EgsHdAsset.Header() { CompressedLength = originalHeader.CompressedLength, DecompressedLength = originalHeader.DecompressedLength, RemasteredAssetCount = originalHeader.RemasteredAssetCount, CreationDate = originalHeader.CreationDate }; // Use the base original asset data by default var decompressedData = asset.OriginalData; var encryptedData = asset.OriginalRawData; var encryptionSeed = asset.Seed; // We want to replace the original file if (File.Exists(completeFilePath)) { Console.WriteLine($"Replacing original: {filename}!"); using var newFileStream = File.OpenRead(completeFilePath); decompressedData = newFileStream.ReadAllBytes(); var compressedData = decompressedData.ToArray(); var compressedDataLenght = originalHeader.CompressedLength; // CompressedLenght => -2: no compression and encryption, -1: no compression if (originalHeader.CompressedLength > -1) { compressedData = Helpers.CompressData(decompressedData); compressedDataLenght = compressedData.Length; } header.CompressedLength = compressedDataLenght; header.DecompressedLength = decompressedData.Length; // Encrypt and write current file data in the PKG stream // The seed used for encryption is the original data header var seed = new MemoryStream(); BinaryMapping.WriteObject <EgsHdAsset.Header>(seed, header); encryptionSeed = seed.ReadAllBytes(); encryptedData = header.CompressedLength > -2 ? EgsEncryption.Encrypt(compressedData, encryptionSeed) : compressedData; } // Write original file header BinaryMapping.WriteObject <EgsHdAsset.Header>(pkgStream, header); var remasteredHeaders = new List <EgsHdAsset.RemasteredEntry>(); // Is there remastered assets? if (header.RemasteredAssetCount > 0) { remasteredHeaders = ReplaceRemasteredAssets(inputFolder, filename, asset, pkgStream, encryptionSeed, encryptedData); } else { // Make sure to write the original file after remastered assets headers pkgStream.Write(encryptedData); } // Write a new entry in the HED stream var hedHeader = new Hed.Entry() { MD5 = Helpers.ToBytes(Helpers.CreateMD5(filename)), ActualLength = decompressedData.Length, DataLength = (int)(pkgStream.Position - offset), Offset = offset }; // For unknown reason, some files have a data length of 0 if (originalHedHeader.DataLength == 0) { Console.WriteLine($"{filename} => {originalHedHeader.ActualLength} ({originalHedHeader.DataLength})"); hedHeader.ActualLength = originalHedHeader.ActualLength; hedHeader.DataLength = originalHedHeader.DataLength; } BinaryMapping.WriteObject <Hed.Entry>(hedStream, hedHeader); return(hedHeader); }