新增 ObfuscationTypeMapper及相应的Instinct函数RegisterReflectionType
parent
3867a98d48
commit
a109511f9e
|
@ -1,5 +1,6 @@
|
|||
using dnlib.DotNet;
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using UnityEngine.Assertions;
|
||||
|
||||
namespace Obfuz.Emit
|
||||
|
@ -143,6 +144,9 @@ namespace Obfuz.Emit
|
|||
_verifySecretKey = mod.Import(typeof(AssetUtility).GetMethod("VerifySecretKey", new[] { typeof(int), typeof(int) }));
|
||||
Assert.IsNotNull(_verifySecretKey, "VerifySecretKey not found");
|
||||
|
||||
_obfuscationTypeMapperRegisterType = mod.Import(typeof(ObfuscationTypeMapper).GetMethod("RegisterType", 1, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static, null, new[] { typeof(string) }, null));
|
||||
Assert.IsNotNull(_obfuscationTypeMapperRegisterType, "ObfuscationTypeMapper.RegisterType not found");
|
||||
|
||||
_staticDefaultEncryptionServiceMetadataImporter = new EncryptionServiceMetadataImporter(mod, typeof(EncryptionService<DefaultStaticEncryptionScope>));
|
||||
_dynamicDefaultEncryptionServiceMetadataImporter = new EncryptionServiceMetadataImporter(mod, typeof(EncryptionService<DefaultDynamicEncryptionScope>));
|
||||
if (_encryptionScopeProvider.IsDynamicSecretAssembly(mod))
|
||||
|
@ -168,6 +172,8 @@ namespace Obfuz.Emit
|
|||
private IMethod _initializeArray;
|
||||
private IMethod _verifySecretKey;
|
||||
|
||||
private IMethod _obfuscationTypeMapperRegisterType;
|
||||
|
||||
public IMethod CastIntAsFloat => _castIntAsFloat;
|
||||
public IMethod CastLongAsDouble => _castLongAsDouble;
|
||||
public IMethod CastFloatAsInt => _castFloatAsInt;
|
||||
|
@ -177,6 +183,8 @@ namespace Obfuz.Emit
|
|||
|
||||
public IMethod VerifySecretKey => _verifySecretKey;
|
||||
|
||||
public IMethod ObfuscationTypeMapperRegisterType => _obfuscationTypeMapperRegisterType;
|
||||
|
||||
public IMethod EncryptBlock => _defaultEncryptionServiceMetadataImporter.EncryptBlock;
|
||||
public IMethod DecryptBlock => _defaultEncryptionServiceMetadataImporter.DecryptBlock;
|
||||
|
||||
|
|
|
@ -25,7 +25,6 @@ namespace Obfuz.ObfusPasses.Instinct
|
|||
|
||||
public override void Start()
|
||||
{
|
||||
var ctx = ObfuscationPassContext.Current;
|
||||
}
|
||||
|
||||
public override void Stop()
|
||||
|
@ -92,11 +91,15 @@ namespace Obfuz.ObfusPasses.Instinct
|
|||
return false;
|
||||
}
|
||||
|
||||
ObfuscationPassContext ctx = ObfuscationPassContext.Current;
|
||||
var importer = ctx.moduleEntityManager.GetDefaultModuleMetadataImporter(callingMethod.Module, ctx.encryptionScopeProvider);
|
||||
|
||||
string methodName = methodDef.Name;
|
||||
switch (methodName)
|
||||
{
|
||||
case "FullNameOf":
|
||||
case "NameOf":
|
||||
case "RegisterReflectionType":
|
||||
{
|
||||
MethodSpec methodSpec = (MethodSpec)method;
|
||||
GenericInstMethodSig gims = methodSpec.GenericInstMethodSig;
|
||||
|
@ -116,6 +119,14 @@ namespace Obfuz.ObfusPasses.Instinct
|
|||
outputInstructions.Add(Instruction.Create(OpCodes.Ldstr, typeName));
|
||||
break;
|
||||
}
|
||||
case "RegisterReflectionType":
|
||||
{
|
||||
string typeFullName = GetTypeFullName(type);
|
||||
outputInstructions.Add(Instruction.Create(OpCodes.Ldstr, typeFullName));
|
||||
var finalMethod = new MethodSpecUser((IMethodDefOrRef)importer.ObfuscationTypeMapperRegisterType, gims);
|
||||
outputInstructions.Add(Instruction.Create(OpCodes.Call, finalMethod));
|
||||
break;
|
||||
}
|
||||
default: throw new NotSupportedException($"Unsupported instinct method: {methodDef.FullName}");
|
||||
}
|
||||
break;
|
||||
|
|
|
@ -27,5 +27,14 @@ namespace Obfuz
|
|||
{
|
||||
return typeof(T).Name;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// register original type name to type mapping.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public static void RegisterReflectionType<T>()
|
||||
{
|
||||
ObfuscationTypeMapper.RegisterType<T>(typeof(T).FullName);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,76 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Obfuz
|
||||
{
|
||||
public static class ObfuscationTypeMapper
|
||||
{
|
||||
private static readonly Dictionary<Type, string> _type2OriginalFullName = new Dictionary<Type, string>();
|
||||
private static readonly Dictionary<Assembly, Dictionary<string, Type>> _originalFullName2Types = new Dictionary<Assembly, Dictionary<string, Type>>();
|
||||
|
||||
internal static void RegisterType<T>(string originalFullName)
|
||||
{
|
||||
RegisterType(typeof(T), originalFullName);
|
||||
}
|
||||
|
||||
internal static void RegisterType(Type type, string originalFullName)
|
||||
{
|
||||
if (_type2OriginalFullName.ContainsKey(type))
|
||||
{
|
||||
throw new ArgumentException($"Type '{type.FullName}' is already registered with original name '{_type2OriginalFullName[type]}'.");
|
||||
}
|
||||
_type2OriginalFullName.Add(type, originalFullName);
|
||||
Assembly assembly = type.Assembly;
|
||||
if (!_originalFullName2Types.TryGetValue(assembly, out var originalFullName2Types))
|
||||
{
|
||||
originalFullName2Types = new Dictionary<string, Type>();
|
||||
_originalFullName2Types[assembly] = originalFullName2Types;
|
||||
}
|
||||
if (originalFullName2Types.ContainsKey(originalFullName))
|
||||
{
|
||||
throw new ArgumentException($"Original full name '{originalFullName}' is already registered with type '{originalFullName2Types[originalFullName].FullName}'.");
|
||||
}
|
||||
originalFullName2Types.Add(originalFullName, type);
|
||||
}
|
||||
|
||||
public static string GetOriginalTypeFullName(Type type)
|
||||
{
|
||||
return _type2OriginalFullName.TryGetValue(type, out string originalFullName)
|
||||
? originalFullName
|
||||
: throw new KeyNotFoundException($"Type '{type.FullName}' not found in the obfuscation mapping.");
|
||||
}
|
||||
|
||||
public static string GetOriginalTypeFullNameOrCurrent(Type type)
|
||||
{
|
||||
if (_type2OriginalFullName.TryGetValue(type, out string originalFullName))
|
||||
{
|
||||
return originalFullName;
|
||||
}
|
||||
return type.FullName;
|
||||
}
|
||||
|
||||
public static Type GetTypeByOriginalFullName(Assembly assembly, string originalFullName)
|
||||
{
|
||||
if (_originalFullName2Types.TryGetValue(assembly, out var n2t))
|
||||
{
|
||||
if (n2t.TryGetValue(originalFullName, out Type type))
|
||||
{
|
||||
return type;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public static void Clear()
|
||||
{
|
||||
_type2OriginalFullName.Clear();
|
||||
_originalFullName2Types.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
fileFormatVersion: 2
|
||||
guid: db6168acedd85984fa2c197fee1b0c15
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
Loading…
Reference in New Issue