diff --git a/src/StardewModdingAPI.AssemblyRewriters/Finders/EventFinder.cs b/src/StardewModdingAPI.AssemblyRewriters/Finders/EventFinder.cs
index 848e54ff..bcceee32 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Finders/EventFinder.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Finders/EventFinder.cs
@@ -3,8 +3,8 @@ using Mono.Cecil.Cil;
namespace StardewModdingAPI.AssemblyRewriters.Finders
{
- /// Finds CIL instructions that reference a given event.
- public sealed class EventFinder : IInstructionFinder
+ /// Finds incompatible CIL instructions that reference a given event and throws an .
+ public class EventFinder : IInstructionRewriter
{
/*********
** Properties
@@ -37,6 +37,22 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
this.NounPhrase = nounPhrase ?? $"{fullTypeName}.{eventName} event";
}
+ /// Rewrite a CIL instruction for compatibility.
+ /// The module being rewritten.
+ /// The CIL rewriter.
+ /// The instruction to rewrite.
+ /// Metadata for mapping assemblies to the current platform.
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
+ {
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ throw new IncompatibleInstructionException(this.NounPhrase);
+ }
+
/*********
** Protected methods
@@ -44,7 +60,7 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
/// Get whether a CIL instruction matches.
/// The IL instruction.
/// Whether the mod was compiled on a different platform.
- public bool IsMatch(Instruction instruction, bool platformChanged)
+ protected bool IsMatch(Instruction instruction, bool platformChanged)
{
MethodReference methodRef = RewriteHelper.AsMethodReference(instruction);
return
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Finders/FieldFinder.cs b/src/StardewModdingAPI.AssemblyRewriters/Finders/FieldFinder.cs
index 068119b8..cdfc3bd5 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Finders/FieldFinder.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Finders/FieldFinder.cs
@@ -3,8 +3,8 @@ using Mono.Cecil.Cil;
namespace StardewModdingAPI.AssemblyRewriters.Finders
{
- /// Finds CIL instructions that reference a given field.
- public class FieldFinder : IInstructionFinder
+ /// Finds incompatible CIL instructions that reference a given field and throws an .
+ public class FieldFinder : IInstructionRewriter
{
/*********
** Properties
@@ -37,6 +37,22 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
this.NounPhrase = nounPhrase ?? $"{fullTypeName}.{fieldName} field";
}
+ /// Rewrite a CIL instruction for compatibility.
+ /// The module being rewritten.
+ /// The CIL rewriter.
+ /// The instruction to rewrite.
+ /// Metadata for mapping assemblies to the current platform.
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public virtual bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
+ {
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ throw new IncompatibleInstructionException(this.NounPhrase);
+ }
+
/*********
** Protected methods
@@ -44,7 +60,7 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
/// Get whether a CIL instruction matches.
/// The IL instruction.
/// Whether the mod was compiled on a different platform.
- public bool IsMatch(Instruction instruction, bool platformChanged)
+ protected bool IsMatch(Instruction instruction, bool platformChanged)
{
FieldReference fieldRef = RewriteHelper.AsFieldReference(instruction);
return
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Finders/MethodFinder.cs b/src/StardewModdingAPI.AssemblyRewriters/Finders/MethodFinder.cs
index d174bacd..2efcbb0f 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Finders/MethodFinder.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Finders/MethodFinder.cs
@@ -3,8 +3,8 @@ using Mono.Cecil.Cil;
namespace StardewModdingAPI.AssemblyRewriters.Finders
{
- /// Finds CIL instructions that reference a given method.
- public class MethodFinder : IInstructionFinder
+ /// Finds incompatible CIL instructions that reference a given method and throws an .
+ public class MethodFinder : IInstructionRewriter
{
/*********
** Properties
@@ -37,6 +37,22 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
this.NounPhrase = nounPhrase ?? $"{fullTypeName}.{methodName} method";
}
+ /// Rewrite a CIL instruction for compatibility.
+ /// The module being rewritten.
+ /// The CIL rewriter.
+ /// The instruction to rewrite.
+ /// Metadata for mapping assemblies to the current platform.
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
+ {
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ throw new IncompatibleInstructionException(this.NounPhrase);
+ }
+
/*********
** Protected methods
@@ -44,7 +60,7 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
/// Get whether a CIL instruction matches.
/// The IL instruction.
/// Whether the mod was compiled on a different platform.
- public bool IsMatch(Instruction instruction, bool platformChanged)
+ protected bool IsMatch(Instruction instruction, bool platformChanged)
{
MethodReference methodRef = RewriteHelper.AsMethodReference(instruction);
return
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Finders/TypeFinder.cs b/src/StardewModdingAPI.AssemblyRewriters/Finders/TypeFinder.cs
index 8f492d5f..96cbb229 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Finders/TypeFinder.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Finders/TypeFinder.cs
@@ -4,8 +4,8 @@ using Mono.Cecil.Cil;
namespace StardewModdingAPI.AssemblyRewriters.Finders
{
- /// Finds CIL instructions that reference a given type.
- public class TypeFinder : IInstructionFinder
+ /// Finds incompatible CIL instructions that reference a given type and throws an .
+ public class TypeFinder : IInstructionRewriter
{
/*********
** Accessors
@@ -33,10 +33,30 @@ namespace StardewModdingAPI.AssemblyRewriters.Finders
this.NounPhrase = nounPhrase ?? $"{fullTypeName} type";
}
+ /// Rewrite a CIL instruction for compatibility.
+ /// The module being rewritten.
+ /// The CIL rewriter.
+ /// The instruction to rewrite.
+ /// Metadata for mapping assemblies to the current platform.
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public virtual bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
+ {
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ throw new IncompatibleInstructionException(this.NounPhrase);
+ }
+
+
+ /*********
+ ** Protected methods
+ *********/
/// Get whether a CIL instruction matches.
/// The IL instruction.
/// Whether the mod was compiled on a different platform.
- public bool IsMatch(Instruction instruction, bool platformChanged)
+ protected bool IsMatch(Instruction instruction, bool platformChanged)
{
string fullName = this.FullTypeName;
diff --git a/src/StardewModdingAPI.AssemblyRewriters/IInstructionFinder.cs b/src/StardewModdingAPI.AssemblyRewriters/IInstructionFinder.cs
deleted file mode 100644
index cc3006b9..00000000
--- a/src/StardewModdingAPI.AssemblyRewriters/IInstructionFinder.cs
+++ /dev/null
@@ -1,23 +0,0 @@
-using Mono.Cecil.Cil;
-
-namespace StardewModdingAPI.AssemblyRewriters
-{
- /// Finds CIL instructions considered incompatible.
- public interface IInstructionFinder
- {
- /*********
- ** Accessors
- *********/
- /// A brief noun phrase indicating what the instruction finder matches.
- string NounPhrase { get; }
-
-
- /*********
- ** Methods
- *********/
- /// Get whether a CIL instruction matches.
- /// The IL instruction.
- /// Whether the mod was compiled on a different platform.
- bool IsMatch(Instruction instruction, bool platformChanged);
- }
-}
diff --git a/src/StardewModdingAPI.AssemblyRewriters/IInstructionRewriter.cs b/src/StardewModdingAPI.AssemblyRewriters/IInstructionRewriter.cs
index b230f227..3a7b1365 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/IInstructionRewriter.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/IInstructionRewriter.cs
@@ -3,9 +3,16 @@ using Mono.Cecil.Cil;
namespace StardewModdingAPI.AssemblyRewriters
{
- /// Rewrites a CIL instruction for compatibility.
- public interface IInstructionRewriter : IInstructionFinder
+ /// Rewrites CIL instructions for compatibility.
+ public interface IInstructionRewriter
{
+ /*********
+ ** Accessors
+ *********/
+ /// A brief noun phrase indicating what the rewriter matches.
+ string NounPhrase { get; }
+
+
/*********
** Methods
*********/
@@ -14,6 +21,9 @@ namespace StardewModdingAPI.AssemblyRewriters
/// The CIL rewriter.
/// The instruction to rewrite.
/// Metadata for mapping assemblies to the current platform.
- void Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap);
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged);
}
}
diff --git a/src/StardewModdingAPI/Framework/IncompatibleInstructionException.cs b/src/StardewModdingAPI.AssemblyRewriters/IncompatibleInstructionException.cs
similarity index 63%
rename from src/StardewModdingAPI/Framework/IncompatibleInstructionException.cs
rename to src/StardewModdingAPI.AssemblyRewriters/IncompatibleInstructionException.cs
index affe2cb3..f7e6bd8f 100644
--- a/src/StardewModdingAPI/Framework/IncompatibleInstructionException.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/IncompatibleInstructionException.cs
@@ -1,9 +1,9 @@
using System;
-namespace StardewModdingAPI.Framework
+namespace StardewModdingAPI.AssemblyRewriters
{
/// An exception raised when an incompatible instruction is found while loading a mod assembly.
- internal class IncompatibleInstructionException : Exception
+ public class IncompatibleInstructionException : Exception
{
/*********
** Accessors
@@ -15,6 +15,14 @@ namespace StardewModdingAPI.Framework
/*********
** Public methods
*********/
+ /// Construct an instance.
+ /// A brief noun phrase which describes the incompatible instruction that was found.
+ public IncompatibleInstructionException(string nounPhrase)
+ : base($"Found an incompatible CIL instruction ({nounPhrase}).")
+ {
+ this.NounPhrase = nounPhrase;
+ }
+
/// Construct an instance.
/// A brief noun phrase which describes the incompatible instruction that was found.
/// A message which describes the error.
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldReplaceRewriter.cs b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldReplaceRewriter.cs
index ffd22e7c..95663c49 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldReplaceRewriter.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldReplaceRewriter.cs
@@ -7,16 +7,13 @@ using StardewModdingAPI.AssemblyRewriters.Finders;
namespace StardewModdingAPI.AssemblyRewriters.Rewriters
{
/// Rewrites references to one field with another.
- public class FieldReplaceRewriter : FieldFinder, IInstructionRewriter
+ public class FieldReplaceRewriter : FieldFinder
{
/*********
** Properties
*********/
- /// The type whose field to which references should be rewritten.
- private readonly Type Type;
-
- /// The new field name to reference.
- private readonly string ToFieldName;
+ /// The new field to reference.
+ private readonly FieldInfo ToField;
/*********
@@ -30,8 +27,9 @@ namespace StardewModdingAPI.AssemblyRewriters.Rewriters
public FieldReplaceRewriter(Type type, string fromFieldName, string toFieldName, string nounPhrase = null)
: base(type.FullName, fromFieldName, nounPhrase)
{
- this.Type = type;
- this.ToFieldName = toFieldName;
+ this.ToField = type.GetField(toFieldName);
+ if (this.ToField == null)
+ throw new InvalidOperationException($"The {type.FullName} class doesn't have a {toFieldName} field.");
}
/// Rewrite a CIL instruction for compatibility.
@@ -39,13 +37,17 @@ namespace StardewModdingAPI.AssemblyRewriters.Rewriters
/// The CIL rewriter.
/// The instruction to rewrite.
/// Metadata for mapping assemblies to the current platform.
- public void Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap)
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public override bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
{
- FieldInfo field = this.Type.GetField(this.ToFieldName);
- if (field == null)
- throw new InvalidOperationException($"The {this.Type.FullName} class doesn't have a {this.ToFieldName} field.");
- FieldReference newRef = module.Import(field);
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ FieldReference newRef = module.Import(this.ToField);
cil.Replace(instruction, cil.Create(instruction.OpCode, newRef));
+ return true;
}
}
}
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldToPropertyRewriter.cs b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldToPropertyRewriter.cs
index f2f99cc1..a25f3fef 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldToPropertyRewriter.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/FieldToPropertyRewriter.cs
@@ -6,7 +6,7 @@ using StardewModdingAPI.AssemblyRewriters.Finders;
namespace StardewModdingAPI.AssemblyRewriters.Rewriters
{
/// Rewrites field references into property references.
- public class FieldToPropertyRewriter : FieldFinder, IInstructionRewriter
+ public class FieldToPropertyRewriter : FieldFinder
{
/*********
** Properties
@@ -37,11 +37,18 @@ namespace StardewModdingAPI.AssemblyRewriters.Rewriters
/// The CIL rewriter.
/// The instruction to rewrite.
/// Metadata for mapping assemblies to the current platform.
- public void Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap)
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public override bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
{
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
string methodPrefix = instruction.OpCode == OpCodes.Ldsfld || instruction.OpCode == OpCodes.Ldfld ? "get" : "set";
MethodReference propertyRef = module.Import(this.Type.GetMethod($"{methodPrefix}_{this.FieldName}"));
cil.Replace(instruction, cil.Create(OpCodes.Call, propertyRef));
+ return true;
}
}
}
diff --git a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/MethodParentRewriter.cs b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/MethodParentRewriter.cs
index 24d4dff9..3ec8c704 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/Rewriters/MethodParentRewriter.cs
+++ b/src/StardewModdingAPI.AssemblyRewriters/Rewriters/MethodParentRewriter.cs
@@ -43,10 +43,32 @@ namespace StardewModdingAPI.AssemblyRewriters.Rewriters
this.OnlyIfPlatformChanged = onlyIfPlatformChanged;
}
+ /// Rewrite a CIL instruction for compatibility.
+ /// The module being rewritten.
+ /// The CIL rewriter.
+ /// The instruction to rewrite.
+ /// Metadata for mapping assemblies to the current platform.
+ /// Whether the mod was compiled on a different platform.
+ /// Returns whether the instruction was rewritten.
+ /// The CIL instruction is not compatible, and can't be rewritten.
+ public bool Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap, bool platformChanged)
+ {
+ if (!this.IsMatch(instruction, platformChanged))
+ return false;
+
+ MethodReference methodRef = (MethodReference)instruction.Operand;
+ methodRef.DeclaringType = module.Import(this.ToType);
+ return true;
+ }
+
+
+ /*********
+ ** Protected methods
+ *********/
/// Get whether a CIL instruction matches.
/// The IL instruction.
/// Whether the mod was compiled on a different platform.
- public bool IsMatch(Instruction instruction, bool platformChanged)
+ protected bool IsMatch(Instruction instruction, bool platformChanged)
{
MethodReference methodRef = RewriteHelper.AsMethodReference(instruction);
return
@@ -55,16 +77,5 @@ namespace StardewModdingAPI.AssemblyRewriters.Rewriters
&& methodRef.DeclaringType.FullName == this.FromType.FullName
&& RewriteHelper.HasMatchingSignature(this.ToType, methodRef);
}
-
- /// Rewrite a CIL instruction for compatibility.
- /// The module being rewritten.
- /// The CIL rewriter.
- /// The instruction to rewrite.
- /// Metadata for mapping assemblies to the current platform.
- public void Rewrite(ModuleDefinition module, ILProcessor cil, Instruction instruction, PlatformAssemblyMap assemblyMap)
- {
- MethodReference methodRef = (MethodReference)instruction.Operand;
- methodRef.DeclaringType = module.Import(this.ToType);
- }
}
}
diff --git a/src/StardewModdingAPI.AssemblyRewriters/StardewModdingAPI.AssemblyRewriters.csproj b/src/StardewModdingAPI.AssemblyRewriters/StardewModdingAPI.AssemblyRewriters.csproj
index 09fd79ed..3c3acde3 100644
--- a/src/StardewModdingAPI.AssemblyRewriters/StardewModdingAPI.AssemblyRewriters.csproj
+++ b/src/StardewModdingAPI.AssemblyRewriters/StardewModdingAPI.AssemblyRewriters.csproj
@@ -70,8 +70,8 @@
+
-
diff --git a/src/StardewModdingAPI/Constants.cs b/src/StardewModdingAPI/Constants.cs
index 52be6c05..de0eab57 100644
--- a/src/StardewModdingAPI/Constants.cs
+++ b/src/StardewModdingAPI/Constants.cs
@@ -137,12 +137,15 @@ namespace StardewModdingAPI
return new PlatformAssemblyMap(targetPlatform, removeAssemblyReferences, targetAssemblies);
}
- /// Get finders which match incompatible CIL instructions in mod assemblies.
- internal static IEnumerable GetIncompatibilityFinders()
+ /// Get rewriters which detect or fix incompatible CIL instructions in mod assemblies.
+ internal static IEnumerable GetRewriters()
{
- return new IInstructionFinder[]
+ return new IInstructionRewriter[]
{
- // changes in Stardew Valley 1.2 (that don't have rewriters)
+ /****
+ ** Finders throw an exception when incompatible code is found.
+ ****/
+ // changes in Stardew Valley 1.2 (with no rewriters)
new FieldFinder("StardewValley.Item", "set_Name"),
// APIs removed in SMAPI 1.9
@@ -161,15 +164,11 @@ namespace StardewModdingAPI
new EventFinder("StardewModdingAPI.Events.GraphicsEvents", "OnPostRenderHudEventNoCheck"),
new EventFinder("StardewModdingAPI.Events.GraphicsEvents", "OnPostRenderGuiEventNoCheck"),
new EventFinder("StardewModdingAPI.Events.GraphicsEvents", "OnPreRenderHudEventNoCheck"),
- new EventFinder("StardewModdingAPI.Events.GraphicsEvents", "OnPreRenderGuiEventNoCheck")
- };
- }
+ new EventFinder("StardewModdingAPI.Events.GraphicsEvents", "OnPreRenderGuiEventNoCheck"),
- /// Get rewriters which fix incompatible CIL instructions in mod assemblies.
- internal static IEnumerable GetRewriters()
- {
- return new IInstructionRewriter[]
- {
+ /****
+ ** Rewriters change CIL as needed to fix incompatible code
+ ****/
// crossplatform
new MethodParentRewriter(typeof(SpriteBatch), typeof(SpriteBatchWrapper), onlyIfPlatformChanged: true),
diff --git a/src/StardewModdingAPI/Framework/AssemblyLoader.cs b/src/StardewModdingAPI/Framework/AssemblyLoader.cs
index aee0bbb3..5d00c525 100644
--- a/src/StardewModdingAPI/Framework/AssemblyLoader.cs
+++ b/src/StardewModdingAPI/Framework/AssemblyLoader.cs
@@ -193,33 +193,30 @@ namespace StardewModdingAPI.Framework
this.ChangeTypeScope(type);
}
- // find incompatible instructions
+ // find (and optionally rewrite) incompatible instructions
bool anyRewritten = false;
- IInstructionFinder[] finders = Constants.GetIncompatibilityFinders().ToArray();
IInstructionRewriter[] rewriters = Constants.GetRewriters().ToArray();
foreach (MethodDefinition method in this.GetMethods(module))
{
ILProcessor cil = method.Body.GetILProcessor();
foreach (Instruction instruction in cil.Body.Instructions.ToArray())
{
- // throw exception if instruction is incompatible but can't be rewritten
- IInstructionFinder finder = finders.FirstOrDefault(p => p.IsMatch(instruction, platformChanged));
- if (finder != null)
- {
- if (!assumeCompatible)
- throw new IncompatibleInstructionException(finder.NounPhrase, $"Found an incompatible CIL instruction ({finder.NounPhrase}) while loading assembly {assembly.Name.Name}.");
- this.LogOnce(this.Monitor, loggedMessages, $"Found an incompatible CIL instruction ({finder.NounPhrase}) while loading assembly {assembly.Name.Name}, but SMAPI is configured to allow it anyway. The mod may crash or behave unexpectedly.", LogLevel.Warn);
- }
-
- // rewrite instruction if needed
foreach (IInstructionRewriter rewriter in rewriters)
{
- if (!rewriter.IsMatch(instruction, platformChanged))
- continue;
-
- this.LogOnce(this.Monitor, loggedMessages, $"Rewriting {assembly.Name.Name} to fix {rewriter.NounPhrase}...");
- rewriter.Rewrite(module, cil, instruction, this.AssemblyMap);
- anyRewritten = true;
+ try
+ {
+ if (rewriter.Rewrite(module, cil, instruction, this.AssemblyMap, platformChanged))
+ {
+ this.LogOnce(this.Monitor, loggedMessages, $"Rewrote {assembly.Name.Name} to fix {rewriter.NounPhrase}...");
+ anyRewritten = true;
+ }
+ }
+ catch (IncompatibleInstructionException)
+ {
+ if (!assumeCompatible)
+ throw new IncompatibleInstructionException(rewriter.NounPhrase, $"Found an incompatible CIL instruction ({rewriter.NounPhrase}) while loading assembly {assembly.Name.Name}.");
+ this.LogOnce(this.Monitor, loggedMessages, $"Found an incompatible CIL instruction ({rewriter.NounPhrase}) while loading assembly {assembly.Name.Name}, but SMAPI is configured to allow it anyway. The mod may crash or behave unexpectedly.", LogLevel.Warn);
+ }
}
}
}
diff --git a/src/StardewModdingAPI/Program.cs b/src/StardewModdingAPI/Program.cs
index ac646b1f..25605148 100644
--- a/src/StardewModdingAPI/Program.cs
+++ b/src/StardewModdingAPI/Program.cs
@@ -12,6 +12,7 @@ using System.Windows.Forms;
#endif
using Microsoft.Xna.Framework.Graphics;
using Newtonsoft.Json;
+using StardewModdingAPI.AssemblyRewriters;
using StardewModdingAPI.Events;
using StardewModdingAPI.Framework;
using StardewModdingAPI.Framework.Logging;
diff --git a/src/StardewModdingAPI/StardewModdingAPI.csproj b/src/StardewModdingAPI/StardewModdingAPI.csproj
index 091b3d90..bcd0c390 100644
--- a/src/StardewModdingAPI/StardewModdingAPI.csproj
+++ b/src/StardewModdingAPI/StardewModdingAPI.csproj
@@ -150,7 +150,6 @@
-