// dnlib: See LICENSE.txt for more info using System.Threading; using dnlib.DotNet.Emit; namespace dnlib.DotNet { /// /// context /// public class ModuleContext { IAssemblyResolver assemblyResolver; IResolver resolver; readonly OpCode[][] experimentalOpCodes = new OpCode[12][]; /// /// Gets/sets the assembly resolver. This is never null. /// public IAssemblyResolver AssemblyResolver { get { if (assemblyResolver is null) Interlocked.CompareExchange(ref assemblyResolver, NullResolver.Instance, null); return assemblyResolver; } set => assemblyResolver = value; } /// /// Gets/sets the resolver. This is never null. /// public IResolver Resolver { get { if (resolver is null) Interlocked.CompareExchange(ref resolver, NullResolver.Instance, null); return resolver; } set => resolver = value; } /// /// Default constructor /// public ModuleContext() { } /// /// Constructor /// /// Assembly resolver or null public ModuleContext(IAssemblyResolver assemblyResolver) : this(assemblyResolver, new Resolver(assemblyResolver)) { } /// /// Constructor /// /// Type/method/field resolver or null public ModuleContext(IResolver resolver) : this(null, resolver) { } /// /// Constructor /// /// Assembly resolver or null /// Type/method/field resolver or null public ModuleContext(IAssemblyResolver assemblyResolver, IResolver resolver) { this.assemblyResolver = assemblyResolver; this.resolver = resolver; if (resolver is null && assemblyResolver is not null) this.resolver = new Resolver(assemblyResolver); } /// /// Registers an experimental CIL opcode. It must be a 2-byte opcode /// where the first byte lies within the range 0xF0..0xFB. /// public void RegisterExperimentalOpCode(OpCode opCode) { byte high = (byte)((ushort)opCode.Value >> 8); byte low = (byte)opCode.Value; OpCode[] array = experimentalOpCodes[high - 0xF0] ??= new OpCode[256]; array[low] = opCode; } /// /// Clears an experimental CIL opcode. /// public void ClearExperimentalOpCode(byte high, byte low) { OpCode[] array = experimentalOpCodes[high - 0xF0]; if (array != null) array[low] = null; } /// /// Attempts to get an experimental CIL opcode. /// public OpCode GetExperimentalOpCode(byte high, byte low) { return experimentalOpCodes[high - 0xF0]?[low]; } } }