|
@@ -1,9 +1,14 @@
|
|
|
using System;
|
|
|
using System.Collections.Generic;
|
|
|
+using System.Diagnostics;
|
|
|
using System.IO;
|
|
|
+using System.Linq;
|
|
|
using System.Reflection;
|
|
|
using System.Reflection.Emit;
|
|
|
+using System.Security.Cryptography;
|
|
|
+using System.Text;
|
|
|
using UnityEngine;
|
|
|
+using Debug = UnityEngine.Debug;
|
|
|
|
|
|
namespace COM3D2.CacheEditMenu
|
|
|
{
|
|
@@ -24,7 +29,7 @@ namespace COM3D2.CacheEditMenu
|
|
|
|
|
|
public static class Hooks
|
|
|
{
|
|
|
- private const int CACHE_VERSION = 1011;
|
|
|
+ private const int CACHE_VERSION = 1020;
|
|
|
|
|
|
private static readonly Dictionary<string, MenuInfo> infoCache = new Dictionary<string, MenuInfo>();
|
|
|
private static BinaryWriter cacheWriter;
|
|
@@ -170,53 +175,84 @@ namespace COM3D2.CacheEditMenu
|
|
|
return true;
|
|
|
}
|
|
|
|
|
|
- private static void Init()
|
|
|
+ private static byte[] HashMenus(string[] menuList)
|
|
|
{
|
|
|
- if (cacheWriter != null)
|
|
|
- return;
|
|
|
- var cacheDir = Path.Combine(Patcher.Patcher.SybarisPath, "EditMenuCache");
|
|
|
- var cachePath = Path.Combine(cacheDir, "EditMenuCache.dat");
|
|
|
+ var md5 = MD5.Create();
|
|
|
|
|
|
- var rebuildCache = false;
|
|
|
+ foreach (var s in menuList)
|
|
|
+ {
|
|
|
+ var buf = Encoding.Unicode.GetBytes(s);
|
|
|
+ md5.TransformBlock(buf, 0, buf.Length, null, 0);
|
|
|
+ }
|
|
|
|
|
|
- Directory.CreateDirectory(cacheDir);
|
|
|
+ md5.TransformFinalBlock(new byte[0], 0, 0);
|
|
|
+
|
|
|
+ return md5.Hash;
|
|
|
+ }
|
|
|
|
|
|
- if (File.Exists(cachePath))
|
|
|
- using (var br = new BinaryReader(File.Open(cachePath, FileMode.Open, FileAccess.Read)))
|
|
|
+ private static bool ReadCache(string cachePath)
|
|
|
+ {
|
|
|
+ if (!File.Exists(cachePath))
|
|
|
+ return false;
|
|
|
+ using (var br = new BinaryReader(File.Open(cachePath, FileMode.Open, FileAccess.Read)))
|
|
|
+ {
|
|
|
+ try
|
|
|
{
|
|
|
- try
|
|
|
+ var cacheVer = br.ReadInt32();
|
|
|
+
|
|
|
+ if (cacheVer != CACHE_VERSION)
|
|
|
{
|
|
|
- int cacheVer = br.ReadInt32();
|
|
|
- int menuFilesCount = br.ReadInt32();
|
|
|
- int modMenuFilesCount = br.ReadInt32();
|
|
|
-
|
|
|
- if (cacheVer == CACHE_VERSION &&
|
|
|
- menuFilesCount == GameUty.MenuFiles.Length &&
|
|
|
- modMenuFilesCount == GameUty.ModOnlysMenuFiles.Length)
|
|
|
- {
|
|
|
- while (true)
|
|
|
- {
|
|
|
- var menuInfo = new MenuInfo();
|
|
|
- menuInfo.Deserialize(br);
|
|
|
- infoCache[menuInfo.key] = menuInfo;
|
|
|
- }
|
|
|
- }
|
|
|
- else
|
|
|
- {
|
|
|
- Debug.LogWarning("Outdated cache, rebuilding...");
|
|
|
- rebuildCache = true;
|
|
|
- }
|
|
|
+ Debug.LogWarning("Old cache version, rebuilding...");
|
|
|
+ return false;
|
|
|
}
|
|
|
- catch (FormatException e)
|
|
|
+
|
|
|
+ var menuFilesHashSize = br.ReadInt32();
|
|
|
+ var menuFilesHash = br.ReadBytes(menuFilesHashSize);
|
|
|
+ if (!menuFilesHash.SequenceEqual(HashMenus(GameUty.MenuFiles)))
|
|
|
{
|
|
|
- Debug.Log($"Failed to deserialize cache because {e.Message}. Rebuilding the cache...");
|
|
|
- rebuildCache = true;
|
|
|
+ Debug.LogWarning(".menu files changed, rebuilding cache...");
|
|
|
+ return false;
|
|
|
}
|
|
|
- catch (EndOfStreamException)
|
|
|
+
|
|
|
+ var modMenuFilesHashSize = br.ReadInt32();
|
|
|
+ var modMenuFilesHash = br.ReadBytes(modMenuFilesHashSize);
|
|
|
+ if (!modMenuFilesHash.SequenceEqual(HashMenus(GameUty.ModOnlysMenuFiles)))
|
|
|
{
|
|
|
- // End of file, no need to read more
|
|
|
+ Debug.LogWarning("Mod .menu files changed, rebuilding cache...");
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+
|
|
|
+ while (true)
|
|
|
+ {
|
|
|
+ var menuInfo = new MenuInfo();
|
|
|
+ menuInfo.Deserialize(br);
|
|
|
+ infoCache[menuInfo.key] = menuInfo;
|
|
|
}
|
|
|
}
|
|
|
+ catch (FormatException e)
|
|
|
+ {
|
|
|
+ Debug.Log($"Failed to deserialize cache because {e.Message}. Rebuilding the cache...");
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+ catch (EndOfStreamException)
|
|
|
+ {
|
|
|
+ // End of file, no need to read more
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return true;
|
|
|
+ }
|
|
|
+
|
|
|
+ private static void Init()
|
|
|
+ {
|
|
|
+ if (cacheWriter != null)
|
|
|
+ return;
|
|
|
+ var cacheDir = Path.Combine(Patcher.Patcher.SybarisPath, "EditMenuCache");
|
|
|
+ var cachePath = Path.Combine(cacheDir, "EditMenuCache.dat");
|
|
|
+
|
|
|
+ Directory.CreateDirectory(cacheDir);
|
|
|
+
|
|
|
+ var rebuildCache = !ReadCache(cachePath);
|
|
|
|
|
|
var stream = rebuildCache ? File.Create(cachePath) : File.OpenWrite(cachePath);
|
|
|
cacheWriter = new BinaryWriter(stream);
|
|
@@ -224,8 +260,14 @@ namespace COM3D2.CacheEditMenu
|
|
|
if (rebuildCache)
|
|
|
{
|
|
|
cacheWriter.Write(CACHE_VERSION);
|
|
|
- cacheWriter.Write(GameUty.MenuFiles.Length);
|
|
|
- cacheWriter.Write(GameUty.ModOnlysMenuFiles.Length);
|
|
|
+ var menuHash = HashMenus(GameUty.MenuFiles);
|
|
|
+ var modMenuHash = HashMenus(GameUty.ModOnlysMenuFiles);
|
|
|
+
|
|
|
+ cacheWriter.Write(menuHash.Length);
|
|
|
+ cacheWriter.Write(menuHash);
|
|
|
+
|
|
|
+ cacheWriter.Write(modMenuHash.Length);
|
|
|
+ cacheWriter.Write(modMenuHash);
|
|
|
|
|
|
foreach (var keyValuePair in infoCache)
|
|
|
keyValuePair.Value.Serialize(cacheWriter);
|