diff --git a/Patcher/.idea/.idea.Patcher/.idea/avalonia.xml b/Patcher/.idea/.idea.Patcher/.idea/avalonia.xml
new file mode 100644
index 0000000..49f50b2
--- /dev/null
+++ b/Patcher/.idea/.idea.Patcher/.idea/avalonia.xml
@@ -0,0 +1,11 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Patcher/PatchClient/App.axaml.cs b/Patcher/PatchClient/App.axaml.cs
index 651ae39..4b394b5 100644
--- a/Patcher/PatchClient/App.axaml.cs
+++ b/Patcher/PatchClient/App.axaml.cs
@@ -7,6 +7,7 @@ using ReactiveUI;
using System.Reactive;
using System;
using System.Linq;
+using System.Reflection;
using PatcherUtils.Model;
namespace PatchClient
@@ -46,6 +47,10 @@ namespace PatchClient
PatchLogger.LogInfo("Running with autoclose");
}
+ var version = Assembly.GetExecutingAssembly().GetName().Version;
+
+ PatchLogger.LogInfo($"Patch Client v{version?.ToString() ?? "N/A"}");
+
desktop.MainWindow = new MainWindow
{
DataContext = new MainWindowViewModel(autoClose, debugOutput),
diff --git a/Patcher/PatchClient/PatchClient.csproj b/Patcher/PatchClient/PatchClient.csproj
index b802792..90d23d4 100644
--- a/Patcher/PatchClient/PatchClient.csproj
+++ b/Patcher/PatchClient/PatchClient.csproj
@@ -4,8 +4,8 @@
net6.0
true
enable
- 2.10.0
- 2.10.0
+ 2.10.2
+ 2.10.2
diff --git a/Patcher/PatchGenerator/App.axaml.cs b/Patcher/PatchGenerator/App.axaml.cs
index 0e0c1c6..eda4c00 100644
--- a/Patcher/PatchGenerator/App.axaml.cs
+++ b/Patcher/PatchGenerator/App.axaml.cs
@@ -7,6 +7,7 @@ using PatchGenerator.Views;
using ReactiveUI;
using System.Reactive;
using System;
+using System.Reflection;
using PatcherUtils.Model;
namespace PatchGenerator
@@ -26,6 +27,10 @@ namespace PatchGenerator
public override void OnFrameworkInitializationCompleted()
{
+ var version = Assembly.GetExecutingAssembly().GetName().Version;
+
+ PatchLogger.LogInfo($"Patch Generator v{version?.ToString() ?? "N/A"}");
+
if (ApplicationLifetime is IClassicDesktopStyleApplicationLifetime desktop)
{
desktop.Startup += Desktop_Startup;
diff --git a/Patcher/PatchGenerator/PatchGenerator.csproj b/Patcher/PatchGenerator/PatchGenerator.csproj
index 3a62d2c..ac6becd 100644
--- a/Patcher/PatchGenerator/PatchGenerator.csproj
+++ b/Patcher/PatchGenerator/PatchGenerator.csproj
@@ -4,8 +4,8 @@
net6.0
true
enable
- 2.10.0
- 2.10.0
+ 2.10.2
+ 2.10.2
diff --git a/Patcher/PatchGenerator/Resources/PatchClient.exe b/Patcher/PatchGenerator/Resources/PatchClient.exe
index 758e840..7df4c22 100644
Binary files a/Patcher/PatchGenerator/Resources/PatchClient.exe and b/Patcher/PatchGenerator/Resources/PatchClient.exe differ
diff --git a/Patcher/PatcherUtils/Helpers/XdeltaProcessHelper.cs b/Patcher/PatcherUtils/Helpers/XdeltaProcessHelper.cs
new file mode 100644
index 0000000..836145e
--- /dev/null
+++ b/Patcher/PatcherUtils/Helpers/XdeltaProcessHelper.cs
@@ -0,0 +1,161 @@
+using System;
+using System.Diagnostics;
+using System.IO;
+using System.Text;
+using System.Threading;
+using PatcherUtils.Model;
+
+namespace PatcherUtils.Helpers;
+
+public class XdeltaProcessHelper
+{
+ private readonly int _timeout = (int)TimeSpan.FromMinutes(5).TotalMilliseconds;
+ private string _args;
+ private string _sourcePath;
+ private string _deltaPath;
+ private string _decodedPath;
+ private bool _isDebug;
+
+ public XdeltaProcessHelper(string args, string sourcePath, string deltaPath, string decodedPath, bool isDebug)
+ {
+ _args = args;
+ _sourcePath = sourcePath;
+ _deltaPath = deltaPath;
+ _decodedPath = decodedPath;
+ _isDebug = isDebug;
+ }
+
+ public bool Run() => _isDebug ? RunDebug() : RunNormal();
+
+ private bool RunNormal()
+ {
+ try
+ {
+ using var proc = new Process();
+
+ proc.StartInfo = new ProcessStartInfo
+ {
+ FileName = LazyOperations.XDelta3Path,
+ Arguments = $"{_args} \"{_sourcePath}\" \"{_deltaPath}\" \"{_decodedPath}\"",
+ CreateNoWindow = true
+ };
+
+ proc.Start();
+
+ if (!proc.WaitForExit(_timeout))
+ {
+ PatchLogger.LogError("xdelta3 process timed out");
+ PatchLogger.LogDebug($"xdelta exit code: {proc.ExitCode}");
+ return false;
+ }
+
+ PatchLogger.LogDebug($"xdelta exit code: {proc.ExitCode}");
+ return true;
+ }
+ catch (Exception ex)
+ {
+ PatchLogger.LogException(ex);
+ return false;
+ }
+ }
+
+ private bool DebugPathsCheck()
+ {
+ try
+ {
+ var stream = File.Open(_sourcePath, FileMode.Open, FileAccess.ReadWrite, FileShare.None);
+ stream.Close();
+ stream.Dispose();
+ PatchLogger.LogDebug($"File is openable: {_sourcePath}");
+ }
+ catch (Exception ex)
+ {
+ PatchLogger.LogException(ex);
+ return false;
+ }
+
+ try
+ {
+ var stream = File.Open(_deltaPath, FileMode.Open, FileAccess.ReadWrite, FileShare.None);
+ stream.Close();
+ stream.Dispose();
+ PatchLogger.LogDebug($"File is openable: {_deltaPath}");
+ }
+ catch (Exception ex)
+ {
+ PatchLogger.LogException(ex);
+ return false;
+ }
+
+ return true;
+ }
+
+ private bool RunDebug()
+ {
+ if (!DebugPathsCheck())
+ {
+ return false;
+ }
+
+ using var proc = new Process();
+
+ proc.StartInfo = new ProcessStartInfo
+ {
+ FileName = LazyOperations.XDelta3Path,
+ Arguments = $"{_args} \"{_sourcePath}\" \"{_deltaPath}\" \"{_decodedPath}\"",
+ RedirectStandardOutput = true,
+ RedirectStandardError = true,
+ CreateNoWindow = true
+ };
+
+ var outputBuilder = new StringBuilder();
+ var errorBuilder = new StringBuilder();
+
+ using AutoResetEvent outputWaitHandle = new AutoResetEvent(false);
+ using AutoResetEvent errorWaitHandle = new AutoResetEvent(false);
+
+ proc.OutputDataReceived += (s, e) =>
+ {
+ if (e.Data == null)
+ {
+ outputWaitHandle.Set();
+ }
+ else
+ {
+ outputBuilder.AppendLine(e.Data);
+ }
+ };
+
+ proc.ErrorDataReceived += (s, e) =>
+ {
+ if (e.Data == null)
+ {
+ errorWaitHandle.Set();
+ }
+ else
+ {
+ errorBuilder.AppendLine(e.Data);
+ }
+ };
+
+ proc.Start();
+
+ proc.BeginOutputReadLine();
+ proc.BeginErrorReadLine();
+
+ if (!proc.WaitForExit(_timeout) || !outputWaitHandle.WaitOne(_timeout) || !errorWaitHandle.WaitOne(_timeout))
+ {
+ PatchLogger.LogError("xdelta3 process timed out");
+ PatchLogger.LogDebug($"xdelta exit code: {proc.ExitCode}");
+ return false;
+ }
+
+ PatchLogger.LogDebug("__xdelta stdout__");
+ PatchLogger.LogDebug(outputBuilder.ToString());
+ PatchLogger.LogDebug("__xdelta stderr__");
+ PatchLogger.LogDebug(errorBuilder.ToString());
+ PatchLogger.LogDebug($"xdelta exit code: {proc.ExitCode}");
+
+ return true;
+ }
+}
\ No newline at end of file
diff --git a/Patcher/PatcherUtils/PatchHelper.cs b/Patcher/PatcherUtils/PatchHelper.cs
index 76682ac..6710e21 100644
--- a/Patcher/PatcherUtils/PatchHelper.cs
+++ b/Patcher/PatcherUtils/PatchHelper.cs
@@ -6,6 +6,7 @@ using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Security.Cryptography;
+using PatcherUtils.Helpers;
namespace PatcherUtils
{
@@ -104,71 +105,12 @@ namespace PatcherUtils
var xdeltaArgs = $"-d {(debugOutput ? "-v -v" : "")} -f -s";
- if (debugOutput)
+ var xdeltaHelper =
+ new XdeltaProcessHelper(xdeltaArgs, SourceFilePath, DeltaFilePath, decodedPath, debugOutput);
+
+ if (!xdeltaHelper.Run())
{
- try
- {
- var stream = File.Open(SourceFilePath, FileMode.Open, FileAccess.ReadWrite, FileShare.None);
- stream.Close();
- stream.Dispose();
- PatchLogger.LogDebug($"File is openable: {SourceFilePath}");
- }
- catch (Exception ex)
- {
- PatchLogger.LogException(ex);
- }
-
- try
- {
- var stream = File.Open(SourceFilePath, FileMode.Open, FileAccess.ReadWrite, FileShare.None);
- stream.Close();
- stream.Dispose();
- PatchLogger.LogDebug($"File is openable: {DeltaFilePath}");
- }
- catch (Exception ex)
- {
- PatchLogger.LogException(ex);
- }
- }
-
- var proc = Process.Start(new ProcessStartInfo
- {
- FileName = LazyOperations.XDelta3Path,
- Arguments = $"{xdeltaArgs} \"{SourceFilePath}\" \"{DeltaFilePath}\" \"{decodedPath}\"",
- RedirectStandardError = true,
- RedirectStandardOutput = true,
- CreateNoWindow = true
- });
-
- if (proc == null)
- {
- PatchLogger.LogError($"xdelta3 process failed to start: {nameof(proc)} is null");
- return (false, "xdelta3 process failed to start");
- }
-
- proc.WaitForExit();
-
- if (debugOutput)
- {
- try
- {
- PatchLogger.LogDebug($"xdelta exit code :: {proc.ExitCode}");
- PatchLogger.LogDebug("___Dumping xdelta stdout___");
- while (!proc.StandardOutput.EndOfStream)
- {
- PatchLogger.LogDebug(proc.StandardOutput.ReadLine());
- }
-
- PatchLogger.LogDebug("___Dumping xdelta stderr___");
- while (!proc.StandardError.EndOfStream)
- {
- PatchLogger.LogDebug(proc.StandardError.ReadLine());
- }
- }
- catch (Exception ex)
- {
- PatchLogger.LogException(ex);
- }
+ return (false, "something went wrong during the xdelta3 process");
}
if (File.Exists(decodedPath))