This commit is contained in:
Razmoth
2023-08-21 21:45:57 +04:00
parent 6da2387c8c
commit 0bd3fa6db2
48 changed files with 967 additions and 510 deletions

View File

@@ -1,5 +1,7 @@
using System;
using System.Buffers.Binary;
using System.Collections.Generic;
using System.Text;
namespace AssetStudio
{
@@ -8,16 +10,20 @@ namespace AssetStudio
private const int DataOffset = 0x2A;
private const int KeySize = 0x1000;
private const int SeedBlockSize = 0x800;
private const int BufferSize = 0x10000;
public static XORStream Decrypt(FileReader reader, Blk blk)
{
reader.Endian = EndianType.LittleEndian;
var signature = reader.ReadStringToNull();
Logger.Verbose($"Signature: {signature}");
var count = reader.ReadInt32();
Logger.Verbose($"Key size: {count}");
var key = reader.ReadBytes(count);
reader.Position += count;
var seedSize = Math.Min(reader.ReadInt16(), blk.SBox.IsNullOrEmpty() ? SeedBlockSize : SeedBlockSize * 2);
Logger.Verbose($"Seed size: 0x{seedSize:X8}");
if (!blk.SBox.IsNullOrEmpty() && blk.Type.IsGI())
{
@@ -47,6 +53,8 @@ namespace AssetStudio
var keyHigh = BinaryPrimitives.ReadUInt64LittleEndian(key.AsSpan(8, 8));
var seed = keyLow ^ keyHigh ^ keySeed ^ blk.InitSeed;
Logger.Verbose($"Seed: 0x{seed:X8}");
var mt64 = new MT19937_64(seed);
var xorpad = new byte[KeySize];
for (int i = 0; i < KeySize; i += 8)
@@ -56,5 +64,48 @@ namespace AssetStudio
return new XORStream(reader.BaseStream, DataOffset, xorpad);
}
public static IEnumerable<long> GetOffsets(this XORStream stream, string path)
{
if (AssetsHelper.TryGet(path, out var offsets))
{
foreach(var offset in offsets)
{
stream.Offset = offset;
yield return offset;
}
}
else
{
using var reader = new FileReader(path, stream, true);
var signature = reader.FileType switch
{
FileType.BundleFile => "UnityFS\x00",
FileType.Mhy0File => "mhy0",
_ => throw new InvalidOperationException()
};
Logger.Verbose($"Prased signature: {signature}");
var signatureBytes = Encoding.UTF8.GetBytes(signature);
var buffer = BigArrayPool<byte>.Shared.Rent(BufferSize);
while (stream.Remaining > 0)
{
var index = 0;
var absOffset = stream.AbsolutePosition;
var read = stream.Read(buffer);
while (index < read)
{
index = buffer.AsSpan(0, read).Search(signatureBytes, index);
if (index == -1) break;
var offset = absOffset + index;
stream.Offset = offset;
yield return offset;
index++;
}
}
BigArrayPool<byte>.Shared.Return(buffer);
}
}
}
}