From 61c8c58c2967f0e2b7baab63e9387a59de29a988 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Mon, 26 Jun 2023 10:28:42 +0300 Subject: [PATCH 01/12] Update README.md --- README.md | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/README.md b/README.md index 57f7d9cf..88460a58 100644 --- a/README.md +++ b/README.md @@ -50,6 +50,22 @@
+ + Steam Mod Configuration Menu + + + Steam Downloads + + + Steam Views + + + Steam Subscriptions + + + Steam Favorites + +

Extension library for Mount & Blade II: Bannerlord. From 8f60e539bc75d8a447d2e2a656ac7a7e8e43f20f Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Wed, 28 Jun 2023 12:39:56 +0300 Subject: [PATCH 02/12] Some formatting and nullable fixes --- .../MBSubModuleBaseExSubSystem.cs | 2 +- .../ObjectSystem/MBObjectExtensionDataStore.cs | 4 ++-- .../Patches/CampaignBehaviorManagerPatch.cs | 4 ++-- .../SaveSystem/Patches/BehaviourNamePatch.cs | 2 +- .../SaveSystem/Patches/DefinitionContextPatch.cs | 4 ++-- .../SaveSystem/Patches/TypeExtensionsPatch.cs | 2 +- .../CrashUploader/BUTRCrashUploader.cs | 2 ++ .../CrashUploader/CrashUploaderResult.cs | 1 + .../CrashUploader/CrashUploaderStatus.cs | 1 + .../DynamicAPI/DynamicApiProvider.cs | 8 ++++---- .../ExceptionHandler/BEWPatch.cs | 2 +- .../ExceptionHandler/CrashReport.cs | 14 +++++++------- .../DebuggerDetection/ProcessDebug.cs | 2 +- .../WinForms/HtmlCrashReportForm.cs | 13 ++++++++----- .../SaveSystem/DictionaryToArrayConverter.cs | 6 +++--- .../SaveSystem/Extensions/IDataStoreExtensions.cs | 4 ++-- .../SaveSystem/MBGUIDConverter.cs | 2 +- .../SaveSystem/MBObjectBaseConverter.cs | 2 +- .../Settings/SubSystemSettingsProperty.cs | 4 +++- .../Settings/SubSystemSettingsPropertyDropdown.cs | 2 +- 20 files changed, 45 insertions(+), 36 deletions(-) diff --git a/src/Bannerlord.ButterLib.Implementation/MBSubModuleBaseExtended/MBSubModuleBaseExSubSystem.cs b/src/Bannerlord.ButterLib.Implementation/MBSubModuleBaseExtended/MBSubModuleBaseExSubSystem.cs index ecc2bc24..7047c4b6 100644 --- a/src/Bannerlord.ButterLib.Implementation/MBSubModuleBaseExtended/MBSubModuleBaseExSubSystem.cs +++ b/src/Bannerlord.ButterLib.Implementation/MBSubModuleBaseExtended/MBSubModuleBaseExSubSystem.cs @@ -45,7 +45,7 @@ public void Disable() // Think about DelayedSubModuleManager.Unregister } - internal static void LogNoHooksIssue(ILogger logger, int originalCallIndex, int finallyIndex, List codes, MethodBase currentMethod) + internal static void LogNoHooksIssue(ILogger logger, int originalCallIndex, int finallyIndex, List codes, MethodBase? currentMethod) { var issueInfo = new StringBuilder("Indexes: "); issueInfo.Append($"\n\toriginalCallIndex = {originalCallIndex}.\n\tfinallyIndex={finallyIndex}."); diff --git a/src/Bannerlord.ButterLib.Implementation/ObjectSystem/MBObjectExtensionDataStore.cs b/src/Bannerlord.ButterLib.Implementation/ObjectSystem/MBObjectExtensionDataStore.cs index 30b0b11c..7aeafafb 100755 --- a/src/Bannerlord.ButterLib.Implementation/ObjectSystem/MBObjectExtensionDataStore.cs +++ b/src/Bannerlord.ButterLib.Implementation/ObjectSystem/MBObjectExtensionDataStore.cs @@ -107,13 +107,13 @@ private sealed class DataKey : IEquatable internal readonly MBGUID ObjectId; [SaveableField(1)] - internal readonly string Key; + internal readonly string? Key; private DataKey(MBGUID objectId, string key) => (ObjectId, Key) = (objectId, key); internal static DataKey Make(MBObjectBase obj, string key) => new(obj.Id, key); - public bool Equals(DataKey other) => ObjectId == other.ObjectId && !(Key is null || other.Key is null) && Key.Equals(other.Key); + public bool Equals(DataKey? other) => ObjectId == other?.ObjectId && !(Key is null || other.Key is null) && Key.Equals(other.Key); public override bool Equals(object? obj) => obj is DataKey k && Equals(k); diff --git a/src/Bannerlord.ButterLib.Implementation/ObjectSystem/Patches/CampaignBehaviorManagerPatch.cs b/src/Bannerlord.ButterLib.Implementation/ObjectSystem/Patches/CampaignBehaviorManagerPatch.cs index 05077fb0..f38c9cc7 100755 --- a/src/Bannerlord.ButterLib.Implementation/ObjectSystem/Patches/CampaignBehaviorManagerPatch.cs +++ b/src/Bannerlord.ButterLib.Implementation/ObjectSystem/Patches/CampaignBehaviorManagerPatch.cs @@ -78,9 +78,9 @@ internal static void Disable(Harmony harmony) { } private static readonly Type? CampaignBehaviorDataStoreT = typeof(Campaign).Assembly.GetType("TaleWorlds.CampaignSystem.CampaignBehaviorDataStore"); - private static readonly MethodInfo? LoadBehaviorDataMI = AccessTools2.Method(CampaignBehaviorDataStoreT, "LoadBehaviorData"); + private static readonly MethodInfo? LoadBehaviorDataMI = AccessTools2.Method(CampaignBehaviorDataStoreT!, "LoadBehaviorData"); - private static readonly MethodInfo? SaveBehaviorDataMI = AccessTools2.Method(CampaignBehaviorDataStoreT, "SaveBehaviorData"); + private static readonly MethodInfo? SaveBehaviorDataMI = AccessTools2.Method(CampaignBehaviorDataStoreT!, "SaveBehaviorData"); // Patch implementation: diff --git a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/BehaviourNamePatch.cs b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/BehaviourNamePatch.cs index 7fe75ae9..1e0e6b4c 100644 --- a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/BehaviourNamePatch.cs +++ b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/BehaviourNamePatch.cs @@ -29,7 +29,7 @@ internal static bool Disable(Harmony harmony) return true; } - private static void CampaignBehaviorBaseCtorPostfix(CampaignBehaviorBase __instance, ref string ___StringId) + private static void CampaignBehaviorBaseCtorPostfix(CampaignBehaviorBase __instance, ref string? ___StringId) { var module = ModuleInfoHelper.GetModuleByType(__instance.GetType()); if (module is null) // A non-module dll diff --git a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/DefinitionContextPatch.cs b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/DefinitionContextPatch.cs index c386b9c5..1c5c849d 100644 --- a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/DefinitionContextPatch.cs +++ b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/DefinitionContextPatch.cs @@ -144,7 +144,7 @@ private static bool NotNull(T obj, string name, string? errPrefix = null) whe if (obj is null) { var prefix = errPrefix ?? string.Empty; - _log.LogError($"{prefix}{name} is null!"); + _log.LogError("{Prefix}{Name} is null!", prefix, name); return false; } @@ -168,7 +168,7 @@ protected Patch(string patchMethodName, MethodInfo? targetMethod) internal virtual bool IsReady => ThisNotNull(PatchMethod, nameof(PatchMethod)) & ThisNotNull(TargetMethod, nameof(TargetMethod)); - private MethodInfo? ResolvePatchMethod() => AccessTools2.Method(GetType().DeclaringType, PatchMethodName); + private MethodInfo? ResolvePatchMethod() => AccessTools2.Method(GetType().DeclaringType!, PatchMethodName); protected bool ThisNotNull(object? obj, string objName) => NotNull(obj, objName, $"Patch {PatchMethodName}: "); } diff --git a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/TypeExtensionsPatch.cs b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/TypeExtensionsPatch.cs index 3db6fff7..b8705114 100644 --- a/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/TypeExtensionsPatch.cs +++ b/src/Bannerlord.ButterLib.Implementation/SaveSystem/Patches/TypeExtensionsPatch.cs @@ -52,7 +52,7 @@ internal static bool Disable(Harmony harmony) private static readonly Type? TargetType = typeof(MetaData).Assembly.GetType("TaleWorlds.SaveSystem.TypeExtensions"); private static readonly Type[] TargetMethodParams = { typeof(Type), typeof(ContainerType).MakeByRefType() }; - private static readonly MethodInfo? TargetMethod = AccessTools2.Method(TargetType, "IsContainer", TargetMethodParams); + private static readonly MethodInfo? TargetMethod = AccessTools2.Method(TargetType!, "IsContainer", TargetMethodParams); private static readonly MethodInfo? PatchMethod = AccessTools2.Method("Bannerlord.ButterLib.Implementation.SaveSystem.Patches.TypeExtensionsPatch:IsContainerPrefix"); // ReSharper disable once RedundantAssignment diff --git a/src/Bannerlord.ButterLib/CrashUploader/BUTRCrashUploader.cs b/src/Bannerlord.ButterLib/CrashUploader/BUTRCrashUploader.cs index 56ed8619..fa931f72 100644 --- a/src/Bannerlord.ButterLib/CrashUploader/BUTRCrashUploader.cs +++ b/src/Bannerlord.ButterLib/CrashUploader/BUTRCrashUploader.cs @@ -47,6 +47,8 @@ public async Task UploadAsync(CrashReport crashReport) using var responseReader = new StreamReader(stream); var result = await responseReader.ReadLineAsync().ConfigureAwait(false); + if (string.IsNullOrEmpty(result)) + return CrashUploaderResult.ResponseUrlIsNullOrEmpty(); return CrashUploaderResult.Success(result); } catch (Exception e) diff --git a/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderResult.cs b/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderResult.cs index 26260614..1969be5a 100644 --- a/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderResult.cs +++ b/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderResult.cs @@ -7,6 +7,7 @@ internal record CrashUploaderResult public static CrashUploaderResult ResponseIsNotHttpWebResponse() => new(CrashUploaderStatus.ResponseIsNotHttpWebResponse); public static CrashUploaderResult WrongStatusCode(string statusCode) => new(CrashUploaderStatus.WrongStatusCode) { StatusCode = statusCode }; public static CrashUploaderResult ResponseStreamIsNull() => new(CrashUploaderStatus.ResponseStreamIsNull); + public static CrashUploaderResult ResponseUrlIsNullOrEmpty() => new(CrashUploaderStatus.UrlIsNullOrEmpty); public static CrashUploaderResult FailedWithException(string exception) => new(CrashUploaderStatus.FailedWithException) { Exception = exception }; public CrashUploaderStatus Status { get; } diff --git a/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderStatus.cs b/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderStatus.cs index 044ed7cb..554687ee 100644 --- a/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderStatus.cs +++ b/src/Bannerlord.ButterLib/CrashUploader/CrashUploaderStatus.cs @@ -8,5 +8,6 @@ internal enum CrashUploaderStatus WrongStatusCode, ResponseStreamIsNull, FailedWithException, + UrlIsNullOrEmpty, } } \ No newline at end of file diff --git a/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs b/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs index a1200375..4871323b 100644 --- a/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs +++ b/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs @@ -42,7 +42,7 @@ private record MethodInfoWithAttribute(MethodInfo MethodInfo, CustomAttributeDat private static TypeWithAttribute? GetDynamicAPIClass(Type? type) { bool Predicate(CustomAttributeData x) => - PossibleClassNames.Contains(x.AttributeType.FullName) && x.ConstructorArguments.Count == 1 && x.ConstructorArguments[0].ArgumentType == typeof(string); + PossibleClassNames.Contains(x.AttributeType.FullName!) && x.ConstructorArguments.Count == 1 && x.ConstructorArguments[0].ArgumentType == typeof(string); if (type is null) return null; @@ -59,7 +59,7 @@ bool Predicate(CustomAttributeData x) => private static MethodInfoWithAttribute? GetDynamicAPIMethod(MethodInfo? methodInfo) { bool Predicate(CustomAttributeData x) => - PossibleMethodNames.Contains(x.AttributeType.FullName) && x.ConstructorArguments.Count == 1 && x.ConstructorArguments[0].ArgumentType == typeof(string); + PossibleMethodNames.Contains(x.AttributeType.FullName!) && x.ConstructorArguments.Count == 1 && x.ConstructorArguments[0].ArgumentType == typeof(string); if (methodInfo is null) return null; @@ -71,11 +71,11 @@ bool Predicate(CustomAttributeData x) => } private static string DynamicAPIClassAttributeName(TypeWithAttribute typeWithAttribute) => - (string) typeWithAttribute.CustomAttributeData.ConstructorArguments[0].Value; + (string) typeWithAttribute.CustomAttributeData.ConstructorArguments[0].Value!; private static string DynamicAPIMethodAttributeName(MethodInfoWithAttribute methodInfoWithAttribute) { - var name = (string) methodInfoWithAttribute.CustomAttributeData.ConstructorArguments[0].Value; + var name = (string) methodInfoWithAttribute.CustomAttributeData.ConstructorArguments[0].Value!; return $"{(methodInfoWithAttribute.MethodInfo.IsStatic ? "0static" : "0instance")}_{name}"; } diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs b/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs index 8fb59738..416d56d5 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs @@ -44,7 +44,7 @@ public static bool IsDebuggerAttached() return false; } - internal record ExceptionIdentifier(Type Type, string StackTrace, string Message) + internal record ExceptionIdentifier(Type Type, string? StackTrace, string Message) { public static ExceptionIdentifier FromException(Exception e) => new(e.GetType(), e.StackTrace, e.Message); } diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs index 9e0d8f00..6b80a5b4 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs @@ -35,11 +35,11 @@ public CrashReport(Exception exception) foreach (var subModule in LoadedModules.SelectMany(module => module.SubModules)) { moduleAssemblies.Add(Path.GetFileNameWithoutExtension(subModule.DLLName)); - moduleAssemblies.AddRange(subModule.Assemblies.Select(Path.GetFileNameWithoutExtension)); + moduleAssemblies.AddRange(subModule.Assemblies.Select(Path.GetFileNameWithoutExtension).OfType()); } - ModuleLoadedAssemblies.AddRange(AccessTools2.AllAssemblies().Where(a => moduleAssemblies.Contains(a.GetName().Name))); - ExternalLoadedAssemblies.AddRange(AccessTools2.AllAssemblies().Where(a => !moduleAssemblies.Contains(a.GetName().Name))); + ModuleLoadedAssemblies.AddRange(AccessTools2.AllAssemblies().Where(a => moduleAssemblies.Contains(a.GetName().Name!))); + ExternalLoadedAssemblies.AddRange(AccessTools2.AllAssemblies().Where(a => !moduleAssemblies.Contains(a.GetName().Name!))); foreach (var originalMethod in Harmony.GetAllPatchedMethods()) { @@ -101,7 +101,7 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) { if (!frame.HasMethod()) continue; - MethodBase? method; + MethodBase method; var methodFromStackframeIssue = false; try { @@ -110,15 +110,15 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) // NullReferenceException means the method was not found. Harmony doesn't handle this case gracefully catch (NullReferenceException) { - method = frame.GetMethod(); + method = frame.GetMethod()!; } // The given generic instantiation was invalid. // From what I understand, this will occur with generic methods // Also when static constructors throw errors, Harmony resolution will fail - catch (Exception e) + catch (Exception) { methodFromStackframeIssue = true; - method = frame.GetMethod(); + method = frame.GetMethod()!; } var frameDesc = $"{frame} (IL Offset: {frame.GetILOffset()})"; diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/DebuggerDetection/ProcessDebug.cs b/src/Bannerlord.ButterLib/ExceptionHandler/DebuggerDetection/ProcessDebug.cs index 9dc3de96..4c262c8f 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/DebuggerDetection/ProcessDebug.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/DebuggerDetection/ProcessDebug.cs @@ -6,7 +6,7 @@ namespace Bannerlord.ButterLib.ExceptionHandler.DebuggerDetection { internal static class ProcessDebug { - private const int PROCESS_DEBUG_OBJECT_HANDLE = 0x1E; + private const int PROCESS_DEBUG_OBJECT_HANDLE = 30; private const int PROCESS_DEBUG_PORT = 7; [DllImport("ntdll.dll", SetLastError = true)] diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/WinForms/HtmlCrashReportForm.cs b/src/Bannerlord.ButterLib/ExceptionHandler/WinForms/HtmlCrashReportForm.cs index a6458664..8ea51eff 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/WinForms/HtmlCrashReportForm.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/WinForms/HtmlCrashReportForm.cs @@ -134,7 +134,7 @@ function handleIncludeScreenshot(cb) { } "; - private static string TableText = @$" + private static string TableText = $""" @@ -143,9 +143,9 @@ function handleIncludeScreenshot(cb) { @@ -157,15 +157,18 @@ function handleIncludeScreenshot(cb) { + {(ApplicationPlatform.CurrentPlatform == Platform.GDKDesktop ? "" : """ + """)}
- {(CrashUploaderSubSystem.Instance?.IsEnabled == true - ? "" - : "")} + {(CrashUploaderSubSystem.Instance?.IsEnabled != true ? "" : """ + + """)}
Clicking 'Close Report' will continue with the Game's error report mechanism. -
"; +
+"""; private CrashReport CrashReport { get; } private string ReportInHtml { get; } diff --git a/src/Bannerlord.ButterLib/SaveSystem/DictionaryToArrayConverter.cs b/src/Bannerlord.ButterLib/SaveSystem/DictionaryToArrayConverter.cs index d07fe319..48d0ca08 100644 --- a/src/Bannerlord.ButterLib/SaveSystem/DictionaryToArrayConverter.cs +++ b/src/Bannerlord.ButterLib/SaveSystem/DictionaryToArrayConverter.cs @@ -13,7 +13,7 @@ public sealed class DictionaryToArrayConverter : JsonConverter private static bool TypeImplementsGenericInterface(Type concreteType, Type interfaceType) => concreteType.GetInterfaces().Any(i => i.IsGenericType && i.GetGenericTypeDefinition() == interfaceType); - public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) + public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer) { if (value is IDictionary dictionary) { @@ -33,12 +33,12 @@ public override void WriteJson(JsonWriter writer, object value, JsonSerializer s } } - public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + public override object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer) { if (existingValue is not IDictionary dict) { var contract = serializer.ContractResolver.ResolveContract(objectType); - dict = (IDictionary) contract.DefaultCreator(); + dict = (IDictionary) contract.DefaultCreator!(); } if (reader.TokenType == JsonToken.StartArray) diff --git a/src/Bannerlord.ButterLib/SaveSystem/Extensions/IDataStoreExtensions.cs b/src/Bannerlord.ButterLib/SaveSystem/Extensions/IDataStoreExtensions.cs index 3b420711..224bd6a6 100644 --- a/src/Bannerlord.ButterLib/SaveSystem/Extensions/IDataStoreExtensions.cs +++ b/src/Bannerlord.ButterLib/SaveSystem/Extensions/IDataStoreExtensions.cs @@ -28,7 +28,7 @@ private static string ChunksToString(IReadOnlyList chunks) return strBuilder.ToString(); } - public static bool SyncDataAsJson(this IDataStore dataStore, string key, ref T data, JsonSerializerSettings? settings = null) + public static bool SyncDataAsJson(this IDataStore dataStore, string key, ref T? data, JsonSerializerSettings? settings = null) { // If the type we're synchronizing is a string or string array, then it's ambiguous // with our own internal storage types, which imply that the strings contain valid @@ -63,7 +63,7 @@ public static bool SyncDataAsJson(this IDataStore dataStore, string key, ref var jsonDataChunks = Array.Empty(); if (dataStore.SyncData(key, ref jsonDataChunks)) { - var (format, jsonData) = JsonConvert.DeserializeObject(ChunksToString(jsonDataChunks ?? Array.Empty()), settings); + var (format, jsonData) = JsonConvert.DeserializeObject(ChunksToString(jsonDataChunks ?? Array.Empty()), settings) ?? new(-1, string.Empty); data = format switch { 2 => JsonConvert.DeserializeObject(jsonData, settings), diff --git a/src/Bannerlord.ButterLib/SaveSystem/MBGUIDConverter.cs b/src/Bannerlord.ButterLib/SaveSystem/MBGUIDConverter.cs index 314d4ad1..770e2955 100644 --- a/src/Bannerlord.ButterLib/SaveSystem/MBGUIDConverter.cs +++ b/src/Bannerlord.ButterLib/SaveSystem/MBGUIDConverter.cs @@ -21,7 +21,7 @@ public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer.Serialize(writer, null); } - public override object? ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + public override object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer) { if (serializer.Deserialize(reader) is { } id) { diff --git a/src/Bannerlord.ButterLib/SaveSystem/MBObjectBaseConverter.cs b/src/Bannerlord.ButterLib/SaveSystem/MBObjectBaseConverter.cs index 759ef592..21e40f44 100644 --- a/src/Bannerlord.ButterLib/SaveSystem/MBObjectBaseConverter.cs +++ b/src/Bannerlord.ButterLib/SaveSystem/MBObjectBaseConverter.cs @@ -29,7 +29,7 @@ public override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer.Serialize(writer, null); } - public override object? ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + public override object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer) { if (serializer.Deserialize(reader) is { } mbguid) { diff --git a/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsProperty.cs b/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsProperty.cs index af5f378f..9721384b 100644 --- a/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsProperty.cs +++ b/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsProperty.cs @@ -3,11 +3,13 @@ namespace Bannerlord.ButterLib.SubSystems.Settings { - /// /// /// A property based declaration. /// + /// The name of the settings entry. + /// The description of the settings entry. /// And expression that references the property. + /// The that exposes the settings. /// Type of the property. public abstract record SubSystemSettingsProperty(string Name, string Description, Expression> Property) : SubSystemSettingsDeclaration(Name, Description) where TSubSystem : ISubSystem; diff --git a/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsPropertyDropdown.cs b/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsPropertyDropdown.cs index 7df38979..c7ae1f1f 100644 --- a/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsPropertyDropdown.cs +++ b/src/Bannerlord.ButterLib/SubSystems/Settings/SubSystemSettingsPropertyDropdown.cs @@ -6,7 +6,7 @@ namespace Bannerlord.ButterLib.SubSystems.Settings { /// /// - /// A switch based on a property. + /// IList<> /// public record SubSystemSettingsPropertyDropdown(string Name, string Description, Expression>> Property, int SelectedIndex) : SubSystemSettingsProperty>(Name, Description, Property) where TSubSystem : ISubSystem; From 08c8d5b05d7181b3a2863bbca31bc32d8bc8d01b Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Wed, 28 Jun 2023 16:36:00 +0300 Subject: [PATCH 03/12] Added CIL code for methods Added AsmResolver dependency --- build/common.props | 9 ++-- changelog.txt | 5 ++ ...Bannerlord.ButterLib.Implementation.csproj | 4 +- .../Properties/launchSettings.json | 12 ++--- .../_Module/SubModule.xml | 3 ++ .../Bannerlord.ButterLib.csproj | 9 +++- .../DynamicAPI/DynamicApiProvider.cs | 2 +- .../ExceptionHandler/CrashReport.cs | 39 ++++++++++---- .../ExceptionHandler/HtmlBuilder.cs | 52 ++++++------------- 9 files changed, 77 insertions(+), 58 deletions(-) diff --git a/build/common.props b/build/common.props index 1fcbb887..8416f527 100644 --- a/build/common.props +++ b/build/common.props @@ -4,13 +4,14 @@ - 2.8.1 + 2.9.0 - 2.2.2 + 2.3.0 3.2.0.77 1.0.1.44 - + + 2.0.0 1.1.0.102 @@ -20,12 +21,12 @@ BUTR Team - ButterLib Library for Bannerlord + diff --git a/changelog.txt b/changelog.txt index b8b78aa7..98c1e114 100644 --- a/changelog.txt +++ b/changelog.txt @@ -1,4 +1,9 @@ --------------------------------------------------------------------------------------------------- +Version: 2.9.0 +Game Versions: v1.0.0,v1.0.1,v1.0.2,v1.0.3,v1.1.0,v1.1.1,v1.1.2,v1.1.3,v1.1.4,v1.1.5,v1.2.0 +* Show the whole CIL code of the patched method in enhanced stacktrace +* Requires Lib.Harmony 2.3.0 and higher +--------------------------------------------------------------------------------------------------- Version: 2.8.1 Game Versions: v1.0.0,v1.0.1,v1.0.2,v1.0.3,v1.1.0,v1.1.1,v1.1.2,v1.1.3,v1.1.4,v1.1.5,v1.2.0 * Added support for v1.2.0 diff --git a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj index 6df46153..105ddd33 100644 --- a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj +++ b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj @@ -35,7 +35,9 @@ - + + + diff --git a/src/Bannerlord.ButterLib.Implementation/Properties/launchSettings.json b/src/Bannerlord.ButterLib.Implementation/Properties/launchSettings.json index 9af5d7cf..65805984 100644 --- a/src/Bannerlord.ButterLib.Implementation/Properties/launchSettings.json +++ b/src/Bannerlord.ButterLib.Implementation/Properties/launchSettings.json @@ -18,21 +18,21 @@ "commandLineArgs": "/singleplayer _MODULES_*Bannerlord.Harmony*Bannerlord.ButterLib*Native*SandBoxCore*Sandbox*StoryMode*CustomBattle*Bannerlord.ButterLib.HotKeys.Test*_MODULES_", "workingDirectory": "$(GameFolder)\\bin\\Win64_Shipping_Client" }, - "MBSE Bannerlord": { + "BLSE Bannerlord": { "commandName": "Executable", - "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.MBSE.exe", + "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.BLSE.Standalone.exe", "commandLineArgs": "/singleplayer _MODULES_*Bannerlord.Harmony*Bannerlord.ButterLib*Native*SandBoxCore*Sandbox*StoryMode*CustomBattle*_MODULES_", "workingDirectory": "$(GameFolder)\\bin\\Win64_Shipping_Client" }, - "MBSE BannerlordWithMCM": { + "BLSE BannerlordWithMCM": { "commandName": "Executable", - "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.MBSE.exe", + "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.BLSE.Standalone.exe", "commandLineArgs": "/singleplayer _MODULES_*Bannerlord.Harmony*Bannerlord.ButterLib*Bannerlord.UIExtenderEx*Bannerlord.MBOptionScreen*Native*SandBoxCore*Sandbox*StoryMode*CustomBattle*_MODULES_", "workingDirectory": "$(GameFolder)\\bin\\Win64_Shipping_Client" }, - "MBSE BannerlordWithTests": { + "BLSE BannerlordWithTests": { "commandName": "Executable", - "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.MBSE.exe", + "executablePath": "$(GameFolder)\\bin\\Win64_Shipping_Client\\Bannerlord.BLSE.Standalone.exe", "commandLineArgs": "/singleplayer _MODULES_*Bannerlord.Harmony*Bannerlord.ButterLib*Native*SandBoxCore*Sandbox*StoryMode*CustomBattle*Bannerlord.ButterLib.HotKeys.Test*_MODULES_", "workingDirectory": "$(GameFolder)\\bin\\Win64_Shipping_Client" } diff --git a/src/Bannerlord.ButterLib.Implementation/_Module/SubModule.xml b/src/Bannerlord.ButterLib.Implementation/_Module/SubModule.xml index 04b0d361..b2dc20bb 100644 --- a/src/Bannerlord.ButterLib.Implementation/_Module/SubModule.xml +++ b/src/Bannerlord.ButterLib.Implementation/_Module/SubModule.xml @@ -9,6 +9,9 @@ + diff --git a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj index bbec774f..37cce132 100644 --- a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj +++ b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj @@ -33,10 +33,12 @@ + - + + @@ -46,6 +48,11 @@ + diff --git a/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs b/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs index 4871323b..03b2682b 100644 --- a/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs +++ b/src/Bannerlord.ButterLib/DynamicAPI/DynamicApiProvider.cs @@ -81,7 +81,7 @@ private static string DynamicAPIMethodAttributeName(MethodInfoWithAttribute meth private static IEnumerable GetAssembliesToScan() { - var loadedModules = ModuleInfoHelper.GetLoadedModules().OfType().ToList(); + var loadedModules = ModuleInfoHelper.GetLoadedModules().Where(x => x is not null).ToList(); foreach (var assembly in AccessTools2.AllAssemblies().Where(x => !x.IsDynamic && !string.IsNullOrEmpty(x.Location))) { if (loadedModules.Any(loadedModule => ModuleInfoHelper.IsModuleAssembly(loadedModule, assembly))) diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs index 6b80a5b4..13841e5e 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs @@ -1,9 +1,13 @@ -using Bannerlord.BUTR.Shared.Helpers; +using AsmResolver.DotNet.Code.Cil; + +using Bannerlord.BUTR.Shared.Helpers; using Bannerlord.ModuleManager; using HarmonyLib; using HarmonyLib.BUTR.Extensions; +using MonoMod.Core.Platforms; + using System; using System.Collections.Generic; using System.Diagnostics; @@ -13,7 +17,7 @@ namespace Bannerlord.ButterLib.ExceptionHandler { - internal record StacktraceEntry(MethodBase Method, bool MethodFromStackframeIssue, ModuleInfoExtended? ModuleInfo, string StackFrameDescription); + internal record StacktraceEntry(MethodBase Method, bool MethodFromStackframeIssue, ModuleInfoExtended? ModuleInfo, string StackFrameDescription, CilInstructionCollection? CilInstructions); internal class CrashReport { @@ -35,7 +39,7 @@ public CrashReport(Exception exception) foreach (var subModule in LoadedModules.SelectMany(module => module.SubModules)) { moduleAssemblies.Add(Path.GetFileNameWithoutExtension(subModule.DLLName)); - moduleAssemblies.AddRange(subModule.Assemblies.Select(Path.GetFileNameWithoutExtension).OfType()); + moduleAssemblies.AddRange(subModule.Assemblies.Select(Path.GetFileNameWithoutExtension).Where(x => x is not null)); } ModuleLoadedAssemblies.AddRange(AccessTools2.AllAssemblies().Where(a => moduleAssemblies.Contains(a.GetName().Name!))); @@ -126,27 +130,42 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) var patches = FindPatches(method); foreach (var (methodBase, extendedModuleInfo) in GetFinalizers(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); } foreach (var (methodBase, extendedModuleInfo) in GetPostfixes(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); } foreach (var (methodBase, extendedModuleInfo) in GetPrefixes(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); } foreach (var (methodBase, extendedModuleInfo) in GetTranspilers(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); } var moduleInfo = GetModuleInfoIfMod(method); - yield return new(method, methodFromStackframeIssue, moduleInfo, frameDesc); + yield return new(method, methodFromStackframeIssue, moduleInfo, frameDesc, null); - if (method is MethodInfo methodInfo && Harmony.GetOriginalMethod(methodInfo) is { } original) - yield return new(original, methodFromStackframeIssue, moduleInfo, frameDesc); + // Further versions of Harmony will do `PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod` themselves + if (method is MethodInfo && PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod && Harmony.GetOriginalMethod(identifiableMethod) is { } original) + { + CilInstructionCollection? instructions; + try + { + var module = AsmResolver.DotNet.ModuleDefinition.FromModule(identifiableMethod.Module); + var dynamicMethodDefinition = new AsmResolver.DotNet.Dynamic.DynamicMethodDefinition(module, identifiableMethod); + var cilMethodBody = dynamicMethodDefinition.MethodBody as CilMethodBody; + instructions = cilMethodBody?.Instructions; + } + catch (Exception) + { + instructions = null; + } + yield return new(original, methodFromStackframeIssue, moduleInfo, frameDesc, instructions); + } } } } diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs b/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs index 1a511e19..13b3bb7a 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs @@ -1,6 +1,7 @@ using Bannerlord.BUTR.Shared.Extensions; using Bannerlord.BUTR.Shared.Helpers; using Bannerlord.ButterLib.Common.Extensions; +using Bannerlord.ButterLib.Helpers; using Bannerlord.ButterLib.Logger; using Bannerlord.ModuleManager; @@ -26,7 +27,7 @@ namespace Bannerlord.ButterLib.ExceptionHandler { internal static class HtmlBuilder { - private static readonly int Version = 10; + private static readonly int Version = 11; private static readonly string NL = Environment.NewLine; public static readonly string MiniDumpTag = ""; @@ -315,10 +316,10 @@ function screenshot(element) {{ "; } - private static string GetBUTRLoaderVersion() + private static string? GetBUTRLoaderVersion() { if (AccessTools2.AllAssemblies().FirstOrDefault(x => x.GetName().Name == "Bannerlord.BUTRLoader") is { } bAssembly) - return bAssembly.GetName().Version.ToString(); + return bAssembly.GetName().Version?.ToString(); return string.Empty; } @@ -382,13 +383,14 @@ private static string GetLauncherVersion() private static string GetEnhancedStacktraceHtml(CrashReport crashReport) { var sb = new StringBuilder(); + var sbCil = new StringBuilder(); sb.AppendLine("
    "); foreach (var stacktrace in crashReport.Stacktrace.GroupBy(x => x.StackFrameDescription)) { sb.Append("
  • ") .Append($"Frame: {stacktrace.Key}
    ") .Append("
      "); - foreach (var (method, methodFromStackframeIssue, module, _) in stacktrace) + foreach (var (method, methodFromStackframeIssue, module, _, _) in stacktrace) { sb.Append("
    • ") .Append($"Module: {(module is null ? "UNKNOWN" : module.Id)}
      ") @@ -396,7 +398,15 @@ private static string GetEnhancedStacktraceHtml(CrashReport crashReport) .Append($"Method From Stackframe Issue: {methodFromStackframeIssue}
      ") .Append("
    • "); } - sb.AppendLine("
  • "); + if (stacktrace.FirstOrDefault(x => x.CilInstructions is not null) is { CilInstructions: { } cilInstructions }) + { + foreach (var instruction in cilInstructions) + sbCil.Append('\t').Append(instruction).AppendLine(); + } + sb.Append("
"); + sb.Append($"CIL:
{sbCil}

"); + sb.AppendLine(""); + sbCil.Clear(); } sb.AppendLine(""); return sb.ToString(); @@ -404,41 +414,13 @@ private static string GetEnhancedStacktraceHtml(CrashReport crashReport) private static string GetInvolvedModuleListHtml(CrashReport crashReport) { - static bool Filter(StacktraceEntry stacktraceEntry) - { - if (stacktraceEntry.ModuleInfo?.Id == "Bannerlord.ButterLib") - { - if (stacktraceEntry.Method == BEWPatch.FinalizerMethod) - { - return false; - } - } - if (stacktraceEntry.ModuleInfo?.Id is "BetterExceptionWindow") - { - if (stacktraceEntry.Method is { Name: "Finalizer", DeclaringType: { Namespace: "AutoGeneratedExceptionFilter" } }) - { - return false; - } - } - - if (stacktraceEntry.ModuleInfo?.Id == "Bannerlord.MBOptionScreen") - { - if (stacktraceEntry.Method.Name == "ExecuteCommandPatch") - { - return false; - } - } - - return true; - } - // Do not show Bannerlord.Harmony if it's the only one involved module. if (crashReport.Stacktrace.Count == 1 && crashReport.Stacktrace[0].ModuleInfo?.Id == "Bannerlord.Harmony") return "
    "; var sb = new StringBuilder(); sb.AppendLine("
      "); - foreach (var stacktrace in crashReport.Stacktrace.Where(Filter).GroupBy(m => m.ModuleInfo)) + foreach (var stacktrace in crashReport.Stacktrace.Where(CrashReportFilter.Filter).GroupBy(m => m.ModuleInfo)) { var module = stacktrace.Key; if (module is null) continue; @@ -446,7 +428,7 @@ static bool Filter(StacktraceEntry stacktraceEntry) sb.Append("
    • ") .Append($"").Append(module.Id).Append("
      ") .Append("
        "); - foreach (var (method, harmonyIssue, _, stackFrameDescription) in stacktrace) + foreach (var (method, harmonyIssue, _, stackFrameDescription, _) in stacktrace) { // Ignore blank transpilers used to force the jitter to skip inlining if (method.Name == "BlankTranspiler") continue; From c053669c7de1cc48a055468a5fbd7731aad49dc0 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Wed, 28 Jun 2023 17:35:56 +0300 Subject: [PATCH 04/12] Test fix --- .../Bannerlord.ButterLib.Implementation.Tests.csproj | 2 +- .../Bannerlord.ButterLib.Tests.csproj | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/Bannerlord.ButterLib.Implementation.Tests/Bannerlord.ButterLib.Implementation.Tests.csproj b/tests/Bannerlord.ButterLib.Implementation.Tests/Bannerlord.ButterLib.Implementation.Tests.csproj index f6cf68fb..87aa4320 100644 --- a/tests/Bannerlord.ButterLib.Implementation.Tests/Bannerlord.ButterLib.Implementation.Tests.csproj +++ b/tests/Bannerlord.ButterLib.Implementation.Tests/Bannerlord.ButterLib.Implementation.Tests.csproj @@ -19,7 +19,7 @@ - + diff --git a/tests/Bannerlord.ButterLib.Tests/Bannerlord.ButterLib.Tests.csproj b/tests/Bannerlord.ButterLib.Tests/Bannerlord.ButterLib.Tests.csproj index 5af69de1..5dd606b9 100644 --- a/tests/Bannerlord.ButterLib.Tests/Bannerlord.ButterLib.Tests.csproj +++ b/tests/Bannerlord.ButterLib.Tests/Bannerlord.ButterLib.Tests.csproj @@ -19,7 +19,7 @@ - + From 65a52ae6bb016e527b670bc850e8ce75ad33f4d4 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Thu, 29 Jun 2023 09:15:16 +0300 Subject: [PATCH 05/12] X64 was not being using even when the platform is set --- .../Bannerlord.ButterLib.Implementation.csproj | 4 ++-- src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj index 105ddd33..e16dc7b9 100644 --- a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj +++ b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj @@ -5,12 +5,12 @@ net472;netcoreapp3.1 10.0 enable - x64 + x64 false false Stable_Debug;Stable_Release;Beta_Debug;Beta_Release - $(DefineConstants);$(GameVersionConstant) + $(DefineConstants);$(GameVersionConstant);X64 $(MSBuildProjectName).$(GameVersion) diff --git a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj index 37cce132..77f42869 100644 --- a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj +++ b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj @@ -5,12 +5,12 @@ net472;netcoreapp3.1;netstandard2.0 11.0 enable - x64 + x64 true true $(BANNERLORD_BUTR_UPLOAD_URL) - $(DefineConstants);BANNERLORDBUTRSHARED_BUTTERLIB + $(DefineConstants);BANNERLORDBUTRSHARED_BUTTERLIB;X64 1.0.0 From 2106582e576dccbe2bc291b3036b9ac2d0f9dc95 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sat, 1 Jul 2023 17:08:54 +0300 Subject: [PATCH 06/12] Update publish.yml --- .github/workflows/publish.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 34d7aab1..5886a541 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -121,8 +121,8 @@ jobs: mod_description: ${{ needs.build-module.outputs.mod_description }} artifact_name: bannerlord secrets: - NEXUSMODS_APIKEY: ${{ secrets.NEXUSMODS_APIKEY }} - NEXUSMODS_COOKIES: ${{ secrets.NEXUSMODS_COOKIES }} + NEXUSMODS_APIKEY: ${{ secrets.ARAGAS_NEXUSMOD_API_KEY }} + NEXUSMODS_COOKIES: ${{ secrets.ARAGAS_NEXUSMOD_COOKIES }} ########################### # STEAM # From 24f5c878fdb3fdbf73e5848e19d30bfb1dcc31a3 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 00:16:14 +0300 Subject: [PATCH 07/12] Update publish.yml --- .github/workflows/publish.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 5886a541..b2e48dce 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -121,8 +121,8 @@ jobs: mod_description: ${{ needs.build-module.outputs.mod_description }} artifact_name: bannerlord secrets: - NEXUSMODS_APIKEY: ${{ secrets.ARAGAS_NEXUSMOD_API_KEY }} - NEXUSMODS_COOKIES: ${{ secrets.ARAGAS_NEXUSMOD_COOKIES }} + NEXUSMODS_APIKEY: ${{ secrets.ARAGAS_NEXUSMODS_API_KEY }} + NEXUSMODS_COOKIES: ${{ secrets.ARAGAS_NEXUSMODS_COOKIE_SID_DEVELOP }} ########################### # STEAM # From c38cc41283220dd27b31751d82ae80f792b8a47b Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 19:06:59 +0300 Subject: [PATCH 08/12] Suppress the new TW debugger so ButterLib's Crash Reporter can work --- build/common.props | 8 +- changelog.txt | 5 +- .../ModuleData/Languages/EN/sta_strings.xml | 6 + src/Bannerlord.ButterLib.sln | 146 ++++++++++++++++-- .../Bannerlord.ButterLib.csproj | 4 +- .../ButterLibSubModule.cs | 2 + .../ExceptionHandler/BEWPatch.cs | 4 +- .../ExceptionHandler/CrashReport.cs | 20 ++- .../ExceptionHandlerSubSystem.cs | 40 ++++- .../ExceptionHandler/HtmlBuilder.cs | 2 +- .../ExceptionHandler/WatchdogHandler.cs | 68 ++++++++ ...e.cs => BLSELoaderInterceptorAttribute.cs} | 4 +- .../Helpers/CrashReportFilter.cs | 35 +++++ 13 files changed, 305 insertions(+), 39 deletions(-) create mode 100644 src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs rename src/Bannerlord.ButterLib/Helpers/{BUTRLoaderInterceptorAttribute.cs => BLSELoaderInterceptorAttribute.cs} (54%) create mode 100644 src/Bannerlord.ButterLib/Helpers/CrashReportFilter.cs diff --git a/build/common.props b/build/common.props index 8416f527..c50f8056 100644 --- a/build/common.props +++ b/build/common.props @@ -4,11 +4,11 @@ - 2.9.0 + 2.8.2 - 2.3.0 + 2.2.2 3.2.0.77 - 1.0.1.44 + 1.0.1.50 @@ -144,5 +144,5 @@ runtime; build; native; contentfiles; analyzers; buildtransitive - + diff --git a/changelog.txt b/changelog.txt index 98c1e114..bc01c2e1 100644 --- a/changelog.txt +++ b/changelog.txt @@ -1,8 +1,7 @@ --------------------------------------------------------------------------------------------------- -Version: 2.9.0 +Version: 2.8.2 Game Versions: v1.0.0,v1.0.1,v1.0.2,v1.0.3,v1.1.0,v1.1.1,v1.1.2,v1.1.3,v1.1.4,v1.1.5,v1.2.0 -* Show the whole CIL code of the patched method in enhanced stacktrace -* Requires Lib.Harmony 2.3.0 and higher +* v1.2.0 - Suppress the new TW debugger so ButterLib's Crash Reporter can work --------------------------------------------------------------------------------------------------- Version: 2.8.1 Game Versions: v1.0.0,v1.0.1,v1.0.2,v1.0.3,v1.1.0,v1.1.1,v1.1.2,v1.1.3,v1.1.4,v1.1.5,v1.2.0 diff --git a/src/Bannerlord.ButterLib.Implementation/_Module/ModuleData/Languages/EN/sta_strings.xml b/src/Bannerlord.ButterLib.Implementation/_Module/ModuleData/Languages/EN/sta_strings.xml index 9b2103f0..701703f1 100644 --- a/src/Bannerlord.ButterLib.Implementation/_Module/ModuleData/Languages/EN/sta_strings.xml +++ b/src/Bannerlord.ButterLib.Implementation/_Module/ModuleData/Languages/EN/sta_strings.xml @@ -17,5 +17,11 @@ + + + + + + \ No newline at end of file diff --git a/src/Bannerlord.ButterLib.sln b/src/Bannerlord.ButterLib.sln index 05923a4c..f981fc79 100644 --- a/src/Bannerlord.ButterLib.sln +++ b/src/Bannerlord.ButterLib.sln @@ -112,72 +112,192 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Development", "Development" ..\docs\articles\Development\Overview.md = ..\docs\articles\Development\Overview.md EndProjectSection EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ben.Demystifier", "Ben.Demystifier\src\Ben.Demystifier\Ben.Demystifier.csproj", "{0F069603-5A4C-4397-A741-0E4D9D5A9635}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ben.Demystifier", "Ben.Demystifier\src\Ben.Demystifier\Ben.Demystifier.csproj", "{0F069603-5A4C-4397-A741-0E4D9D5A9635}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution + Beta_Debug|Any CPU = Beta_Debug|Any CPU Beta_Debug|x64 = Beta_Debug|x64 + Beta_Release|Any CPU = Beta_Release|Any CPU Beta_Release|x64 = Beta_Release|x64 + Debug|Any CPU = Debug|Any CPU + Debug|x64 = Debug|x64 + Release|Any CPU = Release|Any CPU + Release|x64 = Release|x64 + Stable_Debug|Any CPU = Stable_Debug|Any CPU Stable_Debug|x64 = Stable_Debug|x64 + Stable_Release|Any CPU = Stable_Release|Any CPU Stable_Release|x64 = Stable_Release|x64 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|x64.ActiveCfg = Beta_Debug|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|x64.Build.0 = Beta_Debug|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|x64.ActiveCfg = Beta_Release|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|x64.Build.0 = Beta_Release|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|x64.ActiveCfg = Stable_Debug|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|x64.Build.0 = Stable_Debug|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|x64.ActiveCfg = Stable_Release|x64 - {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|x64.Build.0 = Stable_Release|x64 + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|Any CPU.ActiveCfg = Beta_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|Any CPU.Build.0 = Beta_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|x64.ActiveCfg = Beta_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Debug|x64.Build.0 = Beta_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|Any CPU.ActiveCfg = Beta_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|Any CPU.Build.0 = Beta_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|x64.ActiveCfg = Beta_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Beta_Release|x64.Build.0 = Beta_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Debug|Any CPU.ActiveCfg = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Debug|Any CPU.Build.0 = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Debug|x64.ActiveCfg = Stable_Debug|x64 + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Debug|x64.Build.0 = Stable_Debug|x64 + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Release|Any CPU.ActiveCfg = Stable_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Release|Any CPU.Build.0 = Stable_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Release|x64.ActiveCfg = Stable_Release|x64 + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Release|x64.Build.0 = Stable_Release|x64 + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|Any CPU.ActiveCfg = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|Any CPU.Build.0 = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|x64.ActiveCfg = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Debug|x64.Build.0 = Stable_Debug|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|Any CPU.ActiveCfg = Stable_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|Any CPU.Build.0 = Stable_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|x64.ActiveCfg = Stable_Release|Any CPU + {1339A1C0-C2F0-4491-91BB-D49C00332F68}.Stable_Release|x64.Build.0 = Stable_Release|Any CPU + {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Debug|Any CPU.ActiveCfg = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Debug|Any CPU.Build.0 = Debug|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Debug|x64.ActiveCfg = Debug|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Debug|x64.Build.0 = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Release|Any CPU.ActiveCfg = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Release|Any CPU.Build.0 = Release|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Release|x64.ActiveCfg = Release|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Beta_Release|x64.Build.0 = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Debug|Any CPU.ActiveCfg = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Debug|Any CPU.Build.0 = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Debug|x64.ActiveCfg = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Debug|x64.Build.0 = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Release|Any CPU.ActiveCfg = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Release|Any CPU.Build.0 = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Release|x64.ActiveCfg = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Release|x64.Build.0 = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Debug|Any CPU.ActiveCfg = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Debug|Any CPU.Build.0 = Debug|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Debug|x64.ActiveCfg = Debug|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Debug|x64.Build.0 = Debug|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Release|Any CPU.ActiveCfg = Release|x64 + {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Release|Any CPU.Build.0 = Release|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Release|x64.ActiveCfg = Release|x64 {17BE8506-B22B-4705-A777-C862888DA1F5}.Stable_Release|x64.Build.0 = Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Debug|Any CPU.ActiveCfg = Beta_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Debug|Any CPU.Build.0 = Beta_Debug|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Debug|x64.ActiveCfg = Beta_Debug|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Debug|x64.Build.0 = Beta_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Release|Any CPU.ActiveCfg = Beta_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Release|Any CPU.Build.0 = Beta_Release|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Release|x64.ActiveCfg = Beta_Release|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Beta_Release|x64.Build.0 = Beta_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Debug|Any CPU.Build.0 = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Debug|x64.ActiveCfg = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Debug|x64.Build.0 = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Release|Any CPU.ActiveCfg = Stable_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Release|Any CPU.Build.0 = Stable_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Release|x64.ActiveCfg = Stable_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Release|x64.Build.0 = Stable_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Debug|Any CPU.Build.0 = Stable_Debug|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Debug|x64.ActiveCfg = Stable_Debug|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Debug|x64.Build.0 = Stable_Debug|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Release|Any CPU.ActiveCfg = Stable_Release|x64 + {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Release|Any CPU.Build.0 = Stable_Release|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Release|x64.ActiveCfg = Stable_Release|x64 {C2FEF2CB-356C-4045-948D-F0755ABA6378}.Stable_Release|x64.Build.0 = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Debug|Any CPU.ActiveCfg = Beta_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Debug|Any CPU.Build.0 = Beta_Debug|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Debug|x64.ActiveCfg = Beta_Debug|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Debug|x64.Build.0 = Beta_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Release|Any CPU.ActiveCfg = Beta_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Release|Any CPU.Build.0 = Beta_Release|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Release|x64.ActiveCfg = Beta_Release|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Beta_Release|x64.Build.0 = Beta_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Debug|Any CPU.Build.0 = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Debug|x64.ActiveCfg = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Debug|x64.Build.0 = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Release|Any CPU.ActiveCfg = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Release|Any CPU.Build.0 = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Release|x64.ActiveCfg = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Release|x64.Build.0 = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Debug|Any CPU.Build.0 = Stable_Debug|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Debug|x64.ActiveCfg = Stable_Debug|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Debug|x64.Build.0 = Stable_Debug|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Release|Any CPU.ActiveCfg = Stable_Release|x64 + {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Release|Any CPU.Build.0 = Stable_Release|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Release|x64.ActiveCfg = Stable_Release|x64 {CC56F4AA-1C6F-4B20-9DA3-79A30E1F6734}.Stable_Release|x64.Build.0 = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Debug|Any CPU.ActiveCfg = Beta_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Debug|Any CPU.Build.0 = Beta_Debug|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Debug|x64.ActiveCfg = Beta_Debug|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Debug|x64.Build.0 = Beta_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Release|Any CPU.ActiveCfg = Beta_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Release|Any CPU.Build.0 = Beta_Release|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Release|x64.ActiveCfg = Beta_Release|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Beta_Release|x64.Build.0 = Beta_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Debug|Any CPU.Build.0 = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Debug|x64.ActiveCfg = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Debug|x64.Build.0 = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Release|Any CPU.ActiveCfg = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Release|Any CPU.Build.0 = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Release|x64.ActiveCfg = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Release|x64.Build.0 = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Debug|Any CPU.Build.0 = Stable_Debug|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Debug|x64.ActiveCfg = Stable_Debug|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Debug|x64.Build.0 = Stable_Debug|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Release|Any CPU.ActiveCfg = Stable_Release|x64 + {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Release|Any CPU.Build.0 = Stable_Release|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Release|x64.ActiveCfg = Stable_Release|x64 {451849FC-0522-493D-B0DF-9538ABDBE56D}.Stable_Release|x64.Build.0 = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Debug|Any CPU.ActiveCfg = Beta_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Debug|Any CPU.Build.0 = Beta_Debug|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Debug|x64.ActiveCfg = Beta_Debug|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Debug|x64.Build.0 = Beta_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Release|Any CPU.ActiveCfg = Beta_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Release|Any CPU.Build.0 = Beta_Release|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Release|x64.ActiveCfg = Beta_Release|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Beta_Release|x64.Build.0 = Beta_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Debug|Any CPU.Build.0 = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Debug|x64.ActiveCfg = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Debug|x64.Build.0 = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Release|Any CPU.ActiveCfg = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Release|Any CPU.Build.0 = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Release|x64.ActiveCfg = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Release|x64.Build.0 = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Debug|Any CPU.ActiveCfg = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Debug|Any CPU.Build.0 = Stable_Debug|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Debug|x64.ActiveCfg = Stable_Debug|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Debug|x64.Build.0 = Stable_Debug|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Release|Any CPU.ActiveCfg = Stable_Release|x64 + {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Release|Any CPU.Build.0 = Stable_Release|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Release|x64.ActiveCfg = Stable_Release|x64 {5C1705E2-CC31-4215-A4CE-7A8AFF6D9BC3}.Stable_Release|x64.Build.0 = Stable_Release|x64 + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Debug|Any CPU.ActiveCfg = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Debug|Any CPU.Build.0 = Debug|Any CPU {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Debug|x64.ActiveCfg = Debug|Any CPU {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Debug|x64.Build.0 = Debug|Any CPU - {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|x64.ActiveCfg = Debug|Any CPU - {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|x64.Build.0 = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|Any CPU.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|Any CPU.Build.0 = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|x64.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Beta_Release|x64.Build.0 = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Debug|Any CPU.Build.0 = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Debug|x64.ActiveCfg = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Debug|x64.Build.0 = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Release|Any CPU.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Release|Any CPU.Build.0 = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Release|x64.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Release|x64.Build.0 = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Debug|Any CPU.ActiveCfg = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Debug|Any CPU.Build.0 = Debug|Any CPU {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Debug|x64.ActiveCfg = Debug|Any CPU {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Debug|x64.Build.0 = Debug|Any CPU - {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|x64.ActiveCfg = Debug|Any CPU - {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|x64.Build.0 = Debug|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|Any CPU.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|Any CPU.Build.0 = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|x64.ActiveCfg = Release|Any CPU + {0F069603-5A4C-4397-A741-0E4D9D5A9635}.Stable_Release|x64.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj index 77f42869..0a7b84d3 100644 --- a/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj +++ b/src/Bannerlord.ButterLib/Bannerlord.ButterLib.csproj @@ -33,7 +33,9 @@ - + diff --git a/src/Bannerlord.ButterLib/ButterLibSubModule.cs b/src/Bannerlord.ButterLib/ButterLibSubModule.cs index 3d03d283..c03341e4 100644 --- a/src/Bannerlord.ButterLib/ButterLibSubModule.cs +++ b/src/Bannerlord.ButterLib/ButterLibSubModule.cs @@ -78,6 +78,8 @@ public void OnServiceRegistration() this.AddDefaultSerilogLogger(); this.AddSerilogLoggerProvider("butterlib.txt", new[] { "Bannerlord.ButterLib.*" }); this.AddSerilogLoggerProvider("trace.txt", new[] { "System.Diagnostics.Logger.*" }); + //this.AddSteamWriterLogger("harmony.txt", out var harmonyStreamWriter); + //HarmonyLib.FileLog.LogWriter = harmonyStreamWriter; Services.AddSubSystem(); Services.AddSubSystem(); diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs b/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs index 416d56d5..7f76cfba 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/BEWPatch.cs @@ -1,4 +1,4 @@ -using Bannerlord.BUTRLoader; +using Bannerlord.BLSE; using Bannerlord.ButterLib.Common.Extensions; using Bannerlord.ButterLib.ExceptionHandler.DebuggerDetection; @@ -28,7 +28,7 @@ namespace Bannerlord.ButterLib.ExceptionHandler // TaleWorlds.MountAndBlade.MissionBehaviour:OnMissionTick -> Called by TaleWorlds.MountAndBlade.Mission:Tick // TaleWorlds.MountAndBlade.MBSubModuleBase:OnSubModuleLoad -> Replicated - [BUTRLoaderInterceptor] + [BLSELoaderInterceptor] internal sealed class BEWPatch { public static bool IsDebuggerAttached() diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs index 13841e5e..83cd1f04 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs @@ -1,13 +1,9 @@ -using AsmResolver.DotNet.Code.Cil; - -using Bannerlord.BUTR.Shared.Helpers; +using Bannerlord.BUTR.Shared.Helpers; using Bannerlord.ModuleManager; using HarmonyLib; using HarmonyLib.BUTR.Extensions; -using MonoMod.Core.Platforms; - using System; using System.Collections.Generic; using System.Diagnostics; @@ -17,7 +13,7 @@ namespace Bannerlord.ButterLib.ExceptionHandler { - internal record StacktraceEntry(MethodBase Method, bool MethodFromStackframeIssue, ModuleInfoExtended? ModuleInfo, string StackFrameDescription, CilInstructionCollection? CilInstructions); + internal record StacktraceEntry(MethodBase Method, bool MethodFromStackframeIssue, ModuleInfoExtended? ModuleInfo, string StackFrameDescription, string[] CilInstructions); internal class CrashReport { @@ -130,25 +126,26 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) var patches = FindPatches(method); foreach (var (methodBase, extendedModuleInfo) in GetFinalizers(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, Array.Empty()); } foreach (var (methodBase, extendedModuleInfo) in GetPostfixes(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, Array.Empty()); } foreach (var (methodBase, extendedModuleInfo) in GetPrefixes(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, Array.Empty()); } foreach (var (methodBase, extendedModuleInfo) in GetTranspilers(patches)) { - yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, null); + yield return new(methodBase, methodFromStackframeIssue, extendedModuleInfo, frameDesc, Array.Empty()); } var moduleInfo = GetModuleInfoIfMod(method); - yield return new(method, methodFromStackframeIssue, moduleInfo, frameDesc, null); + yield return new(method, methodFromStackframeIssue, moduleInfo, frameDesc, Array.Empty()); + /* // Further versions of Harmony will do `PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod` themselves if (method is MethodInfo && PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod && Harmony.GetOriginalMethod(identifiableMethod) is { } original) { @@ -166,6 +163,7 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) } yield return new(original, methodFromStackframeIssue, moduleInfo, frameDesc, instructions); } + */ } } } diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/ExceptionHandlerSubSystem.cs b/src/Bannerlord.ButterLib/ExceptionHandler/ExceptionHandlerSubSystem.cs index 06f88198..0e3de08b 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/ExceptionHandlerSubSystem.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/ExceptionHandlerSubSystem.cs @@ -78,6 +78,34 @@ private set } } + private bool _useVanillaCrashHandler = false; + public bool UseVanillaCrashHandler + { + get => _catchAutoGenExceptions; + private set + { + if (_useVanillaCrashHandler != value) + { + _useVanillaCrashHandler = value; + + if (_useVanillaCrashHandler) + { + if (IsEnabled) + { + WatchdogHandler.EnableTWWatchdog(); + } + } + else + { + if (IsEnabled) + { + WatchdogHandler.DisableTWWatchdog(); + } + } + } + } + } + /// public IReadOnlyCollection> Declarations { get; } = new SubSystemSettingsDeclaration[] { @@ -86,9 +114,13 @@ private set "{=r3ktQzFMRz} Stops the Exception Handler when a debugger is attached.", x => x.DisableWhenDebuggerIsAttached), new SubSystemSettingsPropertyBool( - "{=B7bfrDNzIk} Catch AutoGenerated Code Exceptions (Lower Performance)", - "{=r3ktQzFMRz} Catch every Native->Managed call. Should catch every exception not catched the standard way. Might decrease the overall performance a bit.", + "{=jorWb502pD} Catch AutoGenerated Code Exceptions (Lower Performance) (DISABLED)", + "{=ji1brrsEZz} Catch every Native->Managed call. Should catch every exception not catched the standard way. Might decrease the overall performance a bit.", x => x.CatchAutoGenExceptions), + new SubSystemSettingsPropertyBool( + "{=ZD69h3IpF5} Use Vanilla Crash Handler", + "{=o0DgSNv5V1} Disables ButterLib's and BEW's Crash Handlers with the new Watchdog Crash Handler. Do not enable if not sure.", + x => x.UseVanillaCrashHandler), }; @@ -105,6 +137,8 @@ public void Enable() SubscribeToUnhandledException(); BEWPatch.Enable(Harmony); + + WatchdogHandler.DisableTWWatchdog(); } public void Disable() @@ -117,6 +151,8 @@ public void Disable() { BEWPatch.Disable(Harmony); } + + WatchdogHandler.EnableTWWatchdog(); } private static bool _isSubscribedToUnhandledException; diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs b/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs index 13b3bb7a..95432dc5 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/HtmlBuilder.cs @@ -398,7 +398,7 @@ private static string GetEnhancedStacktraceHtml(CrashReport crashReport) .Append($"Method From Stackframe Issue: {methodFromStackframeIssue}
        ") .Append(""); } - if (stacktrace.FirstOrDefault(x => x.CilInstructions is not null) is { CilInstructions: { } cilInstructions }) + if (stacktrace.FirstOrDefault(x => x.CilInstructions.Length > 0) is { CilInstructions: { } cilInstructions }) { foreach (var instruction in cilInstructions) sbCil.Append('\t').Append(instruction).AppendLine(); diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs new file mode 100644 index 00000000..2e767cdc --- /dev/null +++ b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs @@ -0,0 +1,68 @@ +using System; +using System.IO; +using System.Runtime.InteropServices; + +namespace Bannerlord.ButterLib.ExceptionHandler +{ + internal static class WatchdogHandler + { + [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] + private static extern unsafe byte* LoadLibrary(string libname); + + [DllImport("kernel32.dll", SetLastError = true)] + private static extern unsafe bool VirtualProtect(byte* lpAddress, int dwSize, int flNewProtect, out int lpflOldProtect); + + private static string WatchdogLibraryName = "TaleWorlds.Native.dll"; + private static byte[] WatchdogOriginal = "Watchdog.exe"u8.ToArray(); + private static byte[] WatchdogReplacement = "Wetchdog.exe"u8.ToArray(); + + // Disable Watchdog by renaming it, thus performing a soft delete in it's eyes + public static unsafe void DisableTWWatchdog() + { + var library = LoadLibrary(WatchdogLibraryName); + var size = (int) new FileInfo(WatchdogLibraryName).Length; + var watchdogSize = WatchdogOriginal.Length; + + var libraryMemoryBlock = new Span(library, size); + + var searchSpan = libraryMemoryBlock; + var searchSpanOffset = 0; + while (searchSpan.IndexOf(WatchdogOriginal) is var idx and not -1) + { + var address = library + searchSpanOffset + idx; + var textMemoryBlock = new Span(address, watchdogSize); + + VirtualProtect(address, watchdogSize, 0x40, out var old); + WatchdogReplacement.CopyTo(textMemoryBlock); + VirtualProtect(address, watchdogSize, old, out _); + + searchSpanOffset = idx; + searchSpan = searchSpan.Slice(searchSpanOffset); + } + } + + public static unsafe void EnableTWWatchdog() + { + var library = LoadLibrary(WatchdogLibraryName); + var size = (int) new FileInfo(WatchdogLibraryName).Length; + var watchdogSize = WatchdogOriginal.Length; + + var libraryMemoryBlock = new Span(library, size); + + var searchSpan = libraryMemoryBlock; + var searchSpanOffset = 0; + while (searchSpan.IndexOf(WatchdogReplacement) is var idx and not -1) + { + var address = library + searchSpanOffset + idx; + var textMemoryBlock = new Span(address, watchdogSize); + + VirtualProtect(address, watchdogSize, 0x40, out var old); + WatchdogOriginal.CopyTo(textMemoryBlock); + VirtualProtect(address, watchdogSize, old, out _); + + searchSpanOffset = idx; + searchSpan = searchSpan.Slice(searchSpanOffset); + } + } + } +} \ No newline at end of file diff --git a/src/Bannerlord.ButterLib/Helpers/BUTRLoaderInterceptorAttribute.cs b/src/Bannerlord.ButterLib/Helpers/BLSELoaderInterceptorAttribute.cs similarity index 54% rename from src/Bannerlord.ButterLib/Helpers/BUTRLoaderInterceptorAttribute.cs rename to src/Bannerlord.ButterLib/Helpers/BLSELoaderInterceptorAttribute.cs index e5529c8f..0aec301b 100644 --- a/src/Bannerlord.ButterLib/Helpers/BUTRLoaderInterceptorAttribute.cs +++ b/src/Bannerlord.ButterLib/Helpers/BLSELoaderInterceptorAttribute.cs @@ -1,8 +1,8 @@ using System; // ReSharper disable once CheckNamespace -namespace Bannerlord.BUTRLoader +namespace Bannerlord.BLSE { [AttributeUsage(AttributeTargets.Class)] - internal sealed class BUTRLoaderInterceptorAttribute : Attribute { } + internal sealed class BLSELoaderInterceptorAttribute : Attribute { } } \ No newline at end of file diff --git a/src/Bannerlord.ButterLib/Helpers/CrashReportFilter.cs b/src/Bannerlord.ButterLib/Helpers/CrashReportFilter.cs new file mode 100644 index 00000000..6aa596f7 --- /dev/null +++ b/src/Bannerlord.ButterLib/Helpers/CrashReportFilter.cs @@ -0,0 +1,35 @@ +using Bannerlord.ButterLib.ExceptionHandler; + +namespace Bannerlord.ButterLib.Helpers +{ + internal static class CrashReportFilter + { + public static bool Filter(StacktraceEntry stacktraceEntry) + { + if (stacktraceEntry.ModuleInfo?.Id == "Bannerlord.ButterLib") + { + if (stacktraceEntry.Method == BEWPatch.FinalizerMethod) + { + return false; + } + } + if (stacktraceEntry.ModuleInfo?.Id is "BetterExceptionWindow") + { + if (stacktraceEntry.Method is { Name: "Finalizer", DeclaringType: { Namespace: "AutoGeneratedExceptionFilter" } }) + { + return false; + } + } + + if (stacktraceEntry.ModuleInfo?.Id == "Bannerlord.MBOptionScreen") + { + if (stacktraceEntry.Method.Name == "ExecuteCommandPatch") + { + return false; + } + } + + return true; + } + } +} \ No newline at end of file From 9f7167dd6f1e50f092593344421e31b7e6c243bf Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 19:48:53 +0300 Subject: [PATCH 09/12] Improvements --- .../ExceptionHandler/WatchdogHandler.cs | 24 +++++++++++-------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs index 2e767cdc..8fce137e 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs @@ -4,22 +4,25 @@ namespace Bannerlord.ButterLib.ExceptionHandler { - internal static class WatchdogHandler + internal static unsafe class WatchdogHandler { [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] - private static extern unsafe byte* LoadLibrary(string libname); + private static extern byte* LoadLibrary(string libname); [DllImport("kernel32.dll", SetLastError = true)] - private static extern unsafe bool VirtualProtect(byte* lpAddress, int dwSize, int flNewProtect, out int lpflOldProtect); + private static extern bool VirtualProtect(byte* address, nint dwSize, int newProtect, out int oldProtect); - private static string WatchdogLibraryName = "TaleWorlds.Native.dll"; - private static byte[] WatchdogOriginal = "Watchdog.exe"u8.ToArray(); - private static byte[] WatchdogReplacement = "Wetchdog.exe"u8.ToArray(); + private static readonly int PAGE_EXECUTE_READWRITE = 0x40; + + private static readonly string WatchdogLibraryName = "TaleWorlds.Native.dll"; + private static readonly byte[] WatchdogOriginal = "Watchdog.exe"u8.ToArray(); + private static readonly byte[] WatchdogReplacement = "Wetchdog.exe"u8.ToArray(); // Disable Watchdog by renaming it, thus performing a soft delete in it's eyes - public static unsafe void DisableTWWatchdog() + public static void DisableTWWatchdog() { var library = LoadLibrary(WatchdogLibraryName); + // Don't like the fact that I can't get the concrete memory size var size = (int) new FileInfo(WatchdogLibraryName).Length; var watchdogSize = WatchdogOriginal.Length; @@ -32,7 +35,7 @@ public static unsafe void DisableTWWatchdog() var address = library + searchSpanOffset + idx; var textMemoryBlock = new Span(address, watchdogSize); - VirtualProtect(address, watchdogSize, 0x40, out var old); + VirtualProtect(address, watchdogSize, PAGE_EXECUTE_READWRITE, out var old); WatchdogReplacement.CopyTo(textMemoryBlock); VirtualProtect(address, watchdogSize, old, out _); @@ -41,9 +44,10 @@ public static unsafe void DisableTWWatchdog() } } - public static unsafe void EnableTWWatchdog() + public static void EnableTWWatchdog() { var library = LoadLibrary(WatchdogLibraryName); + // Don't like the fact that I can't get the concrete memory size var size = (int) new FileInfo(WatchdogLibraryName).Length; var watchdogSize = WatchdogOriginal.Length; @@ -56,7 +60,7 @@ public static unsafe void EnableTWWatchdog() var address = library + searchSpanOffset + idx; var textMemoryBlock = new Span(address, watchdogSize); - VirtualProtect(address, watchdogSize, 0x40, out var old); + VirtualProtect(address, watchdogSize, PAGE_EXECUTE_READWRITE, out var old); WatchdogOriginal.CopyTo(textMemoryBlock); VirtualProtect(address, watchdogSize, old, out _); From ebbaf3d0d427f99507eec90e0de2b6c59a1063e0 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 20:01:29 +0300 Subject: [PATCH 10/12] Another improvement --- .../ExceptionHandler/WatchdogHandler.cs | 34 +++++++++---------- 1 file changed, 16 insertions(+), 18 deletions(-) diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs index 8fce137e..a197e4bc 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs @@ -21,23 +21,22 @@ internal static unsafe class WatchdogHandler // Disable Watchdog by renaming it, thus performing a soft delete in it's eyes public static void DisableTWWatchdog() { - var library = LoadLibrary(WatchdogLibraryName); + var libraryPtr = LoadLibrary(WatchdogLibraryName); // Don't like the fact that I can't get the concrete memory size var size = (int) new FileInfo(WatchdogLibraryName).Length; - var watchdogSize = WatchdogOriginal.Length; - var libraryMemoryBlock = new Span(library, size); + var librarySpan = new ReadOnlySpan(libraryPtr, size); - var searchSpan = libraryMemoryBlock; + var searchSpan = librarySpan; var searchSpanOffset = 0; while (searchSpan.IndexOf(WatchdogOriginal) is var idx and not -1) { - var address = library + searchSpanOffset + idx; - var textMemoryBlock = new Span(address, watchdogSize); + var watchdogLocationPtr = libraryPtr + searchSpanOffset + idx; + var watchdogLocationSpan = new Span(watchdogLocationPtr, WatchdogOriginal.Length); - VirtualProtect(address, watchdogSize, PAGE_EXECUTE_READWRITE, out var old); - WatchdogReplacement.CopyTo(textMemoryBlock); - VirtualProtect(address, watchdogSize, old, out _); + VirtualProtect(watchdogLocationPtr, watchdogLocationSpan.Length, PAGE_EXECUTE_READWRITE, out var old); + WatchdogReplacement.CopyTo(watchdogLocationSpan); + VirtualProtect(watchdogLocationPtr, watchdogLocationSpan.Length, old, out _); searchSpanOffset = idx; searchSpan = searchSpan.Slice(searchSpanOffset); @@ -46,23 +45,22 @@ public static void DisableTWWatchdog() public static void EnableTWWatchdog() { - var library = LoadLibrary(WatchdogLibraryName); + var libraryPtr = LoadLibrary(WatchdogLibraryName); // Don't like the fact that I can't get the concrete memory size var size = (int) new FileInfo(WatchdogLibraryName).Length; - var watchdogSize = WatchdogOriginal.Length; - var libraryMemoryBlock = new Span(library, size); + var librarySpan = new ReadOnlySpan(libraryPtr, size); - var searchSpan = libraryMemoryBlock; + var searchSpan = librarySpan; var searchSpanOffset = 0; while (searchSpan.IndexOf(WatchdogReplacement) is var idx and not -1) { - var address = library + searchSpanOffset + idx; - var textMemoryBlock = new Span(address, watchdogSize); + var watchdogLocationPtr = libraryPtr + searchSpanOffset + idx; + var watchdogLocationSpan = new Span(watchdogLocationPtr, WatchdogOriginal.Length); - VirtualProtect(address, watchdogSize, PAGE_EXECUTE_READWRITE, out var old); - WatchdogOriginal.CopyTo(textMemoryBlock); - VirtualProtect(address, watchdogSize, old, out _); + VirtualProtect(watchdogLocationPtr, watchdogLocationSpan.Length, PAGE_EXECUTE_READWRITE, out var old); + WatchdogOriginal.CopyTo(watchdogLocationSpan); + VirtualProtect(watchdogLocationPtr, watchdogLocationSpan.Length, old, out _); searchSpanOffset = idx; searchSpan = searchSpan.Slice(searchSpanOffset); From bae391e4893c3555a29765c94b416cda81167a64 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 20:37:06 +0300 Subject: [PATCH 11/12] Fix --- .../Bannerlord.ButterLib.Implementation.csproj | 3 +++ .../ExceptionHandler/CrashReport.cs | 10 ++++++---- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj index e16dc7b9..b6580ead 100644 --- a/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj +++ b/src/Bannerlord.ButterLib.Implementation/Bannerlord.ButterLib.Implementation.csproj @@ -43,6 +43,9 @@ + + +
        diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs index 83cd1f04..fcb76907 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/CrashReport.cs @@ -147,21 +147,23 @@ private static IEnumerable GetAllInvolvedModules(Exception ex) /* // Further versions of Harmony will do `PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod` themselves - if (method is MethodInfo && PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod && Harmony.GetOriginalMethod(identifiableMethod) is { } original) + if (method is MethodInfo && MonoMod.Core.Platforms.PlatformTriple.Current.GetIdentifiable(method) is MethodInfo identifiableMethod && Harmony.GetOriginalMethod(identifiableMethod) is { } original) { - CilInstructionCollection? instructions; + AsmResolver.DotNet.Code.Cil.CilInstructionCollection? instructions; try { var module = AsmResolver.DotNet.ModuleDefinition.FromModule(identifiableMethod.Module); var dynamicMethodDefinition = new AsmResolver.DotNet.Dynamic.DynamicMethodDefinition(module, identifiableMethod); - var cilMethodBody = dynamicMethodDefinition.MethodBody as CilMethodBody; + var cilMethodBody = dynamicMethodDefinition.MethodBody as AsmResolver.DotNet.Code.Cil.CilMethodBody; instructions = cilMethodBody?.Instructions; } catch (Exception) { instructions = null; } - yield return new(original, methodFromStackframeIssue, moduleInfo, frameDesc, instructions); + + var instructionsStr = instructions.Select(x => x.ToString()).ToArray(); + yield return new(original, methodFromStackframeIssue, moduleInfo, frameDesc, instructionsStr); } */ } From 48be2a5d83f896271de6f804c6a0db206b0511c7 Mon Sep 17 00:00:00 2001 From: Vitalii Mikhailov Date: Sun, 2 Jul 2023 20:52:31 +0300 Subject: [PATCH 12/12] Test fix --- .../ExceptionHandler/WatchdogHandler.cs | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs index a197e4bc..6e696d44 100644 --- a/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs +++ b/src/Bannerlord.ButterLib/ExceptionHandler/WatchdogHandler.cs @@ -21,9 +21,12 @@ internal static unsafe class WatchdogHandler // Disable Watchdog by renaming it, thus performing a soft delete in it's eyes public static void DisableTWWatchdog() { + var watchdogLibraryFile = new FileInfo(WatchdogLibraryName); + if (!watchdogLibraryFile.Exists) return; + var libraryPtr = LoadLibrary(WatchdogLibraryName); // Don't like the fact that I can't get the concrete memory size - var size = (int) new FileInfo(WatchdogLibraryName).Length; + var size = (int) watchdogLibraryFile.Length; var librarySpan = new ReadOnlySpan(libraryPtr, size); @@ -45,9 +48,12 @@ public static void DisableTWWatchdog() public static void EnableTWWatchdog() { + var watchdogLibraryFile = new FileInfo(WatchdogLibraryName); + if (!watchdogLibraryFile.Exists) return; + var libraryPtr = LoadLibrary(WatchdogLibraryName); // Don't like the fact that I can't get the concrete memory size - var size = (int) new FileInfo(WatchdogLibraryName).Length; + var size = (int) watchdogLibraryFile.Length; var librarySpan = new ReadOnlySpan(libraryPtr, size);